From 37e3d2aac1a3493171b28aa5c7344833aa5a8303 Mon Sep 17 00:00:00 2001 From: Paul Gardiner Date: Fri, 19 Jan 2018 12:14:20 +0000 Subject: Signature support: separate pkcs7 specifics into a separate file. Previously, pdf-pkcs7.c contained mishmash of functions required for creating and checking signatures, with no separation between the parts relating to pdf and those relating to pkcs7. This commit introduces pdf_signature.c which contains the pdf specifics, leaving pdf-pkcs7.c to be purely pkcs7 functions. This should more easily allow the use of pkcs7 solutions other than openssl. The pkcs7 api is declared in pdf-pkcs7.h. It is entirely free of mupdf specifics, other than using an fz_stream to specify the bytes to be hashed. --- include/mupdf/pdf.h | 2 ++ include/mupdf/pdf/crypt.h | 30 +---------------------- include/mupdf/pdf/document.h | 4 ++-- include/mupdf/pdf/field.h | 2 +- include/mupdf/pdf/pdf-pkcs7.h | 56 +++++++++++++++++++++++++++++++++++++++++++ include/mupdf/pdf/xref.h | 2 +- 6 files changed, 63 insertions(+), 33 deletions(-) create mode 100644 include/mupdf/pdf/pdf-pkcs7.h (limited to 'include') diff --git a/include/mupdf/pdf.h b/include/mupdf/pdf.h index eab70ee9..f593e680 100644 --- a/include/mupdf/pdf.h +++ b/include/mupdf/pdf.h @@ -31,6 +31,8 @@ extern "C" { #include "mupdf/pdf/clean.h" +#include "mupdf/pdf/pdf-pkcs7.h" + #ifdef __cplusplus } #endif diff --git a/include/mupdf/pdf/crypt.h b/include/mupdf/pdf/crypt.h index 555a8d25..59513acc 100644 --- a/include/mupdf/pdf/crypt.h +++ b/include/mupdf/pdf/crypt.h @@ -21,35 +21,7 @@ unsigned char *pdf_crypt_key(fz_context *ctx, pdf_document *doc); void pdf_print_crypt(fz_context *ctx, fz_output *out, pdf_crypt *crypt); -typedef enum -{ - SignatureError_Okay, - SignatureError_NoSignatures, - SignatureError_NoCertificate, - SignatureError_DocumentChanged, - SignatureError_SelfSigned, - SignatureError_SelfSignedInChain, - SignatureError_NotTrusted, - SignatureError_Unknown -} SignatureError; - -typedef struct pdf_designated_name_s -{ - char *cn; - char *o; - char *ou; - char *email; - char *c; -} -pdf_designated_name; - -void pdf_drop_designated_name(fz_context *ctx, pdf_designated_name *dn); - -pdf_signer *pdf_read_pfx(fz_context *ctx, const char *sigfile, const char *password); -pdf_signer *pdf_keep_signer(fz_context *ctx, pdf_signer *signer); -void pdf_drop_signer(fz_context *ctx, pdf_signer *signer); -pdf_designated_name *pdf_signer_designated_name(fz_context *ctx, pdf_signer *signer); -void pdf_write_digest(fz_context *ctx, fz_output *out, pdf_obj *byte_range, int digest_offset, int digest_length, pdf_signer *signer); +void pdf_write_digest(fz_context *ctx, fz_output *out, pdf_obj *byte_range, int digest_offset, int digest_length, pdf_pkcs7_signer *signer); /* pdf_signature_widget_byte_range: retrieve the byte range for a signature widget diff --git a/include/mupdf/pdf/document.h b/include/mupdf/pdf/document.h index ebd04401..ef861145 100644 --- a/include/mupdf/pdf/document.h +++ b/include/mupdf/pdf/document.h @@ -535,7 +535,7 @@ void pdf_update_page(fz_context *ctx, pdf_page *page); */ int pdf_has_unsaved_changes(fz_context *ctx, pdf_document *doc); -typedef struct pdf_signer_s pdf_signer; +typedef struct pdf_pkcs7_signer_s pdf_pkcs7_signer; /* Unsaved signature fields */ typedef struct pdf_unsaved_sig_s pdf_unsaved_sig; @@ -547,7 +547,7 @@ struct pdf_unsaved_sig_s int byte_range_end; int contents_start; int contents_end; - pdf_signer *signer; + pdf_pkcs7_signer *signer; pdf_unsaved_sig *next; }; diff --git a/include/mupdf/pdf/field.h b/include/mupdf/pdf/field.h index baf650f4..c3509938 100644 --- a/include/mupdf/pdf/field.h +++ b/include/mupdf/pdf/field.h @@ -45,7 +45,7 @@ void pdf_field_set_border_style(fz_context *ctx, pdf_document *doc, pdf_obj *fie void pdf_field_set_button_caption(fz_context *ctx, pdf_document *doc, pdf_obj *field, const char *text); void pdf_field_set_fill_color(fz_context *ctx, pdf_document *doc, pdf_obj *field, pdf_obj *col); void pdf_field_set_text_color(fz_context *ctx, pdf_document *doc, pdf_obj *field, pdf_obj *col); -void pdf_signature_set_value(fz_context *ctx, pdf_document *doc, pdf_obj *field, pdf_signer *signer); +void pdf_signature_set_value(fz_context *ctx, pdf_document *doc, pdf_obj *field, pdf_pkcs7_signer *signer); int pdf_field_display(fz_context *ctx, pdf_document *doc, pdf_obj *field); char *pdf_field_name(fz_context *ctx, pdf_document *doc, pdf_obj *field); void pdf_field_set_display(fz_context *ctx, pdf_document *doc, pdf_obj *field, int d); diff --git a/include/mupdf/pdf/pdf-pkcs7.h b/include/mupdf/pdf/pdf-pkcs7.h new file mode 100644 index 00000000..8f11a6b4 --- /dev/null +++ b/include/mupdf/pdf/pdf-pkcs7.h @@ -0,0 +1,56 @@ +#ifndef MUPDF_PDF_PKCS7_H +#define MUPDF_PDF_PKCS7_H + +typedef enum +{ + SignatureError_Okay, + SignatureError_NoSignatures, + SignatureError_NoCertificate, + SignatureError_DocumentChanged, + SignatureError_SelfSigned, + SignatureError_SelfSignedInChain, + SignatureError_NotTrusted, + SignatureError_Unknown +} SignatureError; + +typedef struct pdf_pkcs7_designated_name_s +{ + char *cn; + char *o; + char *ou; + char *email; + char *c; +} +pdf_pkcs7_designated_name; + +/* Check a signature's digest against ranges of bytes drawn from a stream */ +SignatureError pdf_pkcs7_check_digest(fz_context *ctx, fz_stream *stm, char *sig, int sig_len, int (*byte_range)[2], int byte_range_len); + +/* Check a singature's certificate is trusted */ +SignatureError pdf_pkcs7_check_certificate(char *sig, int sig_len); + +/* Obtain the designated name information from signature's certificate */ +pdf_pkcs7_designated_name *pdf_cert_designated_name(fz_context *ctx, char *sig, int sig_len); + +/* Free the resources associated with designated name information */ +void pdf_pkcs7_drop_designated_name(fz_context *ctx, pdf_pkcs7_designated_name *dn); + +/* Read the certificate and private key from a pfx file, holding it as an opaque structure */ +pdf_pkcs7_signer *pdf_pkcs7_read_pfx(fz_context *ctx, const char *pfile, const char *pw); + +/* Increment the reference count for a signer object */ +pdf_pkcs7_signer *pdf_pkcs7_keep_signer(fz_context *ctx, pdf_pkcs7_signer *signer); + +/* Drop a reference for a signer object */ +void pdf_pkcs7_drop_signer(fz_context *ctx, pdf_pkcs7_signer *signer); + +/* Obtain the designated name information from a signer object */ +pdf_pkcs7_designated_name *pdf_pkcs7_signer_designated_name(fz_context *ctx, pdf_pkcs7_signer *signer); + +/* Create a signature based on ranges of bytes drawn from a steam */ +int pdf_pkcs7_create_digest(fz_context *ctx, fz_stream *in, int brange[][2], int brange_len, pdf_pkcs7_signer *signer, unsigned char *digest, int *digest_len); + +/* Report whether pkcs7 is supported in the current build */ +int pdf_pkcs7_supported(fz_context *ctx); + +#endif diff --git a/include/mupdf/pdf/xref.h b/include/mupdf/pdf/xref.h index de23147e..87a84efe 100644 --- a/include/mupdf/pdf/xref.h +++ b/include/mupdf/pdf/xref.h @@ -105,7 +105,7 @@ pdf_xref_entry *pdf_get_xref_entry(fz_context *ctx, pdf_document *doc, int i); void pdf_replace_xref(fz_context *ctx, pdf_document *doc, pdf_xref_entry *entries, int n); void pdf_xref_ensure_incremental_object(fz_context *ctx, pdf_document *doc, int num); int pdf_xref_is_incremental(fz_context *ctx, pdf_document *doc, int num); -void pdf_xref_store_unsaved_signature(fz_context *ctx, pdf_document *doc, pdf_obj *field, pdf_signer *signer); +void pdf_xref_store_unsaved_signature(fz_context *ctx, pdf_document *doc, pdf_obj *field, pdf_pkcs7_signer *signer); int pdf_xref_obj_is_unsaved_signature(pdf_document *doc, pdf_obj *obj); void pdf_repair_xref(fz_context *ctx, pdf_document *doc); -- cgit v1.2.3