gitee.com/lh-her-team/common@v1.5.1/crypto/pkcs11/aeskey.go (about) 1 package pkcs11 2 3 import ( 4 "crypto/rand" 5 "fmt" 6 "strconv" 7 8 "gitee.com/lh-her-team/common/crypto/hsm" 9 10 "gitee.com/lh-her-team/common/crypto/sym/util" 11 12 "github.com/pkg/errors" 13 14 "gitee.com/lh-her-team/common/crypto/sym/modes" 15 16 bccrypto "gitee.com/lh-her-team/common/crypto" 17 "github.com/miekg/pkcs11" 18 ) 19 20 var defaultAESOpts = &bccrypto.EncOpts{ 21 EncodingType: modes.PADDING_PKCS5, 22 BlockMode: modes.BLOCK_MODE_CBC, 23 EnableMAC: true, 24 Hash: 0, 25 Label: nil, 26 EnableASN1: true, 27 } 28 29 var _ bccrypto.SymmetricKey = (*aesKey)(nil) 30 31 type aesKey struct { 32 p11Ctx *P11Handle 33 keyId []byte 34 keyType P11KeyType 35 keyObject pkcs11.ObjectHandle 36 keySize int 37 blockSize int 38 } 39 40 func NewAESKey(ctx *P11Handle, keyId []byte) (bccrypto.SymmetricKey, error) { 41 //find private key 42 id, err := strconv.Atoi(string(keyId)) 43 if err != nil { 44 return nil, err 45 } 46 keyIdStr, err := hsm.GetHSMAdapter("").PKCS11_GetAESKeyId(id) 47 if err != nil { 48 return nil, err 49 } 50 obj, err := ctx.findSecretKey([]byte(keyIdStr)) 51 if err != nil { 52 return nil, errors.WithMessagef(err, "PKCS11 error: fail to find aes key, keyId = %s", keyIdStr) 53 } 54 sk := aesKey{p11Ctx: ctx, 55 keyId: keyId, 56 keyObject: *obj, 57 keyType: AES, 58 blockSize: 16, 59 } 60 sk.keySize, err = ctx.getSecretKeySize(*obj) 61 if err != nil { 62 return nil, errors.WithMessage(err, "failed to get aes keySize") 63 } 64 return &sk, nil 65 } 66 67 func (s *aesKey) Bytes() ([]byte, error) { 68 return s.keyId, nil 69 } 70 71 func (s *aesKey) Type() bccrypto.KeyType { 72 return bccrypto.AES 73 } 74 75 func (s *aesKey) String() (string, error) { 76 return string(s.keyId), nil 77 } 78 79 func (s *aesKey) Encrypt(plain []byte) ([]byte, error) { 80 return s.EncryptWithOpts(plain, defaultAESOpts) 81 } 82 83 func (s *aesKey) EncryptWithOpts(plain []byte, opts *bccrypto.EncOpts) ([]byte, error) { 84 iv := make([]byte, s.blockSize) 85 if _, err := rand.Read(iv); err != nil { 86 return nil, err 87 } 88 var cipherWithPad []byte 89 switch opts.BlockMode { 90 case modes.BLOCK_MODE_CBC: 91 switch opts.EncodingType { 92 case modes.PADDING_PKCS5: 93 plainWithPad := util.PKCS5Padding(plain, s.blockSize) 94 ciphertex, err := s.p11Ctx.Encrypt(s.keyObject, pkcs11.NewMechanism(pkcs11.CKM_AES_CBC, iv), plainWithPad) 95 if err != nil { 96 return nil, err 97 } 98 cipherWithPad = append(iv, ciphertex...) 99 default: 100 return nil, fmt.Errorf("sm4 CBC encryption fails: invalid padding scheme [%s]", opts.EncodingType) 101 } 102 default: 103 return nil, fmt.Errorf("sm4 encryption fails: unknown cipher block mode [%s]", opts.BlockMode) 104 } 105 return cipherWithPad, nil 106 } 107 108 func (s *aesKey) Decrypt(ciphertext []byte) ([]byte, error) { 109 return s.DecryptWithOpts(ciphertext, defaultAESOpts) 110 } 111 112 func (s *aesKey) DecryptWithOpts(ciphertext []byte, opts *bccrypto.EncOpts) ([]byte, error) { 113 if len(ciphertext) < s.blockSize { 114 return nil, errors.New("invalid ciphertext length") 115 } 116 var plain []byte 117 switch opts.BlockMode { 118 case modes.BLOCK_MODE_CBC: 119 switch opts.EncodingType { 120 case modes.PADDING_PKCS5: 121 iv := ciphertext[:s.blockSize] 122 out, err := s.p11Ctx.Decrypt(s.keyObject, pkcs11.NewMechanism(pkcs11.CKM_AES_CBC, iv), ciphertext[s.blockSize:]) 123 if err != nil { 124 return nil, fmt.Errorf("PKCS11 error: fail to encrypt [%s]", err) 125 } 126 plain, err = util.PKCS5UnPadding(out) 127 if err != nil { 128 return nil, err 129 } 130 default: 131 return nil, fmt.Errorf("sm4 CBC encryption fails: invalid padding scheme [%s]", opts.EncodingType) 132 } 133 default: 134 return nil, fmt.Errorf("sm4 encryption fails: unknown cipher block mode [%s]", opts.BlockMode) 135 } 136 return plain, nil 137 }