From ea0340426545025aa95452bb7588e7cda2be35b3 Mon Sep 17 00:00:00 2001 From: Eugene Medvedev Date: Thu, 22 Jun 2023 13:49:20 +0300 Subject: [PATCH] =?UTF-8?q?=E2=9C=85=20Test=20harness,=20of=20sorts.?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit --- .gitignore | 10 +- README.md | 4 +- main.go | 2 +- test.sh | 23 ++++ testcases/files/lipsum.txt | 10 ++ testcases/files/sstv.jpg | Bin 0 -> 70561 bytes testcases/generator/README.md | 8 ++ testcases/generator/generate_keys.sh | 61 +++++++++ testcases/generator/intermediate/01.pem | 23 ++++ testcases/generator/intermediate/ca.cert.pem | 32 +++++ testcases/generator/intermediate/ca.csr.pem | 19 +++ testcases/generator/intermediate/ca.key.pem | 28 +++++ testcases/generator/intermediate/index.txt | 1 + .../generator/intermediate/index.txt.attr | 1 + testcases/generator/intermediate/serial | 1 + testcases/generator/openssl.conf | 119 ++++++++++++++++++ testcases/generator/root/01.pem | 32 +++++ testcases/generator/root/ca.cert.pem | 38 ++++++ testcases/generator/root/ca.key.pem | 52 ++++++++ testcases/generator/root/index.txt | 1 + testcases/generator/root/index.txt.attr | 1 + testcases/generator/root/serial | 1 + testcases/generator/user/user.cert.pem | 23 ++++ testcases/generator/user/user.csr.pem | 16 +++ testcases/generator/user/user.key.pem | 28 +++++ testcases/keys/N0CALL.p12 | Bin 0 -> 4195 bytes testcases/keys/cache/chain/mockup.der | Bin 0 -> 1395 bytes testcases/keys/cache/roots/mockup.der | Bin 0 -> 1685 bytes testcases/results/.gitkeep | 0 version.txt | 2 +- 30 files changed, 532 insertions(+), 4 deletions(-) create mode 100755 test.sh create mode 100644 testcases/files/lipsum.txt create mode 100644 testcases/files/sstv.jpg create mode 100644 testcases/generator/README.md create mode 100644 testcases/generator/generate_keys.sh create mode 100644 testcases/generator/intermediate/01.pem create mode 100644 testcases/generator/intermediate/ca.cert.pem create mode 100644 testcases/generator/intermediate/ca.csr.pem create mode 100644 testcases/generator/intermediate/ca.key.pem create mode 100644 testcases/generator/intermediate/index.txt create mode 100644 testcases/generator/intermediate/index.txt.attr create mode 100644 testcases/generator/intermediate/serial create mode 100644 testcases/generator/openssl.conf create mode 100644 testcases/generator/root/01.pem create mode 100644 testcases/generator/root/ca.cert.pem create mode 100644 testcases/generator/root/ca.key.pem create mode 100644 testcases/generator/root/index.txt create mode 100644 testcases/generator/root/index.txt.attr create mode 100644 testcases/generator/root/serial create mode 100644 testcases/generator/user/user.cert.pem create mode 100644 testcases/generator/user/user.csr.pem create mode 100644 testcases/generator/user/user.key.pem create mode 100644 testcases/keys/N0CALL.p12 create mode 100644 testcases/keys/cache/chain/mockup.der create mode 100644 testcases/keys/cache/roots/mockup.der create mode 100644 testcases/results/.gitkeep diff --git a/.gitignore b/.gitignore index 01f9707..eb9b47a 100644 --- a/.gitignore +++ b/.gitignore @@ -21,5 +21,13 @@ go.work .vscode/launch.json build/* lotw-trust -test.sh +# Testcases tree +testcases/results/* +testcases/keys/cache/chain/*.der +!testcases/keys/cache/chain/mockup.der +testcases/keys/cache/*.der +testcases/**/*.old + +# This, surprisingly, goes last. +!.gitkeep diff --git a/README.md b/README.md index 7b6b80f..44f9580 100644 --- a/README.md +++ b/README.md @@ -93,7 +93,9 @@ This is a [Go](https://go.dev/) program, so this should be easy enough, provided go install github.com/Mihara/lotw-trust@latest -It was written with go 1.20.5 and I currently don't know what's the minimum version requirement. Binaries for a number of platforms are provided in the releases section. +It was written with go 1.20.5 and I currently don't know what's the minimum version requirement. Binaries for a number of platforms are provided in the releases section. `build.sh` will cross-compile binaries for all supported platforms. + +See `testcases` and `test.sh` for simple test cases and a faux-LoTW certification tree structure to play with. ## Plans for future development diff --git a/main.go b/main.go index d6b6d58..0e81a67 100644 --- a/main.go +++ b/main.go @@ -268,7 +268,7 @@ func main() { rootFiles, _ = os.ReadDir(rootsCacheDir) for _, f := range rootFiles { if strings.HasSuffix(strings.ToLower(f.Name()), ".der") { - der, err := dataFiles.ReadFile(filepath.Join(rootsCacheDir, f.Name())) + der, err := os.ReadFile(filepath.Join(rootsCacheDir, f.Name())) check(err, "Failed to read a root certificate from cache.") crt, err := x509.ParseCertificate(der) check(err, "Failed to parse a root certificate from cache.") diff --git a/test.sh b/test.sh new file mode 100755 index 0000000..88edc68 --- /dev/null +++ b/test.sh @@ -0,0 +1,23 @@ +#!/bin/bash + +# This is a preliminary smoke test engine, and not a proper integration test framework. +# Yet. It lets people run tests without ever touching their real key file though. + +CACHE=testcases/keys/cache +KEY=testcases/keys/N0CALL.p12 +SRC=testcases/files +DST=testcases/results + +# Straightforward signature. +go run *.go sign -c $CACHE -p changeme $KEY $SRC/sstv.jpg $DST/sstv-signed.jpg +go run *.go verify -c $CACHE $DST/sstv-signed.jpg $DST/sstv-unsigned.jpg +cmp -l $SRC/sstv.jpg $DST/sstv-unsigned.jpg + +# Uncompressed signature. +go run *.go sign -c $CACHE -p changeme -u -a $KEY $SRC/sstv.jpg $DST/sstv-signed-unc.jpg +go run *.go verify -c $CACHE $DST/sstv-signed-unc.jpg $DST/sstv-unsigned.jpg +cmp -l $SRC/sstv.jpg $DST/sstv-unsigned.jpg + +# Text mode signing. +go run *.go sign -t -c $CACHE -p changeme $KEY $SRC/lipsum.txt $DST/lipsum-signed.txt +go run *.go verify -t -c $CACHE $DST/lipsum-signed.txt $DST/lipsum-unsigned.txt diff --git a/testcases/files/lipsum.txt b/testcases/files/lipsum.txt new file mode 100644 index 0000000..15dac90 --- /dev/null +++ b/testcases/files/lipsum.txt @@ -0,0 +1,10 @@ +Lorem ipsum dolor sit amet, consectetur adipiscing elit, sed do eiusmod tempor incididunt ut labore et dolore magna aliqua. Imperdiet massa tincidunt nunc pulvinar sapien et ligula. Enim facilisis gravida neque convallis a cras semper. Viverra maecenas accumsan lacus vel facilisis volutpat est. Nunc sed velit dignissim sodales ut eu sem. Tellus integer feugiat scelerisque varius morbi. Nec nam aliquam sem et tortor consequat. Urna porttitor rhoncus dolor purus. Ac ut consequat semper viverra. Amet venenatis urna cursus eget nunc scelerisque viverra mauris. Tortor condimentum lacinia quis vel eros. Tellus cras adipiscing enim eu turpis egestas pretium aenean. Duis convallis convallis tellus id interdum. Varius duis at consectetur lorem donec massa sapien faucibus et. Aenean euismod elementum nisi quis eleifend quam adipiscing. Nibh sit amet commodo nulla facilisi nullam. Sit amet purus gravida quis blandit. Nullam vehicula ipsum a arcu cursus vitae congue mauris. + +Dui accumsan sit amet nulla. Nunc sed blandit libero volutpat sed cras ornare arcu dui. Tellus at urna condimentum mattis pellentesque id nibh tortor. Magna sit amet purus gravida quis blandit turpis cursus in. Non curabitur gravida arcu ac tortor dignissim convallis aenean. Sed risus ultricies tristique nulla. Varius duis at consectetur lorem donec massa sapien. Lobortis feugiat vivamus at augue eget arcu dictum varius duis. Netus et malesuada fames ac turpis egestas integer. Lectus magna fringilla urna porttitor rhoncus dolor. Dignissim cras tincidunt lobortis feugiat vivamus at. Non odio euismod lacinia at quis. Praesent elementum facilisis leo vel fringilla. + +At tempor commodo ullamcorper a lacus. Sit amet massa vitae tortor condimentum lacinia quis vel eros. Non blandit massa enim nec. Tortor at risus viverra adipiscing at. Nulla pellentesque dignissim enim sit amet venenatis urna cursus. Eget lorem dolor sed viverra ipsum nunc. Vitae ultricies leo integer malesuada nunc vel risus commodo viverra. Accumsan in nisl nisi scelerisque eu. At quis risus sed vulputate odio ut enim blandit. Dictum varius duis at consectetur lorem donec massa. Ultrices dui sapien eget mi proin sed. Nisl vel pretium lectus quam id leo. Ipsum a arcu cursus vitae congue mauris rhoncus. + +Nisl suscipit adipiscing bibendum est ultricies integer quis auctor elit. Nulla porttitor massa id neque aliquam. Praesent semper feugiat nibh sed pulvinar proin gravida. Interdum velit laoreet id donec. Feugiat in ante metus dictum at tempor. Convallis posuere morbi leo urna molestie at elementum. Netus et malesuada fames ac turpis egestas integer eget aliquet. Gravida cum sociis natoque penatibus et. Amet facilisis magna etiam tempor orci eu lobortis elementum nibh. Tristique nulla aliquet enim tortor. At tellus at urna condimentum mattis pellentesque id nibh tortor. Lectus mauris ultrices eros in. Purus faucibus ornare suspendisse sed nisi lacus sed viverra tellus. Vestibulum lectus mauris ultrices eros in cursus turpis. Pharetra convallis posuere morbi leo urna molestie at elementum. + +Bibendum arcu vitae elementum curabitur vitae. Eu facilisis sed odio morbi quis commodo. Tristique et egestas quis ipsum suspendisse. Eu volutpat odio facilisis mauris sit amet massa vitae tortor. Ultricies integer quis auctor elit. Quis ipsum suspendisse ultrices gravida dictum. Integer malesuada nunc vel risus commodo viverra maecenas accumsan lacus. Eget duis at tellus at urna. Egestas egestas fringilla phasellus faucibus scelerisque eleifend donec pretium vulputate. Turpis egestas maecenas pharetra convallis posuere. Nunc sed id semper risus. Nunc scelerisque viverra mauris in aliquam sem fringilla ut morbi. Id consectetur purus ut faucibus pulvinar. Nisi porta lorem mollis aliquam ut porttitor leo a. Nunc aliquet bibendum enim facilisis gravida neque convallis a cras. Enim eu turpis egestas pretium aenean pharetra magna. Vitae nunc sed velit dignissim sodales. + diff --git a/testcases/files/sstv.jpg b/testcases/files/sstv.jpg new file mode 100644 index 0000000000000000000000000000000000000000..e8117d5d88a879c356776a0002538222fb2fe628 GIT binary patch literal 70561 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

1f18q7Gl^nv-AKS*k)b2>J z(b?(*Sld?pTP@Wg@Sv|B2m%IxBuxp@%w!LNSe(l5ru46-8Uu1@F$gK?TsQ!Hl~nkq zq0RV0ai)*BPmktde>Gtbxl{mu@+s5oOJWgn+a84b3}db3jcJU_5V zmieiTrH=*_YH7QkYk2Q+-M~FlmhgJxmLqCsbSC6@ci0-(`i#G*J2;50#@6P%%#_ii zCPYKSZAX(s+Az2l7rAM^SI|Idtv&E`eQ$Rekp|KRMr=3M-Oald`*er#b#MKXNB%Jf z{Kct$z9=(h_c2dDI2+CHFp1+L*CWXR(^>a?yrOD{ADrII!CTSB_b~-K7TTOo6~j~F^BdGW(xn_)q-cEz-#7t zwz9GSfv9Wsroqt@pe^?RNO|oK(Dv`W+)fV&6GxW#H`If~2FxGm79*(i;?>*jQy%RU zy36?X_s{)mZ$JqJ!S?Xs5py$M#v^^imi#WOQk~6!&;2YM1Kug8m1X0))=KEw|EL~M zeFMrec12R5UeQH2_8Egiq3;%~rbBpHU#Z;;NHqj(Q(4yvnfLX?XJZ}oIBZw0DAYr0 zX27N}w+4Fub5JdsBS!)Fh9GXJE4Eo23nObp1;??X0#R?grx+XvjF;Sa_S~rDaFPW6nr{@e{lbwc0hh!yp9G zGrw)1UK-%@QtB6E57|n-KBbIIL6V2mi=xQ|;9}_AayV)C*!@&+uaIUUIM!M!4gU2) SsvK0z!3D?$2t@GL`u_s80(gV~ literal 0 HcmV?d00001 diff --git a/testcases/generator/README.md b/testcases/generator/README.md new file mode 100644 index 0000000..bbe147d --- /dev/null +++ b/testcases/generator/README.md @@ -0,0 +1,8 @@ +# CA tree generator + +The `generate_keys.sh` script builds a certificate authority structure that looks very much like LoTW's, but isn't, in addition to producing a user certificate for N0CALL. This certificate will not be recognized by `lotw-trust` unless the requisite `mockup.der` files are placed directly into the key cache -- or the key cache is pointed at the directory where they live, `testcases/keys/cache`, with `-c` command line option. This particular stunt makes it possible to use a completely fake certificate authority structure for testing purposes. + +Running this script will wipe the existing structure in `testcases/generator` and start again, so signatures created with keys you had before will stop verifying. + +Generally you shouldn't need to do use this again, unless LoTW does something unusual. + diff --git a/testcases/generator/generate_keys.sh b/testcases/generator/generate_keys.sh new file mode 100644 index 0000000..b96e884 --- /dev/null +++ b/testcases/generator/generate_keys.sh @@ -0,0 +1,61 @@ +#!/bin/bash + +rm root/* intermediate/* user/* + +touch root/index.txt +echo 01 >root/serial +touch intermediate/index.txt +echo 01 >intermediate/serial + +echo === Generating root CA. +openssl genrsa -out root/ca.key.pem 4096 +openssl req -config ./openssl.conf \ + -key root/ca.key.pem \ + -new -x509 -days 7300 -sha512 -extensions v3_ca \ + -out root/ca.cert.pem \ + -subj "/C=US/ST=CT/L=Pseudocity/O=Fake American Radio Relay League/OU=Logbook of the World Mockup/CN=Logbook of the World Root CA Mockup/emailAddress=lotw@example.com" + +echo === Generating Intermediate CA CSR +openssl genrsa -out intermediate/ca.key.pem 2048 +openssl req -config ./openssl.conf -new -sha256 \ + -key intermediate/ca.key.pem \ + -out intermediate/ca.csr.pem \ + -subj "/C=US/ST=CT/L=Pseudocity/O=Fake American Radio Relay League/OU=Logbook of the World Mockup/CN=Logbook of the World Production CA Mockup/emailAddress=lotw@example.com" + +echo === Signing the Intermediate CA CSR with Root CA. +openssl ca -config ./openssl.conf -extensions v3_intermediate_ca \ + -days 6000 -notext -md sha256 -batch \ + -in intermediate/ca.csr.pem \ + -out intermediate/ca.cert.pem + +echo === Generating a callsign CSR. +openssl genrsa -out user/user.key.pem 2048 +openssl req -config ./openssl.conf -new -sha256 \ + -subj "/CN=John Doe/emailAddress=john@example.com/Callsign=N0CALL" \ + -key user/user.key.pem \ + -out user/user.csr.pem + +echo === Signing the callsign CSR with Intermediate CA. +openssl ca -config openssl.conf -name CA_intermediate -batch \ + -extensions user_cert -days 5000 -notext -md sha256 \ + -in user/user.csr.pem \ + -out user/user.cert.pem + +echo === Saving results. + +KEYS=../keys +CACHE=$KEYS/cache + +mkdir -p $CACHE/roots +openssl x509 -in root/ca.cert.pem -outform der -out $CACHE/roots/mockup.der +mkdir -p $CACHE/chain +openssl x509 -in intermediate/ca.cert.pem -outform der -out $CACHE/chain/mockup.der + +# Now the fun part, making a pkcs12 file... +openssl pkcs12 -export -out $KEYS/N0CALL.p12 \ + -password pass:changeme \ + -inkey user/user.key.pem \ + -in user/user.cert.pem \ + -certfile intermediate/ca.cert.pem + +echo === Done! diff --git a/testcases/generator/intermediate/01.pem b/testcases/generator/intermediate/01.pem new file mode 100644 index 0000000..6299d6a --- /dev/null +++ b/testcases/generator/intermediate/01.pem @@ -0,0 +1,23 @@ +-----BEGIN CERTIFICATE----- +MIID5DCCAsygAwIBAgIBATANBgkqhkiG9w0BAQsFADCBwDELMAkGA1UEBhMCVVMx +CzAJBgNVBAgMAkNUMSkwJwYDVQQKDCBGYWtlIEFtZXJpY2FuIFJhZGlvIFJlbGF5 +IExlYWd1ZTEkMCIGA1UECwwbTG9nYm9vayBvZiB0aGUgV29ybGQgTW9ja3VwMTIw +MAYDVQQDDClMb2dib29rIG9mIHRoZSBXb3JsZCBQcm9kdWN0aW9uIENBIE1vY2t1 +cDEfMB0GCSqGSIb3DQEJARYQbG90d0BleGFtcGxlLmNvbTAeFw0yMzA2MjIxMDIy +MjVaFw0zNzAyMjgxMDIyMjVaMEsxETAPBgNVBAMMCEpvaG4gRG9lMRUwEwYJKwYB +BAHgPAEBDAZOMENBTEwxHzAdBgkqhkiG9w0BCQEWEGpvaG5AZXhhbXBsZS5jb20w +ggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQCSxlSePX690qTCbhJ53XQs +UzcqfJgXceSUxzq4JiVgTvbSqjRGQpuHBEAZrUmbiij+GZEnMIErcIhefZt4MBXx +gNp+CI/820VDV1fUAitkawOc8RKqq2jFn7EBBdUTMFL4jSlshjjr+x1KDA3vKpL4 +Pt2HW+oa0Fx7G0Wt7r4BFIhDvpkRGRsVVdt2XF6LhCSJCOOjf59CuXkAVbvCRmac +mYPA3/p0nrLodurrb3cEyVCi9t1Q7M0EFwSV0eyLkPRVhgzr0B9AAXNBnynxzAG+ +I8LlAv4kmilmryWkyfx35Fwes48oVDerSWoHuOi1RR6bZneyqmrZBdHUXWc6wbw/ +AgMBAAGjXTBbMB0GA1UdDgQWBBQ6hJqgn06AAldyLgdcx7ufjJMs6jAJBgNVHRME +AjAAMB8GA1UdIwQYMBaAFHYffR9m6SgxxTvJuyIZ/YJQVtsFMA4GA1UdDwEB/wQE +AwIF4DANBgkqhkiG9w0BAQsFAAOCAQEAkuTC3H28HbvCgL/2OksrOEg8xQnQ+bDo +fRoMlcDhZNOEpCMRYxfuEwXVpkNRJufiJA+XPJg9jKtk+bTDYzp2DBZgeBsJ5C0k +J03hn4z/rCcVMUNoArVE5C+fkZwCBx9hzaJPyYEvwnGbtpyTWPcmfnyeXtzCDj0T +qAGLDtDQw7ERZpj25jsnCPEJN1NmvRxmw4+Tx/1IIxn8s6iWdyUGChHNXK5KJnaU +HUJOVy6k42gjpCKXRDGrwntMyMWUjhWDwjBoUEYeVMspq5I00hptCzMRoVo2CSQC +0PeU3f3qb4L00JzmzHEwa6uNyK0FOjPgxKXIOJUnAQsEWPcmR/i4+A== +-----END CERTIFICATE----- diff --git a/testcases/generator/intermediate/ca.cert.pem b/testcases/generator/intermediate/ca.cert.pem new file mode 100644 index 0000000..f0c8412 --- /dev/null +++ b/testcases/generator/intermediate/ca.cert.pem @@ -0,0 +1,32 @@ +-----BEGIN CERTIFICATE----- +MIIFbzCCA1egAwIBAgIBATANBgkqhkiG9w0BAQsFADCBzzELMAkGA1UEBhMCVVMx +CzAJBgNVBAgMAkNUMRMwEQYDVQQHDApQc2V1ZG9jaXR5MSkwJwYDVQQKDCBGYWtl +IEFtZXJpY2FuIFJhZGlvIFJlbGF5IExlYWd1ZTEkMCIGA1UECwwbTG9nYm9vayBv +ZiB0aGUgV29ybGQgTW9ja3VwMSwwKgYDVQQDDCNMb2dib29rIG9mIHRoZSBXb3Js +ZCBSb290IENBIE1vY2t1cDEfMB0GCSqGSIb3DQEJARYQbG90d0BleGFtcGxlLmNv +bTAeFw0yMzA2MjIxMDIyMjVaFw0zOTExMjUxMDIyMjVaMIHAMQswCQYDVQQGEwJV +UzELMAkGA1UECAwCQ1QxKTAnBgNVBAoMIEZha2UgQW1lcmljYW4gUmFkaW8gUmVs +YXkgTGVhZ3VlMSQwIgYDVQQLDBtMb2dib29rIG9mIHRoZSBXb3JsZCBNb2NrdXAx +MjAwBgNVBAMMKUxvZ2Jvb2sgb2YgdGhlIFdvcmxkIFByb2R1Y3Rpb24gQ0EgTW9j +a3VwMR8wHQYJKoZIhvcNAQkBFhBsb3R3QGV4YW1wbGUuY29tMIIBIjANBgkqhkiG +9w0BAQEFAAOCAQ8AMIIBCgKCAQEAoFK1iYtdMHbDp3Pe8s+EmGmPUBwpczEhK0l5 +eGzXQz4PGkCEY6fv/qi/WzVSfs6FsKrIHelPmyS4SEwL2jjQQzIxm4II9PGu3yzT +M7un1Y1NY4jENSR2Gs1TxSmjvcMEuniLXdXv41D30ae+i8gKHlvpZ1teJzeWJyMK +ZQKtgNd2VytjOXkYbbmzOShyBvoQrXT20NDVtH/qYzSIEJ98CVHpzh7DZQHDb9bP +77ILSqK5NSexPaAUzQY4vP3IgxIQAg0NT+MkA8opNq11jW8f0yHwL5gfCKz+2xN6 +JkShawJm68cdYr8aRj/KFhcBujj514yxM6PIhbyF9G0BFTCeZwIDAQABo2MwYTAd +BgNVHQ4EFgQUdh99H2bpKDHFO8m7Ihn9glBW2wUwHwYDVR0jBBgwFoAUtccMME0V +jHrWHeP8MzpJcIRIuE0wDwYDVR0TAQH/BAUwAwEB/zAOBgNVHQ8BAf8EBAMCAYYw +DQYJKoZIhvcNAQELBQADggIBAHisuMAGui94Xf0NG9/DU1Q9DQuMrv/MEuE4KtPp +higiUQwXTepthmFxJycuyYhbGvoVTVoV7HO/pcQTiKp1bUcM55lAazT4rA3nJOuZ +frj5DhnAZX9rqkyddPxHSgY51Vb8gpIAZSNdMhOAblA3bGq8bSeeIrwUMtF8viD9 +d2wdrm4APJLTiDfswCJdp3lGDQg5et+Kqlqhee3O0+/Y9pNM+xokuslQDyx/QqTf +hhyvEw1JHMRv4RWi2/Wzs38lGSvy8UnnerW9RhYRrwuSHIVrdLFO/+LGl7w7TNnh +9o3t1oYZZlGRN93rVp+ApbhC+OgpcqkTB16f6L7YHkX+toeKlEZYUzjGF/EMOn6T +iLTamzIrU1+J0dJTRIpHX7EW9o+a4JhafLMcqV9xfZkadqOBS4z80/prGzJ5AtKN +b8CAOy+G+H65+lNjBCtYrqohti9jJ8TlDf7UtDV2rg2rSFuxfbkna07+DeqzyNAq +YsWTTnXxHcYVQcZJpqp+m2OorPnYguEr+mgnP2hTCvqOxdralqtCKF8tWa64PhSf +2GQptkHCAmAsrMlxU7JBI8JRVRbgMNiLvONIxaooz1O7WQyRFPqkLy8fmcnQeQHl +stqQ1JsJfsvwNZzAkL/PfBGdGsITtLRH+UhgEYzexuuZzPMZ0mWD44kE4M5ueyBg +3JON +-----END CERTIFICATE----- diff --git a/testcases/generator/intermediate/ca.csr.pem b/testcases/generator/intermediate/ca.csr.pem new file mode 100644 index 0000000..7f861b3 --- /dev/null +++ b/testcases/generator/intermediate/ca.csr.pem @@ -0,0 +1,19 @@ +-----BEGIN CERTIFICATE REQUEST----- +MIIDGzCCAgMCAQAwgdUxCzAJBgNVBAYTAlVTMQswCQYDVQQIDAJDVDETMBEGA1UE +BwwKUHNldWRvY2l0eTEpMCcGA1UECgwgRmFrZSBBbWVyaWNhbiBSYWRpbyBSZWxh +eSBMZWFndWUxJDAiBgNVBAsMG0xvZ2Jvb2sgb2YgdGhlIFdvcmxkIE1vY2t1cDEy +MDAGA1UEAwwpTG9nYm9vayBvZiB0aGUgV29ybGQgUHJvZHVjdGlvbiBDQSBNb2Nr +dXAxHzAdBgkqhkiG9w0BCQEWEGxvdHdAZXhhbXBsZS5jb20wggEiMA0GCSqGSIb3 +DQEBAQUAA4IBDwAwggEKAoIBAQCgUrWJi10wdsOnc97yz4SYaY9QHClzMSErSXl4 +bNdDPg8aQIRjp+/+qL9bNVJ+zoWwqsgd6U+bJLhITAvaONBDMjGbggj08a7fLNMz +u6fVjU1jiMQ1JHYazVPFKaO9wwS6eItd1e/jUPfRp76LyAoeW+lnW14nN5YnIwpl +Aq2A13ZXK2M5eRhtubM5KHIG+hCtdPbQ0NW0f+pjNIgQn3wJUenOHsNlAcNv1s/v +sgtKork1J7E9oBTNBji8/ciDEhACDQ1P4yQDyik2rXWNbx/TIfAvmB8IrP7bE3om +RKFrAmbrxx1ivxpGP8oWFwG6OPnXjLEzo8iFvIX0bQEVMJ5nAgMBAAGgADANBgkq +hkiG9w0BAQsFAAOCAQEAkyvGwl42w3mgx9MvCRr8Q4Wi7iZeiBKoyErb612jJ/5i +R7lksThwfW+SjpLWnQqcNxd/PZ40/YLAyQbTCkdL2v8/jbMcFNO550lu/AgsrEID +MqaSvJvO44Lh8d2OrorCPVSm625uLg9WruaJNqc6SZ1n/8jKgn8vnI13aKsLcDHL +Rtng/Bk1W3VpWlsXwb2fcuViUHXAVrnXsAVLGP3fht2iUie3zEpHjQCPh1epYYXX +JHQdArzu/q3TV0FlmhWiu42nuxaZ6NzjuPEHyGk7Vta4jy7EkmhTjfMF/iz8dD6W +iu/Fi7b0YrFyIyZPBXDm0Fn4bJRLszyaMyAEkLYrZw== +-----END CERTIFICATE REQUEST----- diff --git a/testcases/generator/intermediate/ca.key.pem b/testcases/generator/intermediate/ca.key.pem new file mode 100644 index 0000000..2b86895 --- /dev/null +++ b/testcases/generator/intermediate/ca.key.pem @@ -0,0 +1,28 @@ +-----BEGIN PRIVATE KEY----- +MIIEvgIBADANBgkqhkiG9w0BAQEFAASCBKgwggSkAgEAAoIBAQCgUrWJi10wdsOn +c97yz4SYaY9QHClzMSErSXl4bNdDPg8aQIRjp+/+qL9bNVJ+zoWwqsgd6U+bJLhI +TAvaONBDMjGbggj08a7fLNMzu6fVjU1jiMQ1JHYazVPFKaO9wwS6eItd1e/jUPfR +p76LyAoeW+lnW14nN5YnIwplAq2A13ZXK2M5eRhtubM5KHIG+hCtdPbQ0NW0f+pj +NIgQn3wJUenOHsNlAcNv1s/vsgtKork1J7E9oBTNBji8/ciDEhACDQ1P4yQDyik2 +rXWNbx/TIfAvmB8IrP7bE3omRKFrAmbrxx1ivxpGP8oWFwG6OPnXjLEzo8iFvIX0 +bQEVMJ5nAgMBAAECggEAKyZ3s+BtoYilmmFGZWXTE05+AxrBUT6s5cCtz+rDeVav +q+ond8cQgiMa9cqBPJ4LP4SHvf04rtIQQ20sV3ypGRzeWzOBg6O05F5lLexY/NI+ +PQbngEIjA421+T/+0Sk3EZU2NXhKS41UVfpm/6pEhu1IAciGq9l7MWdt+cfhuOZX +QLMY/5+MWJf8Ru16tQjl34XeM0+3wFt6glcdiCtcCr/sxGYU/vsKaZvrtvqs7PkU +82MtyJfXjAKkC94FekEVOSUJtGuKrTffxy4yH/dtNyeaNiLkRDpXIAbP1xZiAz9N +aG7MjunfvObpLAHCeiwVQdNRkO2XjpY5VyUhLbM3gQKBgQC1qp/Tv/C0FiMTWhZE +bF2Wy4FXHnK+rgnqCLlKCDFi0Cb760HJnlJa/kc+pWFCTRhoE+80iEdE+66aVIE2 +WdzpLuA8GPfibvklu7ASpa0R437UAkKroF8dZXXdEOKBe7u1HFrGhv1dNftM/fVu +D4gKlA+I+cZJ5wJvb2htpKPhJwKBgQDh7GJRa4FH6JX837LYedxHI1Z6VkC6h+qL +id9t7+svf+ftqe4CMWLqzp1+39ci1TF3trwXWdEnbBDWLOTfe9pKoDrH/e+qtF/4 +N6JL5j2afSivY6QbZadsL8sKyn3QjWTX++r/N4DpptGsQ390z/8nsVEw0Hel1RUW +Xn4mK+kgwQKBgQCKj/jWJsluYpAgW48uY0VDFjex/kxg+hgfxMWnHPamOsPxVDBa +mwKP2vD2bGfxjSI3iDTkaamKiTlVB22CyioARbvMuvKfaCtqx2x13J5UTaPYC11U +0L6bil7K3e0V/A1hB56JXD72EI173RyM9RW7k9EBlhnTFns6CcyqDHDe8wKBgQCI +nliqIdeQ835X57KQI8joH994pVYJNo3ICfzZz16qX6+R0dPC8bh+g6lMAvJm9wMu +AIvnlwHa1AeubIGO/6d2v0QskkvvL5plUMdNHJMeLBeBUED57FP9IT2obeD9T7Ou +xIFMCnVjVeSvRjX6HpmOmDSfz0C7QIq69zNTw/P7QQKBgBA+IpYxe6wMEcMnb124 +f3Rl8y5JvsvZMz44r9BrVRW870Aaex8IRpTtKrg0aLftks5to69frgIf/ri6PFXs +uaACayleku6C8eWGEsqpaXNzN36bsu8D/MH5XoVG6LpP1fGLlMpujGyYO+jCQmWA +OVYvQxVNfnIZuxll11Hk1mnz +-----END PRIVATE KEY----- diff --git a/testcases/generator/intermediate/index.txt b/testcases/generator/intermediate/index.txt new file mode 100644 index 0000000..4c156ef --- /dev/null +++ b/testcases/generator/intermediate/index.txt @@ -0,0 +1 @@ +V 370228102225Z 01 unknown /CN=John Doe/Callsign=N0CALL/emailAddress=john@example.com diff --git a/testcases/generator/intermediate/index.txt.attr b/testcases/generator/intermediate/index.txt.attr new file mode 100644 index 0000000..8f7e63a --- /dev/null +++ b/testcases/generator/intermediate/index.txt.attr @@ -0,0 +1 @@ +unique_subject = yes diff --git a/testcases/generator/intermediate/serial b/testcases/generator/intermediate/serial new file mode 100644 index 0000000..9e22bcb --- /dev/null +++ b/testcases/generator/intermediate/serial @@ -0,0 +1 @@ +02 diff --git a/testcases/generator/openssl.conf b/testcases/generator/openssl.conf new file mode 100644 index 0000000..8dc5daf --- /dev/null +++ b/testcases/generator/openssl.conf @@ -0,0 +1,119 @@ + +oid_section = lotw_oids + +[ lotw_oids ] +Callsign=1.3.6.1.4.1.12348.1.1 + +[ ca ] +default_ca = CA_root + +[ CA_root ] +dir = ./root +certs = $dir/certs +crl_dir = $dir/crl +new_certs_dir = $dir +database = $dir/index.txt +serial = $dir/serial +RANDFILE = $dir/private/.rand + +private_key = $dir/ca.key.pem +certificate = $dir/ca.cert.pem + +crlnumber = $dir/crlnumber +crl = $dir/ca.crl.pem +crl_extensions = crl_ext +default_crl_days = 30 + +default_md = sha256 + +name_opt = ca_default +cert_opt = ca_default +default_days = 375 +preserve = no +policy = policy_strict + +[ CA_intermediate ] +dir = ./intermediate +certs = $dir +crl_dir = $dir +new_certs_dir = $dir +database = $dir/index.txt +serial = $dir/serial +RANDFILE = $dir/.rand +private_key = $dir/ca.key.pem +certificate = $dir/ca.cert.pem + +crlnumber = $dir/crlnumber +crl = $dir/ca.crl.pem +crl_extensions = crl_ext +default_crl_days = 30 + +default_md = sha256 + +name_opt = ca_default +cert_opt = ca_default +default_days = 375 +preserve = no +policy = policy_loose + +[ policy_strict ] +countryName = match +stateOrProvinceName = match +organizationName = match +organizationalUnitName = optional +commonName = supplied +emailAddress = optional + +[ policy_loose ] +countryName = optional +stateOrProvinceName = optional +localityName = optional +organizationName = optional +organizationalUnitName = optional +commonName = supplied +Callsign = supplied +emailAddress = optional + +[ req ] +default_bits = 2048 +distinguished_name = req_distinguished_name +string_mask = utf8only +default_md = sha256 +x509_extensions = v3_ca + +[ req_distinguished_name ] +countryName = Country Name (2 letter code) +stateOrProvinceName = State or Province Name +localityName = Locality Name +0.organizationName = Organization Name +organizationalUnitName = Organizational Unit Name +commonName = Common Name +emailAddress = Email Address +Callsign = Callsign + +countryName_default = US +stateOrProvinceName_default = CT +localityName_default = NotNewington +0.organizationName_default = Logbook of the World Mockup +organizationalUnitName_default = Fake American Radio Relay League +emailAddress_default = lotw@example.com +Callsign_default = N0CALL + +[ v3_ca ] +subjectKeyIdentifier = hash +authorityKeyIdentifier = keyid:always,issuer +basicConstraints = critical, CA:true +keyUsage = critical, digitalSignature, cRLSign, keyCertSign + +[ v3_intermediate_ca ] +subjectKeyIdentifier = hash +authorityKeyIdentifier = keyid:always,issuer +basicConstraints = critical, CA:true +keyUsage = critical, digitalSignature, cRLSign, keyCertSign + +[ user_cert ] +subjectKeyIdentifier = hash +basicConstraints = CA:FALSE +authorityKeyIdentifier = keyid,issuer +keyUsage = critical, nonRepudiation, digitalSignature, keyEncipherment + diff --git a/testcases/generator/root/01.pem b/testcases/generator/root/01.pem new file mode 100644 index 0000000..f0c8412 --- /dev/null +++ b/testcases/generator/root/01.pem @@ -0,0 +1,32 @@ +-----BEGIN CERTIFICATE----- +MIIFbzCCA1egAwIBAgIBATANBgkqhkiG9w0BAQsFADCBzzELMAkGA1UEBhMCVVMx +CzAJBgNVBAgMAkNUMRMwEQYDVQQHDApQc2V1ZG9jaXR5MSkwJwYDVQQKDCBGYWtl +IEFtZXJpY2FuIFJhZGlvIFJlbGF5IExlYWd1ZTEkMCIGA1UECwwbTG9nYm9vayBv +ZiB0aGUgV29ybGQgTW9ja3VwMSwwKgYDVQQDDCNMb2dib29rIG9mIHRoZSBXb3Js +ZCBSb290IENBIE1vY2t1cDEfMB0GCSqGSIb3DQEJARYQbG90d0BleGFtcGxlLmNv +bTAeFw0yMzA2MjIxMDIyMjVaFw0zOTExMjUxMDIyMjVaMIHAMQswCQYDVQQGEwJV +UzELMAkGA1UECAwCQ1QxKTAnBgNVBAoMIEZha2UgQW1lcmljYW4gUmFkaW8gUmVs +YXkgTGVhZ3VlMSQwIgYDVQQLDBtMb2dib29rIG9mIHRoZSBXb3JsZCBNb2NrdXAx +MjAwBgNVBAMMKUxvZ2Jvb2sgb2YgdGhlIFdvcmxkIFByb2R1Y3Rpb24gQ0EgTW9j +a3VwMR8wHQYJKoZIhvcNAQkBFhBsb3R3QGV4YW1wbGUuY29tMIIBIjANBgkqhkiG +9w0BAQEFAAOCAQ8AMIIBCgKCAQEAoFK1iYtdMHbDp3Pe8s+EmGmPUBwpczEhK0l5 +eGzXQz4PGkCEY6fv/qi/WzVSfs6FsKrIHelPmyS4SEwL2jjQQzIxm4II9PGu3yzT +M7un1Y1NY4jENSR2Gs1TxSmjvcMEuniLXdXv41D30ae+i8gKHlvpZ1teJzeWJyMK +ZQKtgNd2VytjOXkYbbmzOShyBvoQrXT20NDVtH/qYzSIEJ98CVHpzh7DZQHDb9bP +77ILSqK5NSexPaAUzQY4vP3IgxIQAg0NT+MkA8opNq11jW8f0yHwL5gfCKz+2xN6 +JkShawJm68cdYr8aRj/KFhcBujj514yxM6PIhbyF9G0BFTCeZwIDAQABo2MwYTAd +BgNVHQ4EFgQUdh99H2bpKDHFO8m7Ihn9glBW2wUwHwYDVR0jBBgwFoAUtccMME0V +jHrWHeP8MzpJcIRIuE0wDwYDVR0TAQH/BAUwAwEB/zAOBgNVHQ8BAf8EBAMCAYYw +DQYJKoZIhvcNAQELBQADggIBAHisuMAGui94Xf0NG9/DU1Q9DQuMrv/MEuE4KtPp +higiUQwXTepthmFxJycuyYhbGvoVTVoV7HO/pcQTiKp1bUcM55lAazT4rA3nJOuZ +frj5DhnAZX9rqkyddPxHSgY51Vb8gpIAZSNdMhOAblA3bGq8bSeeIrwUMtF8viD9 +d2wdrm4APJLTiDfswCJdp3lGDQg5et+Kqlqhee3O0+/Y9pNM+xokuslQDyx/QqTf +hhyvEw1JHMRv4RWi2/Wzs38lGSvy8UnnerW9RhYRrwuSHIVrdLFO/+LGl7w7TNnh +9o3t1oYZZlGRN93rVp+ApbhC+OgpcqkTB16f6L7YHkX+toeKlEZYUzjGF/EMOn6T +iLTamzIrU1+J0dJTRIpHX7EW9o+a4JhafLMcqV9xfZkadqOBS4z80/prGzJ5AtKN +b8CAOy+G+H65+lNjBCtYrqohti9jJ8TlDf7UtDV2rg2rSFuxfbkna07+DeqzyNAq +YsWTTnXxHcYVQcZJpqp+m2OorPnYguEr+mgnP2hTCvqOxdralqtCKF8tWa64PhSf +2GQptkHCAmAsrMlxU7JBI8JRVRbgMNiLvONIxaooz1O7WQyRFPqkLy8fmcnQeQHl +stqQ1JsJfsvwNZzAkL/PfBGdGsITtLRH+UhgEYzexuuZzPMZ0mWD44kE4M5ueyBg +3JON +-----END CERTIFICATE----- diff --git a/testcases/generator/root/ca.cert.pem b/testcases/generator/root/ca.cert.pem new file mode 100644 index 0000000..e73950f --- /dev/null +++ b/testcases/generator/root/ca.cert.pem @@ -0,0 +1,38 @@ +-----BEGIN CERTIFICATE----- +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 +3i9Q2Ag= +-----END CERTIFICATE----- diff --git a/testcases/generator/root/ca.key.pem b/testcases/generator/root/ca.key.pem new file mode 100644 index 0000000..d28faa4 --- /dev/null +++ b/testcases/generator/root/ca.key.pem @@ -0,0 +1,52 @@ +-----BEGIN PRIVATE KEY----- +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 +sZaSqNNXeWr+Wn4NnqHN8lFAkb3aCA== +-----END PRIVATE KEY----- diff --git a/testcases/generator/root/index.txt b/testcases/generator/root/index.txt new file mode 100644 index 0000000..56c7373 --- /dev/null +++ b/testcases/generator/root/index.txt @@ -0,0 +1 @@ +V 391125102225Z 01 unknown /C=US/ST=CT/O=Fake American Radio Relay League/OU=Logbook of the World Mockup/CN=Logbook of the World Production CA Mockup/emailAddress=lotw@example.com diff --git a/testcases/generator/root/index.txt.attr b/testcases/generator/root/index.txt.attr new file mode 100644 index 0000000..8f7e63a --- /dev/null +++ b/testcases/generator/root/index.txt.attr @@ -0,0 +1 @@ +unique_subject = yes diff --git a/testcases/generator/root/serial b/testcases/generator/root/serial new file mode 100644 index 0000000..9e22bcb --- /dev/null +++ b/testcases/generator/root/serial @@ -0,0 +1 @@ +02 diff --git a/testcases/generator/user/user.cert.pem b/testcases/generator/user/user.cert.pem new file mode 100644 index 0000000..6299d6a --- /dev/null +++ b/testcases/generator/user/user.cert.pem @@ -0,0 +1,23 @@ +-----BEGIN CERTIFICATE----- +MIID5DCCAsygAwIBAgIBATANBgkqhkiG9w0BAQsFADCBwDELMAkGA1UEBhMCVVMx +CzAJBgNVBAgMAkNUMSkwJwYDVQQKDCBGYWtlIEFtZXJpY2FuIFJhZGlvIFJlbGF5 +IExlYWd1ZTEkMCIGA1UECwwbTG9nYm9vayBvZiB0aGUgV29ybGQgTW9ja3VwMTIw +MAYDVQQDDClMb2dib29rIG9mIHRoZSBXb3JsZCBQcm9kdWN0aW9uIENBIE1vY2t1 +cDEfMB0GCSqGSIb3DQEJARYQbG90d0BleGFtcGxlLmNvbTAeFw0yMzA2MjIxMDIy +MjVaFw0zNzAyMjgxMDIyMjVaMEsxETAPBgNVBAMMCEpvaG4gRG9lMRUwEwYJKwYB +BAHgPAEBDAZOMENBTEwxHzAdBgkqhkiG9w0BCQEWEGpvaG5AZXhhbXBsZS5jb20w +ggEiMA0GCSqGSIb3DQEBAQUAA4IBDwAwggEKAoIBAQCSxlSePX690qTCbhJ53XQs +UzcqfJgXceSUxzq4JiVgTvbSqjRGQpuHBEAZrUmbiij+GZEnMIErcIhefZt4MBXx +gNp+CI/820VDV1fUAitkawOc8RKqq2jFn7EBBdUTMFL4jSlshjjr+x1KDA3vKpL4 +Pt2HW+oa0Fx7G0Wt7r4BFIhDvpkRGRsVVdt2XF6LhCSJCOOjf59CuXkAVbvCRmac +mYPA3/p0nrLodurrb3cEyVCi9t1Q7M0EFwSV0eyLkPRVhgzr0B9AAXNBnynxzAG+ +I8LlAv4kmilmryWkyfx35Fwes48oVDerSWoHuOi1RR6bZneyqmrZBdHUXWc6wbw/ +AgMBAAGjXTBbMB0GA1UdDgQWBBQ6hJqgn06AAldyLgdcx7ufjJMs6jAJBgNVHRME +AjAAMB8GA1UdIwQYMBaAFHYffR9m6SgxxTvJuyIZ/YJQVtsFMA4GA1UdDwEB/wQE +AwIF4DANBgkqhkiG9w0BAQsFAAOCAQEAkuTC3H28HbvCgL/2OksrOEg8xQnQ+bDo +fRoMlcDhZNOEpCMRYxfuEwXVpkNRJufiJA+XPJg9jKtk+bTDYzp2DBZgeBsJ5C0k +J03hn4z/rCcVMUNoArVE5C+fkZwCBx9hzaJPyYEvwnGbtpyTWPcmfnyeXtzCDj0T +qAGLDtDQw7ERZpj25jsnCPEJN1NmvRxmw4+Tx/1IIxn8s6iWdyUGChHNXK5KJnaU +HUJOVy6k42gjpCKXRDGrwntMyMWUjhWDwjBoUEYeVMspq5I00hptCzMRoVo2CSQC +0PeU3f3qb4L00JzmzHEwa6uNyK0FOjPgxKXIOJUnAQsEWPcmR/i4+A== +-----END CERTIFICATE----- diff --git a/testcases/generator/user/user.csr.pem b/testcases/generator/user/user.csr.pem new file mode 100644 index 0000000..d66f3de --- /dev/null +++ b/testcases/generator/user/user.csr.pem @@ -0,0 +1,16 @@ +-----BEGIN CERTIFICATE REQUEST----- +MIICkDCCAXgCAQAwSzERMA8GA1UEAwwISm9obiBEb2UxHzAdBgkqhkiG9w0BCQEW +EGpvaG5AZXhhbXBsZS5jb20xFTATBgkrBgEEAeA8AQEMBk4wQ0FMTDCCASIwDQYJ +KoZIhvcNAQEBBQADggEPADCCAQoCggEBAJLGVJ49fr3SpMJuEnnddCxTNyp8mBdx +5JTHOrgmJWBO9tKqNEZCm4cEQBmtSZuKKP4ZkScwgStwiF59m3gwFfGA2n4Ij/zb +RUNXV9QCK2RrA5zxEqqraMWfsQEF1RMwUviNKWyGOOv7HUoMDe8qkvg+3Ydb6hrQ +XHsbRa3uvgEUiEO+mREZGxVV23ZcXouEJIkI46N/n0K5eQBVu8JGZpyZg8Df+nSe +suh26utvdwTJUKL23VDszQQXBJXR7IuQ9FWGDOvQH0ABc0GfKfHMAb4jwuUC/iSa +KWavJaTJ/HfkXB6zjyhUN6tJage46LVFHptmd7KqatkF0dRdZzrBvD8CAwEAAaAA +MA0GCSqGSIb3DQEBCwUAA4IBAQBbAnapV2CoymHSx5UVm8EJNJ5jb2BdqCoIylTH +y3dB4rzGuEvH0c7uOZzMxo/z+pQdmyojqOnI21Uc70yTObGrVjoGwz2s6QmsdI3/ +ksom4Mi6TSbBxLg2uj+bsdDhq1pvOAyUrHK6boFeWlhguH5sdSdHTdEr1Q6QL0Nz +LUhiB04PeN+g0jNyehhfVkz9Tgz58A8bbRx6gREUSDJKexKi3nyVhhwNtlDo6aw6 +BgdYoMtb05bkgECvUJZdLczOk9vnKF4Zjv6jIrJF0Us2JB78TH1M8OFXQ+R3da6p +bAt0f2RIZn/xizGvKyhsRXIDV7zFubRea/xPr8T/8B4AdjTa +-----END CERTIFICATE REQUEST----- diff --git a/testcases/generator/user/user.key.pem b/testcases/generator/user/user.key.pem new file mode 100644 index 0000000..7585d4a --- /dev/null +++ b/testcases/generator/user/user.key.pem @@ -0,0 +1,28 @@ +-----BEGIN PRIVATE KEY----- +MIIEvQIBADANBgkqhkiG9w0BAQEFAASCBKcwggSjAgEAAoIBAQCSxlSePX690qTC +bhJ53XQsUzcqfJgXceSUxzq4JiVgTvbSqjRGQpuHBEAZrUmbiij+GZEnMIErcIhe +fZt4MBXxgNp+CI/820VDV1fUAitkawOc8RKqq2jFn7EBBdUTMFL4jSlshjjr+x1K +DA3vKpL4Pt2HW+oa0Fx7G0Wt7r4BFIhDvpkRGRsVVdt2XF6LhCSJCOOjf59CuXkA +VbvCRmacmYPA3/p0nrLodurrb3cEyVCi9t1Q7M0EFwSV0eyLkPRVhgzr0B9AAXNB +nynxzAG+I8LlAv4kmilmryWkyfx35Fwes48oVDerSWoHuOi1RR6bZneyqmrZBdHU +XWc6wbw/AgMBAAECggEAHuFcd0iP7Gcvo/qdp4coxJSjhCxfoXskcQrztz/LWFZ0 +xsDpq6ii6UbDJ8PWO0PXuRJvADRL0PRltJ+vwJs5WqzWC3NIvBX0HiV3xJLKR1/e +jDwKRd83dXDSQFlWSam+oy2r+/nHaxrTwDsGCX5HGrS7ThnQCOEyu/HyeJRE5Jv4 +GtVupY+lQkvI+uV/KZTyAfluCPVPz+MjsOhDlv7oy7NAgjvTN+b/l4mUDFQHkjw7 +8kJvi9mrfYXxY/9TpzzIrLfm9yICdoDe6AegNyOR54sEoFt3vtZlD2BDvmbL/LXu +nBMGHNa72lxtNR2IiSuhCOp2FnJkEwi7qeueE2OG0QKBgQC3za5MoZxu6EMcjm84 +BgquWaIjbFvcRCqg+Zb52VjaMBWVIB7Dy9+lgFN7w/QAQ5NlFGloSID/ZD/app/+ +8mGFSGvD5y+V/Y4fiqQrooX1P6txIaUH8t64QnQqgKz2/gQHb7qyIEkH0Woaaysd +4zSxFx7rPPKoLhP6Kuqdh5P9MQKBgQDMbTwYupAywRUGNMDz2k+Jm11uMSeqNG2/ +hwKzVKFk1FYuYBBcsnPQHn4QQT3OsqiJAfGUOAL0Higmshby2fbDGa4Kd8jN8enW +Myjr7vmJZWEUpUKcnbEofwp5f+BD/QLGQLbbazCmYptug6IxlwemxicFR/PZekup +ecPilnk0bwKBgGBM+nKaBh0xwd/XXLxMphH9Um8e2e5JJNCclJapYt1Gbjho0NWj +HrVWy+a/nzr4LOS70hJaUoP84VvNC20HT0MG07ebjBoY8/rgp+1YxLjfOBMZHp9Q +h5Kg9r5CFt1971x6FKY5NipLdT0MQ1Xwce4LAB8eGsE1CzB6hdwtacMxAoGBAJed +VHsKszPRXCR0L78r5N2sKwk0z7Q+mj74hRo35FOB4EEY4km92IM8ekbX/F02yCSF +GoTRXe9sBl9cqgSHf6qHezssR/PmPYWt/+WsIcqzM+M6BkNd+SyNvFkMbGpAVjRv +fq8Rus1MSPcYDc01tGkOgZY7HTHosAEL3CpLa61lAoGANBly/IdaziEEGJQ1KyoS +srDyrza5Oe+WmLwA7KXqtoOExvS+WGB/HBPRhhdjcDZy4HGgKM0bYgD+3OQwlqtY +ISDNkPJG35htue9qkNoce3cBJnyI4gRB48qnPHTa+5VUrlZrfKfkWSL0rFHCnhTX +jFFhRHTxPN0i192B6JEnlZU= +-----END PRIVATE KEY----- diff --git a/testcases/keys/N0CALL.p12 b/testcases/keys/N0CALL.p12 new file mode 100644 index 0000000000000000000000000000000000000000..3a440a1e5a69251ca6c86c6830e06d01e7a8d455 GIT binary patch literal 4195 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 literal 0 HcmV?d00001 diff --git a/testcases/keys/cache/chain/mockup.der b/testcases/keys/cache/chain/mockup.der new file mode 100644 index 0000000000000000000000000000000000000000..a3105e60abb98aa2dcb13c346497d33f298ec479 GIT binary patch literal 1395 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 kg>N!2kdN literal 0 HcmV?d00001 diff --git a/testcases/results/.gitkeep b/testcases/results/.gitkeep new file mode 100644 index 0000000..e69de29 diff --git a/version.txt b/version.txt index 5c4511c..7d6b3eb 100644 --- a/version.txt +++ b/version.txt @@ -1 +1 @@ -0.0.7 \ No newline at end of file +0.0.8 \ No newline at end of file