1
1
# Copyright 2018 Nordic Semiconductor ASA
2
2
# Copyright 2017 Linaro Limited
3
- # Copyright 2019 Arm Limited
3
+ # Copyright 2019-2020 Arm Limited
4
4
#
5
5
# Licensed under the Apache License, Version 2.0 (the "License");
6
6
# you may not use this file except in compliance with the License.
61
61
'ENCRSA2048' : 0x30 ,
62
62
'ENCKW128' : 0x31 ,
63
63
'ENCEC256' : 0x32 ,
64
- 'DEPENDENCY' : 0x40
64
+ 'DEPENDENCY' : 0x40 ,
65
+ 'SEC_CNT' : 0x50 ,
65
66
}
66
67
67
68
TLV_SIZE = 4
@@ -119,7 +120,7 @@ def __init__(self, version=None, header_size=IMAGE_HEADER_SIZE,
119
120
pad_header = False , pad = False , align = 1 , slot_size = 0 ,
120
121
max_sectors = DEFAULT_MAX_SECTORS , overwrite_only = False ,
121
122
endian = "little" , load_addr = 0 , erased_val = None ,
122
- save_enctlv = False ):
123
+ save_enctlv = False , security_counter = None ):
123
124
self .version = version or versmod .decode_version ("0" )
124
125
self .header_size = header_size
125
126
self .pad_header = pad_header
@@ -137,12 +138,23 @@ def __init__(self, version=None, header_size=IMAGE_HEADER_SIZE,
137
138
self .save_enctlv = save_enctlv
138
139
self .enctlv_len = 0
139
140
141
+ if security_counter == 'auto' :
142
+ # Security counter has not been explicitly provided,
143
+ # generate it from the version number
144
+ self .security_counter = ((self .version .major << 24 )
145
+ + (self .version .minor << 16 )
146
+ + self .version .revision )
147
+ else :
148
+ self .security_counter = security_counter
149
+
140
150
def __repr__ (self ):
141
- return "<Image version={}, header_size={}, base_addr={}, load_addr={}, \
142
- align={}, slot_size={}, max_sectors={}, overwrite_only={}, \
143
- endian={} format={}, payloadlen=0x{:x}>" .format (
151
+ return "<Image version={}, header_size={}, security_counter={}, \
152
+ base_addr={}, load_addr={}, align={}, slot_size={}, \
153
+ max_sectors={}, overwrite_only={}, endian={} format={}, \
154
+ payloadlen=0x{:x}>" .format (
144
155
self .version ,
145
156
self .header_size ,
157
+ self .security_counter ,
146
158
self .base_addr if self .base_addr is not None else "N/A" ,
147
159
self .load_addr ,
148
160
self .align ,
@@ -246,14 +258,22 @@ def ecies_p256_hkdf(self, enckey, plainkey):
246
258
def create (self , key , enckey , dependencies = None ):
247
259
self .enckey = enckey
248
260
249
- if dependencies is None :
250
- dependencies_num = 0
251
- protected_tlv_size = 0
252
- else :
253
- # Size of a Dependency TLV = Header ('BBH') + Payload('IBBHI')
254
- # = 16 Bytes
261
+ protected_tlv_size = 0
262
+
263
+ if self .security_counter is not None :
264
+ # Size of the security counter TLV: header ('HH') + payload ('I')
265
+ # = 4 + 4 = 8 Bytes
266
+ protected_tlv_size += TLV_SIZE + 4
267
+
268
+ if dependencies is not None :
269
+ # Size of a Dependency TLV = Header ('HH') + Payload('IBBHI')
270
+ # = 4 + 12 = 16 Bytes
255
271
dependencies_num = len (dependencies [DEP_IMAGES_KEY ])
256
- protected_tlv_size = (dependencies_num * 16 ) + TLV_INFO_SIZE
272
+ protected_tlv_size += (dependencies_num * 16 )
273
+
274
+ if protected_tlv_size != 0 :
275
+ # Add the size of the TLV info header
276
+ protected_tlv_size += TLV_INFO_SIZE
257
277
258
278
# At this point the image is already on the payload, this adds
259
279
# the header to the payload as well
@@ -265,17 +285,24 @@ def create(self, key, enckey, dependencies=None):
265
285
# in the hash calculation
266
286
protected_tlv_off = None
267
287
if protected_tlv_size != 0 :
268
- for i in range (dependencies_num ):
269
- e = STRUCT_ENDIAN_DICT [self .endian ]
270
- payload = struct .pack (
271
- e + 'B3x' + 'BBHI' ,
272
- int (dependencies [DEP_IMAGES_KEY ][i ]),
273
- dependencies [DEP_VERSIONS_KEY ][i ].major ,
274
- dependencies [DEP_VERSIONS_KEY ][i ].minor ,
275
- dependencies [DEP_VERSIONS_KEY ][i ].revision ,
276
- dependencies [DEP_VERSIONS_KEY ][i ].build
277
- )
278
- prot_tlv .add ('DEPENDENCY' , payload )
288
+
289
+ e = STRUCT_ENDIAN_DICT [self .endian ]
290
+
291
+ if self .security_counter is not None :
292
+ payload = struct .pack (e + 'I' , self .security_counter )
293
+ prot_tlv .add ('SEC_CNT' , payload )
294
+
295
+ if dependencies is not None :
296
+ for i in range (dependencies_num ):
297
+ payload = struct .pack (
298
+ e + 'B3x' + 'BBHI' ,
299
+ int (dependencies [DEP_IMAGES_KEY ][i ]),
300
+ dependencies [DEP_VERSIONS_KEY ][i ].major ,
301
+ dependencies [DEP_VERSIONS_KEY ][i ].minor ,
302
+ dependencies [DEP_VERSIONS_KEY ][i ].revision ,
303
+ dependencies [DEP_VERSIONS_KEY ][i ].build
304
+ )
305
+ prot_tlv .add ('DEPENDENCY' , payload )
279
306
280
307
protected_tlv_off = len (self .payload )
281
308
self .payload += prot_tlv .get ()
0 commit comments