diff options
author | Raghuram Subramani <raghus2247@gmail.com> | 2022-06-19 19:47:51 +0530 |
---|---|---|
committer | Raghuram Subramani <raghus2247@gmail.com> | 2022-06-19 19:47:51 +0530 |
commit | 4fd287655a72b9aea14cdac715ad5b90ed082ed2 (patch) | |
tree | 65d393bc0e699dd12d05b29ba568e04cea666207 /circuitpython/lib/nrfutil/nordicsemi/dfu/init_packet.py | |
parent | 0150f70ce9c39e9e6dd878766c0620c85e47bed0 (diff) |
add circuitpython code
Diffstat (limited to 'circuitpython/lib/nrfutil/nordicsemi/dfu/init_packet.py')
-rw-r--r-- | circuitpython/lib/nrfutil/nordicsemi/dfu/init_packet.py | 131 |
1 files changed, 131 insertions, 0 deletions
diff --git a/circuitpython/lib/nrfutil/nordicsemi/dfu/init_packet.py b/circuitpython/lib/nrfutil/nordicsemi/dfu/init_packet.py new file mode 100644 index 0000000..ccf8c34 --- /dev/null +++ b/circuitpython/lib/nrfutil/nordicsemi/dfu/init_packet.py @@ -0,0 +1,131 @@ +# Copyright (c) 2015, Nordic Semiconductor +# All rights reserved. +# +# Redistribution and use in source and binary forms, with or without +# modification, are permitted provided that the following conditions are met: +# +# * Redistributions of source code must retain the above copyright notice, this +# list of conditions and the following disclaimer. +# +# * Redistributions in binary form must reproduce the above copyright notice, +# this list of conditions and the following disclaimer in the documentation +# and/or other materials provided with the distribution. +# +# * Neither the name of Nordic Semiconductor ASA nor the names of its +# contributors may be used to endorse or promote products derived from +# this software without specific prior written permission. +# +# THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS "AS IS" +# AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE +# IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE +# DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT HOLDER OR CONTRIBUTORS BE LIABLE +# FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL +# DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR +# SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER +# CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, +# OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE +# OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. + +from enum import Enum +import struct + + +INIT_PACKET_USES_CRC16 = 0 +INIT_PACKET_USES_HASH = 1 +INIT_PACKET_EXT_USES_ECDS = 2 + + +class PacketField(Enum): + DEVICE_TYPE = 1 + DEVICE_REVISION = 2 + APP_VERSION = 3 + REQUIRED_SOFTDEVICES_ARRAY = 4 + OPT_DATA = 5 + NORDIC_PROPRIETARY_OPT_DATA_EXT_PACKET_ID = 6 + NORDIC_PROPRIETARY_OPT_DATA_FIRMWARE_LENGTH = 7 + NORDIC_PROPRIETARY_OPT_DATA_FIRMWARE_HASH = 8 + NORDIC_PROPRIETARY_OPT_DATA_FIRMWARE_CRC16 = 9 + NORDIC_PROPRIETARY_OPT_DATA_INIT_PACKET_ECDS = 10 + + +class Packet(object): + """ + Class that implements the INIT packet format. + http://developer.nordicsemi.com/nRF51_SDK/doc/7.1.0/s110/html/a00065.html + """ + + UNSIGNED_SHORT = "H" + UNSIGNED_INT = "I" + UNSIGNED_CHAR = "B" + CHAR_ARRAY = "s" + + def __init__(self, init_packet_fields): + """ + + :param init_packet_fields: Dictionary with packet fields + """ + self.init_packet_fields = init_packet_fields + + def generate_packet(self): + """ + Generates a binary packet from provided init_packet_fields provided in constructor. + This version includes the extended data + + :return str: Returns a string representing the init_packet (in binary) + + """ + # Create struct format string based on keys that are + # present in self.init_packet_fields + format_string = self.__generate_struct_format_string() + args = [] + + # If you got error message AttributeError: 'int' object has no attribute 'value'. + # Uncomment line 84 and comment out line 85 and run 'python setup.py install' + #for key in sorted(self.init_packet_fields.keys(), key=lambda x: x): + for key in sorted(self.init_packet_fields.keys(), key=lambda x: x.value): + # Add length to fields that required that + if key in [PacketField.REQUIRED_SOFTDEVICES_ARRAY, + PacketField.OPT_DATA]: + args.append(len(self.init_packet_fields[key])) + args.extend(self.init_packet_fields[key]) + else: + args.append(self.init_packet_fields[key]) + + return struct.pack(format_string, *args) + + def __generate_struct_format_string(self): + format_string = "<" # Use little endian format with standard sizes for python, + # see https://docs.python.org/2/library/struct.html + + # If you got error message AttributeError: 'int' object has no attribute 'value'. + # Uncomment line 102 and comment out line 103 and run 'python setup.py install' + #for key in sorted(self.init_packet_fields.keys(), key=lambda x: x): + for key in sorted(self.init_packet_fields.keys(), key=lambda x: x.value): + if key in [PacketField.DEVICE_TYPE, + PacketField.DEVICE_REVISION, + ]: + format_string += Packet.UNSIGNED_SHORT + + elif key in [PacketField.APP_VERSION]: + format_string += Packet.UNSIGNED_INT + elif key in [PacketField.REQUIRED_SOFTDEVICES_ARRAY]: + array_elements = self.init_packet_fields[key] + format_string += Packet.UNSIGNED_SHORT # Add length field to format packet + + for _ in range(len(array_elements)): + format_string += Packet.UNSIGNED_SHORT + elif key in [PacketField.OPT_DATA]: + format_string += Packet.UNSIGNED_SHORT # Add length field to optional data + format_string += "{0}{1}".format(len(self.init_packet_fields[key]), Packet.CHAR_ARRAY) + elif key in [PacketField.NORDIC_PROPRIETARY_OPT_DATA_EXT_PACKET_ID]: + format_string += Packet.UNSIGNED_INT # Add the extended packet id field + elif key == PacketField.NORDIC_PROPRIETARY_OPT_DATA_FIRMWARE_LENGTH: + format_string += Packet.UNSIGNED_INT # Add the firmware length field + elif key == PacketField.NORDIC_PROPRIETARY_OPT_DATA_FIRMWARE_HASH: + format_string += "32{0}".format(Packet.CHAR_ARRAY) # SHA-256 requires 32 bytes + elif key == PacketField.NORDIC_PROPRIETARY_OPT_DATA_FIRMWARE_CRC16: + format_string += Packet.UNSIGNED_SHORT + elif key == PacketField.NORDIC_PROPRIETARY_OPT_DATA_INIT_PACKET_ECDS: + format_string += "64{0}".format(Packet.CHAR_ARRAY) # ECDS based on P-256 using SHA-256 requires 64 bytes + + return format_string |