Update README
Document resources and fix some outdated information.
This commit is contained in:
parent
cc48b88713
commit
12ee7b7e39
|
@ -3,12 +3,114 @@ OTA Update
|
|||
==========
|
||||
|
||||
OTA stands for "Over the Air". OTA update is used to flash a new
|
||||
firmware to a device over the air. This document (some of) the
|
||||
requirements for OTA.
|
||||
firmware to a device over the air. This documents (some of) the
|
||||
requirements for OTA and how to use the current prototype
|
||||
implementation.
|
||||
|
||||
For the impatient
|
||||
=================
|
||||
|
||||
First see the Security note below.
|
||||
|
||||
Then, if you've decided you want to try this: This is experimental code,
|
||||
use at your own risk.
|
||||
|
||||
OK, how to run this:
|
||||
There is now a new make variable that determines which image (the one
|
||||
for the upper or the one for the lower half of flash memory) is to be
|
||||
built. Set ::
|
||||
|
||||
BOOTLOADER_PARTITION=0
|
||||
|
||||
for building the first partition (the default) or set it to 1 for
|
||||
building the second one.
|
||||
|
||||
There are now two ELF files, ``ota.osd-merkur-256.0`` and
|
||||
``ota.osd-merkur-256.1``. From each of these two .hex files can be
|
||||
generated (we're describing only the files for the first image, the
|
||||
filenames of the second image are determined by replacing '0' with '1'
|
||||
in the following):
|
||||
|
||||
- ota.osd-merkur-256.0.hex is the file used for OTA update
|
||||
- ota.osd-merkur-256.0-combined.hex is the file used for uploading via
|
||||
the bootloader. This file has an additional section that contains a
|
||||
copy of the irq-vector table (see below for further details). This is
|
||||
only necessary if you're using the latest bootloader.
|
||||
|
||||
To upload an image via OTA:
|
||||
|
||||
- Create the ``.hex`` file with::
|
||||
|
||||
make TARGET=osd-merkur-256 BOOTLOADER_PARTITION=1 ota.osd-merkur-256.0.hex
|
||||
|
||||
- Generate the ``.bin`` file with::
|
||||
|
||||
./ota_uploader.py x ota.osd-merkur-256.0.hex > ota.osd-merkur-256.0.bin
|
||||
|
||||
Note that the ``ota_uploader.py`` tool is intended to turn into a
|
||||
full-fledged upgrade tool. This is work in progress. The first
|
||||
parameter will be the destination IP-Address in the future and is
|
||||
currently ignored.
|
||||
|
||||
- Upload this image to the ``/update`` resource, either via the firefox
|
||||
copper plugin or via the commandline::
|
||||
|
||||
coap-client -t application/octet-stream -f ota.osd-merkur-256.1.bin
|
||||
-m put -b 64 'coap://[2001:db8:c001:f00d:221:2eff:ff00:5dd4]/update'
|
||||
|
||||
Be sure to specify the type ``application/octet-stream`` if you are
|
||||
uploading via copper. Also make sure you replace the IP address above
|
||||
with the IP address of your board to be upgraded.
|
||||
|
||||
CoAP-Resources, Image Management
|
||||
++++++++++++++++++++++++++++++++
|
||||
|
||||
The bootloader now keeps a directory of the images. In this directory we
|
||||
keep the following information which can be retrieved or set via CoAP
|
||||
resources:
|
||||
|
||||
- partition-ok: A flag per partition that indicates if this partition
|
||||
has ever been successfully booted. This flag can only be set for a
|
||||
partition that is currently running. Via CoAP this is set via the
|
||||
``/part_ok`` URI. In addition to the URI, a query-parameter indicating
|
||||
the partition has to be specified, e.g., ``/part_ok?part=1``.
|
||||
Note that when a partition is flashed via the bootloader (and not via
|
||||
OTA) this flag is *not* set. So if later a new partition is loaded via
|
||||
OTA and the old partition never was marked OK, the old partition has
|
||||
to be rebooted before it can be made the default partition again.
|
||||
The part_ok resource can currently not be queried via a GET request.
|
||||
- boot-default: The default boot partition, can be changed if the new
|
||||
default partition has the partition-ok flag set. The CoAP resource is
|
||||
``/boot_default`` and it can be queried via a GET request and set via
|
||||
a PUT request, the parameter to the PUT request is the partition
|
||||
number.
|
||||
- boot-next: A temporary flag that can be set on a partition to boot it
|
||||
just the next time. If booting fails the system will automatically
|
||||
boot the boot-default partition next time. This is automatically set
|
||||
after uploading an image. The CoAP resource is ``boot_next``. It can
|
||||
also be changed via the resource similar to ``/boot_default`` but
|
||||
without any constraints.
|
||||
|
||||
Additional CoAP resources exist to query the bootloader for parameters
|
||||
that are not kept in the directory:
|
||||
|
||||
- ``/part_count``: Currently always 2, in the future the bootloader may
|
||||
support more than two partitions
|
||||
- ``/part_size``: The size of one partition, all partitions are equal in
|
||||
size.
|
||||
- ``/part_start``: This resource needs an additional query-parameter
|
||||
indicating the partition number, e.g., ``/part_start?part=1`` and
|
||||
returns the partition start address in flash.
|
||||
- ``active_part``: The partition that is currently booted.
|
||||
|
||||
|
||||
Security
|
||||
========
|
||||
|
||||
This is experimental code. There is currently no security, everybody (!)
|
||||
can update your node. So use this only in experimental setups for now
|
||||
until client-side DTLS authentication is available.
|
||||
|
||||
Position Independent Code
|
||||
=========================
|
||||
|
||||
|
@ -37,29 +139,33 @@ are accessed and the bootloader then only relocates the addresses in the
|
|||
jump-table.
|
||||
|
||||
The first implementation will use two images (one for upper-, one for
|
||||
lower half).
|
||||
lower half). We may decide to add on-the-fly relocation or we may always
|
||||
ship two images (e.g. in a .zip file) and create a flash tool that
|
||||
determines the correct image from the system to be updated.
|
||||
|
||||
Memory Layout
|
||||
=============
|
||||
|
||||
The following table might have changed when you read this. See the
|
||||
``stk500boot_atmega256rfr2`` bootloader on github, in particular the
|
||||
file ``flash_layout.h`` for details.
|
||||
|
||||
+--------------------------------------+
|
||||
| 3E000-3FFFF Bootloader |
|
||||
+--------------------------------------+
|
||||
| 3DE00-3DFFF Flash image directory |
|
||||
+--------------------------------------+
|
||||
| 3DC00-3DDFF IRQVec copy upper image |
|
||||
| 3D600-3DDFF IRQVec copy upper image |
|
||||
+--------------------------------------+
|
||||
| 1F100-3DBFF |
|
||||
| Upper Image (w/o first two pages) |
|
||||
| 1EF00-3D5FF |
|
||||
| Upper Image |
|
||||
| |
|
||||
| |
|
||||
+--------------------------------------+
|
||||
| 1EF00-1F0FF IRQVec upper image |
|
||||
| 1E700-1EEFF IRQVec copy lower image |
|
||||
+--------------------------------------+
|
||||
| 1ED00-1EEFF IRQVec copy lower image |
|
||||
+--------------------------------------+
|
||||
| 00200-1ECFF |
|
||||
| Lower Image (w/o first two pages) |
|
||||
| 00000-1E6FF |
|
||||
| Lower Image |
|
||||
| |
|
||||
| |
|
||||
+--------------------------------------+
|
||||
|
@ -68,14 +174,19 @@ Memory Layout
|
|||
|
||||
We have two identical images. Each image contains the IRQ vectors (and
|
||||
some code after the vector table) in the lower two pages. A copy of
|
||||
these two pages is kept in two pages after the image. The reason is that
|
||||
the IRQ vectors are fixed at address 00000 in this processor
|
||||
architecture. So for running an image we need to copy the irq-vectors to
|
||||
these pages (currently 8 pages as of this writing) is kept after the
|
||||
image. The reason is that the IRQ vectors are fixed at address 00000 in
|
||||
this processor architecture. In addition the compiler creates jumptables
|
||||
(so-called trampoline code) to reach functions everywhere in memory via
|
||||
a near call. So for running an image we need to copy the irq-vectors to
|
||||
the fixed location (and therefore we keep a backup to be able to restore
|
||||
the original image at that location).
|
||||
|
||||
We use the irq vectors in the bootloader to determine the
|
||||
currently-running image: The first vector at position 0 is a jump to the
|
||||
start of our program. From the address of this jump we can find out
|
||||
which image is currently running.
|
||||
|
||||
Note that in the table above an image as generated by the compiler
|
||||
consists of the IRQ vectors in the first two pages (00000-001FF for the
|
||||
first and 1EF00-1F0FF for the second image) plus the rest of the code
|
||||
consists of the IRQ vectors in the first pages plus the rest of the code
|
||||
for that image.
|
||||
|
||||
|
||||
|
|
Loading…
Reference in a new issue