diff --git a/bincopy.py b/bincopy.py index 1aaa676..946f130 100755 --- a/bincopy.py +++ b/bincopy.py @@ -1101,6 +1101,36 @@ def add_elf(self, data, overwrite=True): self.word_size_bytes), overwrite) + def add_microchip_hex(self, records, overwrite=False): + """Add given Microchip HEX data. + + Microchip's HEX format is identical to Intel's except an address in + the HEX file is twice the actual machine address. For example: + + :02000E00E4C943 + + : Start code + 02 Record contains two data bytes + 000E Address 0x000E; Machine address is 0x000E // 2 == 0x0007 + 00 Record type is data + E4 Low byte at address 0x0007 is 0xE4 + C9 High byte at address 0x0007 is 0xC9 + + Microchip HEX records therefore need to be parsed as if the word size + is one byte, but the parsed data must be handled as if the word size + is two bytes. This is true for both 8-bit PICs such as PIC18 and + 16-bit PICs such as PIC24. + + """ + + self.word_size_bytes = 1 + self.add_ihex(records, overwrite) + self.word_size_bytes = 2 + self.segments.word_size_bytes = 2 + + for segment in self.segments: + segment.word_size_bytes = 2 + def add_file(self, filename, overwrite=False): """Open given file and add its data by guessing its format. The format must be Motorola S-Records, Intel HEX, TI-TXT. Set `overwrite` @@ -1171,6 +1201,15 @@ def add_elf_file(self, filename, overwrite=False): with open(filename, 'rb') as fin: self.add_elf(fin.read(), overwrite) + def add_microchip_hex_file(self, filename, overwrite=False): + """Open given Microchip HEX file and add its contents. Set `overwrite` + to ``True`` to allow already added data to be overwritten. + + """ + + with open(filename, 'r') as fin: + self.add_microchip_hex(fin.read(), overwrite) + def as_srec(self, number_of_data_bytes=32, address_length_bits=32): """Format the binary file as Motorola S-Records records and return them as a string. diff --git a/tests/test_bincopy.py b/tests/test_bincopy.py index f0cb72d..ba11a8b 100644 --- a/tests/test_bincopy.py +++ b/tests/test_bincopy.py @@ -1856,6 +1856,13 @@ def test_segment_len_16(self): word_size_bytes) self.assertEqual(length, len(segment)) + def test_add_microchip_hex_record(self): + binfile = bincopy.BinFile() + binfile.add_microchip_hex(':02000E00E4C943') + self.assertEqual(0x0007, binfile.minimum_address) + first_word = int.from_bytes(binfile[:binfile.minimum_address + 1], "little") + self.assertEqual(0xC9E4, first_word) + if __name__ == '__main__': unittest.main()