diff options
Diffstat (limited to 'src/pki/commands')
-rw-r--r-- | src/pki/commands/acert.c | 5 | ||||
-rw-r--r-- | src/pki/commands/gen.c | 2 | ||||
-rw-r--r-- | src/pki/commands/issue.c | 5 | ||||
-rw-r--r-- | src/pki/commands/keyid.c | 1 | ||||
-rw-r--r-- | src/pki/commands/pkcs7.c | 1 | ||||
-rw-r--r-- | src/pki/commands/print.c | 1 | ||||
-rw-r--r-- | src/pki/commands/pub.c | 2 | ||||
-rw-r--r-- | src/pki/commands/req.c | 5 | ||||
-rw-r--r-- | src/pki/commands/self.c | 5 | ||||
-rw-r--r-- | src/pki/commands/signcrl.c | 4 | ||||
-rw-r--r-- | src/pki/commands/verify.c | 135 |
11 files changed, 107 insertions, 59 deletions
diff --git a/src/pki/commands/acert.c b/src/pki/commands/acert.c index d49365db5..185aa40b4 100644 --- a/src/pki/commands/acert.c +++ b/src/pki/commands/acert.c @@ -53,8 +53,7 @@ static int acert() case 'h': goto usage; case 'g': - digest = enum_from_name(hash_algorithm_short_names, arg); - if (digest == -1) + if (!enum_from_name(hash_algorithm_short_names, arg, &digest)) { error = "invalid --digest type"; goto usage; @@ -197,6 +196,7 @@ static int acert() } else { + set_file_mode(stdin, CERT_ASN1_DER); if (!chunk_from_fd(0, &encoding)) { fprintf(stderr, "%s: ", strerror(errno)); @@ -233,6 +233,7 @@ static int acert() error = "encoding attribute certificate failed"; goto end; } + set_file_mode(stdout, form); if (fwrite(encoding.ptr, encoding.len, 1, stdout) != 1) { error = "writing attribute certificate key failed"; diff --git a/src/pki/commands/gen.c b/src/pki/commands/gen.c index b74be7d98..ce28a0971 100644 --- a/src/pki/commands/gen.c +++ b/src/pki/commands/gen.c @@ -133,6 +133,7 @@ static int gen() return 1; } key->destroy(key); + set_file_mode(stdout, form); if (fwrite(encoding.ptr, encoding.len, 1, stdout) != 1) { fprintf(stderr, "writing private key failed\n"); @@ -163,4 +164,3 @@ static void __attribute__ ((constructor))reg() } }); } - diff --git a/src/pki/commands/issue.c b/src/pki/commands/issue.c index d03326e3d..aaa2c2ff7 100644 --- a/src/pki/commands/issue.c +++ b/src/pki/commands/issue.c @@ -106,8 +106,7 @@ static int issue() } continue; case 'g': - digest = enum_from_name(hash_algorithm_short_names, arg); - if (digest == -1) + if (!enum_from_name(hash_algorithm_short_names, arg, &digest)) { error = "invalid --digest type"; goto usage; @@ -403,6 +402,7 @@ static int issue() { chunk_t chunk; + set_file_mode(stdin, CERT_ASN1_DER); if (!chunk_from_fd(0, &chunk)) { fprintf(stderr, "%s: ", strerror(errno)); @@ -501,6 +501,7 @@ static int issue() error = "encoding certificate failed"; goto end; } + set_file_mode(stdout, form); if (fwrite(encoding.ptr, encoding.len, 1, stdout) != 1) { error = "writing certificate key failed"; diff --git a/src/pki/commands/keyid.c b/src/pki/commands/keyid.c index 64bb3cc2c..c3ac0c288 100644 --- a/src/pki/commands/keyid.c +++ b/src/pki/commands/keyid.c @@ -91,6 +91,7 @@ static int keyid() { chunk_t chunk; + set_file_mode(stdin, CERT_ASN1_DER); if (!chunk_from_fd(0, &chunk)) { fprintf(stderr, "reading input failed: %s\n", strerror(errno)); diff --git a/src/pki/commands/pkcs7.c b/src/pki/commands/pkcs7.c index 6c75693ab..28bcd1397 100644 --- a/src/pki/commands/pkcs7.c +++ b/src/pki/commands/pkcs7.c @@ -58,6 +58,7 @@ static bool write_to_stream(FILE *stream, chunk_t data) { size_t len, total = 0; + set_file_mode(stream, CERT_ASN1_DER); while (total < data.len) { len = fwrite(data.ptr + total, 1, data.len - total, stream); diff --git a/src/pki/commands/print.c b/src/pki/commands/print.c index 15ace035d..fb07169bf 100644 --- a/src/pki/commands/print.c +++ b/src/pki/commands/print.c @@ -604,6 +604,7 @@ static int print() { chunk_t chunk; + set_file_mode(stdin, CERT_ASN1_DER); if (!chunk_from_fd(0, &chunk)) { fprintf(stderr, "reading input failed: %s\n", strerror(errno)); diff --git a/src/pki/commands/pub.c b/src/pki/commands/pub.c index 260044c4e..b8d2f701d 100644 --- a/src/pki/commands/pub.c +++ b/src/pki/commands/pub.c @@ -110,6 +110,7 @@ static int pub() { chunk_t chunk; + set_file_mode(stdin, CERT_ASN1_DER); if (!chunk_from_fd(0, &chunk)) { fprintf(stderr, "reading input failed: %s\n", strerror(errno)); @@ -163,6 +164,7 @@ static int pub() return 1; } public->destroy(public); + set_file_mode(stdout, form); if (fwrite(encoding.ptr, encoding.len, 1, stdout) != 1) { fprintf(stderr, "writing public key failed\n"); diff --git a/src/pki/commands/req.c b/src/pki/commands/req.c index 5b2c128b7..023683569 100644 --- a/src/pki/commands/req.c +++ b/src/pki/commands/req.c @@ -64,8 +64,7 @@ static int req() } continue; case 'g': - digest = enum_from_name(hash_algorithm_short_names, arg); - if (digest == -1) + if (!enum_from_name(hash_algorithm_short_names, arg, &digest)) { error = "invalid --digest type"; goto usage; @@ -119,6 +118,7 @@ static int req() { chunk_t chunk; + set_file_mode(stdin, CERT_ASN1_DER); if (!chunk_from_fd(0, &chunk)) { fprintf(stderr, "reading private key failed: %s\n", strerror(errno)); @@ -151,6 +151,7 @@ static int req() error = "encoding certificate request failed"; goto end; } + set_file_mode(stdout, form); if (fwrite(encoding.ptr, encoding.len, 1, stdout) != 1) { error = "writing certificate request failed"; diff --git a/src/pki/commands/self.c b/src/pki/commands/self.c index a35a42b89..daefcdc10 100644 --- a/src/pki/commands/self.c +++ b/src/pki/commands/self.c @@ -95,8 +95,7 @@ static int self() } continue; case 'g': - digest = enum_from_name(hash_algorithm_short_names, arg); - if (digest == -1) + if (!enum_from_name(hash_algorithm_short_names, arg, &digest)) { error = "invalid --digest type"; goto usage; @@ -293,6 +292,7 @@ static int self() { chunk_t chunk; + set_file_mode(stdin, CERT_ASN1_DER); if (!chunk_from_fd(0, &chunk)) { fprintf(stderr, "%s: ", strerror(errno)); @@ -361,6 +361,7 @@ static int self() error = "encoding certificate failed"; goto end; } + set_file_mode(stdout, form); if (fwrite(encoding.ptr, encoding.len, 1, stdout) != 1) { error = "writing certificate key failed"; diff --git a/src/pki/commands/signcrl.c b/src/pki/commands/signcrl.c index c9eebbf59..e5f49efe2 100644 --- a/src/pki/commands/signcrl.c +++ b/src/pki/commands/signcrl.c @@ -142,8 +142,7 @@ static int sign_crl() case 'h': goto usage; case 'g': - digest = enum_from_name(hash_algorithm_short_names, arg); - if (digest == -1) + if (!enum_from_name(hash_algorithm_short_names, arg, &digest)) { error = "invalid --digest type"; goto usage; @@ -406,6 +405,7 @@ static int sign_crl() error = "encoding CRL failed"; goto error; } + set_file_mode(stdout, form); if (fwrite(encoding.ptr, encoding.len, 1, stdout) != 1) { error = "writing CRL failed"; diff --git a/src/pki/commands/verify.c b/src/pki/commands/verify.c index f30dda94d..8cc633a95 100644 --- a/src/pki/commands/verify.c +++ b/src/pki/commands/verify.c @@ -19,32 +19,53 @@ #include <credentials/certificates/certificate.h> #include <credentials/certificates/x509.h> +#include <credentials/sets/mem_cred.h> /** * Verify a certificate signature */ static int verify() { - certificate_t *cert, *ca; - char *file = NULL, *cafile = NULL; - bool good = FALSE; - char *arg; + bool trusted = FALSE, valid = FALSE, revoked = FALSE; + bool has_ca = FALSE, online = FALSE; + certificate_t *cert; + enumerator_t *enumerator; + auth_cfg_t *auth; + mem_cred_t *creds; + char *arg, *file = NULL; + + creds = mem_cred_create(); + lib->credmgr->add_set(lib->credmgr, &creds->set); while (TRUE) { switch (command_getopt(&arg)) { case 'h': + creds->destroy(creds); return command_usage(NULL); case 'i': file = arg; continue; case 'c': - cafile = arg; + cert = lib->creds->create(lib->creds, + CRED_CERTIFICATE, CERT_X509, + BUILD_FROM_FILE, arg, BUILD_END); + if (!cert) + { + fprintf(stderr, "parsing CA certificate failed\n"); + goto end; + } + has_ca = TRUE; + creds->add_cert(creds, TRUE, cert); + continue; + case 'o': + online = TRUE; continue; case EOF: break; default: + creds->destroy(creds); return command_usage("invalid --verify option"); } break; @@ -59,10 +80,11 @@ static int verify() { chunk_t chunk; + set_file_mode(stdin, CERT_ASN1_DER); if (!chunk_from_fd(0, &chunk)) { fprintf(stderr, "reading certificate failed: %s\n", strerror(errno)); - return 1; + goto end; } cert = lib->creds->create(lib->creds, CRED_CERTIFICATE, CERT_X509, BUILD_BLOB, chunk, BUILD_END); @@ -71,60 +93,76 @@ static int verify() if (!cert) { fprintf(stderr, "parsing certificate failed\n"); - return 1; - } - if (cafile) - { - ca = lib->creds->create(lib->creds, CRED_CERTIFICATE, CERT_X509, - BUILD_FROM_FILE, cafile, BUILD_END); - if (!ca) - { - fprintf(stderr, "parsing CA certificate failed\n"); - return 1; - } + goto end; } - else - { - ca = cert; - } - if (cert->issued_by(cert, ca, NULL)) + creds->add_cert(creds, !has_ca, cert); + + enumerator = lib->credmgr->create_trusted_enumerator(lib->credmgr, + KEY_ANY, cert->get_subject(cert), online); + if (enumerator->enumerate(enumerator, &cert, &auth)) { + trusted = TRUE; if (cert->get_validity(cert, NULL, NULL, NULL)) { - if (cafile) - { - if (ca->get_validity(ca, NULL, NULL, NULL)) - { - printf("signature good, certificates valid\n"); - good = TRUE; - } - else - { - printf("signature good, CA certificates not valid now\n"); - } - } - else - { - printf("signature good, certificate valid\n"); - good = TRUE; - } + printf("certificate trusted, lifetimes valid"); + valid = TRUE; } else { - printf("certificate not valid now\n"); + printf("certificate trusted, but no valid lifetime"); } + if (online) + { + switch ((uintptr_t)auth->get(auth, AUTH_RULE_CRL_VALIDATION)) + { + case VALIDATION_GOOD: + printf(", certificate not revoked"); + break; + case VALIDATION_SKIPPED: + printf(", no revocation information"); + break; + case VALIDATION_STALE: + printf(", revocation information stale"); + break; + case VALIDATION_FAILED: + printf(", revocation checking failed"); + break; + case VALIDATION_ON_HOLD: + printf(", certificate revocation on hold"); + revoked = TRUE; + break; + case VALIDATION_REVOKED: + printf(", certificate revoked"); + revoked = TRUE; + break; + } + } + printf("\n"); } - else + enumerator->destroy(enumerator); + + if (!trusted) { - printf("signature invalid\n"); + printf("certificate untrusted\n"); } - if (cafile) + +end: + lib->credmgr->remove_set(lib->credmgr, &creds->set); + creds->destroy(creds); + + if (!trusted) { - ca->destroy(ca); + return 1; } - cert->destroy(cert); - - return good ? 0 : 2; + if (!valid) + { + return 2; + } + if (revoked) + { + return 3; + } + return 0; } /** @@ -139,7 +177,8 @@ static void __attribute__ ((constructor))reg() { {"help", 'h', 0, "show usage information"}, {"in", 'i', 1, "X.509 certificate to verify, default: stdin"}, - {"cacert", 'c', 1, "CA certificate, default: verify self signed"}, + {"cacert", 'c', 1, "CA certificate for trustchain verification"}, + {"online", 'o', 0, "enable online CRL/OCSP revocation checking"}, } }); } |