github.com/hxx258456/ccgo@v0.0.5-0.20230213014102-48b35f46f66f/x509/pem_decrypt_test.go (about) 1 // Copyright 2012 The Go Authors. All rights reserved. 2 // Use of this source code is governed by a BSD-style 3 // license that can be found in the LICENSE file. 4 5 package x509 6 7 import ( 8 "bytes" 9 "crypto/rand" 10 "encoding/base64" 11 "encoding/pem" 12 "os" 13 "reflect" 14 "strings" 15 "testing" 16 17 "github.com/hxx258456/ccgo/sm2" 18 ) 19 20 func TestDecrypt(t *testing.T) { 21 for i, data := range testData { 22 t.Logf("test %v. %v", i, data.kind) 23 block, rest := pem.Decode(data.pemData) 24 if len(rest) > 0 { 25 t.Error("extra data") 26 } 27 der, err := DecryptPEMBlock(block, data.password) 28 if err != nil { 29 t.Error("decrypt failed: ", err) 30 continue 31 } 32 if _, err := ParsePKCS1PrivateKey(der); err != nil { 33 t.Error("invalid private key: ", err) 34 } 35 plainDER, err := base64.StdEncoding.DecodeString(data.plainDER) 36 if err != nil { 37 t.Fatal("cannot decode test DER data: ", err) 38 } 39 if !bytes.Equal(der, plainDER) { 40 t.Error("data mismatch") 41 } 42 } 43 } 44 45 func TestEncrypt(t *testing.T) { 46 for i, data := range testData { 47 t.Logf("test %v. %v", i, data.kind) 48 plainDER, err := base64.StdEncoding.DecodeString(data.plainDER) 49 if err != nil { 50 t.Fatal("cannot decode test DER data: ", err) 51 } 52 password := []byte("kremvax1") 53 block, err := EncryptPEMBlock(rand.Reader, "RSA PRIVATE KEY", plainDER, password, data.kind) 54 if err != nil { 55 t.Error("encrypt: ", err) 56 continue 57 } 58 if !IsEncryptedPEMBlock(block) { 59 t.Error("PEM block does not appear to be encrypted") 60 } 61 if block.Type != "RSA PRIVATE KEY" { 62 t.Errorf("unexpected block type; got %q want %q", block.Type, "RSA PRIVATE KEY") 63 } 64 if block.Headers["Proc-Type"] != "4,ENCRYPTED" { 65 t.Errorf("block does not have correct Proc-Type header") 66 } 67 der, err := DecryptPEMBlock(block, password) 68 if err != nil { 69 t.Error("decrypt: ", err) 70 continue 71 } 72 if !bytes.Equal(der, plainDER) { 73 t.Errorf("data mismatch") 74 } 75 } 76 } 77 78 var testData = []struct { 79 kind PEMCipher 80 password []byte 81 pemData []byte 82 plainDER string 83 }{ 84 { 85 kind: PEMCipherDES, 86 password: []byte("asdf"), 87 pemData: []byte(testingKey(` 88 -----BEGIN RSA TESTING KEY----- 89 Proc-Type: 4,ENCRYPTED 90 DEK-Info: DES-CBC,34F09A4FC8DE22B5 91 92 WXxy8kbZdiZvANtKvhmPBLV7eVFj2A5z6oAxvI9KGyhG0ZK0skfnt00C24vfU7m5 93 ICXeoqP67lzJ18xCzQfHjDaBNs53DSDT+Iz4e8QUep1xQ30+8QKX2NA2coee3nwc 94 6oM1cuvhNUDemBH2i3dKgMVkfaga0zQiiOq6HJyGSncCMSruQ7F9iWEfRbFcxFCx 95 qtHb1kirfGKEtgWTF+ynyco6+2gMXNu70L7nJcnxnV/RLFkHt7AUU1yrclxz7eZz 96 XOH9VfTjb52q/I8Suozq9coVQwg4tXfIoYUdT//O+mB7zJb9HI9Ps77b9TxDE6Gm 97 4C9brwZ3zg2vqXcwwV6QRZMtyll9rOpxkbw6NPlpfBqkc3xS51bbxivbO/Nve4KD 98 r12ymjFNF4stXCfJnNqKoZ50BHmEEUDu5Wb0fpVn82XrGw7CYc4iug== 99 -----END RSA TESTING KEY-----`)), 100 plainDER: ` 101 MIIBPAIBAAJBAPASZe+tCPU6p80AjHhDkVsLYa51D35e/YGa8QcZyooeZM8EHozo 102 KD0fNiKI+53bHdy07N+81VQ8/ejPcRoXPlsCAwEAAQJBAMTxIuSq27VpR+zZ7WJf 103 c6fvv1OBvpMZ0/d1pxL/KnOAgq2rD5hDtk9b0LGhTPgQAmrrMTKuSeGoIuYE+gKQ 104 QvkCIQD+GC1m+/do+QRurr0uo46Kx1LzLeSCrjBk34wiOp2+dwIhAPHfTLRXS2fv 105 7rljm0bYa4+eDZpz+E8RcXEgzhhvcQQ9AiAI5eHZJGOyml3MXnQjiPi55WcDOw0w 106 glcRgT6QCEtz2wIhANSyqaFtosIkHKqrDUGfz/bb5tqMYTAnBruVPaf/WEOBAiEA 107 9xORWeRG1tRpso4+dYy4KdDkuLPIO01KY6neYGm3BCM=`, 108 }, 109 { 110 kind: PEMCipher3DES, 111 password: []byte("asdf"), 112 pemData: []byte(testingKey(` 113 -----BEGIN RSA TESTING KEY----- 114 Proc-Type: 4,ENCRYPTED 115 DEK-Info: DES-EDE3-CBC,C1F4A6A03682C2C7 116 117 0JqVdBEH6iqM7drTkj+e2W/bE3LqakaiWhb9WUVonFkhyu8ca/QzebY3b5gCvAZQ 118 YwBvDcT/GHospKqPx+cxDHJNsUASDZws6bz8ZXWJGwZGExKzr0+Qx5fgXn44Ms3x 119 8g1ENFuTXtxo+KoNK0zuAMAqp66Llcds3Fjl4XR18QaD0CrVNAfOdgATWZm5GJxk 120 Fgx5f84nT+/ovvreG+xeOzWgvtKo0UUZVrhGOgfKLpa57adumcJ6SkUuBtEFpZFB 121 ldw5w7WC7d13x2LsRkwo8ZrDKgIV+Y9GNvhuCCkTzNP0V3gNeJpd201HZHR+9n3w 122 3z0VjR/MGqsfcy1ziEWMNOO53At3zlG6zP05aHMnMcZoVXadEK6L1gz++inSSDCq 123 gI0UJP4e3JVB7AkgYymYAwiYALAkoEIuanxoc50njJk= 124 -----END RSA TESTING KEY-----`)), 125 plainDER: ` 126 MIIBOwIBAAJBANOCXKdoNS/iP/MAbl9cf1/SF3P+Ns7ZeNL27CfmDh0O6Zduaax5 127 NBiumd2PmjkaCu7lQ5JOibHfWn+xJsc3kw0CAwEAAQJANX/W8d1Q/sCqzkuAn4xl 128 B5a7qfJWaLHndu1QRLNTRJPn0Ee7OKJ4H0QKOhQM6vpjRrz+P2u9thn6wUxoPsef 129 QQIhAP/jCkfejFcy4v15beqKzwz08/tslVjF+Yq41eJGejmxAiEA05pMoqfkyjcx 130 fyvGhpoOyoCp71vSGUfR2I9CR65oKh0CIC1Msjs66LlfJtQctRq6bCEtFCxEcsP+ 131 eEjYo/Sk6WphAiEAxpgWPMJeU/shFT28gS+tmhjPZLpEoT1qkVlC14u0b3ECIQDX 132 tZZZxCtPAm7shftEib0VU77Lk8MsXJcx2C4voRsjEw==`, 133 }, 134 { 135 kind: PEMCipherAES128, 136 password: []byte("asdf"), 137 pemData: []byte(testingKey(` 138 -----BEGIN RSA TESTING KEY----- 139 Proc-Type: 4,ENCRYPTED 140 DEK-Info: AES-128-CBC,D4492E793FC835CC038A728ED174F78A 141 142 EyfQSzXSjv6BaNH+NHdXRlkHdimpF9izWlugVJAPApgXrq5YldPe2aGIOFXyJ+QE 143 ZIG20DYqaPzJRjTEbPNZ6Es0S2JJ5yCpKxwJuDkgJZKtF39Q2i36JeGbSZQIuWJE 144 GZbBpf1jDH/pr0iGonuAdl2PCCZUiy+8eLsD2tyviHUkFLOB+ykYoJ5t8ngZ/B6D 145 33U43LLb7+9zD4y3Q9OVHqBFGyHcxCY9+9Qh4ZnFp7DTf6RY5TNEvE3s4g6aDpBs 146 3NbvRVvYTgs8K9EPk4K+5R+P2kD8J8KvEIGxVa1vz8QoCJ/jr7Ka2rvNgPCex5/E 147 080LzLHPCrXKdlr/f50yhNWq08ZxMWQFkui+FDHPDUaEELKAXV8/5PDxw80Rtybo 148 AVYoCVIbZXZCuCO81op8UcOgEpTtyU5Lgh3Mw5scQL0= 149 -----END RSA TESTING KEY-----`)), 150 plainDER: ` 151 MIIBOgIBAAJBAMBlj5FxYtqbcy8wY89d/S7n0+r5MzD9F63BA/Lpl78vQKtdJ5dT 152 cDGh/rBt1ufRrNp0WihcmZi7Mpl/3jHjiWECAwEAAQJABNOHYnKhtDIqFYj1OAJ3 153 k3GlU0OlERmIOoeY/cL2V4lgwllPBEs7r134AY4wMmZSBUj8UR/O4SNO668ElKPE 154 cQIhAOuqY7/115x5KCdGDMWi+jNaMxIvI4ETGwV40ykGzqlzAiEA0P9oEC3m9tHB 155 kbpjSTxaNkrXxDgdEOZz8X0uOUUwHNsCIAwzcSCiGLyYJTULUmP1ESERfW1mlV78 156 XzzESaJpIM/zAiBQkSTcl9VhcJreQqvjn5BnPZLP4ZHS4gPwJAGdsj5J4QIhAOVR 157 B3WlRNTXR2WsJ5JdByezg9xzdXzULqmga0OE339a`, 158 }, 159 { 160 kind: PEMCipherAES192, 161 password: []byte("asdf"), 162 pemData: []byte(testingKey(` 163 -----BEGIN RSA TESTING KEY----- 164 Proc-Type: 4,ENCRYPTED 165 DEK-Info: AES-192-CBC,E2C9FB02BCA23ADE1829F8D8BC5F5369 166 167 cqVslvHqDDM6qwU6YjezCRifXmKsrgEev7ng6Qs7UmDJOpHDgJQZI9fwMFUhIyn5 168 FbCu1SHkLMW52Ld3CuEqMnzWMlhPrW8tFvUOrMWPYSisv7nNq88HobZEJcUNL2MM 169 Y15XmHW6IJwPqhKyLHpWXyOCVEh4ODND2nV15PCoi18oTa475baxSk7+1qH7GuIs 170 Rb7tshNTMqHbCpyo9Rn3UxeFIf9efdl8YLiMoIqc7J8E5e9VlbeQSdLMQOgDAQJG 171 ReUtTw8exmKsY4gsSjhkg5uiw7/ZB1Ihto0qnfQJgjGc680qGkT1d6JfvOfeYAk6 172 xn5RqS/h8rYAYm64KnepfC9vIujo4NqpaREDmaLdX5MJPQ+SlytITQvgUsUq3q/t 173 Ss85xjQEZH3hzwjQqdJvmA4hYP6SUjxYpBM+02xZ1Xw= 174 -----END RSA TESTING KEY-----`)), 175 plainDER: ` 176 MIIBOwIBAAJBAMGcRrZiNNmtF20zyS6MQ7pdGx17aFDl+lTl+qnLuJRUCMUG05xs 177 OmxmL/O1Qlf+bnqR8Bgg65SfKg21SYuLhiMCAwEAAQJBAL94uuHyO4wux2VC+qpj 178 IzPykjdU7XRcDHbbvksf4xokSeUFjjD3PB0Qa83M94y89ZfdILIqS9x5EgSB4/lX 179 qNkCIQD6cCIqLfzq/lYbZbQgAAjpBXeQVYsbvVtJrPrXJAlVVQIhAMXpDKMeFPMn 180 J0g2rbx1gngx0qOa5r5iMU5w/noN4W2XAiBjf+WzCG5yFvazD+dOx3TC0A8+4x3P 181 uZ3pWbaXf5PNuQIgAcdXarvhelH2w2piY1g3BPeFqhzBSCK/yLGxR82KIh8CIQDD 182 +qGKsd09NhQ/G27y/DARzOYtml1NvdmCQAgsDIIOLA==`, 183 }, 184 { 185 kind: PEMCipherAES256, 186 password: []byte("asdf"), 187 pemData: []byte(testingKey(` 188 -----BEGIN RSA TESTING KEY----- 189 Proc-Type: 4,ENCRYPTED 190 DEK-Info: AES-256-CBC,8E7ED5CD731902CE938957A886A5FFBD 191 192 4Mxr+KIzRVwoOP0wwq6caSkvW0iS+GE2h2Ov/u+n9ZTMwL83PRnmjfjzBgfRZLVf 193 JFPXxUK26kMNpIdssNnqGOds+DhB+oSrsNKoxgxSl5OBoYv9eJTVYm7qOyAFIsjr 194 DRKAcjYCmzfesr7PVTowwy0RtHmYwyXMGDlAzzZrEvaiySFFmMyKKvtoavwaFoc7 195 Pz3RZScwIuubzTGJ1x8EzdffYOsdCa9Mtgpp3L136+23dOd6L/qK2EG2fzrJSHs/ 196 2XugkleBFSMKzEp9mxXKRfa++uidQvMZTFLDK9w5YjrRvMBo/l2BoZIsq0jAIE1N 197 sv5Z/KwlX+3MDEpPQpUwGPlGGdLnjI3UZ+cjgqBcoMiNc6HfgbBgYJSU6aDSHuCk 198 clCwByxWkBNgJ2GrkwNrF26v+bGJJJNR4SKouY1jQf0= 199 -----END RSA TESTING KEY-----`)), 200 plainDER: ` 201 MIIBOgIBAAJBAKy3GFkstoCHIEeUU/qO8207m8WSrjksR+p9B4tf1w5k+2O1V/GY 202 AQ5WFCApItcOkQe/I0yZZJk/PmCqMzSxrc8CAwEAAQJAOCAz0F7AW9oNelVQSP8F 203 Sfzx7O1yom+qWyAQQJF/gFR11gpf9xpVnnyu1WxIRnDUh1LZwUsjwlDYb7MB74id 204 oQIhANPcOiLwOPT4sIUpRM5HG6BF1BI7L77VpyGVk8xNP7X/AiEA0LMHZtk4I+lJ 205 nClgYp4Yh2JZ1Znbu7IoQMCEJCjwKDECIGd8Dzm5tViTkUW6Hs3Tlf73nNs65duF 206 aRnSglss8I3pAiEAonEnKruawgD8RavDFR+fUgmQiPz4FnGGeVgfwpGG1JECIBYq 207 PXHYtPqxQIbD2pScR5qum7iGUh11lEUPkmt+2uqS`, 208 }, 209 { 210 // generated with: 211 // openssl genrsa -aes128 -passout pass:asdf -out server.orig.key 128 212 kind: PEMCipherAES128, 213 password: []byte("asdf"), 214 pemData: []byte(testingKey(` 215 -----BEGIN RSA TESTING KEY----- 216 Proc-Type: 4,ENCRYPTED 217 DEK-Info: AES-128-CBC,74611ABC2571AF11B1BF9B69E62C89E7 218 219 6ei/MlytjE0FFgZOGQ+jrwomKfpl8kdefeE0NSt/DMRrw8OacHAzBNi3pPEa0eX3 220 eND9l7C9meCirWovjj9QWVHrXyugFuDIqgdhQ8iHTgCfF3lrmcttVrbIfMDw+smD 221 hTP8O1mS/MHl92NE0nhv0w== 222 -----END RSA TESTING KEY-----`)), 223 plainDER: ` 224 MGMCAQACEQC6ssxmYuauuHGOCDAI54RdAgMBAAECEQCWIn6Yv2O+kBcDF7STctKB 225 AgkA8SEfu/2i3g0CCQDGNlXbBHX7kQIIK3Ww5o0cYbECCQDCimPb0dYGsQIIeQ7A 226 jryIst8=`, 227 }, 228 } 229 230 var incompleteBlockPEM = testingKey(` 231 -----BEGIN RSA TESTING KEY----- 232 Proc-Type: 4,ENCRYPTED 233 DEK-Info: AES-128-CBC,74611ABC2571AF11B1BF9B69E62C89E7 234 235 6L8yXK2MTQUWBk4ZD6OvCiYp+mXyR1594TQ1K38MxGvDw5pwcDME2Lek8RrR5fd40P2XsL2Z4KKt 236 ai+OP1BZUetfK6AW4MiqB2FDyIdOAJ8XeWuZy21Wtsh8wPD6yYOFM/w7WZL8weX3Y0TSeG/T 237 -----END RSA TESTING KEY-----`) 238 239 func TestIncompleteBlock(t *testing.T) { 240 // incompleteBlockPEM contains ciphertext that is not a multiple of the 241 // block size. This previously panicked. See #11215. 242 block, _ := pem.Decode([]byte(incompleteBlockPEM)) 243 _, err := DecryptPEMBlock(block, []byte("foo")) 244 if err == nil { 245 t.Fatal("Bad PEM data decrypted successfully") 246 } 247 const expectedSubstr = "block size" 248 if e := err.Error(); !strings.Contains(e, expectedSubstr) { 249 t.Fatalf("Expected error containing %q but got: %q", expectedSubstr, e) 250 } 251 } 252 253 func testingKey(s string) string { return strings.ReplaceAll(s, "TESTING KEY", "PRIVATE KEY") } 254 255 func TestSm4(t *testing.T) { 256 plainDERStr := "MGMCAQACEQC6ssxmYuauuHGOCDAI54RdAgMBAAECEQCWIn6Yv2O+kBcDF7STctKBAgkA8SEfu/2i3g0CCQDGNlXbBHX7kQIIK3Ww5o0cYbECCQDCimPb0dYGsQIIeQ7AjryIst8=" 257 plainDER, err := base64.StdEncoding.DecodeString(plainDERStr) 258 if err != nil { 259 t.Fatal("cannot decode test DER data: ", err) 260 } 261 password := []byte("kremvax1") 262 block, err := EncryptPEMBlock(rand.Reader, "RSA PRIVATE KEY", plainDER, password, PEMCipherSM4) 263 if err != nil { 264 t.Fatal("encrypt: ", err) 265 } 266 file, err := os.Create("testdata/sm4EncryptPEMBlock.pem") 267 if err != nil { 268 t.Fatal("encrypt: ", err) 269 } 270 err = pem.Encode(file, block) 271 if err != nil { 272 t.Fatal(err) 273 } 274 if !IsEncryptedPEMBlock(block) { 275 t.Fatal("PEM block does not appear to be encrypted") 276 } 277 if block.Type != "RSA PRIVATE KEY" { 278 t.Fatalf("unexpected block type; got %s want %s", block.Type, "RSA PRIVATE KEY") 279 } 280 if block.Headers["Proc-Type"] != "4,ENCRYPTED" { 281 t.Fatal("block does not have correct Proc-Type header") 282 } 283 der, err := DecryptPEMBlock(block, password) 284 if err != nil { 285 t.Fatal("decrypt: ", err) 286 } 287 if !bytes.Equal(der, plainDER) { 288 t.Fatal("data mismatch") 289 } 290 } 291 292 func TestSM2Key(t *testing.T) { 293 password := []byte("testsm2key") 294 sm2PrivKey, _ := sm2.GenerateKey(rand.Reader) 295 privateKeyToPem, err := WritePrivateKeyToPem(sm2PrivKey, password) 296 if err != nil { 297 t.Fatal("x509/pem_decrypt_test.go TestSM2Key WritePrivateKeyToPem faild", err) 298 } 299 keySm2, err := ReadPrivateKeyFromPem(privateKeyToPem, password) 300 if err != nil { 301 t.Fatal("x509/pem_decrypt_test.go TestSM2Key ReadPrivateKeyFromPem faild", err) 302 } 303 if !reflect.DeepEqual(keySm2, sm2PrivKey) { 304 t.Fatal("加密再解密后的pem内容不一致") 305 } 306 307 writeFileOK, err := WritePrivateKeytoPemFile("testdata/encrypt_pem_sm2_privkey.pem", sm2PrivKey, password) 308 if !writeFileOK || err != nil { 309 t.Fatal("x509/pem_decrypt_test.go TestSM2Key WritePrivateKeytoPemFile faild", err) 310 } 311 keySm2FromFile, err := ReadPrivateKeyFromPemFile("testdata/encrypt_pem_sm2_privkey.pem", password) 312 if err != nil { 313 t.Fatal("x509/pem_decrypt_test.go TestSM2Key ReadPrivateKeyFromPemFile faild", err) 314 } 315 if !reflect.DeepEqual(keySm2FromFile, sm2PrivKey) { 316 t.Fatal("加密再解密后的pem内容不一致") 317 } 318 }