************************************************************************
             Examples of How to Use Image-Based OTA Update
************************************************************************
This file provides several examples of how to use an image-based OTA update for
specific use cases.

1. Generating an OTA payload package for OTA updates from R35.5.0 to the latest R36 version.
The following examples show you how to generate an OTA payload package for different
cases. Please export "BASE_BSP=<R35.5.0 BSP>/Linux_for_Tegra" as an environment
variable before running the following commands.
Note: Currently, the latest version of R36 is R36.3.0.

- An OTA update from R35.5.0 to the latest R36 version on the jetson-agx-orin-devkit.
Currently the R35 latest version is R36.3.0.
$ sudo -E ./tools/ota_tools/version_upgrade/l4t_generate_ota_package.sh \
    jetson-agx-orin-devkit R35-5

- An OTA update from R35.5.0 to the latest R36 version on the jetson-agx-orin-devkit-industrial.
$ sudo -E ./tools/ota_tools/version_upgrade/l4t_generate_ota_package.sh \
    jetson-agx-orin-devkit-industrial R35-5

- An OTA update from R35.5.0 to the latest R36 version on jetson-orin-nano-devkit with
booting from an NVMe storage device. The size of the APP partition on an NVMe storage device
is 24GiB.
$ sudo -E ./tools/ota_tools/version_upgrade/l4t_generate_ota_package.sh \
    --external-device nvme0n1 -S 24GiB jetson-orin-nano-devkit R35-5
Note: The size of the APP partition will be overwritten by user's actual size.

- An OTA update from R35.5.0 to the latest R36 version on the jetson-agx-orin-devkit with
disk encryption enabled.
$ sudo -E ROOTFS_ENC=1 ./tools/ota_tools/version_upgrade/l4t_generate_ota_package.sh \
    -i ekb.key jetson-agx-orin-devkit R35-5
The "ekb.key" is the key used for disk encryption. It must be the same as the one used to
flash R35.5.0 to the device.

- An OTA update from R35.5.0 to the latest R36 version on the jetson-agx-orin-devkit-industrial
with rootfs A/B enabled.
$ sudo -E ROOTFS_AB=1 ./tools/ota_tools/version_upgrade/l4t_generate_ota_package.sh \
    jetson-agx-orin-devkit-industrial R35-5

- An OTA update from R35.5.0 to the latest R36 version on jetson-orin-nano-devkit, booting
from an NVMe storage device. The rootfs A/B and disk encryption are enabled. The size of
the APP partition on an NVMe storage device is 24GiB.
$ sudo -E ROOTFS_AB=1 ROOTFS_ENC=1 ./tools/ota_tools/version_upgrade/l4t_generate_ota_package.sh \
    --external-device nvme0n1 -S 24GiB -i ekb.key jetson-orin-nano-devkit R35-5

2. OTA update from R35.5.0 to the latest R36 version
When applying an OTA update from R35.5.0 to the latest R36 version, you need to update both bootloader
chains and both rootfs chains if rootfs A/B is enabled to the latest R36 version. The ESP, recovery,
and recovery-dtb partitions are unique for both A/B chains.

The following examples show you the steps to perform an OTA update from R35.5.0 to the latest R36 version:

- To perform an OTA update from R35.5.0 to the latest R36 version on jetson-agx-orin-devkit, complete the following steps:
  a. Download the latest R36 BSP, sample rootfs, and OTA tools package, and then extract them.
  b. Generate the OTA payload package from R35.5.0 to R36.3.0:
     $ cd Linux_for_Tegra
     $ sudo BASE_BSP=<R35.5.0 BSP>/Linux_for_Tegra ./tools/ota_tools/version_upgrade/l4t_generate_ota_package.sh \
     jetson-agx-orin-devkit R35-5
  c. Copy the OTA tools package "ota_tools_R36.3.0_aarch64.tbz2" and the generated OTA payload
     package "ota_payload_package.tar.gz" to the device, for example, put them in the "~/" directory.
  d. Extract "ota_tools_R36.3.0_aarch64.tbz2" and trigger the OTA update:
     $ cd ~/
     $ tar xjpf ota_tools_R36.3.0_aarch64.tbz2
     $ cd Linux_for_Tegra/tools/ota_tools/version_upgrade
     $ sudo ./nv_ota_start.sh ~/ota_payload_package.tar.gz
  e. Reboot the device.
     The Capsule update is to be executed once the device boots to UEFI. After the Capsule update is finished,
     the device is automatically rebooted and then boots from the chain that was newly upgraded to R36.3.0
  f. Generate the OTA payload package that updates the bootloader only from R36.3.0 to R36.3.0:
     $ cd Linux_for_Tegra
     $ sudo ./tools/ota_tools/version_upgrade/l4t_generate_ota_package.sh \
     -b jetson-agx-orin-devkit R36-3
     Note: The purpose of this step is to update the other boot chains to R36. It is not supported
     using R35 boot chains to boot the R36 kernel/root FS.
  g. Copy the OTA tools package "ota_tools_R36.3.0_aarch64.tbz2" and the generated OTA payload
     package "ota_payload_package.tar.gz" to the device, for example, put them in the "~/" directory.
  h. Extract "ota_tools_R36.3.0_aarch64.tbz2" and trigger the OTA update:
     $ cd ~/
     $ tar xjpf ota_tools_R36.3.0_aarch64.tbz2
     $ cd Linux_for_Tegra/tools/ota_tools/version_upgrade
     $ sudo ./nv_ota_start.sh ~/ota_payload_package.tar.gz
  i. Reboot the device.
     The Capsule update is to be executed once the device boots to UEFI. After the Capsule update is finished,
     the device is automatically rebooted and then boots from the chain that was newly upgraded to R36.3.0.
     Now both bootloader chains and the rootfs are upgraded to R36.3.0

- To perform an OTA update from R35.5.0 to the latest R36 version on jetson-orin-nano-devkit booting from an NVMe with rootfs A/B and
  disk encryption enabled, and 24GiB APP/APP_b partitions, complete the following steps:
  a. Download the latest R36 BSP, sample rootfs, and OTA tools package, and then extract them.
  b. Generate the OTA payload package from R35.5.0 to R36.3.0:
     $ cd Linux_for_Tegra
     $ sudo ROOTFS_AB=1 ROOTFS_ENC=1 BASE_BSP=<R35.5.0 BSP>/Linux_for_Tegra \
     ./tools/ota_tools/version_upgrade/l4t_generate_ota_package.sh \
     -i ekb.ky --external-device nvme0n1 -S 24GiB jetson-orin-nano-devkit R35-5
  c. Copy the OTA tools package "ota_tools_R36.3.0_aarch64.tbz2" and the generated OTA payload
     package "ota_payload_package.tar.gz" to the device, for example, put them in the "~/" directory.
  d. Extract "ota_tools_R36.3.0_aarch64.tbz2" and trigger the OTA update:
     $ cd ~/
     $ tar xjpf ota_tools_R36.3.0_aarch64.tbz2
     $ cd Linux_for_Tegra/tools/ota_tools/version_upgrade
     $ sudo ./nv_ota_start.sh ~/ota_payload_package.tar.gz
  e. Reboot the device.
     The Capsule update is to be executed once the device boots to UEFI. After the Capsule update is finished,
     the device is automatically rebooted and then boots from the chain that was newly upgraded to R36.3.0
  f. Generate the OTA payload package from R36.3.0 to R36.3.0:
     $ cd Linux_for_Tegra
     $ sudo ROOTFS_AB=1 ROOTFS_ENC=1 ./tools/ota_tools/version_upgrade/l4t_generate_ota_package.sh \
     -i ekb.key --external-device nvme0n1 -S 24GiB jetson-orin-nano-devkit R36-3
  g. Copy the OTA tools package "ota_tools_R36.3.0_aarch64.tbz2" and the generated OTA payload
     package "ota_payload_package.tar.gz" to the device, for example, put them in the "~/" directory.
  h. Extract "ota_tools_R36.3.0_aarch64.tbz2" and trigger the OTA update:
     $ cd ~/
     $ tar xjpf ota_tools_R36.3.0_aarch64.tbz2
     $ cd Linux_for_Tegra/tools/ota_tools/version_upgrade
     $ sudo ./nv_ota_start.sh ~/ota_payload_package.tar.gz
  i. Reboot the device.
     The Capsule update is to be executed once the device boots to UEFI. After the Capsule update is finished,
     the device is automatically rebooted and then boots from the chain that was newly upgraded to R36.3.0.
     Now both bootloader chains and both rootfs on the NVMe storage device are upgraded to R36.3.0

3. OTA update from a version earlier than R35.5.0 to the latest R36 version
The image-based OTA scripts do not support an OTA update from a version earlier than
R35.5.0 to the latest R36 version directly. To upgrade from such version, which includes
R35.2.1, R35.3.1 and R35.4.1, you need to upgrade to R35.5.0 first, then upgrade to the
latest R36 version.

The following examples show you the steps to perform an OTA update from an early R35 version to the latest
R36 version:

- To perform an OTA update from R35.2.1 to the latest R36 version on jetson-agx-orin-devkit, complete the following steps:
  a. Download R35.5.0 BSP, sample rootfs, and OTA tools package, and then extract them.
  b. Generate the OTA payload package from R35.2.1 to R35.5.0:
     $ cd Linux_for_Tegra
     $ sudo ./tools/ota_tools/version_upgrade/l4t_generate_ota_package.sh \
     jetson-agx-orin-devkit R35-2
  c. Copy the OTA tools package "ota_tools_R35.5.0_aarch64.tbz2" and the generated OTA payload
     package "ota_payload_package.tar.gz" to the device, for example, put them in the "~/" directory.
  d. Extract "ota_tools_R35.5.0_aarch64.tbz2" and trigger the OTA update:
     $ cd ~/
     $ tar xjpf ota_tools_R35.5.0_aarch64.tbz2
     $ cd Linux_for_Tegra/tools/ota_tools/version_upgrade
     $ sudo ./nv_ota_start.sh ~/ota_payload_package.tar.gz
  e. Reboot the device.
     The Capsule update is to be executed once the device boots to UEFI. After the Capsule update is finished,
     the device is automatically rebooted and then boots from the chain that was newly upgraded to R35.5.0
  f. Download the latest R36 BSP, sample rootfs, and OTA tools package, and then extract them.
  g. Generate the OTA payload package from R35.5.0 to R36.3.0:
     $ cd Linux_for_Tegra
     $ sudo BASE_BSP=<R35.5.0 BSP>/Linux_for_Tegra ./tools/ota_tools/version_upgrade/l4t_generate_ota_package.sh \
     jetson-agx-orin-devkit R35-5
  h. Copy the OTA tools package "ota_tools_R36.3.0_aarch64.tbz2" and the generated OTA payload
     package "ota_payload_package.tar.gz" to the device, for example, put them in the "~/" directory.
  i. Extract "ota_tools_R36.3.0_aarch64.tbz2" and trigger the OTA update:
     $ cd ~/
     $ tar xjpf ota_tools_R36.3.0_aarch64.tbz2
     $ cd Linux_for_Tegra/tools/ota_tools/version_upgrade
     $ sudo ./nv_ota_start.sh ~/ota_payload_package.tar.gz
  j. Reboot the device.
     The Capsule update is to be executed once the device boots to UEFI. After the Capsule update is finished,
     the device is automatically rebooted and then boots from the chain that was newly upgraded to R36.3.0
  k. Generate the OTA payload package that updates the bootloader only from R36.3.0 to R36.3.0:
     $ cd Linux_for_Tegra
     $ sudo ./tools/ota_tools/version_upgrade/l4t_generate_ota_package.sh \
     -b jetson-agx-orin-devkit R36-3
     Note: The purpose of this step is to update the other boot chains to R36. It is not supported
     using R35 boot chains to boot the R36 kernel/root FS.
  l. Copy the OTA tools package "ota_tools_R36.3.0_aarch64.tbz2" and the generated OTA payload
     package "ota_payload_package.tar.gz" to the device, for example, put them in the "~/" directory.
  m. Extract "ota_tools_R36.3.0_aarch64.tbz2" and trigger the OTA update:
     $ cd ~/
     $ tar xjpf ota_tools_R36.3.0_aarch64.tbz2
     $ cd Linux_for_Tegra/tools/ota_tools/version_upgrade
     $ sudo ./nv_ota_start.sh ~/ota_payload_package.tar.gz
  n. Reboot the device.
     The Capsule update is to be executed once the device boots to UEFI. After the Capsule update is finished,
     the device is automatically rebooted and then boots from the chain that was newly upgraded to R36.3.0.
     Now both bootloader chains and the rootfs are upgraded to R36.3.0

- To perform an OTA update from R35.2.1 to the latest R36 version on jetson-agx-orin-devkit with rootfs A/B and
  disk encryption enabled, complete the following steps:
  a. Download R35.5.0 BSP, sample rootfs, and OTA tools package, and then extract them.
  b. Generate the OTA payload package from R35.2.1 to R35.5.0:
     $ cd Linux_for_Tegra
     $ sudo ROOTFS_AB=1 ROOTFS_ENC=1 ./tools/ota_tools/version_upgrade/l4t_generate_ota_package.sh \
     -i ekb.key jetson-agx-orin-devkit R35-2
  c. Copy the OTA tools package "ota_tools_R35.5.0_aarch64.tbz2" and the generated OTA payload
     package "ota_payload_package.tar.gz" to the device, for example, put them in the "~/" directory.
  d. Extract "ota_tools_R35.5.0_aarch64.tbz2" and trigger the OTA update:
     $ cd ~/
     $ tar xjpf ota_tools_R35.5.0_aarch64.tbz2
     $ cd Linux_for_Tegra/tools/ota_tools/version_upgrade
     $ sudo ./nv_ota_start.sh ~/ota_payload_package.tar.gz
  e. Reboot the device.
     The Capsule update is to be executed once the device boots to UEFI. After the Capsule update is finished,
     the device is automatically rebooted and then boots from the chain that was newly upgraded to R35.5.0
  f. Download the latest R36 BSP, sample rootfs, and OTA tools package, and then extract them.
  g. Generate the OTA payload package from R35.5.0 to R36.3.0:
     $ cd Linux_for_Tegra
     $ sudo ROOTFS_AB=1 ROOTFS_ENC=1 BASE_BSP=<R35.5.0 BSP>/Linux_for_Tegra \
     ./tools/ota_tools/version_upgrade/l4t_generate_ota_package.sh \
     -i ekb.key jetson-agx-orin-devkit R35-5
  h. Copy the OTA tools package "ota_tools_R36.3.0_aarch64.tbz2" and the generated OTA payload
     package "ota_payload_package.tar.gz" to the device, for example, put them in the "~/" directory.
  i. Extract "ota_tools_R36.3.0_aarch64.tbz2" and trigger the OTA update:
     $ cd ~/
     $ tar xjpf ota_tools_R36.3.0_aarch64.tbz2
     $ cd Linux_for_Tegra/tools/ota_tools/version_upgrade
     $ sudo ./nv_ota_start.sh ~/ota_payload_package.tar.gz
  j. Reboot the device.
     The Capsule update is to be executed once the device boots to UEFI. After the Capsule update is finished,
     the device is automatically rebooted and then boots from the chain that was newly upgraded to R36.3.0
  k. Generate the OTA payload package from R36.3.0 to R36.3.0:
     $ cd Linux_for_Tegra
     $ sudo ROOTFS_AB=1 ROOTFS_ENC=1 ./tools/ota_tools/version_upgrade/l4t_generate_ota_package.sh \
     -i ekb.key jetson-agx-orin-devkit R36-3
  l. Copy the OTA tools package "ota_tools_R36.3.0_aarch64.tbz2" and the generated OTA payload
     package "ota_payload_package.tar.gz" to the device, for example, put them in the "~/" directory.
  m. Extract "ota_tools_R36.3.0_aarch64.tbz2" and trigger the OTA update:
     $ cd ~/
     $ tar xjpf ota_tools_R36.3.0_aarch64.tbz2
     $ cd Linux_for_Tegra/tools/ota_tools/version_upgrade
     $ sudo ./nv_ota_start.sh ~/ota_payload_package.tar.gz
  n. Reboot the device.
     The Capsule update is to be executed once the device boots to UEFI. After the Capsule update is finished,
     the device is automatically rebooted and then boots from the chain that was newly upgraded to R36.3.0.
     Now both bootloader chains and both rootfs are upgraded to R36.3.0

- To perform an OTA update from R35.4.1 to the latest R36 version on jetson-orin-nano-devkit booting from an NVMe with rootfs A/B and
  disk encryption enabled, and 24GiB APP/APP_b partitions, complete the following steps:
  a. Download R35.5.0 BSP, sample rootfs, and OTA tools package, and then extract them.
  b. Generate the OTA payload package from R35.4.1 to R35.5.0:
     $ cd Linux_for_Tegra
     $ sudo ROOTFS_AB=1 ROOTFS_ENC=1 ./tools/ota_tools/version_upgrade/l4t_generate_ota_package.sh \
     -i ekb.key --external-device nvme0n1 -S 24GiB jetson-orin-nano-devkit R35-4
  c. Copy the OTA tools package "ota_tools_R35.5.0_aarch64.tbz2" and the generated OTA payload
     package "ota_payload_package.tar.gz" to the device, for example, put them in the "~/" directory.
  d. Extract "ota_tools_R35.5.0_aarch64.tbz2" and trigger the OTA update:
     $ cd ~/
     $ tar xjpf ota_tools_R35.5.0_aarch64.tbz2
     $ cd Linux_for_Tegra/tools/ota_tools/version_upgrade
     $ sudo ./nv_ota_start.sh ~/ota_payload_package.tar.gz
  e. Reboot the device.
     The Capsule update is to be executed once the device boots to UEFI. After the Capsule update is finished,
     the device is automatically rebooted and then boots from the chain that was newly upgraded to R35.5.0
  f. Download the latest R36 BSP, sample rootfs, and OTA tools package, and then extract them.
  g. Generate the OTA payload package from R35.5.0 to R36.3.0:
     $ cd Linux_for_Tegra
     $ sudo ROOTFS_AB=1 ROOTFS_ENC=1 BASE_BSP=<R35.5.0 BSP>/Linux_for_Tegra \
     ./tools/ota_tools/version_upgrade/l4t_generate_ota_package.sh \
     -i ekb.ky --external-device nvme0n1 -S 24GiB jetson-orin-nano-devkit R35-5
  h. Copy the OTA tools package "ota_tools_R36.3.0_aarch64.tbz2" and the generated OTA payload
     package "ota_payload_package.tar.gz" to the device, for example, put them in the "~/" directory.
  i. Extract "ota_tools_R36.3.0_aarch64.tbz2" and trigger the OTA update:
     $ cd ~/
     $ tar xjpf ota_tools_R36.3.0_aarch64.tbz2
     $ cd Linux_for_Tegra/tools/ota_tools/version_upgrade
     $ sudo ./nv_ota_start.sh ~/ota_payload_package.tar.gz
  j. Reboot the device.
     The Capsule update is to be executed once the device boots to UEFI. After the Capsule update is finished,
     the device is automatically rebooted and then boots from the chain that was newly upgraded to R36.3.0
  k. Generate the OTA payload package from R36.3.0 to R36.3.0:
     $ cd Linux_for_Tegra
     $ sudo ROOTFS_AB=1 ROOTFS_ENC=1 ./tools/ota_tools/version_upgrade/l4t_generate_ota_package.sh \
     -i ekb.key --external-device nvme0n1 -S 24GiB jetson-orin-nano-devkit R36-3
  l. Copy the OTA tools package "ota_tools_R36.3.0_aarch64.tbz2" and the generated OTA payload
     package "ota_payload_package.tar.gz" to the device, for example, put them in the "~/" directory.
  m. Extract "ota_tools_R36.3.0_aarch64.tbz2" and trigger the OTA update:
     $ cd ~/
     $ tar xjpf ota_tools_R36.3.0_aarch64.tbz2
     $ cd Linux_for_Tegra/tools/ota_tools/version_upgrade
     $ sudo ./nv_ota_start.sh ~/ota_payload_package.tar.gz
  n. Reboot the device.
     The Capsule update is to be executed once the device boots to UEFI. After the Capsule update is finished,
     the device is automatically rebooted and then boots from the chain that was newly upgraded to R36.3.0.
     Now both bootloader chains and both rootfs on the NVMe storage device are upgraded to R36.3.0

4. Using golden image in OTA update.
Customers might flash a device with the latest released BSP and then make a golden image
dependent on this device. They can deploy the golden image on other devices that were
flashed with the previously released BSP through an OTA update.

The "l4t_generate_ota_package.sh" script includes the "-f" and "-o" options so that
customers can use their own rootfs updater and update the rootfs partition with their
own rootfs image (for example, a golden image).

However, for some customers, the golden image is a raw partition image that is
directly obtained from rootfs partition. (These customers might not
want to write their own rootfs updater.)

The following examples provide the steps for using this golden image in an image-based OTA.

- With rootfs A/B disabled, complete the following steps:
  a. Put the target device into recovery mode.
  b. Boot the device to initrd by running the following command:
     $ sudo ./tools/kernel_flash/l4t_initrd_flash.sh --initrd <target board> mmcblk0p1
  c. Enter bash shell on the target device.
  d. Mount a USB drive or network storage on the target device.
  e. Generate golden image in the mounted storage device by running the
     following command:
     $ sudo dd if=<rootfs partition> of=<mount ponint>/golden.img.raw
     The "<rootfs partition>" is /dev/mmcblk0p1 for the internal eMMC storage device
     or /dev/nvme0n1p1 for the external NVMe storage device.
  f. Copy the golden images into the TARGET_BSP directory on the host machine by running
     the following command:
     $ sudo cp golden.img.raw ${TARGET_BSP}/bootloader/system.img.raw
  g. Add the "-s" option when generating the OTA payload package.
     For the internal eMMC storage device, running the following command:
     $ sudo ./tools/ota_tools/version_upgrade/l4t_generate_ota_package.sh \
     -s <target board> <base version>
     For the external NVMe storage device, running the following command:
     $ sudo ./tools/ota_tools/version_upgrade/l4t_generate_ota_package.sh \
     -s --external-device nvme0n1 -S <rootfs size > <target board> <base version>

- With rootfs A/B enabled, complete the following steps:
  a. Put the target device into recovery mode.
  b. Boot the device to initrd by running the following command:
     $ sudo ./tools/kernel_flash/l4t_initrd_flash.sh --initrd <target board> mmcblk0p1
  c. Enter bash shell on the target device.
  d. Mount a USB drive or network storage on the target device.
  e. Generate golden images in the mounted storage device by running the
     following commands:
     $ sudo dd if=<rootfs partition A> of=<mount ponint>/golden_a.img.raw
     $ sudo dd if=<rootfs partition B> of=<mount ponint>/golden_b.img.raw
     The "<rootfs partition A>" is /dev/mmcblk0p1 for the internal eMMC storage
     device or /dev/nvme0n1p1 for the external NVMe storage device, and the "<rootfs partition B>"
     is /dev/mmcblk0p2 for the internal eMMC storage device or /dev/nvme0n1p2 for the external NVMe
     storage device.
  f. Copy the golden images into the TARGET_BSP directory on the host machine by running
     the following commands:
     $ sudo cp golden_a.img.raw ${TARGET_BSP}/bootloader/system.img.raw
     $ sudo cp golden_b.img.raw ${TARGET_BSP}/bootloader/system.img_b.raw
  g. Add the "-s" option when generating the OTA payload package.
     For the internal eMMC storage device, running the following command:
     $ sudo ROOTFSA_AB=1 ./tools/ota_tools/version_upgrade/l4t_generate_ota_package.sh \
     -s <target board> <base version>
     For the external NVMe storage device, running the following command
     $ sudo ROOTFS_AB=1 ./tools/ota_tools/version_upgrade/l4t_generate_ota_package.sh \
     -s --external-device nvme0n1 -S <rootfs size> <target board> <base version>

The content of golden image is now packed into the OTA payload package and then extracted
into the corresponding rootfs partition by the default rootfs updater provided by NVIDIA
during the OTA update.
