diff --git a/.github/workflows/testing.yml b/.github/workflows/testing.yml index 61e185789..bc757b222 100644 --- a/.github/workflows/testing.yml +++ b/.github/workflows/testing.yml @@ -143,8 +143,8 @@ jobs: - sdk-version: 'bundle-2.10.0-1-gfa775b383-r486-linux-x86_64' coveralls: false ssl: true - - sdk-path: 'dev/linux/x86_64/master/' - sdk-version: 'sdk-gc64-2.11.0-entrypoint-113-g803baaffe-r529.linux.x86_64' + - sdk-path: 'release/linux/x86_64/2.11/' + sdk-version: 'sdk-gc64-2.11.0-0-r563.linux.x86_64' coveralls: true ssl: true diff --git a/.gitignore b/.gitignore index fcd3c3236..2aff2335e 100644 --- a/.gitignore +++ b/.gitignore @@ -4,3 +4,15 @@ work_dir* .rocks bench* + +testdata/*.crt +!testdata/ca.crt +!testdata/invalidhost.crt +!testdata/localhost.crt +testdata/*.csr +testdata/*.ext +testdata/*.key +!testdata/localhost.key +!testdata/localhost.enc.key +testdata/*.pem +testdata/*.srl diff --git a/Makefile b/Makefile index 4f676a530..3bfa80c58 100644 --- a/Makefile +++ b/Makefile @@ -27,7 +27,7 @@ clean: .PHONY: deps deps: clean ( cd ./queue/testdata; $(TTCTL) rocks install queue 1.3.0 ) - ( cd ./crud/testdata; $(TTCTL) rocks install crud 1.1.1 ) + ( cd ./crud/testdata; $(TTCTL) rocks install vshard 0.1.24; $(TTCTL) rocks install crud 1.1.1 ) .PHONY: datetime-timezones datetime-timezones: diff --git a/connection.go b/connection.go index 37de22e82..0e0a50dc7 100644 --- a/connection.go +++ b/connection.go @@ -345,6 +345,11 @@ type SslOpts struct { // // * https://www.openssl.org/docs/man1.1.1/man1/ciphers.html Ciphers string + // Password is a password for decrypting private SSL key file. + Password string + // PasswordFile is a path to the list of passwords for decrypting private SSL + // key file. Connection tries every line from the file as a password. + PasswordFile string } // Clone returns a copy of the Opts object. diff --git a/ssl.go b/ssl.go index d9373ace2..1c334aa9d 100644 --- a/ssl.go +++ b/ssl.go @@ -4,9 +4,13 @@ package tarantool import ( + "bufio" "errors" + "fmt" "io/ioutil" "net" + "os" + "strings" "time" "github.com/tarantool/go-openssl" @@ -43,7 +47,7 @@ func sslCreateContext(opts SslOpts) (ctx interface{}, err error) { } if opts.KeyFile != "" { - if err = sslLoadKey(sslCtx, opts.KeyFile); err != nil { + if err = sslLoadKey(sslCtx, opts.KeyFile, opts.Password, opts.PasswordFile); err != nil { return } } @@ -95,16 +99,69 @@ func sslLoadCert(ctx *openssl.Ctx, certFile string) (err error) { return } -func sslLoadKey(ctx *openssl.Ctx, keyFile string) (err error) { +func sslLoadKey(ctx *openssl.Ctx, keyFile string, password string, + passwordFile string) error { var keyBytes []byte + var err error + if keyBytes, err = ioutil.ReadFile(keyFile); err != nil { - return + return err } var key openssl.PrivateKey - if key, err = openssl.LoadPrivateKeyFromPEM(keyBytes); err != nil { - return + var errs []error + + // If key is encrypted and password is not provided, + // openssl.LoadPrivateKeyFromPEM(keyBytes) asks to enter PEM pass phrase + // interactively. On the other hand, + // openssl.LoadPrivateKeyFromPEMWithPassword(keyBytes, '') works fine for + // non-encrypted key. + key, err = openssl.LoadPrivateKeyFromPEMWithPassword(keyBytes, password) + if err == nil { + return ctx.UsePrivateKey(key) + } else { + errs = append(errs, err) + } + + if passwordFile != "" { + var file *os.File + file, err = os.Open(passwordFile) + if err == nil { + defer file.Close() + + scanner := bufio.NewScanner(file) + for scanner.Scan() { + password = strings.TrimSpace(scanner.Text()) + + key, err = openssl.LoadPrivateKeyFromPEMWithPassword(keyBytes, password) + if err == nil { + return ctx.UsePrivateKey(key) + } else { + errs = append(errs, err) + } + } + } else { + errs = append(errs, err) + } + } + + if len(errs) > 1 { + // Convenient multiple error wrapping was introduced only in Go 1.20 + // https://pkg.go.dev/errors#example-Join + // https://github.com/golang/go/issues/53435 + rerr := errors.New("got multiple errors on SSL decryption") + var i int + for i, err = range errs { + if i == 0 { + // gofmt forbids error strings to end with punctuation or newlines + rerr = fmt.Errorf("%s: %w", rerr, err) + } else { + rerr = fmt.Errorf("%s, %w", rerr, err) + } + } + + return rerr } - return ctx.UsePrivateKey(key) + return errs[0] } diff --git a/ssl_test.go b/ssl_test.go index 12cab7304..df5a78a01 100644 --- a/ssl_test.go +++ b/ssl_test.go @@ -117,6 +117,16 @@ func serverTnt(serverOpts, clientOpts SslOpts, auth Auth) (test_helpers.Tarantoo listen += fmt.Sprintf("ssl_ciphers=%s&", ciphers) } + password := serverOpts.Password + if password != "" { + listen += fmt.Sprintf("ssl_password=%s&", password) + } + + passwordFile := serverOpts.PasswordFile + if passwordFile != "" { + listen += fmt.Sprintf("ssl_password_file=%s&", passwordFile) + } + listen = listen[:len(listen)-1] return test_helpers.StartTarantool(test_helpers.StartOpts{ @@ -139,6 +149,21 @@ func serverTntStop(inst test_helpers.TarantoolInstance) { test_helpers.StopTarantoolWithCleanup(inst) } +func skipEncrypted(t testing.TB, serverOpts SslOpts) { + if serverOpts.Password == "" && serverOpts.PasswordFile == "" { + return + } + + isLess, err := test_helpers.IsTarantoolVersionLess(2, 11, 0) + if err != nil { + t.Fatalf("Could not check the Tarantool version") + } + + if isLess { + t.Skipf("Skipping test for Tarantool without SSL encryption support") + } +} + func assertConnectionSslFail(t testing.TB, serverOpts, clientOpts SslOpts) { t.Helper() @@ -171,6 +196,8 @@ func assertConnectionSslOk(t testing.TB, serverOpts, clientOpts SslOpts) { func assertConnectionTntFail(t testing.TB, serverOpts, clientOpts SslOpts) { t.Helper() + skipEncrypted(t, serverOpts) + inst, err := serverTnt(serverOpts, clientOpts, AutoAuth) serverTntStop(inst) @@ -182,6 +209,8 @@ func assertConnectionTntFail(t testing.TB, serverOpts, clientOpts SslOpts) { func assertConnectionTntOk(t testing.TB, serverOpts, clientOpts SslOpts) { t.Helper() + skipEncrypted(t, serverOpts) + inst, err := serverTnt(serverOpts, clientOpts, AutoAuth) serverTntStop(inst) @@ -431,6 +460,142 @@ var tests = []test{ Ciphers: "TLS_AES_128_GCM_SHA256", }, }, + { + "pass_no_key_encrypt", + true, + SslOpts{ + KeyFile: "testdata/localhost.key", + CertFile: "testdata/localhost.crt", + CaFile: "testdata/ca.crt", + }, + SslOpts{ + KeyFile: "testdata/localhost.enc.key", + CertFile: "testdata/localhost.crt", + Password: "mysslpassword", + }, + }, + { + "pass_file_no_key_encrypt", + true, + SslOpts{ + KeyFile: "testdata/localhost.key", + CertFile: "testdata/localhost.crt", + CaFile: "testdata/ca.crt", + }, + SslOpts{ + KeyFile: "testdata/localhost.enc.key", + CertFile: "testdata/localhost.crt", + PasswordFile: "testdata/passwords", + }, + }, + { + "pass_key_encrypt", + true, + SslOpts{ + KeyFile: "testdata/localhost.enc.key", + CertFile: "testdata/localhost.crt", + CaFile: "testdata/ca.crt", + Password: "mysslpassword", + }, + SslOpts{ + KeyFile: "testdata/localhost.enc.key", + CertFile: "testdata/localhost.crt", + Password: "mysslpassword", + }, + }, + { + "pass_file_key_encrypt", + true, + SslOpts{ + KeyFile: "testdata/localhost.enc.key", + CertFile: "testdata/localhost.crt", + CaFile: "testdata/ca.crt", + PasswordFile: "testdata/passwords", + }, + SslOpts{ + KeyFile: "testdata/localhost.enc.key", + CertFile: "testdata/localhost.crt", + PasswordFile: "testdata/passwords", + }, + }, + { + "pass_and_pass_file_key_encrypt", + true, + SslOpts{ + KeyFile: "testdata/localhost.enc.key", + CertFile: "testdata/localhost.crt", + CaFile: "testdata/ca.crt", + PasswordFile: "testdata/passwords", + }, + SslOpts{ + KeyFile: "testdata/localhost.enc.key", + CertFile: "testdata/localhost.crt", + Password: "mysslpassword", + PasswordFile: "testdata/passwords", + }, + }, + { + "inv_pass_and_pass_file_key_encrypt", + true, + SslOpts{ + KeyFile: "testdata/localhost.enc.key", + CertFile: "testdata/localhost.crt", + CaFile: "testdata/ca.crt", + PasswordFile: "testdata/passwords", + }, + SslOpts{ + KeyFile: "testdata/localhost.enc.key", + CertFile: "testdata/localhost.crt", + Password: "invalidpassword", + PasswordFile: "testdata/passwords", + }, + }, + { + "pass_and_inv_pass_file_key_encrypt", + true, + SslOpts{ + KeyFile: "testdata/localhost.enc.key", + CertFile: "testdata/localhost.crt", + CaFile: "testdata/ca.crt", + PasswordFile: "testdata/passwords", + }, + SslOpts{ + KeyFile: "testdata/localhost.enc.key", + CertFile: "testdata/localhost.crt", + Password: "mysslpassword", + PasswordFile: "testdata/invalidpasswords", + }, + }, + { + "pass_and_inv_pass_file_key_encrypt", + false, + SslOpts{ + KeyFile: "testdata/localhost.enc.key", + CertFile: "testdata/localhost.crt", + CaFile: "testdata/ca.crt", + PasswordFile: "testdata/passwords", + }, + SslOpts{ + KeyFile: "testdata/localhost.enc.key", + CertFile: "testdata/localhost.crt", + Password: "invalidpassword", + PasswordFile: "testdata/invalidpasswords", + }, + }, + { + "no_pass_key_encrypt", + false, + SslOpts{ + KeyFile: "testdata/localhost.enc.key", + CertFile: "testdata/localhost.crt", + CaFile: "testdata/ca.crt", + PasswordFile: "testdata/passwords", + }, + SslOpts{ + KeyFile: "testdata/localhost.enc.key", + CertFile: "testdata/localhost.crt", + }, + }, } func isTestTntSsl() bool { diff --git a/testdata/ca.crt b/testdata/ca.crt index 2fa1a12ff..75fe29a56 100644 --- a/testdata/ca.crt +++ b/testdata/ca.crt @@ -1,20 +1,20 @@ -----BEGIN CERTIFICATE----- -MIIDLzCCAhegAwIBAgIUMMZTmNkhr4qOfSwInVk2dAJvoBEwDQYJKoZIhvcNAQEL +MIIDLzCCAhegAwIBAgIUaw6WTgYBXFRqlGbKRYczFApoNU4wDQYJKoZIhvcNAQEL BQAwJzELMAkGA1UEBhMCVVMxGDAWBgNVBAMMD0V4YW1wbGUtUm9vdC1DQTAeFw0y -MjA1MjYwNjE3NDBaFw00NDEwMjkwNjE3NDBaMCcxCzAJBgNVBAYTAlVTMRgwFgYD +MzA3MjYwODM3MTZaFw00NTEyMjkwODM3MTZaMCcxCzAJBgNVBAYTAlVTMRgwFgYD VQQDDA9FeGFtcGxlLVJvb3QtQ0EwggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEK -AoIBAQCRq/eaA3I6CB8t770H2XDdzcp1yuC/+TZOxV5o0LuRkogTvL2kYULBrfx1 -rVZu8zQJTx1fmSRj1cN8j+IrmXN5goZ3mYFTnnIOgkyi+hJysVlo5s0Kp0qtLLGM -OuaVbxw2oAy75if5X3pFpiDaMvFBtJKsh8+SkncBIC5bbKC5AoLdFANLmPiH0CGr -Mv3rL3ycnbciI6J4uKHcWnYGGiMjBomaZ7jd/cOjcjmGfpI5d0nq13G11omkyEyR -wNX0eJRL02W+93Xu7tD+FEFMxFvak+70GvX+XWomwYw/Pjlio8KbTAlJxhfK2Lh6 -H798k17VfxIrOk0KjzZS7+a20hZ/AgMBAAGjUzBRMB0GA1UdDgQWBBT2f5o8r75C -PWST36akpkKRRTbhvjAfBgNVHSMEGDAWgBT2f5o8r75CPWST36akpkKRRTbhvjAP -BgNVHRMBAf8EBTADAQH/MA0GCSqGSIb3DQEBCwUAA4IBAQA9pb75p6mnqp2MQHSr -5SKRf2UV4wQIUtXgF6V9vNfvVzJii+Lzrqir1YMk5QgavCzD96KlJcqJCcH559RY -5743AxI3tdWfA3wajBctoy35oYnT4M30qbkryYLTUlv7PmeNWvrksTURchyyDt5/ -3T73yj5ZalmzKN6+xLfUDdnudspfWlUMutKU50MU1iuQESf4Fwd53vOg9jMcWJ2E -vAgfVI0XAvYdU3ybJrUvBq5zokYR2RzGv14uHxwVPnLBjrBEHRnbrXvLZJhuIS2b -xZ3CqwWi+9bvNqHz09HvhkU2b6fCGweKaAUGSo8OfQ5FRkjTUomMI/ZLs/qtJ6JR -zzVt +AoIBAQCunm5E+dyoYw+ECp0vOabsA4L7C+dUQLhfqdOEwFSpSanjBTuUEAPB+fEr +wqaZXI2EnUSxYEYO03TkZmWoJgRJq+00laWPA4AuKHpg4SS/LUoveQiQdsie+kUj +YMFu3rtP2CvTMpC4HMRK2CviOnU9iA4hPvRx4o5tESxLW31jNnBDeC/tsEVVR/6i +lwB9Oh1RbZI/c429N67qq5C2rpU5+o+YszDou36WTxw6XeXdkw7QF4W2BNLysPLJ +AY+aPrUVxKDOgDNk77h41HDqu+SuDg6mg528yfRqyAd4ooEE8MLcT0xztn1U8HvZ +SKwWTnS8TSzCmQptRGPlb5oES/NlAgMBAAGjUzBRMB0GA1UdDgQWBBQ/S0H0dFUy +OuEQ/kgDzGarWm2vlDAfBgNVHSMEGDAWgBQ/S0H0dFUyOuEQ/kgDzGarWm2vlDAP +BgNVHRMBAf8EBTADAQH/MA0GCSqGSIb3DQEBCwUAA4IBAQCoP+kH96+b6GWByPTo +LRK/QJmpPRWiZ5naV6CXJQNYg+nVG9wdiGXxEx4BBZs6yGdeHdiWCWbuRPMyH0Wp +w2ajMmK7pC8+MGKzMSC/EISPFwKYumwe/6zNnde7eZ19n7EFwrOihgEf+hNfjOCj +CqDIfMb2ztEHY7mEABMXDviKI80om2P1oIkHj5MD7z8ZetJRf1qCH7ke2cdTJ+Zr +XNGiJ7sz3xRQO/QRCkbBbr/d4zeX3A5/+MXHLtzbPiWs+/XaDbGJTQIO5hFfwwAC +v1/VrNmsy+3YYLLTZzmfpa60Sk3NsZbIQdvwLJJj8pOmH/zae7UZlrxlGWjQKvH5 +evsP -----END CERTIFICATE----- diff --git a/testdata/generate.sh b/testdata/generate.sh index f29f41c90..f78e84dba 100755 --- a/testdata/generate.sh +++ b/testdata/generate.sh @@ -8,7 +8,7 @@ set -xeuo pipefail # $ openssl version # OpenSSL 3.0.2 15 Mar 2022 (Library: OpenSSL 3.0.2 15 Mar 2022) -cat < domains.ext +cat < domains_localhost.ext authorityKeyIdentifier=keyid,issuer basicConstraints=CA:FALSE keyUsage = digitalSignature, nonRepudiation, keyEncipherment, dataEncipherment @@ -18,8 +18,32 @@ DNS.1 = localhost IP.1 = 127.0.0.1 EOF +cat < domains_invalidhost.ext +authorityKeyIdentifier=keyid,issuer +basicConstraints=CA:FALSE +keyUsage = digitalSignature, nonRepudiation, keyEncipherment, dataEncipherment +subjectAltName = @alt_names +[alt_names] +DNS.1 = invalidhostname +EOF + openssl req -x509 -nodes -new -sha256 -days 8192 -newkey rsa:2048 -keyout ca.key -out ca.pem -subj "/C=US/CN=Example-Root-CA" openssl x509 -outform pem -in ca.pem -out ca.crt openssl req -new -nodes -newkey rsa:2048 -keyout localhost.key -out localhost.csr -subj "/C=US/ST=YourState/L=YourCity/O=Example-Certificates/CN=localhost" -openssl x509 -req -sha256 -days 8192 -in localhost.csr -CA ca.pem -CAkey ca.key -CAcreateserial -extfile domains.ext -out localhost.crt +openssl x509 -req -sha256 -days 8192 -in localhost.csr -CA ca.pem -CAkey ca.key -CAcreateserial -extfile domains_localhost.ext -out localhost.crt +openssl x509 -req -sha256 -days 8192 -in localhost.csr -CA ca.pem -CAkey ca.key -CAcreateserial -extfile domains_invalidhost.ext -out invalidhost.crt + +password=mysslpassword + +# Tarantool tries every line from the password file. +cat < passwords +unusedpassword +$password +EOF + +cat < invalidpasswords +unusedpassword1 +EOF + +openssl rsa -aes256 -passout "pass:${password}" -in localhost.key -out localhost.enc.key diff --git a/testdata/invalidhost.crt b/testdata/invalidhost.crt new file mode 100644 index 000000000..e2200dcd8 --- /dev/null +++ b/testdata/invalidhost.crt @@ -0,0 +1,22 @@ +-----BEGIN CERTIFICATE----- +MIIDkjCCAnqgAwIBAgIUQLHZRFM5sRy6sRCuHaevk+YGFpEwDQYJKoZIhvcNAQEL +BQAwJzELMAkGA1UEBhMCVVMxGDAWBgNVBAMMD0V4YW1wbGUtUm9vdC1DQTAeFw0y +MzA3MjYwODM3MTZaFw00NTEyMjkwODM3MTZaMGcxCzAJBgNVBAYTAlVTMRIwEAYD +VQQIDAlZb3VyU3RhdGUxETAPBgNVBAcMCFlvdXJDaXR5MR0wGwYDVQQKDBRFeGFt +cGxlLUNlcnRpZmljYXRlczESMBAGA1UEAwwJbG9jYWxob3N0MIIBIjANBgkqhkiG +9w0BAQEFAAOCAQ8AMIIBCgKCAQEAqG67dtzioYKHDkF4FN2ObVpSNHkX5JgN8cR6 +iOyoAlppZO3upwRePQX0Ra9SMoL4GNuHZrr4daABYW15H9utlT2E8kzZTIcL+7VQ +rhGGrqzQRIXXOb6vGyKVnAC1FJ2mrnB7BfOCDcdMG1FeDcbhD3gyVzmr1wmXSvLh +Zq5XmHc2uinfGgt5Q1HauEso1aQqJ0VjkK0Xh+4O2tP9E1tnzJoetUQt2f2NmigY +hFURUsK+H2w9whWD9ynLkzD7xtNaPZ3o2WI4i/Eu9YHgAgnnSOkuKB0VjmirFWCz +YnrYWdGEdhYC62Wx58vX5vOOeDsZNJyKagh+0/JOLZCKPKbh6QIDAQABo3YwdDAf +BgNVHSMEGDAWgBQ/S0H0dFUyOuEQ/kgDzGarWm2vlDAJBgNVHRMEAjAAMAsGA1Ud +DwQEAwIE8DAaBgNVHREEEzARgg9pbnZhbGlkaG9zdG5hbWUwHQYDVR0OBBYEFEMm +fZC+zfSDniXFevQwlLQ8o1O1MA0GCSqGSIb3DQEBCwUAA4IBAQB/gE4CZdIma4sr ++HHyosi13KuLewUydfwWlPQoBD4s+lbOelhylKj7u+AL/QOiPvYIcreFv7rwXXzj +FTyT79G5pTNhlyMai+ehWRNxPIjksnZnDfa8dDciC3+w8wzWaJOXp/FEH0qfOs87 +F7smnKvOTVFcbshWq9u/bKTlA2dpuVKJub+ISfvbqLSxoaz5/NeBUFBIe8SllpWd +EW+GKbROa2spChpECEEbYOhWgTZ0dVdrnWd0xq34gSnzA6H+gTQ6wSCSMHl7YKJs +yCnPJz++Fl5hmwYGFA6HP60r0GZ4vAHUdfirehwJt/y0PRylFh0cXxDIY84UqRJa +80SDNfZQ +-----END CERTIFICATE----- diff --git a/testdata/invalidpasswords b/testdata/invalidpasswords new file mode 100644 index 000000000..b09d795aa --- /dev/null +++ b/testdata/invalidpasswords @@ -0,0 +1 @@ +unusedpassword1 diff --git a/testdata/localhost.crt b/testdata/localhost.crt index fd04b9900..e71b2f17e 100644 --- a/testdata/localhost.crt +++ b/testdata/localhost.crt @@ -1,22 +1,22 @@ -----BEGIN CERTIFICATE----- -MIIDkjCCAnqgAwIBAgIUAvSBJ3nSv7kdKw1IQ7AjchzI7T8wDQYJKoZIhvcNAQEL +MIIDkjCCAnqgAwIBAgIUAjJTmbM65RwQRByhxeEhlFSi8LwwDQYJKoZIhvcNAQEL BQAwJzELMAkGA1UEBhMCVVMxGDAWBgNVBAMMD0V4YW1wbGUtUm9vdC1DQTAeFw0y -MjA1MjYwNjE3NDBaFw00NDEwMjkwNjE3NDBaMGcxCzAJBgNVBAYTAlVTMRIwEAYD +MzA3MjYwODM3MTZaFw00NTEyMjkwODM3MTZaMGcxCzAJBgNVBAYTAlVTMRIwEAYD VQQIDAlZb3VyU3RhdGUxETAPBgNVBAcMCFlvdXJDaXR5MR0wGwYDVQQKDBRFeGFt cGxlLUNlcnRpZmljYXRlczESMBAGA1UEAwwJbG9jYWxob3N0MIIBIjANBgkqhkiG -9w0BAQEFAAOCAQ8AMIIBCgKCAQEAnbFY+BMqlddktbitgaZICws4Zyj8LFy9QzO+ -AYSQyqFuTCI+cGqbP5r6Qf4f3xHNGykHJGn18brpiFWhNMaVkkgU3dycU8fFayVN -hLEJAXd4acWP1h5/aH4cOZgl+xJlmU2iLHtP/TLYEDDiVkfqL/MgUIMxbndIaiU0 -/e81v+2gi8ydyI6aElN8KbAaFPzXCZ28/RmO/0m36YzF+FSMVD1Hx8xO5V+Q9N1q -dsyrMdh0nCxDDXGdBgDrKt5+U1uJkDpTHfjMAkf7oBoRd8DJ8O74bpue03W5WxKQ -NjNfvHSgkBaQSdnxR93FSCr/Gs6WcUd50Y8z+ZCTNkup0KROTwIDAQABo3YwdDAf -BgNVHSMEGDAWgBT2f5o8r75CPWST36akpkKRRTbhvjAJBgNVHRMEAjAAMAsGA1Ud -DwQEAwIE8DAaBgNVHREEEzARgglsb2NhbGhvc3SHBH8AAAEwHQYDVR0OBBYEFOwH -aHK6QrEfltP7wwldUWrQJ9viMA0GCSqGSIb3DQEBCwUAA4IBAQAGHGuloGJqLoPZ -2iRnb/NaiArowLnUz4Z3ENKMB2KbZFGijMJSXO9i9ZLCFL+O93vCTspKGtHqVX2o -dxcrF7EZ9EaHIijWjKGEp1PszunBIca+Te+zyRg9Z+F9gwRsJYB8ctBGjIhe4qEv -ZSlRY489UVNKLTcHcl6nlUled9hciBJHpXuitiiNhzUareP38hROyiUhrAy8L21L -t7Ww5YGRuSTxM5LQfPZcCy40++TlyvXs0DCQ8ZuUbqZv64bNHbaLOyxIqKfPypXa -nS3AYZzUJjHj7vZwHoL1SyvBjx/DQAsWaEv137d8FlMqCsWLXfCsuNpKeQYZOyDS -7ploP9Gl +9w0BAQEFAAOCAQ8AMIIBCgKCAQEAqG67dtzioYKHDkF4FN2ObVpSNHkX5JgN8cR6 +iOyoAlppZO3upwRePQX0Ra9SMoL4GNuHZrr4daABYW15H9utlT2E8kzZTIcL+7VQ +rhGGrqzQRIXXOb6vGyKVnAC1FJ2mrnB7BfOCDcdMG1FeDcbhD3gyVzmr1wmXSvLh +Zq5XmHc2uinfGgt5Q1HauEso1aQqJ0VjkK0Xh+4O2tP9E1tnzJoetUQt2f2NmigY +hFURUsK+H2w9whWD9ynLkzD7xtNaPZ3o2WI4i/Eu9YHgAgnnSOkuKB0VjmirFWCz +YnrYWdGEdhYC62Wx58vX5vOOeDsZNJyKagh+0/JOLZCKPKbh6QIDAQABo3YwdDAf +BgNVHSMEGDAWgBQ/S0H0dFUyOuEQ/kgDzGarWm2vlDAJBgNVHRMEAjAAMAsGA1Ud +DwQEAwIE8DAaBgNVHREEEzARgglsb2NhbGhvc3SHBH8AAAEwHQYDVR0OBBYEFEMm +fZC+zfSDniXFevQwlLQ8o1O1MA0GCSqGSIb3DQEBCwUAA4IBAQBEAww/Ng7zYgqQ +FdO+8xlJnf6rOFWS/nVwPfh9qfPXeq9VjYkZ6zZ5xEefvQu+xFwUYbF9/jEgkrd3 +hjdY4CiVmwMLwElYwohMXir+jHF1r123NCoWuAxdD9K28OZc8RhEy9WiaPW4EXqX +aS1aSgNeKKQXEY1Wuk/1tLTuJCUVJgJuHnwHDyR7VwLuhRiQ3zTXBi/MJ1IIIux0 +8qosD7LY4uwx0MnnymJw+eHkImVg4zhUCjYPT3AscmXkQ4a4QSC6L9HkD735mM/g +YyBibcftdtfEHwv93eGBfVr0G3l+FO+8ABXSZCIzDEX2/YDd0EPV/pYzHPfEgeiy +Cs3JMGb1 -----END CERTIFICATE----- diff --git a/testdata/localhost.enc.key b/testdata/localhost.enc.key new file mode 100644 index 000000000..e46e4c35d --- /dev/null +++ b/testdata/localhost.enc.key @@ -0,0 +1,30 @@ +-----BEGIN ENCRYPTED PRIVATE KEY----- +MIIFLTBXBgkqhkiG9w0BBQ0wSjApBgkqhkiG9w0BBQwwHAQIBzRuqvG5Oa8CAggA +MAwGCCqGSIb3DQIJBQAwHQYJYIZIAWUDBAEqBBAy0RMpMwecigx7Zu60n58iBIIE +0Hr1UiMgrntaMhNkERyZ4dF/DqHsx5cb4+xYM/GB1uyCycKAQV2DmE4qwjDFawfr +0GWdBjjbrniH/bHMAlaHFKNkGJPR8cUMxJBtdbosGOhL/mebfE3N4AraoXusNBQc +aHEpXsLYGorV6brOCKkQkzQBkdeV8nz4IPQ4A6cmWIoiD2jFyfi0qgU7ACzZU81L +E4Q5nOmSKwM9LbVib+2kF52KaYNtlniuZhyEbPnHYdRIFEh89n2mhO29yHYc1+cB +pEBMeE7xDtjNMEpUTEk14zzlKKmKhibFg+hFr3IvbSTUWnamFT/HUIzEiSAdWmbc ++uVnJhdanlOJK5l9u5f/yznPimvhNFOpFsgUy3QNi16LZoQVYbzqL66mO2ZbQGx1 +betnsNSjLszKT6zuhmP4U8RupuX62GjJ3oKEFw1ZK3JgU1DpwN8RZubD98uamBhB +yWyvlMQz9hmY4OZaKftFl9y5AbpXVsB25w1Oophy5FHfqpc8odbgF9XgmHOJOuhr +iFckpxOEJkZqsEACM8XWXfTnKhT83fNsRweeoczP/qLS/2Pgchi0WB0M557nnwcq +0qmOojhNTkmbu39S/cPMrB5nBNgToKwjIaCNE20lZa65VI6SvzjMAkxtxUPp2U/9 +3vgMy+1urIui+Ql9nIQgp+vcopufTRg+yjgvwKyT7sr5GfE8UWh1W57j7R1DTXr0 +fsIGGzZCWxo5YPvEgJWXaAKF2cj4UD9n0hN6y0RHMsKiUDH4ruc9Tv4kSE/xtf+q +TuLwabtf33Gmg80bkpkDfw47pA39gkeMM2rgrCOs1JFn6NMo4hYjxP8OqUMXsWaC +VnSUjADeHUohJkv5pZioh44uFtxTwIWRmnaKsU8ZFMb3WPHLHMCMNYVH9x727BH5 +ny0vrgga4039dvBxyKIjnmG4N2O2GywB1g6atCJkEeEbUggXssFtGWpFQl6rHskI +kOnjmXDueJT9pw+ApzxDPixWakLSvqeXG2C3hMOP+8IJ8qvQEKOnooqBqvsXdwFN +/5koRwcuCh6913o5sAsc8Dkg0P0h1HjE+Jo06HKPbAufKX+koTx2z0WKTbLMXRB1 +FLmWkeHAV0K1BITgD325+uEmSAWOw4sl4G28E25sxLP2avtfIU5zM3aILTnlhBkx +9MoxcN2CZp+CWWAX+gW493oI4wfw2vMuC8PRIS7wQ7uChTUvay3/ZU14QA5sndI1 +ww/F0AOAnLee66hZpdqsX3TQ+CoLhTMukDmsQ0kl7BPj8osoualbUZKUX8+aREgY +S4IsyVcXfxjCh4NT1fziuUn3gaItwRS5FbxASMwtKkbq+NlwamwG6rLAPlX4TMxk +Pm/K8EOUoMt6ts+s5dKdU7t9mEeBdhD0pYWvr01sCGSj5tFx/pV4v/esb0n0kNek +mvQMV8fsJ5SHc10/31VCCJuc3CrfgLA+MBB7naBg7SlB/S6HSq7Lfw4jQieWM+yS +T29OSn+OxlCyTKqrvNqe50Fxu8IzNrox0aXtfayF/XNf0BqsHqL/SQ45TwLLLD/s ++jU9cS5CZQUQIsbVNUyfNSalmZY8pYFjKUX7dDOXJfU8YMdU71SPs+vQ3W17UWxJ +5Edt7PlyTCYLlW1CcSkHdvyizks33tRk3d3RDTf70EOo +-----END ENCRYPTED PRIVATE KEY----- diff --git a/testdata/localhost.key b/testdata/localhost.key index ed0f55876..2864fdd52 100644 --- a/testdata/localhost.key +++ b/testdata/localhost.key @@ -1,28 +1,28 @@ -----BEGIN PRIVATE KEY----- -MIIEvAIBADANBgkqhkiG9w0BAQEFAASCBKYwggSiAgEAAoIBAQCdsVj4EyqV12S1 -uK2BpkgLCzhnKPwsXL1DM74BhJDKoW5MIj5waps/mvpB/h/fEc0bKQckafXxuumI -VaE0xpWSSBTd3JxTx8VrJU2EsQkBd3hpxY/WHn9ofhw5mCX7EmWZTaIse0/9MtgQ -MOJWR+ov8yBQgzFud0hqJTT97zW/7aCLzJ3IjpoSU3wpsBoU/NcJnbz9GY7/Sbfp -jMX4VIxUPUfHzE7lX5D03Wp2zKsx2HScLEMNcZ0GAOsq3n5TW4mQOlMd+MwCR/ug -GhF3wMnw7vhum57TdblbEpA2M1+8dKCQFpBJ2fFH3cVIKv8azpZxR3nRjzP5kJM2 -S6nQpE5PAgMBAAECggEAFv81l9wHsll6pOu9VfJ/gCjPPXAjMn8F1OaXV5ZTHVHk -iXLXA0LwyBpcU8JxOHFapZLaqUtQpEObahf+zfkF+BLOBDr3i1pPZpxGjUraIt4e -7+HxY4sIDp+Rky6mn1JkAbLqKy2CkUzYaKgQYf/T3dFJjaRMUa1QoLYzX7MCdi5B -GnBICzi2UVsn3HU934l/gJKV+SlprdbrGJ+fRklP2AxLey3EOrwooUViy+k3+w5E -dzBH2HpLL0XuIHaBXQ01J6Mu3ud9ApFLC+Rh+2UFTW/WPnNe+B6BO5CGNN52Pfdr -Q5l+VzmRkXXo2fio+w4z/az8axT/DdhKGT2oBlp35QKBgQDZVGdKjkalH3QH2pdy -CWJIiybzY1R0CpimfgDLIdqEsps9qqgLXsUFB5yTcCRmg8RSWWHvhMVMyJtBcsdY -xGhmHxsFBxuray60UljxBcRQTwqvAX7mP8WEv8t80kbhyaxvOfkg8JD1n2hS7NjL -dOIG9Mh8L0YSOCRkbfv90OnYXQKBgQC5wGs35Ksnqi2swX5MLYfcBaImzoNde86n -cXJ0yyF82O1pk8DkmU2EDcUoQfkKxr3ANvVDG4vYaguIhYsJqPg/t8XQt/epDz/O -WZhqogn0ysaTv2FHrWcgPAkq82hpNII5NfPP8aRaYh8OUSfh4WHkW84m6+usqwjI -wbOq36qmmwKBgGMFFdreYEmzvwYlDoOiyukKncCfLUeB3HNfTbU/w3RafGjobJBh -qZrVEP4MRkl/F9/9YaXj9JE7haGYTkOfmYGOAp2T04OS3kDClEucuQluOgvqvorh -23jUej5xAGK3pJ046M2dTi7bZokB6PUqWCGbPg127JI4ijxH8FyA50rxAoGAQO2d -jMAFg6vco1JPT1lq7+GYOHBfQsIQDj99fo2yeu1or0rSVhWwHsShcdz9rGKj2Rhc -ysRKMa9/sIzdeNbzT3JxVu+3RgTqjLqMqFlTmZl3qBVxb5iRP5c8rSLAEGYmTtEp -FDqm9GDv8hU0F6SsjyH4AWrdylFOlL4Ai237PJkCgYBDC1wAwBD8WXJqRrYVGj7X -l4TQQ0hO7La/zgbasSgLNaJcYu32nut6D0O8IlmcQ2nO0BGPjQmJFGp6xawjViRu -np7fEkJQEf1pK0yeA8A3urjXccuUXEA9kKeqaSZYDzICPFaOlezPPPpW0hbkhnPe -dQn3DcoY6e6o0K5ltt1RvQ== +MIIEvgIBADANBgkqhkiG9w0BAQEFAASCBKgwggSkAgEAAoIBAQCobrt23OKhgocO +QXgU3Y5tWlI0eRfkmA3xxHqI7KgCWmlk7e6nBF49BfRFr1IygvgY24dmuvh1oAFh +bXkf262VPYTyTNlMhwv7tVCuEYaurNBEhdc5vq8bIpWcALUUnaaucHsF84INx0wb +UV4NxuEPeDJXOavXCZdK8uFmrleYdza6Kd8aC3lDUdq4SyjVpConRWOQrReH7g7a +0/0TW2fMmh61RC3Z/Y2aKBiEVRFSwr4fbD3CFYP3KcuTMPvG01o9nejZYjiL8S71 +geACCedI6S4oHRWOaKsVYLNiethZ0YR2FgLrZbHny9fm8454Oxk0nIpqCH7T8k4t +kIo8puHpAgMBAAECggEAPQGamfNojNpjw5iX/2q+T0JjOwlPS6d9iX/CaDzbn7qS +qRF7Gvh8j7rL3r+hVJVWel5tXRrEqooRZfIKaK0fYspdEIwgOtVBVGK4fcvwTe1f +JCqcKZi1AO2WZeJltDlj6ZPpI18vUIFKwixHFlNeKkW9ahWD9cfOCkINvSzRonGZ +BdY6JqyS2MiFPHhFwtdoRXXRKMRomtapwYvPw904X22qjP/FpHKc/bPyQjjOnCJr +AfR8iS6+cbIE3iuAoTT5U2mB5kU/YqLKzAG/dzYzBMUXekrWpKd9xrxbZAGOrTTX +0++wke0/BJv6aYLG8WWMUsG1d5YvEhN/3gTW9ETSxwKBgQDZdMtIyrwfw2fuJCTf +Ol+lgjrygInojFEcuOFSgRMdW0p69KafllvJJwXF16oiU2TXDAoufMDGyiSE//NI +M7f3SxKxtT0lawI6BvOBKN1TVncUznMbdKS9w6JY0lCJW8CMjUVtjuwQ8UgyuHPi +4jmSeug0jrYPNk6ILu/H6OHdgwKBgQDGSXWlEdMLuldE68pr7sguVjcLqkPg5OXT +ya4w/TOIgavDG162UkDK7uuwPtYd9bV45V7Z8GTI/bbZZn88g/mb1QiSjzfnKpgz +WZv1nMdJR7EKcnh4iMUf94M4ZiCbF19H02xco2Qx5ijOXkRkoGyLjFlvTMOLHoEj +oyfsTiGzIwKBgQC8lD6ed8JBQXJl4M5hD/xWSePY3YO7OcQ1xlcQ94KeGMc0ben5 +x6j9fmvRMMAIWI3AuF40BlgfjLmy5UwTN1a4jFA/8E6AnpYlwFV3kvqtBPTsBEVq +b/NV5cxqfqj9FaabvP+SjTlHUBcudSt6fHk1AIVS3tgfxRbBnwKuONV3BQKBgQCp +EzZXXI2CcI+9Wvktc1wJ9sXVEofymftGza/UYfKxMTCOmyX1fMl2wKcDj3Dv9vWY +cqygVRT7NSvW0EkqBrauI8a9gZV/bZh+IKiVk+tyFsllSRpkXOsJSPoA+0ROOm2q +RyMdEs16pvCgl0zmKMylaTVRbDlIxOgExThjjHO71QKBgFD67jERzo+7ZwgyKJ1H +LumwDXn4Tjolc7+J31ahQg6ta9bDDUJuXcWG4SEiPqXUh0GT5toP0KuL1Ocj/aca +YsE10kbQdd/6A5531im+eVt0HQhH39hjr0R+8hC6GgtUTYwcqNS7jD8wbhT+SzOT +FjWgqEyP6oRyNGDe0gQWlR9m -----END PRIVATE KEY----- diff --git a/testdata/passwords b/testdata/passwords new file mode 100644 index 000000000..58530047f --- /dev/null +++ b/testdata/passwords @@ -0,0 +1,2 @@ +unusedpassword +mysslpassword