1#! /usr/bin/env perl 2# Copyright 2022-2023 The OpenSSL Project Authors. All Rights Reserved. 3# 4# Licensed under the Apache License 2.0 (the "License"). You may not use 5# this file except in compliance with the License. You can obtain a copy 6# in the file LICENSE in the source distribution or at 7# https://www.openssl.org/source/license.html 8 9use strict; 10use warnings; 11 12use OpenSSL::Test::Utils; 13use File::Copy; 14use File::Compare qw(compare_text compare); 15use OpenSSL::Test qw/:DEFAULT srctop_file ok_nofips is_nofips/; 16 17setup("test_pkcs8"); 18 19plan tests => 18; 20 21my $pc5_key = srctop_file('test', 'certs', 'pc5-key.pem'); 22 23my $inout = 'inout.pem'; 24copy($pc5_key, $inout); 25ok(run(app(['openssl', 'pkcs8', '-topk8', '-in', $inout, 26 '-out', $inout, '-passout', 'pass:password'])), 27 "identical infile and outfile, to PKCS#8"); 28ok(run(app(['openssl', 'pkcs8', '-in', $inout, 29 '-out', $inout, '-passin', 'pass:password'])), 30 "identical infile and outfile, from PKCS#8"); 31is(compare($pc5_key, $inout), 0, 32 "Same file contents after converting forth and back"); 33 34ok(run(app(([ 'openssl', 'pkcs8', '-topk8', 35 '-in', $pc5_key, 36 '-out', 'pbkdf2_default_saltlen.pem', 37 '-passout', 'pass:password']))), 38 "Convert a private key to PKCS5 v2.0 format using PBKDF2 with the default saltlen"); 39 40# We expect the output to be of the form "0:d=0 hl=2 l= 16 prim: OCTET STRING [HEX DUMP]:FAC7F37508E6B7A805BF4B13861B3687" 41# i.e. 2 byte header + 16 byte salt. 42ok(run(app(([ 'openssl', 'asn1parse', 43 '-in', 'pbkdf2_default_saltlen.pem', 44 '-offset', '34', '-length', '18']))), 45 "Check the default size of the PBKDF2 PARAM 'salt length' is 16"); 46 47SKIP: { 48 skip "scrypt is not supported by this OpenSSL build", 4 49 if disabled("scrypt"); 50 51 ok(run(app(([ 'openssl', 'pkcs8', '-topk8', 52 '-in', $pc5_key, 53 '-scrypt', 54 '-out', 'scrypt_default_saltlen.pem', 55 '-passout', 'pass:password']))), 56 "Convert a private key to PKCS5 v2.0 format using scrypt with the default saltlen"); 57 58# We expect the output to be of the form "0:d=0 hl=2 l= 8 prim: OCTET STRING [HEX DUMP]:FAC7F37508E6B7A805BF4B13861B3687" 59# i.e. 2 byte header + 16 byte salt. 60 ok(run(app(([ 'openssl', 'asn1parse', 61 '-in', 'scrypt_default_saltlen.pem', 62 '-offset', '34', '-length', '18']))), 63 "Check the default size of the SCRYPT PARAM 'salt length' = 16"); 64 65 ok(run(app(([ 'openssl', 'pkcs8', '-topk8', 66 '-in', $pc5_key, 67 '-scrypt', 68 '-saltlen', '8', 69 '-out', 'scrypt_64bit_saltlen.pem', 70 '-passout', 'pass:password']))), 71 "Convert a private key to PKCS5 v2.0 format using scrypt with a salt length of 8 bytes"); 72 73# We expect the output to be of the form "0:d=0 hl=2 l= 8 prim: OCTET STRING [HEX DUMP]:3C1147976A2B61CA" 74# i.e. 2 byte header + 8 byte salt. 75 ok(run(app(([ 'openssl', 'asn1parse', 76 '-in', 'scrypt_64bit_saltlen.pem', 77 '-offset', '34', '-length', '10']))), 78 "Check the size of the SCRYPT PARAM 'salt length' is 8"); 79} 80 81SKIP: { 82 skip "legacy provider is not supported by this OpenSSL build", 4 83 if disabled('legacy') || disabled("des"); 84 85 ok(run(app(([ 'openssl', 'pkcs8', '-topk8', 86 '-in', $pc5_key, 87 '-v1', "PBE-MD5-DES", 88 '-provider', 'legacy', 89 '-provider', 'default', 90 '-out', 'pbe1.pem', 91 '-passout', 'pass:password']))), 92 "Convert a private key to PKCS5 v1.5 format using pbeWithMD5AndDES-CBC with the default saltlen"); 93 94 ok(run(app(([ 'openssl', 'asn1parse', 95 '-in', 'pbe1.pem', 96 '-offset', '19', '-length', '10']))), 97 "Check the default size of the PBE PARAM 'salt length' = 8"); 98 99 ok(run(app(([ 'openssl', 'pkcs8', '-topk8', 100 '-in', $pc5_key, 101 '-v1', "PBE-MD5-DES", 102 '-saltlen', '16', 103 '-provider', 'legacy', 104 '-provider', 'default', 105 '-out', 'pbe1_128bitsalt.pem', 106 '-passout', 'pass:password']))), 107 "Convert a private key to PKCS5 v1.5 format using pbeWithMD5AndDES-CBC with the 16 byte saltlen"); 108 109 ok(run(app(([ 'openssl', 'asn1parse', 110 '-in', 'pbe1_128bitsalt.pem', 111 '-offset', '19', '-length', '18']))), 112 "Check the size of the PBE PARAM 'salt length' = 16"); 113}; 114 115 116ok(run(app(([ 'openssl', 'pkcs8', '-topk8', 117 '-in', $pc5_key, 118 '-saltlen', '8', 119 '-out', 'pbkdf2_64bit_saltlen.pem', 120 '-passout', 'pass:password']))), 121 "Convert a private key to PKCS5 v2.0 format using pbkdf2 with a salt length of 8 bytes"); 122 123# We expect the output to be of the form "0:d=0 hl=2 l= 8 prim: OCTET STRING [HEX DUMP]:3C1147976A2B61CA" 124# i.e. 2 byte header + 8 byte salt. 125ok(run(app(([ 'openssl', 'asn1parse', 126 '-in', 'pbkdf2_64bit_saltlen.pem', 127 '-offset', '34', '-length', '10']))), 128 "Check the size of the PBKDF2 PARAM 'salt length' is 8"); 129 130 131SKIP: { 132 skip "SM2, SM3 or SM4 is not supported by this OpenSSL build", 3 133 if disabled("sm2") || disabled("sm3") || disabled("sm4"); 134 135 ok_nofips(run(app(([ 'openssl', 'pkcs8', '-topk8', 136 '-in', srctop_file('test', 'certs', 'sm2.key'), 137 '-out', 'sm2-pbes2-sm4-hmacWithSM3.key', 138 '-passout', 'pass:password', 139 '-v2', 'sm4', '-v2prf', 'hmacWithSM3']))), 140 "Convert a private key to PKCS#5 v2.0 format using SM4 and hmacWithSM3"); 141 142 ok_nofips(run(app(([ 'openssl', 'pkcs8', '-topk8', 143 '-in', 'sm2-pbes2-sm4-hmacWithSM3.key', 144 '-out', 'sm2.key', 145 '-passin', 'pass:password', '-nocrypt', 146 '-v2', 'sm4', '-v2prf', 'hmacWithSM3']))), 147 "Convert from PKCS#5 v2.0 format to PKCS#8 unencrypted format"); 148 149 is_nofips(compare_text(srctop_file('test', 'certs', 'sm2.key'), 'sm2.key', 150 sub { 151 my $in1 = $_[0]; 152 my $in2 = $_[1]; 153 $in1 =~ s/\r\n/\n/g; 154 $in2 =~ s/\r\n/\n/g; 155 $in1 ne $in2 156 }), 0, "compare test/certs/sm2.key to sm2.key") 157} 158