diff options
author | Nikos Mavrogiannopoulos <nmav@redhat.com> | 2015-06-16 12:18:55 +0200 |
---|---|---|
committer | Nikos Mavrogiannopoulos <nmav@redhat.com> | 2015-06-16 12:29:16 +0200 |
commit | 50c330960e53060a685b7ea9818c1bd29c490be8 (patch) | |
tree | 887eb6da63325e0b1966f78cd99458133d393712 | |
parent | cffd6e92d39b1b6252eb09c098fea70a533afeef (diff) | |
download | gnutls-50c330960e53060a685b7ea9818c1bd29c490be8.tar.gz |
Added gnutls_pkcs7_print()
-rw-r--r-- | lib/includes/gnutls/pkcs7.h | 3 | ||||
-rw-r--r-- | lib/libgnutls.map | 1 | ||||
-rw-r--r-- | lib/x509/Makefile.am | 3 | ||||
-rw-r--r-- | lib/x509/pkcs7.c | 1 | ||||
-rw-r--r-- | lib/x509/pkcs7_output.c | 189 |
5 files changed, 196 insertions, 1 deletions
diff --git a/lib/includes/gnutls/pkcs7.h b/lib/includes/gnutls/pkcs7.h index dd9f2d5304..f0088953ef 100644 --- a/lib/includes/gnutls/pkcs7.h +++ b/lib/includes/gnutls/pkcs7.h @@ -120,6 +120,9 @@ int gnutls_pkcs7_get_crl_raw2(gnutls_pkcs7_t pkcs7, int indx, gnutls_datum_t *crl); +int gnutls_pkcs7_print(gnutls_pkcs7_t pkcs7, + gnutls_certificate_print_formats_t format, + gnutls_datum_t * out); /* *INDENT-OFF* */ #ifdef __cplusplus diff --git a/lib/libgnutls.map b/lib/libgnutls.map index b0ae35ceec..a36df5a3c9 100644 --- a/lib/libgnutls.map +++ b/lib/libgnutls.map @@ -1037,6 +1037,7 @@ GNUTLS_3_4 gnutls_pkcs7_attrs_deinit; gnutls_pkcs7_add_attr; gnutls_pkcs7_get_attr; + gnutls_pkcs7_print; local: *; }; diff --git a/lib/x509/Makefile.am b/lib/x509/Makefile.am index b8249a579a..f1a88c3e2f 100644 --- a/lib/x509/Makefile.am +++ b/lib/x509/Makefile.am @@ -61,7 +61,8 @@ libgnutls_x509_la_SOURCES = \ verify-high2.c \ verify-high.h \ x509_ext.c \ - email-verify.c + email-verify.c \ + pkcs7_output.c if ENABLE_OCSP libgnutls_x509_la_SOURCES += ocsp.c ocsp_output.c diff --git a/lib/x509/pkcs7.c b/lib/x509/pkcs7.c index e84079f91c..171b40b2f6 100644 --- a/lib/x509/pkcs7.c +++ b/lib/x509/pkcs7.c @@ -2043,3 +2043,4 @@ int gnutls_pkcs7_sign(gnutls_pkcs7_t pkcs7, gnutls_free(signature.data); return ret; } + diff --git a/lib/x509/pkcs7_output.c b/lib/x509/pkcs7_output.c new file mode 100644 index 0000000000..3918d00d50 --- /dev/null +++ b/lib/x509/pkcs7_output.c @@ -0,0 +1,189 @@ +/* + * Copyright (C) 2015 Red Hat, Inc. + * + * Author: Nikos Mavrogiannopoulos + * + * This file is part of GnuTLS. + * + * The GnuTLS is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public License + * as published by the Free Software Foundation; either version 2.1 of + * the License, or (at your option) any later version. + * + * This library 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 + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public License + * along with this program. If not, see <http://www.gnu.org/licenses/> + * + */ + +#include <gnutls_int.h> +#include <common.h> +#include <gnutls_x509.h> +#include <x509_int.h> +#include <gnutls_num.h> +#include <gnutls_errors.h> +#include <extras/randomart.h> +#include <c-ctype.h> +#include <gnutls-idna.h> + +#define addf _gnutls_buffer_append_printf +#define adds _gnutls_buffer_append_str + +static void print_dn(gnutls_buffer_st *str, const char *prefix, const gnutls_datum_t *raw) +{ + gnutls_x509_dn_t dn = NULL; + gnutls_datum_t output = {NULL, 0}; + int ret; + + ret = gnutls_x509_dn_init(&dn); + if (ret < 0) { + addf(str, "%s: [error]\n", prefix); + return; + } + + ret = gnutls_x509_dn_import(dn, raw); + if (ret < 0) { + addf(str, "%s: [error]\n", prefix); + goto cleanup; + } + + ret = gnutls_x509_dn_get_str(dn, &output); + if (ret < 0) { + addf(str, "%s: [error]\n", prefix); + goto cleanup; + } + + addf(str, "%s: %s\n", prefix, output.data); + + cleanup: + gnutls_x509_dn_deinit(dn); + gnutls_free(output.data); +} + +static void print_raw(gnutls_buffer_st *str, const char *prefix, const gnutls_datum_t *raw) +{ + char data[512]; + size_t data_size; + int ret; + + if (raw->data == NULL || raw->size == 0) + return; + + data_size = sizeof(data); + ret = gnutls_hex_encode(raw, data, &data_size); + if (ret < 0) { + addf(str, "%s: [error]\n", prefix); + return; + } + + addf(str, "%s: %s\n", prefix, data); +} + +static void print_pkcs7_info(gnutls_pkcs7_signature_info_st *info, gnutls_buffer_st *str) +{ + unsigned i; + char *oid; + gnutls_datum_t data; + char prefix[128]; + char s[42]; + size_t max; + int ret; + + print_dn(str, "\tSigner's issuer DN", &info->issuer_dn); + print_raw(str, "\tSigner's serial", &info->signer_serial); + print_raw(str, "\tSigner's issuer key ID", &info->issuer_keyid); + if (info->signing_time != -1) { + struct tm t; + if (gmtime_r(&info->signing_time, &t) == NULL) { + addf(str, "error: gmtime_r (%ld)\n", (unsigned long)info->signing_time); + } else { + max = sizeof(s); + if (strftime(s, max, "%a %b %d %H:%M:%S UTC %Y", &t) == 0) { + addf(str, "error: strftime (%ld)\n", (unsigned long)info->signing_time); + } else { + addf(str, "\tSigning time: %s\n", s); + } + } + } + + addf(str, "\tSignature Algorithm: %s\n", gnutls_sign_get_name(info->algo)); + + if (info->signed_attrs) { + for (i=0;;i++) { + ret = gnutls_pkcs7_get_attr(info->signed_attrs, i, &oid, &data, 0); + if (ret < 0) + break; + if (i==0) + addf(str, "\tSigned Attributes:\n"); + + snprintf(prefix, sizeof(prefix), "\t\t%s", oid); + print_raw(str, prefix, &data); + gnutls_free(data.data); + } + } + if (info->unsigned_attrs) { + for (i=0;;i++) { + ret = gnutls_pkcs7_get_attr(info->unsigned_attrs, i, &oid, &data, 0); + if (ret < 0) + break; + if (i==0) + addf(str, "\tUnsigned Attributes:\n"); + + snprintf(prefix, sizeof(prefix), "\t\t%s", oid); + print_raw(str, prefix, &data); + gnutls_free(data.data); + } + } + adds(str, "\n"); +} + +/** + * gnutls_pkcs7_crt_print: + * @pkcs7: The PKCS7 struct to be printed + * @format: Indicate the format to use + * @out: Newly allocated datum with null terminated string. + * + * This function will pretty print a signed PKCS #7 structure, suitable for + * display to a human. + * + * Currently the supported formats are %GNUTLS_CRT_PRINT_FULL and + * %GNUTLS_CRT_PRINT_COMPACT. + * + * The output @out needs to be deallocated using gnutls_free(). + * + * Returns: On success, %GNUTLS_E_SUCCESS (0) is returned, otherwise a + * negative error value. + **/ +int gnutls_pkcs7_print(gnutls_pkcs7_t pkcs7, + gnutls_certificate_print_formats_t format, + gnutls_datum_t * out) +{ + unsigned i; + int ret; + gnutls_pkcs7_signature_info_st info; + gnutls_buffer_st str; + + _gnutls_buffer_init(&str); + + for (i=0;;i++) { + if (i==0) + addf(&str, "Signers:\n"); + + ret = gnutls_pkcs7_get_signature_info(pkcs7, i, &info); + if (ret < 0) + break; + + print_pkcs7_info(&info, &str); + } + + if (format == GNUTLS_CRT_PRINT_FULL) { + addf(&str, "Number of certificates present: %u\n", gnutls_pkcs7_get_crt_count(pkcs7)); + addf(&str, "Number of CRLs present: %u\n", gnutls_pkcs7_get_crl_count(pkcs7)); + } + + return _gnutls_buffer_to_datum(&str, out, 1); +} |