├── .gitignore ├── .stats.yml ├── .travis.yml ├── CONTRIBUTING.md ├── LICENSE ├── Makefile.am ├── Makefile.riot ├── README.md ├── Vagrantfile ├── autogen.sh ├── build ├── contiki-ng │ ├── .gitignore │ ├── Makefile.target │ ├── README.md │ ├── application │ │ ├── Makefile │ │ ├── project-conf.h │ │ ├── runner.c │ │ └── update_process.c │ ├── autogen.sh │ ├── bootloader │ │ ├── Makefile │ │ ├── README.md │ │ ├── bootloader.c │ │ ├── bootloader_ctx.c │ │ └── project-conf.h │ ├── config.toml │ ├── evaluator.h │ ├── make_firmware.sh │ ├── makefiles │ │ ├── Makefile.cryptoauthlib │ │ ├── Makefile.libpull │ │ ├── Makefile.tinycrypt │ │ └── Makefile.tinydtls │ ├── memory_evaluator.sh │ ├── patches │ │ └── contiki-ng │ │ │ ├── 0001-Allow-to-define-the-main-in-the-application.patch │ │ │ ├── 0002-do-not-reinitialize-the-UART-over-Devpack-in-the-OTA.patch │ │ │ ├── 0003-Fix-external-spi-flash-device-id.patch │ │ │ ├── 0004-Fix-compilation-warnings.patch │ │ │ ├── 0006-Allow-to-disable-all-output.patch │ │ │ ├── arch │ │ │ └── cpu │ │ │ │ └── cc26xx-cc13xx │ │ │ │ └── lib │ │ │ │ └── cc26xxware │ │ │ │ └── 0001-Avoid-symbol-collision-with-TinyDTLS.patch │ │ │ └── os │ │ │ └── net │ │ │ └── security │ │ │ └── tinydtls │ │ │ └── 0001-Remove-errors-while-building-Coap-with-DTLS-support.patch │ ├── target │ │ ├── srf06-cc26xx │ │ │ └── sensortag │ │ │ │ └── cc2650 │ │ │ │ ├── Makefile.board │ │ │ │ ├── Makefile.conf │ │ │ │ ├── Makefile.export │ │ │ │ ├── bootloader │ │ │ │ ├── pull_board.c │ │ │ │ ├── pull_contiki-main.c │ │ │ │ └── pull_platform.c │ │ │ │ └── linker_script.c │ │ └── zoul │ │ │ └── firefly-reva │ │ │ ├── Makefile.board │ │ │ ├── Makefile.conf │ │ │ ├── Makefile.export │ │ │ └── linker_script.c │ ├── test-ci.sh │ └── test │ │ ├── memory │ │ ├── Makefile │ │ └── test.c │ │ └── security │ │ ├── Makefile │ │ └── test.c ├── doc │ ├── .gitignore │ ├── Makefile │ ├── README.md │ ├── requirements.txt │ ├── source │ │ ├── Doxyfile │ │ ├── api │ │ │ ├── agents.rst │ │ │ ├── api.rst │ │ │ ├── common.rst │ │ │ ├── memory.rst │ │ │ ├── network.rst │ │ │ └── security.rst │ │ ├── badges.md │ │ ├── basics │ │ │ ├── agents.rst │ │ │ ├── basics.rst │ │ │ ├── contributing.rst │ │ │ ├── cryptographic_libraries.md │ │ │ ├── documentation.rst │ │ │ └── library.md │ │ ├── conf.py │ │ ├── img │ │ │ └── libpull.png │ │ ├── index.rst │ │ ├── platform │ │ │ ├── contiki_ng_link.rst │ │ │ ├── new_link.rst │ │ │ ├── platform.rst │ │ │ ├── riot_link.rst │ │ │ └── zephyr_link.rst │ │ ├── static │ │ │ └── override.css │ │ └── tutorial │ │ │ ├── 1_introduction.md │ │ │ ├── 2_getting_started.md │ │ │ ├── 3_libpull_setup.md │ │ │ ├── 4_network_setup.md │ │ │ ├── 5_build_libpull.md │ │ │ ├── 6_test_update.md │ │ │ └── tutorial.rst │ └── test-ci.sh ├── new │ └── README.md ├── posix │ └── .gitkeep ├── riot │ ├── .gitignore │ ├── README.md │ ├── application │ │ ├── Makefile │ │ └── runner.c │ ├── autogen.sh │ ├── boards │ │ └── remote-reva │ │ │ ├── .gitignore │ │ │ ├── Makefile.conf │ │ │ ├── Makefile.export │ │ │ └── linker_script.c │ ├── bootloader │ │ ├── .gitignore │ │ ├── Makefile │ │ ├── bootloader.c │ │ └── bootloader_ctx.c │ ├── config.toml │ ├── make_firmware.sh │ ├── patches │ │ └── riot │ │ │ ├── 0001-Add-tinycrypt-package.patch │ │ │ ├── 0002-Use-AntonioLangiu-fork-of-libcoap.patch │ │ │ └── 0003-Fix-error-when-building-with-setsockopt.patch │ ├── test-ci.sh │ └── test │ │ ├── memory │ │ ├── Makefile │ │ └── test.c │ │ ├── network │ │ ├── Makefile │ │ └── test.c │ │ └── security │ │ ├── Makefile │ │ └── test.c └── zephyr │ ├── .gitignore │ ├── README.md │ ├── application │ ├── CMakeLists.txt │ ├── evaluation │ │ ├── FW1.0.txt │ │ ├── FW1.3.txt │ │ ├── FW1.4.txt │ │ ├── config.toml │ │ ├── fwV1.0.txt │ │ └── make_diff.sh │ ├── prj_nrf52840_pca10056.conf │ ├── prj_nrf52840_pca10056.conf.tiny │ └── src │ │ └── runner.c │ ├── application_ble │ ├── CMakeLists.txt │ ├── prj_nrf52840_pca10056.conf │ └── src │ │ └── main.c │ ├── autogen.sh │ ├── board │ └── nrf52840_pca10056 │ │ ├── Makefile.conf │ │ └── loader.c │ ├── bootloader │ ├── CMakeLists.txt │ ├── prj_nrf52840_pca10056.conf │ └── src │ │ └── bootloader.c │ ├── bootloader_ctx │ ├── .gitignore │ ├── Makefile │ └── bootloader_ctx.c │ ├── config.toml │ ├── make_eval_bt.sh │ ├── make_firmware.sh │ ├── test-ci.sh │ └── test │ ├── memory │ ├── CMakeLists.txt │ ├── prj.conf │ └── src │ │ └── main.c │ ├── network │ ├── CMakeLists.txt │ ├── prj.conf │ ├── prj_nrf52840_ot.conf │ └── src │ │ └── main.c │ └── security │ ├── CMakeLists.txt │ ├── prj.conf │ └── src │ └── main.c ├── configure.ac ├── default_keys.h ├── include ├── libpull │ ├── common.h │ ├── common │ │ ├── callback.h │ │ ├── error.h │ │ ├── external.h │ │ ├── libpull_config.h │ │ ├── loader.h │ │ ├── logger.h │ │ ├── pull_assert.h │ │ └── types.h │ ├── memory.h │ ├── memory │ │ ├── flash_interface.h │ │ ├── manifest.h │ │ ├── memory_interface.h │ │ ├── memory_objects.h │ │ └── simple_manifest.h │ ├── network.h │ ├── network │ │ ├── async_interface.h │ │ ├── connection_config.h │ │ ├── connection_interface.h │ │ ├── fsm.h │ │ ├── gatt.h │ │ ├── receiver.h │ │ └── request.h │ ├── pipeline.h │ ├── pipeline │ │ ├── bspatch.h │ │ ├── buffer.h │ │ ├── decript.h │ │ ├── lzss.h │ │ ├── pipeline.h │ │ └── writer.h │ ├── security.h │ └── security │ │ ├── aes.h │ │ ├── decrypt.h │ │ ├── digest.h │ │ ├── ecc.h │ │ ├── rng.h │ │ ├── safestore.h │ │ └── verifier.h ├── libpull_agents │ ├── README.md │ ├── bootloader_agent.h │ ├── bootloader_ctx.h │ ├── coroutines.h │ └── update.h └── libpull_network │ └── coap │ ├── async_libcoap.h │ ├── connection_ercoap.h │ ├── connection_libcoap.h │ └── connection_zoap.h ├── libpull_config.h.in ├── patches ├── libcoap │ └── 0001-add-ecdh-support-for-tinydtls.patch └── tinydtls │ ├── 0001_contiki_ng_Add-watchdog-for-ECC-verification.patch │ └── 0002_contiki_ng_Disable-TinyDTLS-debug-for-Contiki.patch ├── src ├── Makefile ├── agents │ ├── bootloader_agent.c │ └── update.c ├── core │ ├── common │ │ └── error.c │ ├── memory │ │ ├── manifest.c │ │ ├── memory_flash.c │ │ ├── memory_impl.c │ │ ├── memory_objects.c │ │ └── simple_manifest.c │ ├── network │ │ ├── connection_config.c │ │ ├── fsm.c │ │ └── request.c │ ├── pipeline │ │ ├── bspatch.c │ │ ├── buffer.c │ │ ├── lzss.c │ │ └── writer.c │ └── security │ │ ├── cryptoauthlib.c │ │ ├── mbedtls.c │ │ ├── safestore.c │ │ ├── tinycrypt.c │ │ ├── tinydtls.c │ │ └── verifier.c ├── cpu │ └── arm │ │ └── arm_cortex_loader.c ├── network │ ├── ble │ │ └── zephyr_ble.c │ └── coap │ │ ├── er-coap │ │ └── connection_ercoap.c │ │ ├── libcoap │ │ ├── async_libcoap.c │ │ └── connection_libcoap.c │ │ └── zoap │ │ ├── async_zoap.c │ │ └── connection_zoap.c └── platform │ ├── cc2538 │ ├── memory_firefly.c │ ├── platform_headers.h │ ├── rng.c │ ├── rom.h │ └── utils.h │ ├── cc2650 │ ├── memory_cc2650.c │ ├── platform_headers.h │ ├── rng_cc2560.c │ └── utils.h │ ├── nrf52840 │ ├── memory_nrf52840_pca10056.c │ ├── platform_headers.h │ ├── rng.c │ └── utils.h │ └── posix │ ├── memory_posix.c │ ├── memory_posix.h │ └── rng.c ├── test ├── .gitignore ├── Makefile.am ├── agents │ ├── test_bootloader_agent.c │ ├── test_update_pull.c │ └── test_update_push.c ├── memory │ ├── test_manifest.c │ ├── test_memory.c │ └── test_memory_objects.c ├── mocks │ ├── manifest_mock.c │ ├── manifest_mock.h │ ├── memory_mock.c │ └── memory_mock.h ├── network │ ├── test_connection_dtls.c │ ├── test_receiver.c │ └── test_request.c ├── pipeline │ ├── test_bspatch.c │ ├── test_buffer.c │ ├── test_lzss.c │ └── test_pipeline.c ├── platform │ ├── README.md │ ├── memory.h │ ├── network.h │ ├── ntest.h │ └── security.h ├── push-size.sh ├── script.sh ├── security │ ├── test_mbedtls.c │ ├── test_tinycrypt.c │ ├── test_tinydtls.c │ └── test_verifier.h ├── support │ ├── external_variables.c │ ├── invalid_digest.h │ ├── platform_headers.h │ ├── support.h │ ├── test_runner.h │ ├── utils.c │ └── utils.h ├── test-ci.sh └── test_update └── utils ├── assets_generator.sh ├── firmware_tool ├── .gitignore ├── Makefile.am ├── commands │ ├── bootctx.cpp │ ├── commands.hpp │ ├── configs.cpp │ ├── help.cpp │ ├── keys.cpp │ ├── manifest.cpp │ ├── pipeline.cpp │ └── utils.cpp ├── config.toml ├── context.cpp ├── context.hpp ├── deps │ ├── cpptoml.h │ └── update.sh ├── firmware_tool.cpp └── keys │ ├── server.priv │ ├── server.pub │ ├── vendor.priv │ └── vendor.pub ├── hooks ├── README.md └── commit-msg └── server ├── .gitignore ├── Makefile.am ├── README.md ├── config.h ├── network.c ├── resources ├── echo.c ├── firmware.c ├── firmware_diff.c ├── firmware_invalid_signature.c ├── firmware_invalid_size.c ├── next_version.c ├── resources.h ├── version.c └── version_invalid.c ├── server.c └── server.h /.gitignore: -------------------------------------------------------------------------------- 1 | # Prerequisites 2 | *.d 3 | 4 | # Makefile folders 5 | **/.deps 6 | **/.dirstamp 7 | missing 8 | **/Makefile.in 9 | install.sh 10 | configure 11 | config.status 12 | autom4te.cache 13 | config.h 14 | **/*.trs 15 | **/stamp-h1 16 | **/stamp-h2 17 | *.m4 18 | ar-lib 19 | compile 20 | config.guess 21 | config.sub 22 | depcomp 23 | install-sh 24 | ltmain.sh 25 | test-driver 26 | 27 | # Autogenerated files 28 | include/common/libpull_config.h 29 | default_config.h 30 | default_config.h.in 31 | 32 | # Object files 33 | *.o 34 | *.ko 35 | *.obj 36 | *.elf 37 | 38 | # Linker output 39 | *.ilk 40 | *.map 41 | *.exp 42 | 43 | # Precompiled Headers 44 | *.gch 45 | *.pch 46 | 47 | # Libraries 48 | *.lib 49 | *.a 50 | *.la 51 | *.lo 52 | 53 | # Shared objects (inc. Windows DLLs) 54 | *.dll 55 | *.so 56 | *.so.* 57 | *.dylib 58 | 59 | # Executables 60 | *.exe 61 | *.out 62 | *.app 63 | *.i*86 64 | *.x86_64 65 | *.hex 66 | 67 | # Debug files 68 | *.dSYM/ 69 | *.su 70 | *.idb 71 | *.pdb 72 | 73 | # Kernel Module Compile Results 74 | *.mod* 75 | *.cmd 76 | .tmp_versions/ 77 | modules.order 78 | Module.symvers 79 | Mkfile.old 80 | dkms.conf 81 | 82 | # Contiki folder 83 | ./contiki 84 | symbols.c 85 | symbols.h 86 | obj_native/ 87 | 88 | # Contiki 89 | *.co 90 | *.log 91 | *.native 92 | *.bin 93 | *.srf06-cc26xx 94 | 95 | # Testing 96 | assets/ 97 | build/ceedling/*/* 98 | 99 | # Coverage 100 | *.gcda 101 | *.gcno 102 | 103 | # Utils 104 | utils/fake_firmware_generator 105 | .vagrant 106 | ext/ 107 | node_modules 108 | package-lock.json 109 | 110 | # OSX 111 | .DS_Store 112 | 113 | # Generated Makefiles 114 | /Makefile 115 | test/Makefile 116 | utils/server/Makefile 117 | utils/firmware_tool/Makefile 118 | stats_ci 119 | -------------------------------------------------------------------------------- /.stats.yml: -------------------------------------------------------------------------------- 1 | workspaces: 2 | default: 3 | -alias: size 4 | -spreadsheet_key: 1Fg2EqCLWgidfPpiCXaasJ3KqdOgRxuFkicMSE2O11vc 5 | -worksheet_index: 0 6 | -------------------------------------------------------------------------------- /.travis.yml: -------------------------------------------------------------------------------- 1 | language: cpp 2 | sudo: false 3 | dist: trusty 4 | 5 | addons: 6 | apt: 7 | packages: 8 | - srecord 9 | - gcovr 10 | - gcc-arm-none-eabi 11 | - libnewlib-arm-none-eabi 12 | - device-tree-compiler 13 | - gperf 14 | 15 | #cache: 16 | #directories: 17 | #- ext 18 | #- build/contiki-ng/ext 19 | #- build/riot/ext 20 | #- build/zephyr/ext 21 | 22 | before_install: 23 | - pip install --user cpp-coveralls 24 | 25 | install: 26 | - ./autogen.sh 27 | - ./configure --enable-gcov 28 | 29 | script: 30 | - ./$SCRIPT 31 | 32 | matrix: 33 | include: 34 | - name: "Unit Test" 35 | env: SCRIPT=test/test-ci.sh 36 | - name: "Build Test: Contiki-NG" 37 | env: SCRIPT=build/contiki-ng/test-ci.sh 38 | - name: "Build Test: RIOT" 39 | env: SCRIPT=build/riot/test-ci.sh 40 | - name: "Build Test: Zephyr" 41 | env: SCRIPT=build/zephyr/test-ci.sh 42 | - name: "Build Documentation" 43 | env: SCRIPT=build/doc/test-ci.sh 44 | allow_failures: 45 | - name: "Build Test: Zephyr" 46 | env: SCRIPT=build/zephyr/test-ci.sh 47 | - name: "Build Documentation" 48 | env: SCRIPT=build/doc/test-ci.sh 49 | 50 | -------------------------------------------------------------------------------- /LICENSE: -------------------------------------------------------------------------------- 1 | MIT License 2 | 3 | Copyright (c) 2018 Antonio Langiu 4 | 5 | Permission is hereby granted, free of charge, to any person obtaining a copy 6 | of this software and associated documentation files (the "Software"), to deal 7 | in the Software without restriction, including without limitation the rights 8 | to use, copy, modify, merge, publish, distribute, sublicense, and/or sell 9 | copies of the Software, and to permit persons to whom the Software is 10 | furnished to do so, subject to the following conditions: 11 | 12 | The above copyright notice and this permission notice shall be included in all 13 | copies or substantial portions of the Software. 14 | 15 | THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND, EXPRESS OR 16 | IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF MERCHANTABILITY, 17 | FITNESS FOR A PARTICULAR PURPOSE AND NONINFRINGEMENT. IN NO EVENT SHALL THE 18 | AUTHORS OR COPYRIGHT HOLDERS BE LIABLE FOR ANY CLAIM, DAMAGES OR OTHER 19 | LIABILITY, WHETHER IN AN ACTION OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, 20 | OUT OF OR IN CONNECTION WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE 21 | SOFTWARE. 22 | -------------------------------------------------------------------------------- /Makefile.am: -------------------------------------------------------------------------------- 1 | AUTOMAKE_OPTIONS = subdir-objects 2 | SUBDIRS = test 3 | 4 | AM_CFLAGS = -Wall -I. -Iinclude -Iext/tinycrypt/lib/include -Iext/tinydtls -Iext/mbedtls/include -DHAVE_CONFIG_H -ffreestanding -pedantic-errors -std=c99 -DENABLE_SIGN=1 -DSIMPLE_MANIFEST=1 -DWITH_TINYDTLS=1 -DWITH_TINYCRYPT=1 -DWITH_MBEDTLS=1 5 | 6 | noinst_LIBRARIES = libpull.a 7 | 8 | libpull_a_SOURCES = src/core/common/error.c 9 | libpull_a_SOURCES += src/core/memory/manifest.c src/core/memory/memory_objects.c src/core/memory/simple_manifest.c 10 | libpull_a_SOURCES += src/core/memory/memory_impl.c src/core/memory/memory_flash.c 11 | libpull_a_SOURCES += src/core/network/connection_config.c src/core/network/fsm.c src/core/network/request.c 12 | libpull_a_SOURCES += src/core/security/verifier.c src/core/security/tinycrypt.c src/core/security/tinydtls.c src/core/security/cryptoauthlib.c src/core/security/safestore.c src/core/security/mbedtls.c 13 | libpull_a_SOURCES += src/core/pipeline/lzss.c src/core/pipeline/bspatch.c src/core/pipeline/buffer.c src/core/pipeline/writer.c 14 | 15 | pkginclude_HEADERS = include/ 16 | # TODO Finish including all the headers 17 | 18 | assets: firmware_tool 19 | ./utils/assets_generator.sh 20 | 21 | firmware_tool: libpull.a 22 | $(MAKE) -C utils/firmware_tool 23 | 24 | run_server: server assets 25 | ./utils/server/server -f assets/slot_d.bin 26 | 27 | server: libpull.a 28 | $(MAKE) -C utils/server 29 | -------------------------------------------------------------------------------- /Makefile.riot: -------------------------------------------------------------------------------- 1 | # This Makefile is used to build libpull for RIOT as a package 2 | # This Makefile assumes to be called from the RIOT Makfile so 3 | # that all the CFLAGS and includes are setted already by RIOT. 4 | # Moreover it assumes that BINDIR is defined. 5 | # 6 | # This Makefile will build the objects files in the current directory 7 | # so if you change the build platform you need to clean the generated 8 | # files. 9 | 10 | MODULES = common memory network security 11 | SRCS := $(foreach module,$(MODULES), $(wildcard src/$(module)/*.c)) 12 | 13 | CFLAGS += -Iinclude -I. $(INCLUDES) 14 | 15 | # Default configuration 16 | CFLAGS += -DWITH_SIMPLE_MANIFEST=1 17 | 18 | OBJS=$(subst .c,.o,$(SRCS)) 19 | 20 | %.o: %.c 21 | $(CC) -c $< -o $@ $(CFLAGS) 22 | 23 | $(BINDIR)/libpull.a: $(OBJS) 24 | $(AR) -rsv $@ $(OBJS) 25 | $(RANLIB) -t $@ 26 | 27 | clean: 28 | rm -f $(OBJS) $(BINDIR)/libpull.a 29 | 30 | # Check input parameters 31 | ifeq (,$(BINDIR)) 32 | $(warning The BINDIR variable is not defined) 33 | endif 34 | ifeq (,$(AR)) 35 | $(warning The AR variable in not defined) 36 | endif 37 | ifeq (,$(RANLIB)) 38 | $(warning The RANLIB variable is not defined) 39 | endif 40 | -------------------------------------------------------------------------------- /README.md: -------------------------------------------------------------------------------- 1 | # UpKit 2 | 3 | #### An Open-Source, Portable, and Lightweight Update Framework for Constrained IoT Devices 4 | 5 | [![Codacy Badge](https://api.codacy.com/project/badge/Grade/2d7c1102e03446a1abad33d768306677)](https://app.codacy.com/app/AntonioLangiu/libpull?utm_source=github.com&utm_medium=referral&utm_content=libpull/libpull&utm_campaign=Badge_Grade_Dashboard) 6 | [![GitHub license](https://img.shields.io/github/license/updatekit/upkit.svg)](https://github.com/updatekit/upkit/blob/update/readme/LICENSE) 7 | [![GitHub issues](https://img.shields.io/github/issues/updatekit/upkit.svg)](https://github.com/updatekit/upkit/issues) 8 | [![GitHub release](https://img.shields.io/github/release/updatekit/upkit.svg)](https://github.com/updatekit/upkit/releases) 9 | [![Documentation Status](https://readthedocs.org/projects/libpull/badge/?version=latest)](https://libpull.readthedocs.io/en/latest/?badge=latest) 10 | [![Coverage Status](https://coveralls.io/repos/github/libpull/libpull/badge.svg)](https://coveralls.io/github/libpull/libpull) 11 | [![GitHub pull-requests](https://img.shields.io/github/issues-pr/updatekit/upkit.svg)](https://github.com/updatekit/upkit/pulls) 12 | 13 | UpKit is a C library to implement secure and portable software updates on IoT devices. 14 | 15 | It targets [Class 1 and Class 2](https://tools.ietf.org/html/rfc7228#section-3) 16 | constrained devices, characterized by ~10 kB of RAM and ~100 kB of ROM. 17 | However, its lightweight and modular approach can be beneficial also for bigger devices. 18 | 19 | The library can be included into MCU firmware to perform 20 | Over The Air updates. It is composed of many high-level 21 | modules that interact with the low-level abstraction layer, implemented 22 | for the specific platform. This is needed since 23 | accessing the memory and the network on embedded systems 24 | is a complex task and each platform and architecture uses its 25 | own primitive. 26 | 27 | The goal of the library is to be a portable and secure solution 28 | to reduce the costs of securing IoT devices, allowing an easy 29 | device update and management also for very 30 | constrained applications. 31 | -------------------------------------------------------------------------------- /Vagrantfile: -------------------------------------------------------------------------------- 1 | $script = <