2323import re
2424import struct
2525import sys
26+ import os
2627
2728import click
2829
@@ -450,13 +451,17 @@ def convert(self, value, param, ctx):
450451 help = 'Unique vendor identifier, format: (<raw_uuid>|<domain_name)>' )
451452@click .option ('--cid' , default = None , required = False ,
452453 help = 'Unique image class identifier, format: (<raw_uuid>|<image_class_name>)' )
453- def sign (key , public_key_format , align , version , pad_sig , header_size ,
454+ @click .option ('--aes-raw-key' , default = None , required = False ,
455+ help = 'String representing raw AES key, format: hex byte string of 32 or 64'
456+ 'hexadecimal characters' )
457+ @click .pass_context
458+ def sign (ctx , key , public_key_format , align , version , pad_sig , header_size ,
454459 pad_header , slot_size , pad , confirm , test , max_sectors , overwrite_only ,
455460 endian , encrypt_keylen , encrypt , compression , infile , outfile ,
456461 dependencies , load_addr , hex_addr , erased_val , save_enctlv ,
457462 security_counter , boot_record , custom_tlv , rom_fixed , max_align ,
458463 clear , fix_sig , fix_sig_pubkey , sig_out , user_sha , hmac_sha , is_pure ,
459- vector_to_sign , non_bootable , vid , cid ):
464+ vector_to_sign , non_bootable , vid , cid , aes_raw_key ):
460465
461466 if confirm or test :
462467 # Confirmed but non-padded images don't make much sense, because
@@ -472,17 +477,30 @@ def sign(key, public_key_format, align, version, pad_sig, header_size,
472477 non_bootable = non_bootable , vid = vid , cid = cid )
473478 compression_tlvs = {}
474479 img .load (infile )
480+
475481 key = load_key (key ) if key else None
476- enckey = load_key (encrypt ) if encrypt else None
477- if enckey and key and ((isinstance (key , keys .ECDSA256P1 ) and
478- not isinstance (enckey , keys .ECDSA256P1Public ))
479- or (isinstance (key , keys .ECDSA384P1 ) and
480- not isinstance (enckey , keys .ECDSA384P1Public ))
481- or (isinstance (key , keys .RSA ) and
482- not isinstance (enckey , keys .RSAPublic ))):
483- # FIXME
484- raise click .UsageError ("Signing and encryption must use the same "
485- "type of key" )
482+ enckey = None
483+ if not aes_raw_key :
484+ enckey = load_key (encrypt ) if encrypt else None
485+ if enckey and key :
486+ if ((isinstance (key , keys .ECDSA256P1 ) and
487+ not isinstance (enckey , keys .ECDSA256P1Public ))
488+ or (isinstance (key , keys .ECDSA384P1 ) and
489+ not isinstance (enckey , keys .ECDSA384P1Public ))
490+ or (isinstance (key , keys .RSA ) and
491+ not isinstance (enckey , keys .RSAPublic ))):
492+ # FIXME
493+ raise click .UsageError ("Signing and encryption must use the same "
494+ "type of key" )
495+ else :
496+ if encrypt :
497+ encrypt = None
498+ print ('Raw AES key overrides --key, there will be no encrypted key added to the image' )
499+ if clear :
500+ clear = False
501+ print ('Raw AES key overrides --clear, image will be encrypted' )
502+ if ctx .get_parameter_source ('encrypt_keylen' ) != click .core .ParameterSource .DEFAULT :
503+ print ('Raw AES key len overrides --encrypt-keylen' )
486504
487505 if pad_sig and hasattr (key , 'pad_sig' ):
488506 key .pad_sig = True
@@ -527,11 +545,28 @@ def sign(key, public_key_format, align, version, pad_sig, header_size,
527545 'Pure signatures, currently, enforces preferred hash algorithm, '
528546 'and forbids sha selection by user.' )
529547
548+ plainkey = None
549+ if aes_raw_key :
550+ # Converting the command line provided raw AES key to byte array;
551+ # this aray will be truncated to desired len.
552+ plainkey = bytes .fromhex (aes_raw_key )
553+ plainkey_len = len (plainkey )
554+ if plainkey_len not in (16 , 32 ):
555+ raise click .UsageError ("Provided keylen, {int(plainkey_len)} in bytes, not supported" )
556+ elif enckey :
557+ if encrypt_keylen == 256 :
558+ encrypt_keylen_bytes = 32
559+ else :
560+ encrypt_keylen_bytes = 16
561+
562+ # No AES plain key and there is request to encrypt, generate random AES key
563+ plainkey = os .urandom (encrypt_keylen_bytes )
564+
530565 if compression in ["lzma2" , "lzma2armthumb" ]:
531566 img .create (key , public_key_format , enckey , dependencies , boot_record ,
532- custom_tlvs , compression_tlvs , None , int ( encrypt_keylen ) , clear ,
567+ custom_tlvs , compression_tlvs , None , None , clear ,
533568 baked_signature , pub_key , vector_to_sign , user_sha = user_sha ,
534- hmac_sha = hmac_sha , is_pure = is_pure , keep_comp_size = False , dont_encrypt = True )
569+ hmac_sha = hmac_sha , is_pure = is_pure , keep_comp_size = False )
535570 compressed_img = image .Image (version = decode_version (version ),
536571 header_size = header_size , pad_header = pad_header ,
537572 pad = pad , confirm = confirm , align = int (align ),
@@ -575,13 +610,13 @@ def sign(key, public_key_format, align, version, pad_sig, header_size,
575610 keep_comp_size = True
576611 compressed_img .create (key , public_key_format , enckey ,
577612 dependencies , boot_record , custom_tlvs , compression_tlvs ,
578- compression , int ( encrypt_keylen ) , clear , baked_signature ,
613+ compression , plainkey , clear , baked_signature ,
579614 pub_key , vector_to_sign , user_sha = user_sha , hmac_sha = hmac_sha ,
580615 is_pure = is_pure , keep_comp_size = keep_comp_size )
581616 img = compressed_img
582617 else :
583618 img .create (key , public_key_format , enckey , dependencies , boot_record ,
584- custom_tlvs , compression_tlvs , None , int ( encrypt_keylen ) , clear ,
619+ custom_tlvs , compression_tlvs , None , plainkey , clear ,
585620 baked_signature , pub_key , vector_to_sign , user_sha = user_sha ,
586621 hmac_sha = hmac_sha , is_pure = is_pure )
587622 img .save (outfile , hex_addr )
0 commit comments