diff --git a/Makefile.am b/Makefile.am index f2a89949..fbecea9e 100644 --- a/Makefile.am +++ b/Makefile.am @@ -34,7 +34,7 @@ include src/include.am include wolfssh/include.am include examples/include.am include test/include.am -include certs/include.am +include keys/include.am TEST_EXTENSIONS = .test diff --git a/README.md b/README.md index e87ad597..6e7d6e86 100644 --- a/README.md +++ b/README.md @@ -44,8 +44,7 @@ testing notes After cloning the repository, be sure to make the testing private keys read- only for the user, otherwise ssh_client will tell you to do it. - $ chmod 0600 ./certs/key-gretel.pem ./certs/key-hansel.pem \ - ./certs/key-ecc.pem + $ chmod 0600 ./certs/key-gretel.pem ./certs/key-hansel.pem Authentication against the example echoserver can be done with a password or public key. To use a password the command line: diff --git a/certs/include.am b/certs/include.am deleted file mode 100644 index fcbedd3e..00000000 --- a/certs/include.am +++ /dev/null @@ -1,16 +0,0 @@ -# vim:ft=automake -# included from Top Level Makefile.am -# All paths should be given relative to the root - - -EXTRA_DIST+= \ - certs/key-gretel.pem \ - certs/publickeys.txt \ - certs/server-key.der \ - certs/key-ecc.pem \ - certs/key-hansel.pem \ - certs/server-cert.der \ - certs/server-key.pem \ - certs/key-ecc.pub \ - certs/passwd.txt \ - certs/server-cert.pem diff --git a/certs/key-ecc.pem b/certs/key-ecc.pem deleted file mode 100644 index 426658f0..00000000 --- a/certs/key-ecc.pem +++ /dev/null @@ -1,5 +0,0 @@ ------BEGIN EC PRIVATE KEY----- -MHcCAQEEIPIxGlM2XBIY6NulXIJgXdOheM+mZ7ixU8RLaXy2OoJeoAoGCCqGSM49 -AwEHoUQDQgAEpalbz23q5UgbcVHU0uGllXYqEw9kAG/uyCSMfZ1wliKi6tXrs/9p -WCseyyREeyKmmMqt6WkekGJd54jHPa/Wyw== ------END EC PRIVATE KEY----- diff --git a/certs/key-ecc.pub b/certs/key-ecc.pub deleted file mode 100644 index 4d63eaed..00000000 --- a/certs/key-ecc.pub +++ /dev/null @@ -1 +0,0 @@ -ecdsa-sha2-nistp256 AAAAE2VjZHNhLXNoYTItbmlzdHAyNTYAAAAIbmlzdHAyNTYAAABBBKWpW89t6uVIG3FR1NLhpZV2KhMPZABv7sgkjH2dcJYiourV67P/aVgrHsskRHsippjKrelpHpBiXeeIxz2v1ss= john@johnwork.local diff --git a/certs/server-cert.der b/certs/server-cert.der deleted file mode 100644 index d3f75c21..00000000 Binary files a/certs/server-cert.der and /dev/null differ diff --git a/certs/server-cert.pem b/certs/server-cert.pem deleted file mode 100644 index 09676a0d..00000000 --- a/certs/server-cert.pem +++ /dev/null @@ -1,87 +0,0 @@ -Certificate: - Data: - Version: 3 (0x2) - Serial Number: - fa:24:ef:1a:5a:f2:b2:a4 - Signature Algorithm: sha1WithRSAEncryption - Issuer: C=US, ST=Washington, L=Seattle, O=wolfSSL Inc., OU=Engineering, CN=wolfssh/emailAddress=info@wolfssl.com - Validity - Not Before: Aug 15 19:46:24 2014 GMT - Not After : May 11 19:46:24 2017 GMT - Subject: C=US, ST=Washington, L=Seattle, O=wolfSSL Inc., OU=Engineering, CN=wolfssh/emailAddress=info@wolfssl.com - Subject Public Key Info: - Public Key Algorithm: rsaEncryption - RSA Public Key: (2048 bit) - Modulus (2048 bit): - 00:c5:7e:5d:0c:c5:47:95:67:ad:89:ff:db:fa:77: - e8:1f:76:d3:ac:6f:10:8a:93:bf:ee:1b:93:9f:5b: - 71:79:4c:d8:d5:6d:8e:d0:d2:b9:6b:e8:75:c8:73: - f5:5d:1c:61:60:27:da:79:40:18:a3:b4:b8:f3:c3: - 79:4e:12:6f:a2:20:46:6c:29:50:5d:f8:b6:82:89: - 34:22:2a:14:00:77:38:ad:fa:e3:61:8d:71:c4:ff: - 76:bc:34:3d:85:b5:ca:96:f8:46:d9:90:0f:e4:05: - 31:4b:cf:2e:9b:5b:58:f8:2e:fc:88:68:d4:36:e0: - 01:4c:0b:a4:ee:58:a0:ce:20:ef:78:b3:e6:50:56: - 51:4d:de:1e:3d:2f:5c:49:6b:3d:78:94:6b:2e:ab: - ae:0c:c0:b2:e8:29:a8:bc:ec:d2:05:a5:ac:3d:87: - 50:55:3e:48:55:b4:b7:91:e5:2e:ce:89:51:02:14: - 60:53:96:d7:7b:3e:61:2b:d3:54:f4:38:8d:55:78: - 48:f0:ad:67:39:fd:41:34:a3:fa:90:02:a0:d9:d4: - 01:fe:7a:8b:52:08:c9:0f:8b:5e:89:42:f1:bd:b7: - 40:35:b0:29:50:3c:66:46:59:31:e3:01:03:9d:16: - e8:87:8a:13:0b:ab:6e:bf:d9:b8:f0:fd:3d:82:4c: - cc:2f - Exponent: 65537 (0x10001) - X509v3 extensions: - X509v3 Subject Key Identifier: - 3C:38:D7:FD:0C:54:14:F4:3A:DB:08:04:44:DB:4F:41:5D:E9:E9:DE - X509v3 Authority Key Identifier: - keyid:3C:38:D7:FD:0C:54:14:F4:3A:DB:08:04:44:DB:4F:41:5D:E9:E9:DE - DirName:/C=US/ST=Washington/L=Seattle/O=wolfSSL Inc./OU=Engineering/CN=wolfssh/emailAddress=info@wolfssl.com - serial:FA:24:EF:1A:5A:F2:B2:A4 - - X509v3 Basic Constraints: - CA:TRUE - Signature Algorithm: sha1WithRSAEncryption - 18:c2:d1:ee:39:b4:6b:24:06:63:13:37:93:18:4f:e1:5f:12: - 5d:bf:03:88:ef:5b:bb:c8:b6:09:b6:e1:61:a2:df:4c:88:af: - e0:cf:fd:b9:48:52:6d:1c:91:45:e1:4b:51:c4:c1:c5:11:57: - 96:4f:74:d0:4d:58:70:4d:82:43:62:bd:e0:42:e1:76:a5:16: - 55:ca:01:c4:6e:90:ff:09:1c:9e:c9:f3:98:ab:5c:c0:5f:8a: - c3:80:f2:28:11:bd:99:e9:29:a9:ce:3c:aa:6b:fc:76:cc:93: - 8b:60:1f:bb:b3:e9:a2:a2:67:c9:3d:cb:e8:20:a4:bd:00:78: - 23:49:65:4a:96:50:09:db:f1:46:46:c1:08:9d:74:63:10:95: - b4:ec:da:85:a2:96:50:7b:af:e5:54:aa:96:4e:77:3a:88:8c: - f6:0e:5e:24:9f:22:ee:bc:a3:86:5d:11:48:63:65:eb:55:30: - 4b:75:22:5d:e5:14:89:cb:c9:52:21:5f:8f:47:3e:31:2c:58: - cd:5a:09:19:4d:d6:a4:0d:85:8d:86:ef:fe:fa:77:87:8f:c2: - 07:1f:20:ad:86:d9:94:91:e8:63:6a:2f:9d:bb:c1:f1:4e:85: - 02:8e:1d:9a:21:c4:94:28:0a:3d:9a:cb:19:87:4d:e0:a2:4c: - 0f:11:8a:6c ------BEGIN CERTIFICATE----- -MIIEqjCCA5KgAwIBAgIJAPok7xpa8rKkMA0GCSqGSIb3DQEBBQUAMIGUMQswCQYD -VQQGEwJVUzETMBEGA1UECBMKV2FzaGluZ3RvbjEQMA4GA1UEBxMHU2VhdHRsZTEV -MBMGA1UEChMMd29sZlNTTCBJbmMuMRQwEgYDVQQLEwtFbmdpbmVlcmluZzEQMA4G -A1UEAxMHd29sZnNzaDEfMB0GCSqGSIb3DQEJARYQaW5mb0B3b2xmc3NsLmNvbTAe -Fw0xNDA4MTUxOTQ2MjRaFw0xNzA1MTExOTQ2MjRaMIGUMQswCQYDVQQGEwJVUzET -MBEGA1UECBMKV2FzaGluZ3RvbjEQMA4GA1UEBxMHU2VhdHRsZTEVMBMGA1UEChMM -d29sZlNTTCBJbmMuMRQwEgYDVQQLEwtFbmdpbmVlcmluZzEQMA4GA1UEAxMHd29s -ZnNzaDEfMB0GCSqGSIb3DQEJARYQaW5mb0B3b2xmc3NsLmNvbTCCASIwDQYJKoZI -hvcNAQEBBQADggEPADCCAQoCggEBAMV+XQzFR5VnrYn/2/p36B9206xvEIqTv+4b -k59bcXlM2NVtjtDSuWvodchz9V0cYWAn2nlAGKO0uPPDeU4Sb6IgRmwpUF34toKJ -NCIqFAB3OK3642GNccT/drw0PYW1ypb4RtmQD+QFMUvPLptbWPgu/Iho1DbgAUwL -pO5YoM4g73iz5lBWUU3eHj0vXElrPXiUay6rrgzAsugpqLzs0gWlrD2HUFU+SFW0 -t5HlLs6JUQIUYFOW13s+YSvTVPQ4jVV4SPCtZzn9QTSj+pACoNnUAf56i1IIyQ+L -XolC8b23QDWwKVA8ZkZZMeMBA50W6IeKEwurbr/ZuPD9PYJMzC8CAwEAAaOB/DCB -+TAdBgNVHQ4EFgQUPDjX/QxUFPQ62wgERNtPQV3p6d4wgckGA1UdIwSBwTCBvoAU -PDjX/QxUFPQ62wgERNtPQV3p6d6hgZqkgZcwgZQxCzAJBgNVBAYTAlVTMRMwEQYD -VQQIEwpXYXNoaW5ndG9uMRAwDgYDVQQHEwdTZWF0dGxlMRUwEwYDVQQKEwx3b2xm -U1NMIEluYy4xFDASBgNVBAsTC0VuZ2luZWVyaW5nMRAwDgYDVQQDEwd3b2xmc3No -MR8wHQYJKoZIhvcNAQkBFhBpbmZvQHdvbGZzc2wuY29tggkA+iTvGlrysqQwDAYD -VR0TBAUwAwEB/zANBgkqhkiG9w0BAQUFAAOCAQEAGMLR7jm0ayQGYxM3kxhP4V8S -Xb8DiO9bu8i2CbbhYaLfTIiv4M/9uUhSbRyRReFLUcTBxRFXlk900E1YcE2CQ2K9 -4ELhdqUWVcoBxG6Q/wkcnsnzmKtcwF+Kw4DyKBG9mekpqc48qmv8dsyTi2Afu7Pp -oqJnyT3L6CCkvQB4I0llSpZQCdvxRkbBCJ10YxCVtOzahaKWUHuv5VSqlk53OoiM -9g5eJJ8i7ryjhl0RSGNl61UwS3UiXeUUicvJUiFfj0c+MSxYzVoJGU3WpA2FjYbv -/vp3h4/CBx8grYbZlJHoY2ovnbvB8U6FAo4dmiHElCgKPZrLGYdN4KJMDxGKbA== ------END CERTIFICATE----- diff --git a/certs/server-key.der b/certs/server-key.der deleted file mode 100644 index d6813dd6..00000000 Binary files a/certs/server-key.der and /dev/null differ diff --git a/certs/server-key.pem b/certs/server-key.pem deleted file mode 100644 index c9d242c2..00000000 --- a/certs/server-key.pem +++ /dev/null @@ -1,27 +0,0 @@ ------BEGIN RSA PRIVATE KEY----- -MIIEogIBAAKCAQEAxX5dDMVHlWetif/b+nfoH3bTrG8QipO/7huTn1txeUzY1W2O -0NK5a+h1yHP1XRxhYCfaeUAYo7S488N5ThJvoiBGbClQXfi2gok0IioUAHc4rfrj -YY1xxP92vDQ9hbXKlvhG2ZAP5AUxS88um1tY+C78iGjUNuABTAuk7ligziDveLPm -UFZRTd4ePS9cSWs9eJRrLquuDMCy6CmovOzSBaWsPYdQVT5IVbS3keUuzolRAhRg -U5bXez5hK9NU9DiNVXhI8K1nOf1BNKP6kAKg2dQB/nqLUgjJD4teiULxvbdANbAp -UDxmRlkx4wEDnRboh4oTC6tuv9m48P09gkzMLwIDAQABAoIBACB4WSYbXVyUEjUp -KuqwQirCJ6UnEYonJpwoTooZx7tQxim4/I0ayD+UlaDiZ8nqO5xKkSH0RtjLgskZ -L12FrHL0aX+o/zykAqXNlxOy5Vz6PQhlwnKshbME6WmiESdlryxJH6TviZ1MuUEk -jB4g06ziVMS8r39iLvRoybIiQjYBa/p6ElxNGof1xGxgYEd4kUhuGEF7VWUkoarB -0XlUN3lNlRJ4AnkWvWjgix6Zc2+YKgX0Cafc6gZ9Dc+J/jmlr2P4k4VjdhfOEMPa -vB7FfEPMCfCHBHkeF9KYX1MGfpKpITvBSwNug44Z1D78u0Q/yvfIGYFoeJzznh45 -Dwc00rECgYEA9vtYtUk8j08ufW7OUHIRdgZ7dM9tEiDBdDvBoQKUw+GQqXToQydj -i9UgCCIdX9Rc2u3HY3Mu4CblUHKCckw6miV9EG08r+HktqZL+hPlBO/7osLNkMzc -feJVKQt7bjTzat3RSns+7DOP85GWpm2v2Br0i+7Eu+FJQoln/8bK2WcCgYEAzLRt -fVTyZMOjenTKL8qw4mNbry1iguqYO0pdzvcB3QT085OvWfDunEto8hOPNuWPhTX3 -IhXHQ9KryThJgIR/pdZXLdKm+DkKGy1ZTylfnB7eDnzStRgVWBvW6iqzES4Psoob -lFTMpy0yV/tWlzpmxh33BtPeEuRbH2Fan1nEkfkCgYBynx2BLNb1L2tE/Tq0rOub -mdCL2oQlCJyfY+gt4DPIYJOxgTcVi18wkx2FiMeXJMhfNkD1z4vurT55Qlt1zhjY -VxOenwOuIKjzd2QFUFxWGUXwOHYMgHbH2VVqchC7icl6TC2IYoBGQHvLL0L6RCd6 -pK/fjVUyWJCWV4yzcL/NewKBgEGNif53xIPGLsTZP6IcW5az0LmBZCmebI+YGgBc -E2mu265g3eeEgzTj5UCYSOWAj/xNss1kggJTJZXzg343cBUwVYykB7o3sefQFuiF -zEtXiy7ChEtf4f3sNF+auutGf9ph5cETgtIKZDPOlgUpu524HNI/6L7OB+w9peKf -wZYpAoGAEeuFwcwVfvscoz17th/J43qOyAWT+vAk7qZdyGBEF98jg8kA2OcWykI1 -q/KdTLW9dXz0NVWzA2eoLv3SDxD3NgAXdcXq4NhJiNI9/Zrk7kybAcMstPJKtquK -xXYH/xv41HqJ2IpfYjqqifV+HG6e37HeCWQDj1zyZulEMyrRN1s= ------END RSA PRIVATE KEY----- diff --git a/configure.ac b/configure.ac index e650145f..e4636a0c 100644 --- a/configure.ac +++ b/configure.ac @@ -97,6 +97,14 @@ fi AM_CONDITIONAL([BUILD_INLINE], [test "x$ENABLED_INLINE" = "xyes"]) +# Key Generation +AC_ARG_ENABLE([keygen], + [AS_HELP_STRING([--enable-keygen],[Enable key generation (default: disabled)])], + [ENABLED_KEYGEN=$enableval],[ENABLED_KEYGEN=no]) + +AS_IF([test "x$ENABLED_KEYGEN" = "xyes"], + [AM_CFLAGS="$AM_CFLAGS -DWOLFSSH_KEYGEN"]) + # Checks for typedefs, structures, and compiler characteristics. if test "$ac_cv_sizeof_long" = "8"; then @@ -142,4 +150,7 @@ echo " * C Flags: $CFLAGS" echo " * CPP Flags: $CPPFLAGS" echo " * Linker Flags: $LDFLAGS" echo " * LIB Flags: $LIB" +echo +echo " Features " +echo " * keygen: $ENABLED_KEYGEN" diff --git a/examples/echoserver/echoserver.c b/examples/echoserver/echoserver.c index 338780bc..2d46fb45 100644 --- a/examples/echoserver/echoserver.c +++ b/examples/echoserver/echoserver.c @@ -640,18 +640,7 @@ int main(void) uint8_t buf[SCRATCH_BUFFER_SIZE]; uint32_t bufSz; - bufSz = load_file("./certs/server-cert.der", buf, SCRATCH_BUFFER_SIZE); - if (bufSz == 0) { - fprintf(stderr, "Couldn't load certificate file.\n"); - exit(EXIT_FAILURE); - } - if (wolfSSH_CTX_UseCert_buffer(ctx, - buf, bufSz, WOLFSSH_FORMAT_ASN1) < 0) { - fprintf(stderr, "Couldn't use certificate buffer.\n"); - exit(EXIT_FAILURE); - } - - bufSz = load_file("./certs/server-key.der", buf, SCRATCH_BUFFER_SIZE); + bufSz = load_file("./keys/server-key.der", buf, SCRATCH_BUFFER_SIZE); if (bufSz == 0) { fprintf(stderr, "Couldn't load key file.\n"); exit(EXIT_FAILURE); diff --git a/examples/include.am b/examples/include.am index d1bbde15..d9060ccb 100644 --- a/examples/include.am +++ b/examples/include.am @@ -3,4 +3,3 @@ # All paths should be given relative to the root include examples/echoserver/include.am -include examples/server/include.am diff --git a/keys/include.am b/keys/include.am new file mode 100644 index 00000000..f5fa27ae --- /dev/null +++ b/keys/include.am @@ -0,0 +1,12 @@ +# vim:ft=automake +# included from Top Level Makefile.am +# All paths should be given relative to the root + + +EXTRA_DIST+= \ + keys/server-key.der \ + keys/server-key.pem \ + keys/key-hansel.pem \ + keys/key-gretel.pem \ + keys/publickeys.txt \ + keys/passwd.txt diff --git a/certs/key-gretel.pem b/keys/key-gretel.pem similarity index 100% rename from certs/key-gretel.pem rename to keys/key-gretel.pem diff --git a/certs/key-hansel.pem b/keys/key-hansel.pem similarity index 100% rename from certs/key-hansel.pem rename to keys/key-hansel.pem diff --git a/certs/passwd.txt b/keys/passwd.txt similarity index 100% rename from certs/passwd.txt rename to keys/passwd.txt diff --git a/certs/publickeys.txt b/keys/publickeys.txt similarity index 100% rename from certs/publickeys.txt rename to keys/publickeys.txt diff --git a/keys/server-key.der b/keys/server-key.der new file mode 100644 index 00000000..a1012e45 Binary files /dev/null and b/keys/server-key.der differ diff --git a/keys/server-key.pem b/keys/server-key.pem new file mode 100644 index 00000000..c9b7a02d --- /dev/null +++ b/keys/server-key.pem @@ -0,0 +1,27 @@ +-----BEGIN RSA PRIVATE KEY----- +MIIEowIBAAKCAQEA2l2tJRR2FVnzQP08uGIws23A+ezsi4MenkKcykFq04rhUjTg +DRNiftQPrlxNBPGN+sWtd6paBcrv+I2r/4opCUwEwvUZy+0fsbQp08NsqSPfo6Dl +CN6tjHH5NIhs7Tvwb6UPrFn/azPxcPuMpLNFIo2dd3rlKV+EFNmZ6urOLVHz41j6 +WwIPybUqvLJe08Iwuzyxw+9Y81CUKIvEZUr3ANmX2WtNjZWhimIGtFARIoO06irn +0KggR0//Rq7FE+E4i/hUrzpNL/gf14SQ2JMFBsJ9kNvjnNDEZVoDrQCsWqLN2j+J +WDdTvytGeqyJQStaLuh2517jKYWjY+rmhmB8LQIDAQABAoH/D5EeBsaupFcFQFzN +N1fIoQHx/98j/c4bIK0fAEwpkWsVJQcf8c6v9tqnQ4bQ9slBld8BvsYmJMOS1+VB +nbX7tu30aPGQJTmCSOjPEomb9XLZPpD5wugc9yYo3dXb7g2X1l2uAFtqGfpZ+/Py +0sr04sG1uA7Kx2hHwjTBBD449IIBWfKKbvdrWwq8BaknN7n5BoBU6HAatDKTa/Um +x4b0WAVD+XKP7EKgO7o1Yszs9LMEouuuPIdAjv6P3RS+vYPJyRjKgXwG+eOZLuwp +xSdW6h6TxugMRMpzaEp/rhYlHRIlFCrsQWklw13mruRZgB36vZ8zNpOdiNaIyVsn +ewthAoGBAN4Bq/pl0vrSb/4/V211f4zmvf4IvccTNGIOh7J6LKnNypPYMZGBLdZo +lqol47h+pZio6BU8wM7e9auAsfW6r6ycwbNDNK4i9xhBhmOiRI4bQZ0tdW8NWxAZ +XRSqgB/uAj74tvbsZY44iQ0LUOQRSYY5gttz5ToPEyKrraB4m5QhAoGBAPvNTFJJ +PyyAlJFKOOwPSn06jrwEkBUlhPvTaL3voEf+zlu/HSqUJ/xRcP/J6bq+K6BQJdPh +oVczzFzHfQn23PtylD3KWVJz4GxFCtnaMN8rM9dSGEEB8N8bAcHTt5sm+ByP/8gZ +/TbQE6VyQqMwWVe02ioJ5UVaOW1wIgy6UyaNAoGBALE8wnDwk8Q89r4TEZhIguEZ +YbsKfYAOO/bAxOLfGQMjUURBCCmy6MZQz1/dSfUD3u6GgmpaC0/cvmMCJpEYTqHO +r/GOiOMw9PX/cevfIz4UUojKPwO+tOGgbihOimVzXYWqiF+PkPA/AGNSkmzRxFIN +XgQXfXyhhlRanQ4M26AhAoGBAOr+G54nsYdssDovlJPpaVEZlx+s+nJhw4vpLrUj +rufBywAgia20+uQldVmiLDkVRU2lvsfQqGvjcXOc0Pq9ologAmzwLRAgCG/Ct2+8 +iyObBBSNDwmMMClm4OrtFUr8wUyWrtUmPAQtiEg9LCdz9c0+gOP+vDNPEo0puv05 +3mP5AoGBAIsfR6KQS4I7iS3pa+Eo5SKHg9DeHg2MzIRDPSONnWy8xMbaRER5ILY+ +78+KxDiw5dpFrFrMe2K6qXMfuidcgvitMR7e8zdyy0fSzff4fwA5240qyk7BzuIV +idY6Ya6dojClha446kZ03AI6rOlfo8ZzT3OBkFbDzndfW7psQvEh +-----END RSA PRIVATE KEY----- diff --git a/src/include.am b/src/include.am index 289765f1..ea8a167f 100644 --- a/src/include.am +++ b/src/include.am @@ -6,6 +6,7 @@ lib_LTLIBRARIES+= src/libwolfssh.la src_libwolfssh_la_SOURCES = src/ssh.c \ src/internal.c \ + src/keygen.c \ src/memory.c \ src/log.c \ src/io.c \ diff --git a/src/internal.c b/src/internal.c index 1bcff7c7..f0fca6c3 100644 --- a/src/internal.c +++ b/src/internal.c @@ -174,10 +174,8 @@ void CtxResourceFree(WOLFSSH_CTX* ctx) if (ctx->privateKey) { ForceZero(ctx->privateKey, ctx->privateKeySz); - WFREE(ctx->privateKey, ctx->heap, DYNTYPE_KEY); + WFREE(ctx->privateKey, ctx->heap, DYNTYPE_PRIVKEY); } - WFREE(ctx->cert, ctx->heap, DYNTYPE_CERT); - WFREE(ctx->caCert, ctx->heap, DYNTYPE_CA); } diff --git a/src/keygen.c b/src/keygen.c new file mode 100644 index 00000000..2bdb09ef --- /dev/null +++ b/src/keygen.c @@ -0,0 +1,102 @@ +/* keygen.c + * + * Copyright (C) 2014-2016 wolfSSL Inc. + * + * This file is part of wolfSSH. + * + * wolfSSH is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 3 of the License, or + * (at your option) any later version. + * + * wolfSSH is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with wolfSSH. If not, see . + */ + + +/* + * The keygen module contains utility functions wrapping the wolfCrypt + * key generation functions to product SSH friendly keys. + */ + + +#ifdef HAVE_CONFIG_H + #include +#endif + +#include +#include +#include +#include +#include +#include + +#ifdef WOLFSSH_KEYGEN + +#ifdef NO_INLINE + #include +#else + #define WOLFSSH_MISC_INCLUDED + #include "src/misc.c" +#endif + + +int wolfSSH_MakeRsaKey(uint8_t* out, uint32_t outSz, + uint32_t size, uint32_t e) +{ + int ret = WS_SUCCESS; + WC_RNG rng; + + WLOG(WS_LOG_DEBUG, "Entering wolfSSH_MakeRsaKey()"); + + if (wc_InitRng(&rng) != 0) { + WLOG(WS_LOG_DEBUG, "Couldn't create RNG"); + ret = WS_CRYPTO_FAILED; + } + + if (ret == WS_SUCCESS) { + RsaKey key; + + if (wc_InitRsaKey(&key, NULL) != 0) + ret = WS_CRYPTO_FAILED; + + if (ret == WS_SUCCESS) { + if (wc_MakeRsaKey(&key, size, e, &rng) != 0) { + WLOG(WS_LOG_DEBUG, "RSA key generation failed"); + ret = WS_CRYPTO_FAILED; + } + } + + if (ret == WS_SUCCESS) { + int keySz; + + keySz = wc_RsaKeyToDer(&key, out, outSz); + if (keySz < 0) { + WLOG(WS_LOG_DEBUG, "RSA key to DER failed"); + ret = WS_CRYPTO_FAILED; + } + else + ret = keySz; + } + + if (wc_FreeRsaKey(&key) != 0) { + WLOG(WS_LOG_DEBUG, "RSA key free failed"); + ret = WS_CRYPTO_FAILED; + } + + if (wc_FreeRng(&rng) != 0) { + WLOG(WS_LOG_DEBUG, "Couldn't free RNG"); + ret = WS_CRYPTO_FAILED; + } + } + + WLOG(WS_LOG_DEBUG, "Leaving wolfSSH_MakeRsaKey(), ret = %d", ret); + return ret; +} + +#endif diff --git a/src/ssh.c b/src/ssh.c index cbfff9eb..bb186c23 100644 --- a/src/ssh.c +++ b/src/ssh.c @@ -474,7 +474,7 @@ static int ProcessBuffer(WOLFSSH_CTX* ctx, const uint8_t* in, uint32_t inSz, else if (type == BUFTYPE_CERT) dynamicType = DYNTYPE_CERT; else if (type == BUFTYPE_PRIVKEY) - dynamicType = DYNTYPE_KEY; + dynamicType = DYNTYPE_PRIVKEY; else return WS_BAD_ARGUMENT; @@ -493,13 +493,7 @@ static int ProcessBuffer(WOLFSSH_CTX* ctx, const uint8_t* in, uint32_t inSz, /* Maybe decrypt */ - if (type == BUFTYPE_CERT) { - if (ctx->cert) - WFREE(ctx->cert, heap, dynamicType); - ctx->cert = der; - ctx->certSz = derSz; - } - else if (type == BUFTYPE_PRIVKEY) { + if (type == BUFTYPE_PRIVKEY) { if (ctx->privateKey) WFREE(ctx->privateKey, heap, dynamicType); ctx->privateKey = der; @@ -531,27 +525,11 @@ static int ProcessBuffer(WOLFSSH_CTX* ctx, const uint8_t* in, uint32_t inSz, int wolfSSH_CTX_UsePrivateKey_buffer(WOLFSSH_CTX* ctx, const uint8_t* in, uint32_t inSz, int format) { - WLOG(WS_LOG_DEBUG, "Entering wolfSSH_CTX_use_private_key_buffer()"); + WLOG(WS_LOG_DEBUG, "Entering wolfSSH_CTX_UsePrivateKey_buffer()"); return ProcessBuffer(ctx, in, inSz, format, BUFTYPE_PRIVKEY); } -int wolfSSH_CTX_UseCert_buffer(WOLFSSH_CTX* ctx, - const uint8_t* in, uint32_t inSz, int format) -{ - WLOG(WS_LOG_DEBUG, "Entering wolfSSH_CTX_use_certificate_buffer()"); - return ProcessBuffer(ctx, in, inSz, format, BUFTYPE_CERT); -} - - -int wolfSSH_CTX_UseCaCert_buffer(WOLFSSH_CTX* ctx, - const uint8_t* in, uint32_t inSz, int format) -{ - WLOG(WS_LOG_DEBUG, "Entering wolfSSH_CTX_use_ca_certificate_buffer()"); - return ProcessBuffer(ctx, in, inSz, format, BUFTYPE_CA); -} - - int wolfSSH_KDF(uint8_t hashId, uint8_t keyId, uint8_t* key, uint32_t keySz, const uint8_t* k, uint32_t kSz, diff --git a/test/unit.c b/test/unit.c index 7b4d6e5a..025b1cba 100644 --- a/test/unit.c +++ b/test/unit.c @@ -21,146 +21,95 @@ #include #include +#include -static int test_KDF(void); -static int ConvertHexToBin(const char* h1, uint8_t** b1, uint32_t* b1Sz, - const char* h2, uint8_t** b2, uint32_t* b2Sz, - const char* h3, uint8_t** b3, uint32_t* b3Sz, - const char* h4, uint8_t** b4, uint32_t* b4Sz); -static void FreeBins(uint8_t* b1, uint8_t* b2, uint8_t* b3, uint8_t* b4); -static int Base16_Decode(const uint8_t* in, uint32_t inLen, - uint8_t* out, uint32_t* outLen); +/* Utility functions */ +#define BAD 0xFF -int main(void) +const uint8_t hexDecode[] = { - int testResult = 0, unitResult = 0; + 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, + BAD, BAD, BAD, BAD, BAD, BAD, BAD, + 10, 11, 12, 13, 14, 15, /* upper case A-F */ + BAD, BAD, BAD, BAD, BAD, BAD, BAD, BAD, + BAD, BAD, BAD, BAD, BAD, BAD, BAD, BAD, + BAD, BAD, BAD, BAD, BAD, BAD, BAD, BAD, + BAD, BAD, /* G - ` */ + 10, 11, 12, 13, 14, 15 /* lower case a-f */ +}; /* A starts at 0x41 not 0x3A */ - unitResult = test_KDF(); - printf("KDF: %s\n", (unitResult == 0 ? "SUCCESS" : "FAILED")); - testResult = testResult || unitResult; - return (testResult ? 1 : 0); +static int Base16_Decode(const uint8_t* in, uint32_t inLen, + uint8_t* out, uint32_t* outLen) +{ + uint32_t inIdx = 0; + uint32_t outIdx = 0; + + if (inLen == 1 && *outLen && in) { + uint8_t b = in[inIdx++] - 0x30; /* 0 starts at 0x30 */ + + /* sanity check */ + if (b >= sizeof(hexDecode)/sizeof(hexDecode[0])) + return -1; + + b = hexDecode[b]; + + if (b == BAD) + return -1; + + out[outIdx++] = b; + + *outLen = outIdx; + return 0; + } + + if (inLen % 2) + return -1; + + if (*outLen < (inLen / 2)) + return -1; + + while (inLen) { + uint8_t b = in[inIdx++] - 0x30; /* 0 starts at 0x30 */ + uint8_t b2 = in[inIdx++] - 0x30; + + /* sanity checks */ + if (b >= sizeof(hexDecode)/sizeof(hexDecode[0])) + return -1; + if (b2 >= sizeof(hexDecode)/sizeof(hexDecode[0])) + return -1; + + b = hexDecode[b]; + b2 = hexDecode[b2]; + + if (b == BAD || b2 == BAD) + return -1; + + out[outIdx++] = (uint8_t)((b << 4) | b2); + inLen -= 2; + } + + *outLen = outIdx; + return 0; } -typedef struct { - uint8_t hashId; - uint8_t keyId; - const char* k; - const char* h; - const char* sessionId; - const char* expectedKey; -} KdfTestVector; - - -/** Test Vector Set #1 **/ -const char kdfTvSet1k[] = - "35618FD3AABF980A5F766408961600D4933C60DD7B22D69EEB4D7A987C938F6F" - "7BB2E60E0F638BB4289297B588E6109057325F010D021DF60EBF8BE67AD9C3E2" - "6376A326A16210C7AF07B3FE562B8DD1DCBECB17AA7BFAF38708B0136120B2FC" - "723E93EF4237AC3737BAE3A16EC03F605C7EEABFD526B38C826B506BBAECD2F7" - "9932F1371AEABFBEB4F8222313506677330C714A2A6FDC70CB859B581AA18625" - "ECCB6BA9DDEEAECF0E41D9E5076B899B477112E59DDADC4B4D9C13E9F07E1107" - "B560FEFDC146B8ED3E73441D05345031C35F9E6911B00319481D80015855BE4D" - "1C7D7ACC8579B1CC2E5F714109C0882C3B57529ABDA1F2255D2B27C4A83AE11E"; -const char kdfTvSet1h[] = "40555741F6DE70CDC4E740104A97E75473F49064"; -const char kdfTvSet1sessionId[] = "40555741F6DE70CDC4E740104A97E75473F49064"; -const char kdfTvSet1a[] = "B2EC4CF6943632C39972EE2801DC7393"; -const char kdfTvSet1b[] = "BC92238B6FA69ECC10B2B013C2FC9785"; -const char kdfTvSet1c[] = "9EF0E2053F66C56F3E4503DA1C2FBD6B"; -const char kdfTvSet1d[] = "47C8395B08277020A0645DA3959FA1A9"; -const char kdfTvSet1e[] = "EE436BFDABF9B0313224EC800E7390445E2F575E"; -const char kdfTvSet1f[] = "FB9FDEEC78B0FB258F1A4F47F6BCE166680994BB"; - -/** Test Vector Set #2 **/ -const char kdfTvSet2k[] = - "19FA2B7C7F4FE7DE61CDE17468C792CCEAB0E3F2CE37CDE2DAA0974BCDFFEDD4" - "A29415CDB330FA6A97ECA742359DC1223B581D8AC61B43CFFDF66D20952840B0" - "2593B48354E352E2A396BDF7F1C9D414FD31C2BF47E6EED306069C4F4F5F66C3" - "003A90E85412A1FBE89CDFB457CDA0D832E8DA701627366ADEC95B70E8A8B7BF" - "3F85775CCF36E40631B83B32CF643088F01A82C97C5C3A820EB4149F551CAF8C" - "C98EE6B3065E6152FF877823F7C618C1CD93CE26DB9FAAFED222F1C93E8F4068" - "BFDA4480432E14F98FFC821F05647693040B07D71DC273121D53866294434D46" - "0E95CFA4AB4414705BF1F8224655F907A418A6A893F2A71019225869CB7FE988"; -const char kdfTvSet2h[] = "DFB748905CC8647684C3E0B7F26A3E8E7414AC51"; -const char kdfTvSet2sessionId[] = "DFB748905CC8647684C3E0B7F26A3E8E7414AC51"; -const char kdfTvSet2a[] = "52EDBFD5E414A3CC6C7F7A0F4EA60503"; -const char kdfTvSet2b[] = "926C6987696C5FFCC6511BFE34557878"; -const char kdfTvSet2c[] = "CB6D56EC5B9AFECD326D544DA2D22DED"; -const char kdfTvSet2d[] = "F712F6451F1BD6CE9BAA597AC87C5A24"; -const char kdfTvSet2e[] = "E42FC62C76B76B37818F78292D3C2226D0264760"; -const char kdfTvSet2f[] = "D14BE4DD0093A3E759580233C80BB8399CE4C4E7"; - -static const KdfTestVector kdfTestVectors[] = { - {0, 'A', kdfTvSet1k, kdfTvSet1h, kdfTvSet1sessionId, kdfTvSet1a}, - {0, 'B', kdfTvSet1k, kdfTvSet1h, kdfTvSet1sessionId, kdfTvSet1b}, - {0, 'C', kdfTvSet1k, kdfTvSet1h, kdfTvSet1sessionId, kdfTvSet1c}, - {0, 'D', kdfTvSet1k, kdfTvSet1h, kdfTvSet1sessionId, kdfTvSet1d}, - {0, 'E', kdfTvSet1k, kdfTvSet1h, kdfTvSet1sessionId, kdfTvSet1e}, - {0, 'F', kdfTvSet1k, kdfTvSet1h, kdfTvSet1sessionId, kdfTvSet1f}, - {0, 'A', kdfTvSet2k, kdfTvSet2h, kdfTvSet2sessionId, kdfTvSet2a}, - {0, 'B', kdfTvSet2k, kdfTvSet2h, kdfTvSet2sessionId, kdfTvSet2b}, - {0, 'C', kdfTvSet2k, kdfTvSet2h, kdfTvSet2sessionId, kdfTvSet2c}, - {0, 'D', kdfTvSet2k, kdfTvSet2h, kdfTvSet2sessionId, kdfTvSet2d}, - {0, 'E', kdfTvSet2k, kdfTvSet2h, kdfTvSet2sessionId, kdfTvSet2e}, - {0, 'F', kdfTvSet2k, kdfTvSet2h, kdfTvSet2sessionId, kdfTvSet2f} -}; - -int test_KDF(void) +static void FreeBins(uint8_t* b1, uint8_t* b2, uint8_t* b3, uint8_t* b4) { - int result = 0; - uint32_t i; - uint32_t tc = sizeof(kdfTestVectors)/sizeof(KdfTestVector); - const KdfTestVector* tv = NULL; - uint8_t* k = NULL; - uint8_t* h = NULL; - uint8_t* sId = NULL; - uint8_t* eKey = NULL; - uint32_t kSz, hSz, sIdSz, eKeySz; - uint8_t cKey[20]; /* Greater of SHA_DIGEST_SIZE and AES_BLOCK_SIZE */ - /* sId - Session ID, eKey - Expected Key, cKey - Calculated Key */ - - for (i = 0, tv = kdfTestVectors; i < tc; i++, tv++) { - - result = ConvertHexToBin(tv->k, &k, &kSz, - tv->h, &h, &hSz, - tv->sessionId, &sId, &sIdSz, - tv->expectedKey, &eKey, &eKeySz); - if (result != 0) { - printf("KDF: Could not convert test vector %u.\n", i); - return -100; - } - - result = wolfSSH_KDF(tv->hashId, tv->keyId, cKey, eKeySz, - k, kSz, h, hSz, sId, sIdSz); - - if (result != 0) { - printf("KDF: Could not derive key.\n"); - result = -101; - } - else { - if (memcmp(cKey, eKey, eKeySz) != 0) { - printf("KDF: Calculated Key does not match Expected Key.\n"); - result = -102; - } - } - - FreeBins(k, h, sId, eKey); - - if (result != 0) break; - } - - return result; + if (b1 != NULL) free(b1); + if (b2 != NULL) free(b2); + if (b3 != NULL) free(b3); + if (b4 != NULL) free(b4); } /* convert hex string to binary, store size, 0 success (free mem on failure) */ -int ConvertHexToBin(const char* h1, uint8_t** b1, uint32_t* b1Sz, - const char* h2, uint8_t** b2, uint32_t* b2Sz, - const char* h3, uint8_t** b3, uint32_t* b3Sz, - const char* h4, uint8_t** b4, uint32_t* b4Sz) +static int ConvertHexToBin(const char* h1, uint8_t** b1, uint32_t* b1Sz, + const char* h2, uint8_t** b2, uint32_t* b2Sz, + const char* h3, uint8_t** b3, uint32_t* b3Sz, + const char* h4, uint8_t** b4, uint32_t* b4Sz) { int ret; @@ -230,82 +179,158 @@ int ConvertHexToBin(const char* h1, uint8_t** b1, uint32_t* b1Sz, } -void FreeBins(uint8_t* b1, uint8_t* b2, uint8_t* b3, uint8_t* b4) +/* Key Derivation Function (KDF) Unit Test */ + +typedef struct { + uint8_t hashId; + uint8_t keyId; + const char* k; + const char* h; + const char* sessionId; + const char* expectedKey; +} KdfTestVector; + + +/** Test Vector Set #1 **/ +const char kdfTvSet1k[] = + "35618FD3AABF980A5F766408961600D4933C60DD7B22D69EEB4D7A987C938F6F" + "7BB2E60E0F638BB4289297B588E6109057325F010D021DF60EBF8BE67AD9C3E2" + "6376A326A16210C7AF07B3FE562B8DD1DCBECB17AA7BFAF38708B0136120B2FC" + "723E93EF4237AC3737BAE3A16EC03F605C7EEABFD526B38C826B506BBAECD2F7" + "9932F1371AEABFBEB4F8222313506677330C714A2A6FDC70CB859B581AA18625" + "ECCB6BA9DDEEAECF0E41D9E5076B899B477112E59DDADC4B4D9C13E9F07E1107" + "B560FEFDC146B8ED3E73441D05345031C35F9E6911B00319481D80015855BE4D" + "1C7D7ACC8579B1CC2E5F714109C0882C3B57529ABDA1F2255D2B27C4A83AE11E"; +const char kdfTvSet1h[] = "40555741F6DE70CDC4E740104A97E75473F49064"; +const char kdfTvSet1sessionId[] = "40555741F6DE70CDC4E740104A97E75473F49064"; +const char kdfTvSet1a[] = "B2EC4CF6943632C39972EE2801DC7393"; +const char kdfTvSet1b[] = "BC92238B6FA69ECC10B2B013C2FC9785"; +const char kdfTvSet1c[] = "9EF0E2053F66C56F3E4503DA1C2FBD6B"; +const char kdfTvSet1d[] = "47C8395B08277020A0645DA3959FA1A9"; +const char kdfTvSet1e[] = "EE436BFDABF9B0313224EC800E7390445E2F575E"; +const char kdfTvSet1f[] = "FB9FDEEC78B0FB258F1A4F47F6BCE166680994BB"; + +/** Test Vector Set #2 **/ +const char kdfTvSet2k[] = + "19FA2B7C7F4FE7DE61CDE17468C792CCEAB0E3F2CE37CDE2DAA0974BCDFFEDD4" + "A29415CDB330FA6A97ECA742359DC1223B581D8AC61B43CFFDF66D20952840B0" + "2593B48354E352E2A396BDF7F1C9D414FD31C2BF47E6EED306069C4F4F5F66C3" + "003A90E85412A1FBE89CDFB457CDA0D832E8DA701627366ADEC95B70E8A8B7BF" + "3F85775CCF36E40631B83B32CF643088F01A82C97C5C3A820EB4149F551CAF8C" + "C98EE6B3065E6152FF877823F7C618C1CD93CE26DB9FAAFED222F1C93E8F4068" + "BFDA4480432E14F98FFC821F05647693040B07D71DC273121D53866294434D46" + "0E95CFA4AB4414705BF1F8224655F907A418A6A893F2A71019225869CB7FE988"; +const char kdfTvSet2h[] = "DFB748905CC8647684C3E0B7F26A3E8E7414AC51"; +const char kdfTvSet2sessionId[] = "DFB748905CC8647684C3E0B7F26A3E8E7414AC51"; +const char kdfTvSet2a[] = "52EDBFD5E414A3CC6C7F7A0F4EA60503"; +const char kdfTvSet2b[] = "926C6987696C5FFCC6511BFE34557878"; +const char kdfTvSet2c[] = "CB6D56EC5B9AFECD326D544DA2D22DED"; +const char kdfTvSet2d[] = "F712F6451F1BD6CE9BAA597AC87C5A24"; +const char kdfTvSet2e[] = "E42FC62C76B76B37818F78292D3C2226D0264760"; +const char kdfTvSet2f[] = "D14BE4DD0093A3E759580233C80BB8399CE4C4E7"; + +static const KdfTestVector kdfTestVectors[] = { + {0, 'A', kdfTvSet1k, kdfTvSet1h, kdfTvSet1sessionId, kdfTvSet1a}, + {0, 'B', kdfTvSet1k, kdfTvSet1h, kdfTvSet1sessionId, kdfTvSet1b}, + {0, 'C', kdfTvSet1k, kdfTvSet1h, kdfTvSet1sessionId, kdfTvSet1c}, + {0, 'D', kdfTvSet1k, kdfTvSet1h, kdfTvSet1sessionId, kdfTvSet1d}, + {0, 'E', kdfTvSet1k, kdfTvSet1h, kdfTvSet1sessionId, kdfTvSet1e}, + {0, 'F', kdfTvSet1k, kdfTvSet1h, kdfTvSet1sessionId, kdfTvSet1f}, + {0, 'A', kdfTvSet2k, kdfTvSet2h, kdfTvSet2sessionId, kdfTvSet2a}, + {0, 'B', kdfTvSet2k, kdfTvSet2h, kdfTvSet2sessionId, kdfTvSet2b}, + {0, 'C', kdfTvSet2k, kdfTvSet2h, kdfTvSet2sessionId, kdfTvSet2c}, + {0, 'D', kdfTvSet2k, kdfTvSet2h, kdfTvSet2sessionId, kdfTvSet2d}, + {0, 'E', kdfTvSet2k, kdfTvSet2h, kdfTvSet2sessionId, kdfTvSet2e}, + {0, 'F', kdfTvSet2k, kdfTvSet2h, kdfTvSet2sessionId, kdfTvSet2f} +}; + + +static int test_KDF(void) { - if (b1 != NULL) free(b1); - if (b2 != NULL) free(b2); - if (b3 != NULL) free(b3); - if (b4 != NULL) free(b4); + int result = 0; + uint32_t i; + uint32_t tc = sizeof(kdfTestVectors)/sizeof(KdfTestVector); + const KdfTestVector* tv = NULL; + uint8_t* k = NULL; + uint8_t* h = NULL; + uint8_t* sId = NULL; + uint8_t* eKey = NULL; + uint32_t kSz, hSz, sIdSz, eKeySz; + uint8_t cKey[20]; /* Greater of SHA_DIGEST_SIZE and AES_BLOCK_SIZE */ + /* sId - Session ID, eKey - Expected Key, cKey - Calculated Key */ + + for (i = 0, tv = kdfTestVectors; i < tc; i++, tv++) { + + result = ConvertHexToBin(tv->k, &k, &kSz, + tv->h, &h, &hSz, + tv->sessionId, &sId, &sIdSz, + tv->expectedKey, &eKey, &eKeySz); + if (result != 0) { + printf("KDF: Could not convert test vector %u.\n", i); + return -100; + } + + result = wolfSSH_KDF(tv->hashId, tv->keyId, cKey, eKeySz, + k, kSz, h, hSz, sId, sIdSz); + + if (result != 0) { + printf("KDF: Could not derive key.\n"); + result = -101; + } + else { + if (memcmp(cKey, eKey, eKeySz) != 0) { + printf("KDF: Calculated Key does not match Expected Key.\n"); + result = -102; + } + } + + FreeBins(k, h, sId, eKey); + + if (result != 0) break; + } + + return result; } -#define BAD 0xFF +/* Key Generation Unit Test */ -const uint8_t hexDecode[] = +#ifdef WOLFSSH_KEYGEN + +static int test_RsaKeyGen(void) { - 0, 1, 2, 3, 4, 5, 6, 7, 8, 9, - BAD, BAD, BAD, BAD, BAD, BAD, BAD, - 10, 11, 12, 13, 14, 15, /* upper case A-F */ - BAD, BAD, BAD, BAD, BAD, BAD, BAD, BAD, - BAD, BAD, BAD, BAD, BAD, BAD, BAD, BAD, - BAD, BAD, BAD, BAD, BAD, BAD, BAD, BAD, - BAD, BAD, /* G - ` */ - 10, 11, 12, 13, 14, 15 /* lower case a-f */ -}; /* A starts at 0x41 not 0x3A */ + int result = 0; + uint8_t der[1200]; + int derSz; - -static int Base16_Decode(const uint8_t* in, uint32_t inLen, - uint8_t* out, uint32_t* outLen) -{ - uint32_t inIdx = 0; - uint32_t outIdx = 0; - - if (inLen == 1 && *outLen && in) { - uint8_t b = in[inIdx++] - 0x30; /* 0 starts at 0x30 */ - - /* sanity check */ - if (b >= sizeof(hexDecode)/sizeof(hexDecode[0])) - return -1; - - b = hexDecode[b]; - - if (b == BAD) - return -1; - - out[outIdx++] = b; - - *outLen = outIdx; - return 0; + derSz = wolfSSH_MakeRsaKey(der, sizeof(der), + WOLFSSH_RSAKEY_DEFAULT_SZ, + WOLFSSH_RSAKEY_DEFAULT_E); + if (derSz < 0) { + printf("RsaKeyGen: MakeRsaKey failed\n"); + result = -103; } - if (inLen % 2) - return -1; - - if (*outLen < (inLen / 2)) - return -1; - - while (inLen) { - uint8_t b = in[inIdx++] - 0x30; /* 0 starts at 0x30 */ - uint8_t b2 = in[inIdx++] - 0x30; - - /* sanity checks */ - if (b >= sizeof(hexDecode)/sizeof(hexDecode[0])) - return -1; - if (b2 >= sizeof(hexDecode)/sizeof(hexDecode[0])) - return -1; - - b = hexDecode[b]; - b2 = hexDecode[b2]; - - if (b == BAD || b2 == BAD) - return -1; - - out[outIdx++] = (uint8_t)((b << 4) | b2); - inLen -= 2; - } - - *outLen = outIdx; - return 0; + return result; } +#endif + + +int main(void) +{ + int testResult = 0, unitResult = 0; + + unitResult = test_KDF(); + printf("KDF: %s\n", (unitResult == 0 ? "SUCCESS" : "FAILED")); + testResult = testResult || unitResult; + +#ifdef WOLFSSH_KEYGEN + unitResult = test_RsaKeyGen(); + printf("RsaKeyGen: %s\n", (unitResult == 0 ? "SUCCESS" : "FAILED")); + testResult = testResult || unitResult; +#endif + + return (testResult ? 1 : 0); +} diff --git a/wolfssh/include.am b/wolfssh/include.am index e8a8e3ed..0fa6c9ed 100644 --- a/wolfssh/include.am +++ b/wolfssh/include.am @@ -6,6 +6,7 @@ nobase_include_HEADERS+= \ wolfssh/version.h \ wolfssh/ssh.h \ + wolfssh/keygen.h \ wolfssh/port.h \ wolfssh/memory.h \ wolfssh/settings.h \ diff --git a/wolfssh/internal.h b/wolfssh/internal.h index 1b23b1aa..a84b843d 100644 --- a/wolfssh/internal.h +++ b/wolfssh/internal.h @@ -141,10 +141,6 @@ struct WOLFSSH_CTX { WS_CallbackUserAuth userAuthCb; /* User Authentication Callback */ WS_CallbackHighwater highwaterCb; /* Data Highwater Mark Callback */ - uint8_t* cert; /* Owned by CTX */ - uint32_t certSz; - uint8_t* caCert; /* Owned by CTX */ - uint32_t caCertSz; uint8_t* privateKey; /* Owned by CTX */ uint32_t privateKeySz; uint32_t countHighwater; @@ -388,7 +384,8 @@ enum WS_DynamicTypes { DYNTYPE_HS, DYNTYPE_CA, DYNTYPE_CERT, - DYNTYPE_KEY, + DYNTYPE_PRIVKEY, + DYNTYPE_PUBKEY, DYNTYPE_DH, DYNTYPE_RNG, DYNTYPE_STRING @@ -398,7 +395,8 @@ enum WS_DynamicTypes { enum WS_BufferTypes { BUFTYPE_CA, BUFTYPE_CERT, - BUFTYPE_PRIVKEY + BUFTYPE_PRIVKEY, + BUFTYPE_PUBKEY }; diff --git a/wolfssh/keygen.h b/wolfssh/keygen.h new file mode 100644 index 00000000..ca55d7b7 --- /dev/null +++ b/wolfssh/keygen.h @@ -0,0 +1,52 @@ +/* keygen.h + * + * Copyright (C) 2014-2016 wolfSSL Inc. + * + * This file is part of wolfSSH. + * + * wolfSSH is free software; you can redistribute it and/or modify + * it under the terms of the GNU General Public License as published by + * the Free Software Foundation; either version 3 of the License, or + * (at your option) any later version. + * + * wolfSSH is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the + * GNU General Public License for more details. + * + * You should have received a copy of the GNU General Public License + * along with wolfSSH. If not, see . + */ + + +/* + * The keygen module contains utility functions wrapping the wolfCrypt + * key generation functions to product SSH friendly keys. + */ + + +#pragma once + +#ifndef WOLFSSH_KEYGEN_H +#define WOLFSSH_KEYGEN_H + +#include +#include + +#ifdef __cplusplus +extern "C" { +#endif + + +#define WOLFSSH_RSAKEY_DEFAULT_SZ 2048 +#define WOLFSSH_RSAKEY_DEFAULT_E 65537 + + +WOLFSSH_API int wolfSSH_MakeRsaKey(uint8_t*, uint32_t, uint32_t, uint32_t); + + +#ifdef __cplusplus +} +#endif + +#endif diff --git a/wolfssh/ssh.h b/wolfssh/ssh.h index 7394a01a..a6f8827b 100644 --- a/wolfssh/ssh.h +++ b/wolfssh/ssh.h @@ -126,10 +126,6 @@ WOLFSSH_API void* wolfSSH_GetUserAuthCtx(WOLFSSH*); WOLFSSH_API int wolfSSH_CTX_UsePrivateKey_buffer(WOLFSSH_CTX*, const uint8_t*, uint32_t, int); -WOLFSSH_API int wolfSSH_CTX_UseCert_buffer(WOLFSSH_CTX*, - const uint8_t*, uint32_t, int); -WOLFSSH_API int wolfSSH_CTX_UseCaCert_buffer(WOLFSSH_CTX*, - const uint8_t*, uint32_t, int); WOLFSSH_API int wolfSSH_accept(WOLFSSH*); WOLFSSH_API int wolfSSH_stream_read(WOLFSSH*, uint8_t*, uint32_t);