Commit 12bf5d47 authored by Evan Hunt's avatar Evan Hunt

[master] address several issues with native pkcs11

parent c0682c23
......@@ -139,7 +139,6 @@ usage(void) {
"records with (default: 0)\n");
fprintf(stderr, " -T <rrtype>: DNSKEY | KEY (default: DNSKEY; "
"use KEY for SIG(0))\n");
fprintf(stderr, " ECCGOST:\tignored\n");
fprintf(stderr, " -t <type>: "
"AUTHCONF | NOAUTHCONF | NOAUTH | NOCONF "
"(default: AUTHCONF)\n");
......
"pkcs11-hmacmd5" is here to check for the presence of a known bug in
the Thales nCipher PKCS#11 provider library. To test for the bug, use
pkcs11-hmacmd5 to hash a test vector from RFC 2104, and determine
whether the resulting digest is is correct. For instance:
echo -n "Hi There" | \
./pkcs11-hmacmd5 -p <PIN> -k '0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b0b'
...must return "9294727a3638bb1c13f48ef8158bfc9d".
If any other value is returned, then the provider library is buggy,
and the compilation flag PKCS11CRYPTOWITHHMAC must *not* be defined.
However, if the correct value is returned, then it is safe to turn
on PKCS11CRYPTOWITHHMAC. (It is off by default.)
......@@ -12,9 +12,11 @@
# OR OTHER TORTIOUS ACTION, ARISING OUT OF OR IN CONNECTION WITH THE USE OR
# PERFORMANCE OF THIS SOFTWARE.
if test "@CHECK_DSA@" -eq 1
then
exit 0
else
if [ "@CHECK_DSA@" -eq 0 ]; then
exit 1
fi
if [ ! -r /dev/random -o ! -r /dev/urandom ]; then
exit 1
fi
exit 0
......@@ -87,3 +87,4 @@ rm -f ns3/test-?.bk
rm -f ns3/test-?.bk.signed
rm -f ns3/test-?.bk.signed.jnl
rm -f import.key Kimport*
rm -f checkgost checkdsa checkecdsa
......@@ -104,46 +104,44 @@ zone=externalkey
rm -f K${zone}.+*+*.key
rm -f K${zone}.+*+*.private
for alg in ECDSAP256SHA256 NSEC3RSASHA1 DSA ECCGOST
for alg in ECCGOST ECDSAP256SHA256 NSEC3RSASHA1 DSA
do
if test $alg = DSA
then
sh ../checkdsa.sh 2> /dev/null || continue
fi
if test $alg = ECCGOST
then
fail=0
$KEYGEN -q -r ../$RANDFILE -a eccgost test > /dev/null 2>&1 || fail=1
rm -f Ktest*
[ $fail != 0 ] && continue
fi
if test $alg = ECDSAP256SHA256
then
fail=0
$KEYGEN -q -r ../$RANDFILE -a ecdsap256sha256 test > /dev/null 2>&1 || fail=1
rm -f Ktest*
[ $fail != 0 ] && continue
sh ../checkdsa.sh 2> /dev/null || continue
fi
test $alg = DSA -a ! -r /dev/random -a ! -r /dev/urandom && continue
case $alg in
DSA)
sh ../checkdsa.sh 2> /dev/null || continue
checkfile=../checkdsa
touch $checkfile ;;
ECCGOST)
fail=0
$KEYGEN -q -r $RANDFILE -a eccgost test > /dev/null 2>&1 || fail=1
rm -f Ktest*
[ $fail != 0 ] && continue
checkfile=../checkgost
touch $checkfile ;;
ECDSAP256SHA256)
fail=0
$KEYGEN -q -r $RANDFILE -a ecdsap256sha256 test > /dev/null 2>&1 || fail=1
rm -f Ktest*
[ $fail != 0 ] && continue
sh ../checkdsa.sh 2> /dev/null || continue
checkfile=../checkecdsa
touch $checkfile ;;
*) ;;
esac
k1=`$KEYGEN -q -r $RANDFILE -a $alg -b 1024 -n zone -f KSK $zone`
k2=`$KEYGEN -q -r $RANDFILE -a $alg -b 1024 -n zone $zone`
k3=`$KEYGEN -q -r $RANDFILE -a $alg -b 1024 -n zone $zone`
k4=`$KEYGEN -q -r $RANDFILE -a $alg -b 1024 -n zone $zone`
keyname=`$KEYGEN -q -r $RANDFILE -a $alg -b 1024 -n zone $zone`
keyname=`$KEYGEN -q -r $RANDFILE -a $alg -b 1024 -n zone -f KSK $zone`
$DSFROMKEY -T 1200 $keyname >> ../ns1/root.db
rm -f ${k3}.* ${k4}.*
k4=`$KEYGEN -q -r $RANDFILE -a $alg -b 1024 -n zone -f KSK $zone`
$DSFROMKEY -T 1200 $k4 >> ../ns1/root.db
#
# Convert k1 and k2 in to External Keys.
rm -f $k1.private
mv $k1.key a-file
$IMPORTKEY -P now -D now+3600 -f a-file $zone > /dev/null 2>&1
$IMPORTKEY -P now -D now+3600 -f a-file $zone > /dev/null 2>&1 ||
( echo "importkey failed: $alg"; rm -f $checkfile )
rm -f $k2.private
mv $k2.key a-file
$IMPORTKEY -f a-file $zone > /dev/null 2>&1
$IMPORTKEY -f a-file $zone > /dev/null 2>&1 ||
( echo "importkey failed: $alg"; rm -f $checkfile )
done
......@@ -847,7 +847,7 @@ $DIG $DIGOPTS @10.53.0.2 -p 5300 test-$zone SOA > dig.out.ns2.$zone.test$n
grep "status: NOERROR," dig.out.ns2.$zone.test$n > /dev/null || { ret=1; cat dig.out.ns2.$zone.test$n; }
$RNDC -c ../common/rndc.conf -s 10.53.0.3 -p 9953 addzone test-$zone \
'{ type slave; masters { 10.53.0.2; }; file "'test-$zone.bk'"; inline-signing yes; auto-dnssec maintain; allow-transfer { any; }; };'
$RNDC -c ../common/rndc.conf -s 10.53.0.3 -p 9953 delzone test-$zone
$RNDC -c ../common/rndc.conf -s 10.53.0.3 -p 9953 delzone test-$zone > /dev/null 2>&1
done
n=`expr $n + 1`
......@@ -856,28 +856,9 @@ ret=0
$DIG $DIGOPTS @10.53.0.3 -p 5300 dnskey externalkey > dig.out.ns3.test$n
for alg in 3 7 12 13
do
if test $alg = 3
then
sh checkdsa.sh 2>/dev/null || continue;
fi
if test $alg = 12
then
fail=0
$KEYGEN -q -r ../$RANDFILE -a eccgost test > /dev/null 2>&1 || fail=1
rm -f Ktest*
[ $fail != 0 ] && continue
fi
if test $alg = 13
then
fail=0
$KEYGEN -q -r ../$RANDFILE -a ecdsap256sha256 test > /dev/null 2>&1 || fail=1
rm -f Ktest*
[ $fail != 0 ] && continue
# dsa and ecdsa both require a source of randomness when
# generating signatures
sh checkdsa.sh 2>/dev/null || continue;
fi
test $alg = 3 -a ! -r /dev/random -a ! -r /dev/urandom && continue
[ $alg = 3 -a ! -f checkdsa ] && continue;
[ $alg = 12 -a ! -f checkgost ] && continue;
[ $alg = 13 -a ! -f checkecdsa ] && continue;
case $alg in
3) echo "I: checking DSA";;
......
......@@ -455,6 +455,9 @@ int sigwait(const unsigned int *set, int *sig);
(O_NDELAY/O_NONBLOCK). */
#undef PORT_NONBLOCK
/* Define if GOST private keys are encoded in ASN.1. */
#undef PREFER_GOSTASN1
/* The size of `void *', as computed by sizeof. */
#undef SIZEOF_VOID_P
......
......@@ -340,6 +340,9 @@ typedef __int64 off_t;
/* Define if your PKCS11 provider supports GOST. */
@HAVE_PKCS11_GOST@
/* Define if GOST private keys are encoded in ASN.1. */
@PREFER_GOSTASN1@
/* Define to 1 if you have the `readline' function. */
@HAVE_READLINE@
......
......@@ -2185,7 +2185,7 @@ Optional Packages:
--with-pkcs11=PATH Build with PKCS11 support yes|no|path
(PATH is for the PKCS11 provider)
--with-ecdsa Crypto ECDSA
--with-gost Crypto GOST
--with-gost Crypto GOST yes|no|raw|asn1.
--with-libxml2=PATH Build with libxml2 library yes|no|path
--with-libjson=PATH Build with libjson0 library yes|no|path
--with-purify=PATH use Rational purify
......@@ -15612,6 +15612,25 @@ else
with_gost="auto"
fi
gosttype="raw"
case "$with_gost" in
raw)
with_gost="yes"
;;
asn1)
$as_echo "#define PREFER_GOSTASN1 1" >>confdefs.h
gosttype="asn1"
with_gost="yes"
;;
auto|yes|no)
;;
*)
as_fn_error $? "unknown GOST private key encoding" "$LINENO" 5
;;
esac
case "$use_openssl" in
native_pkcs11)
{ $as_echo "$as_me:${as_lineno-$LINENO}: result: disabled because of native PKCS11" >&5
......@@ -15998,7 +16017,7 @@ fi
*)
case "$have_gost" in
yes|no) ;;
*) as_fn_error $? "need --with-gost=[yes or no]" "$LINENO" 5 ;;
*) as_fn_error $? "need --with-gost=[yes, no, raw or asn1]" "$LINENO" 5 ;;
esac
;;
esac
......@@ -23679,14 +23698,31 @@ echo "Configuration summary:"
echo "------------------------------------------------------------------------"
echo "Optional features enabled:"
$use_threads && echo " Multiprocessing support (--enable-threads)"
test "$use_geoip" = "no" || echo " GeoIP access control (--with-geoip)"
test "$use_gssapi" = "no" || echo " GSS-API (--with-gssapi)"
test "$want_native_pkcs11" = "yes" && \
echo " Native PKCS#11 support (--enable-native-pkcs11)"
test "$use_pkcs11" = "no" || echo " PKCS#11/Cryptoki support (--with-pkcs11)"
test "$OPENSSL_GOST" = "yes" -o "$PKCS11_GOST" = "yes" && \
echo " GOST algorithm support (--with-gost)"
# these lines are only printed if run with --enable-full-report
if test "$enable_full_report" = "yes"; then
test "$enable_ipv6" = "no" -o "$found_ipv6" = "no" || \
echo " IPv6 support (--enable-ipv6)"
test "X$CRYPTO" = "X" -o "$want_native_pkcs11" = "yes" || \
echo " OpenSSL cryptography/DNSSEC (--with-openssl)"
test "X$PYTHON" = "X" || echo " Python tools (--with-python)"
test "X$libxml2_libs" = "X" || echo " XML statistics (--with-libxml2)"
test "X$have_libjson" = "X" || echo " JSON statistics (--with-libjson)"
fi
if test "$use_pkcs11" != "no"; then
if test "$want_native_pkcs11" = "yes"; then
echo " Native PKCS#11/Cryptoki support (--enable-native-pkcs11)"
else
echo " PKCS#11/Cryptoki support using OpenSSL (--with-pkcs11)"
fi
echo " Provider library: $PKCS11_PROVIDER"
fi
if test "$OPENSSL_GOST" = "yes" -o "$PKCS11_GOST" = "yes"; then
echo " GOST algorithm support (encoding: $gosttype) (--with-gost)"
fi
test "$OPENSSL_ECDSA" = "yes" -o "$PKCS11_ECDSA" = "yes" && \
echo " ECDSA algorithm support (--with-ecdsa)"
test "$enable_fixed" = "yes" && \
......@@ -23699,19 +23735,9 @@ test "$want_symtable" = "minimal" && \
echo " Use symbol table for backtrace, named only (--enable-symtable)"
test "$want_symtable" = "yes" -o "$want_symtable" = "all" && \
echo " Use symbol table for backtrace, all binaries (--enable-symtable=all)"
test "$use_libtool" = "no" || echo " Use GNU libtool (--with-libtool)"
test "$atf" = "no" || echo " Automated Testing Framework (--with-atf)"
# these lines are only printed if run with --enable-full-report
if test "$enable_full_report" = "yes"; then
test "$enable_ipv6" = "no" -o "$found_ipv6" = "no" || \
echo " IPv6 support (--enable-ipv6)"
test "X$CRYPTO" = "X" -o "$want_native_pkcs11" = "yes" || \
echo " OpenSSL cryptography/DNSSEC (--with-openssl)"
test "X$PYTHON" = "X" || echo " Python tools (--with-python)"
test "X$libxml2_libs" = "X" || echo " XML statistics (--with-libxml2)"
test "X$have_libjson" = "X" || echo " JSON statistics (--with-libjson)"
fi
echo " Dynamically loadable zone (DLZ) drivers:"
test "$use_dlz_bdb" = "no" || \
echo " Berkeley DB (--with-dlz-bdb)"
......@@ -23737,21 +23763,27 @@ test "$enable_ipv6" = "no" -o "$found_ipv6" = "no" && \
test "$use_geoip" = "no" && echo " GeoIP access control (--with-geoip)"
test "$use_gssapi" = "no" && echo " GSS-API (--with-gssapi)"
test "$use_pkcs11" = "no" && echo " PKCS#11/Cryptoki support (--with-pkcs11)"
test "$enable_fixed" = "yes" || \
echo " Allow 'fixed' rrset-order (--enable-fixed-rrset)"
test "$want_backtrace" = "yes" || \
echo " Print backtrace on crash (--enable-backtrace)"
test "$atf" = "no" && echo " Automated Testing Framework (--with-atf)"
test "X$CRYPTO" = "X" -o "$want_native_pkcs11" = "yes" && \
if test "X$CRYPTO" = "X" -o "$want_native_pkcs11" = "yes"
then
echo " OpenSSL cryptography/DNSSEC (--with-openssl)"
test "$want_native_pkcs11" != "yes" && \
echo " Native PKCS#11 cryptography/DNSSEC (--enable-native-pkcs11)"
elif "$use_pkcs11" = "no"; then
echo " PKCS#11/Cryptoki support (--with-pkcs11)"
fi
test "$want_native_pkcs11" = "yes" ||
echo " Native PKCS#11/Cryptoki support (--enable-native-pkcs11)"
test "X$CRYPTO" = "X" -o "$OPENSSL_GOST" = "yes" -o "$PKCS11_GOST" = "yes" || \
echo " GOST algorithm support (--with-gost)"
test "X$CRYPTO" = "X" -o "$OPENSSL_ECDSA" = "yes" -o "$PKCS11_ECDSA" = "yes" || \
echo " ECDSA algorithm support (--with-ecdsa)"
test "$want_backtrace" = "yes" || \
echo " Print backtrace on crash (--enable-backtrace)"
test "$use_libtool" = "yes" || echo " Use GNU libtool (--with-libtool)"
test "$atf" = "no" && echo " Automated Testing Framework (--with-atf)"
test "X$PYTHON" = "X" && echo " Python tools (--with-python)"
test "X$libxml2_libs" = "X" && echo " XML statistics (--with-libxml2)"
test "X$have_libjson" = "X" && echo " JSON statistics (--with-libjson)"
......
......@@ -1145,8 +1145,27 @@ OPENSSL_ECDSA=""
OPENSSL_GOST=""
AC_ARG_WITH(ecdsa, [ --with-ecdsa Crypto ECDSA],
with_ecdsa="$withval", with_ecdsa="auto")
AC_ARG_WITH(gost, [ --with-gost Crypto GOST],
AC_ARG_WITH(gost,
[ --with-gost Crypto GOST [yes|no|raw|asn1].],
with_gost="$withval", with_gost="auto")
gosttype="raw"
case "$with_gost" in
raw)
with_gost="yes"
;;
asn1)
AC_DEFINE(PREFER_GOSTASN1, 1,
[Define if GOST private keys are encoded in ASN.1.])
gosttype="asn1"
with_gost="yes"
;;
auto|yes|no)
;;
*)
AC_MSG_ERROR(unknown GOST private key encoding)
;;
esac
case "$use_openssl" in
native_pkcs11)
AC_MSG_RESULT(disabled because of native PKCS11)
......@@ -1418,7 +1437,7 @@ int main() {
*)
case "$have_gost" in
yes|no) ;;
*) AC_MSG_ERROR([need --with-gost=[[yes or no]]]) ;;
*) AC_MSG_ERROR([need --with-gost=[[yes, no, raw or asn1]]]) ;;
esac
;;
esac
......@@ -4114,14 +4133,31 @@ echo "Configuration summary:"
echo "------------------------------------------------------------------------"
echo "Optional features enabled:"
$use_threads && echo " Multiprocessing support (--enable-threads)"
test "$use_geoip" = "no" || echo " GeoIP access control (--with-geoip)"
test "$use_gssapi" = "no" || echo " GSS-API (--with-gssapi)"
test "$want_native_pkcs11" = "yes" && \
echo " Native PKCS#11 support (--enable-native-pkcs11)"
test "$use_pkcs11" = "no" || echo " PKCS#11/Cryptoki support (--with-pkcs11)"
test "$OPENSSL_GOST" = "yes" -o "$PKCS11_GOST" = "yes" && \
echo " GOST algorithm support (--with-gost)"
# these lines are only printed if run with --enable-full-report
if test "$enable_full_report" = "yes"; then
test "$enable_ipv6" = "no" -o "$found_ipv6" = "no" || \
echo " IPv6 support (--enable-ipv6)"
test "X$CRYPTO" = "X" -o "$want_native_pkcs11" = "yes" || \
echo " OpenSSL cryptography/DNSSEC (--with-openssl)"
test "X$PYTHON" = "X" || echo " Python tools (--with-python)"
test "X$libxml2_libs" = "X" || echo " XML statistics (--with-libxml2)"
test "X$have_libjson" = "X" || echo " JSON statistics (--with-libjson)"
fi
if test "$use_pkcs11" != "no"; then
if test "$want_native_pkcs11" = "yes"; then
echo " Native PKCS#11/Cryptoki support (--enable-native-pkcs11)"
else
echo " PKCS#11/Cryptoki support using OpenSSL (--with-pkcs11)"
fi
echo " Provider library: $PKCS11_PROVIDER"
fi
if test "$OPENSSL_GOST" = "yes" -o "$PKCS11_GOST" = "yes"; then
echo " GOST algorithm support (encoding: $gosttype) (--with-gost)"
fi
test "$OPENSSL_ECDSA" = "yes" -o "$PKCS11_ECDSA" = "yes" && \
echo " ECDSA algorithm support (--with-ecdsa)"
test "$enable_fixed" = "yes" && \
......@@ -4134,19 +4170,9 @@ test "$want_symtable" = "minimal" && \
echo " Use symbol table for backtrace, named only (--enable-symtable)"
test "$want_symtable" = "yes" -o "$want_symtable" = "all" && \
echo " Use symbol table for backtrace, all binaries (--enable-symtable=all)"
test "$use_libtool" = "no" || echo " Use GNU libtool (--with-libtool)"
test "$atf" = "no" || echo " Automated Testing Framework (--with-atf)"
# these lines are only printed if run with --enable-full-report
if test "$enable_full_report" = "yes"; then
test "$enable_ipv6" = "no" -o "$found_ipv6" = "no" || \
echo " IPv6 support (--enable-ipv6)"
test "X$CRYPTO" = "X" -o "$want_native_pkcs11" = "yes" || \
echo " OpenSSL cryptography/DNSSEC (--with-openssl)"
test "X$PYTHON" = "X" || echo " Python tools (--with-python)"
test "X$libxml2_libs" = "X" || echo " XML statistics (--with-libxml2)"
test "X$have_libjson" = "X" || echo " JSON statistics (--with-libjson)"
fi
echo " Dynamically loadable zone (DLZ) drivers:"
test "$use_dlz_bdb" = "no" || \
echo " Berkeley DB (--with-dlz-bdb)"
......@@ -4172,21 +4198,27 @@ test "$enable_ipv6" = "no" -o "$found_ipv6" = "no" && \
test "$use_geoip" = "no" && echo " GeoIP access control (--with-geoip)"
test "$use_gssapi" = "no" && echo " GSS-API (--with-gssapi)"
test "$use_pkcs11" = "no" && echo " PKCS#11/Cryptoki support (--with-pkcs11)"
test "$enable_fixed" = "yes" || \
echo " Allow 'fixed' rrset-order (--enable-fixed-rrset)"
test "$want_backtrace" = "yes" || \
echo " Print backtrace on crash (--enable-backtrace)"
test "$atf" = "no" && echo " Automated Testing Framework (--with-atf)"
test "X$CRYPTO" = "X" -o "$want_native_pkcs11" = "yes" && \
if test "X$CRYPTO" = "X" -o "$want_native_pkcs11" = "yes"
then
echo " OpenSSL cryptography/DNSSEC (--with-openssl)"
test "$want_native_pkcs11" != "yes" && \
echo " Native PKCS#11 cryptography/DNSSEC (--enable-native-pkcs11)"
elif "$use_pkcs11" = "no"; then
echo " PKCS#11/Cryptoki support (--with-pkcs11)"
fi
test "$want_native_pkcs11" = "yes" ||
echo " Native PKCS#11/Cryptoki support (--enable-native-pkcs11)"
test "X$CRYPTO" = "X" -o "$OPENSSL_GOST" = "yes" -o "$PKCS11_GOST" = "yes" || \
echo " GOST algorithm support (--with-gost)"
test "X$CRYPTO" = "X" -o "$OPENSSL_ECDSA" = "yes" -o "$PKCS11_ECDSA" = "yes" || \
echo " ECDSA algorithm support (--with-ecdsa)"
test "$want_backtrace" = "yes" || \
echo " Print backtrace on crash (--enable-backtrace)"
test "$use_libtool" = "yes" || echo " Use GNU libtool (--with-libtool)"
test "$atf" = "no" && echo " Automated Testing Framework (--with-atf)"
test "X$PYTHON" = "X" && echo " Python tools (--with-python)"
test "X$libxml2_libs" = "X" && echo " XML statistics (--with-libxml2)"
test "X$have_libjson" = "X" && echo " JSON statistics (--with-libjson)"
......
......@@ -573,8 +573,6 @@ openssldsa_parse(dst_key_t *key, isc_lex_t *lexer, dst_key_t *pub) {
isc_mem_t *mctx = key->mctx;
#define DST_RET(a) {ret = a; goto err;}
UNUSED(pub);
/* read private key file */
ret = dst__privstruct_parse(key, DST_ALG_DSA, lexer, mctx, &priv);
if (ret != ISC_R_SUCCESS)
......
......@@ -340,7 +340,7 @@ opensslgost_fromdns(dst_key_t *key, isc_buffer_t *data) {
return (ISC_R_SUCCESS);
}
#ifdef USE_GOSTASN1
#ifdef PREFER_GOSTASN1
static isc_result_t
opensslgost_tofile(const dst_key_t *key, const char *directory) {
......@@ -429,7 +429,7 @@ opensslgost_tofile(const dst_key_t *key, const char *directory) {
}
#endif
unsigned char gost_dummy_key[71] = {
static unsigned char gost_dummy_key[71] = {
0x30, 0x45, 0x02, 0x01, 0x00, 0x30, 0x1c, 0x06,
0x06, 0x2a, 0x85, 0x03, 0x02, 0x02, 0x13, 0x30,
0x12, 0x06, 0x07, 0x2a, 0x85, 0x03, 0x02, 0x02,
......
......@@ -902,6 +902,11 @@ pkcs11dsa_tofile(const dst_key_t *key, const char *directory) {
if (key->keydata.pkey == NULL)
return (DST_R_NULLKEY);
if (key->external) {
priv.nelements = 0;
return (dst__privstruct_writefile(key, &priv, directory));
}
dsa = key->keydata.pkey;
for (attr = pk11_attribute_first(dsa);
......@@ -928,12 +933,6 @@ pkcs11dsa_tofile(const dst_key_t *key, const char *directory) {
(pub_key == NULL) || (priv_key ==NULL))
return (DST_R_NULLKEY);
if (key->external) {
priv.nelements = 0;
result = dst__privstruct_writefile(key, &priv, directory);
goto fail;
}
priv.elements[cnt].tag = TAG_DSA_PRIME;
priv.elements[cnt].length = (unsigned short) prime->ulValueLen;
memcpy(bufs[cnt], prime->pValue, prime->ulValueLen);
......
......@@ -757,8 +757,7 @@ pkcs11ecdsa_tofile(const dst_key_t *key, const char *directory) {
if (key->external) {
priv.nelements = 0;
result = dst__privstruct_writefile(key, &priv, directory);
goto fail;
return (dst__privstruct_writefile(key, &priv, directory));
}
ec = key->keydata.pkey;
......
......@@ -708,6 +708,16 @@ pkcs11gost_fromdns(dst_key_t *key, isc_buffer_t *data) {
return (ISC_R_NOMEMORY);
}
static unsigned char gost_private_der[39] = {
0x30, 0x45, 0x02, 0x01, 0x00, 0x30, 0x1c, 0x06,
0x06, 0x2a, 0x85, 0x03, 0x02, 0x02, 0x13, 0x30,
0x12, 0x06, 0x07, 0x2a, 0x85, 0x03, 0x02, 0x02,
0x23, 0x01, 0x06, 0x07, 0x2a, 0x85, 0x03, 0x02,
0x02, 0x1e, 0x01, 0x04, 0x22, 0x02, 0x20
};
#ifdef PREFER_GOSTASN1
static isc_result_t
pkcs11gost_tofile(const dst_key_t *key, const char *directory) {
isc_result_t ret;
......@@ -716,14 +726,65 @@ pkcs11gost_tofile(const dst_key_t *key, const char *directory) {
unsigned char *buf = NULL;
unsigned int i = 0;
CK_ATTRIBUTE *attr;
int adj;
if (key->keydata.pkey == NULL)
return (DST_R_NULLKEY);
if (key->external) {
priv.nelements = 0;
result = dst__privstruct_writefile(key, &priv, directory);
goto fail;
return (dst__privstruct_writefile(key, &priv, directory));
}
gost = key->keydata.pkey;
attr = pk11_attribute_bytype(gost, CKA_VALUE2);
if (attr != NULL) {
buf = isc_mem_get(key->mctx, attr->ulValueLen + 39);
if (buf == NULL)
return (ISC_R_NOMEMORY);
priv.elements[i].tag = TAG_GOST_PRIVASN1;
priv.elements[i].length =
(unsigned short) attr->ulValueLen + 39;
memcpy(buf, gost_private_der, 39);
memcpy(buf +39, attr->pValue, attr->ulValueLen);
adj = (int) attr->ulValueLen - 32;
if (adj != 0) {
buf[1] += adj;
buf[36] += adj;
buf[38] += adj;
}
priv.elements[i].data = buf;
i++;
} else
return (DST_R_CRYPTOFAILURE);
priv.nelements = i;
ret = dst__privstruct_writefile(key, &priv, directory);
if (buf != NULL) {
memset(buf, 0, attr->ulValueLen);
isc_mem_put(key->mctx, buf, attr->ulValueLen);
}
return (ret);
}
#else
static isc_result_t
pkcs11gost_tofile(const dst_key_t *key, const char *directory) {
isc_result_t ret;
iscpk11_object_t *gost;
dst_private_t priv;
unsigned char *buf = NULL;
unsigned int i = 0;
CK_ATTRIBUTE *attr;
if (key->keydata.pkey == NULL)
return (DST_R_NULLKEY);
if (key->external) {
priv.nelements = 0;
return (dst__privstruct_writefile(key, &priv, directory));
}
gost = key->keydata.pkey;
......@@ -737,8 +798,8 @@ pkcs11gost_tofile(const dst_key_t *key, const char *directory) {
memcpy(buf, attr->pValue, attr->ulValueLen);
priv.elements[i].data = buf;
i++;
}
/* else return (DST_R_NULLKEY); */
} else
return (DST_R_CRYPTOFAILURE);
priv.nelements = i;
ret = dst__privstruct_writefile(key, &priv, directory);
......@@ -749,6 +810,7 @@ pkcs11gost_tofile(const dst_key_t *key, const char *directory) {
}
return (ret);
}
#endif
static isc_result_t
pkcs11gost_parse(dst_key_t *key, isc_lex_t *lexer, dst_key_t *pub) {
......@@ -769,13 +831,24 @@ pkcs11gost_parse(dst_key_t *key, isc_lex_t *lexer, dst_key_t *pub) {
DST_RET(DST_R_INVALIDPRIVATEKEY);
if (priv.elements[0].tag == TAG_GOST_PRIVASN1) {
dst__privstruct_free(&priv, mctx);
memset(&priv, 0, sizeof(priv));
isc_log_write(dns_lctx, DNS_LOGCATEGORY_GENERAL,
DNS_LOGMODULE_CRYPTO, ISC_LOG_WARNING,
"GostAsn1 private key format is "
"no longer supported\n");
return (DST_R_INVALIDPRIVATEKEY);
int adj = (int) priv.elements[0].length - (39 + 32);
unsigned char buf[39];
if ((adj > 0) || (adj < -31))
DST_RET(DST_R_INVALIDPRIVATEKEY);
memcpy(buf, gost_private_der, 39);
if (adj != 0) {
buf[1] += adj;
buf[36] += adj;
buf[38] += adj;
}
if (memcmp(priv.elements[0].data, buf, 39) != 0)
DST_RET(DST_R_INVALIDPRIVATEKEY);
priv.elements[0].tag = TAG_GOST_PRIVRAW;
priv.elements[0].length -= 39;
memmove(priv.elements[0].data,
priv.elements[0].data + 39,
32 + adj);
}
gost = (iscpk11_object_t *) isc_mem_get(key->mctx, sizeof(*gost));