poppler/Form.cc | 9 +++++---- poppler/Form.h | 5 +++-- poppler/PDFDoc.cc | 4 ++-- poppler/PDFDoc.h | 2 +- utils/pdfsig.cc | 2 +- 5 files changed, 12 insertions(+), 10 deletions(-)
New commits: commit e1613d72c8440b79c0d8c5822bec99eca7fa29af Author: Albert Astals Cid <[email protected]> Date: Wed Dec 29 17:40:11 2021 +0100 pdfsig: Fix signing documents with owner/user password diff --git a/poppler/Form.cc b/poppler/Form.cc index 209b6cfb..f42801b4 100644 --- a/poppler/Form.cc +++ b/poppler/Form.cc @@ -573,7 +573,8 @@ static bool hashFileRange(FILE *f, SignatureHandler *handler, Goffset start, Gof } #endif -bool FormWidgetSignature::signDocument(const char *saveFilename, const char *certNickname, const char *digestName, const char *password, const GooString *reason, const GooString *location) +bool FormWidgetSignature::signDocument(const char *saveFilename, const char *certNickname, const char *digestName, const char *password, const GooString *reason, const GooString *location, const GooString *ownerPassword, + const GooString *userPassword) { #ifdef ENABLE_NSS3 if (!certNickname) { @@ -612,7 +613,7 @@ bool FormWidgetSignature::signDocument(const char *saveFilename, const char *cer // Get start/end offset of signature object in the saved PDF Goffset objStart, objEnd; - if (!getObjectStartEnd(fname, vref.num, &objStart, &objEnd)) { + if (!getObjectStartEnd(fname, vref.num, &objStart, &objEnd, ownerPassword, userPassword)) { fprintf(stderr, "signDocument: unable to get signature object offsets\n"); } @@ -660,9 +661,9 @@ bool FormWidgetSignature::signDocument(const char *saveFilename, const char *cer } // Get start and end file position of objNum in the PDF named filename. -bool FormWidgetSignature::getObjectStartEnd(GooString *filename, int objNum, Goffset *objStart, Goffset *objEnd) +bool FormWidgetSignature::getObjectStartEnd(GooString *filename, int objNum, Goffset *objStart, Goffset *objEnd, const GooString *ownerPassword, const GooString *userPassword) { - PDFDoc newDoc(filename); + PDFDoc newDoc(filename, ownerPassword, userPassword); if (!newDoc.isOk()) return false; diff --git a/poppler/Form.h b/poppler/Form.h index 61174e83..9f98c02e 100644 --- a/poppler/Form.h +++ b/poppler/Form.h @@ -310,7 +310,8 @@ public: // field "ByteRange" in the dictionary "V". // Arguments reason and location are UTF-16 big endian strings with BOM. An empty string and nullptr are acceptable too. // Returns success. - bool signDocument(const char *filename, const char *certNickname, const char *digestName, const char *password, const GooString *reason = nullptr, const GooString *location = nullptr); + bool signDocument(const char *filename, const char *certNickname, const char *digestName, const char *password, const GooString *reason = nullptr, const GooString *location = nullptr, const GooString *ownerPassword = nullptr, + const GooString *userPassword = nullptr); // checks the length encoding of the signature and returns the hex encoded signature // if the check passed (and the checked file size as output parameter in checkedFileSize) @@ -321,7 +322,7 @@ public: private: bool createSignature(Object &vObj, Ref vRef, const GooString &name, const GooString *signature, const GooString *reason = nullptr, const GooString *location = nullptr); - bool getObjectStartEnd(GooString *filename, int objNum, Goffset *objStart, Goffset *objEnd); + bool getObjectStartEnd(GooString *filename, int objNum, Goffset *objStart, Goffset *objEnd, const GooString *ownerPassword, const GooString *userPassword); bool updateOffsets(FILE *f, Goffset objStart, Goffset objEnd, Goffset *sigStart, Goffset *sigEnd, Goffset *fileSize); bool updateSignature(FILE *f, Goffset sigStart, Goffset sigEnd, const GooString *signature); diff --git a/poppler/PDFDoc.cc b/poppler/PDFDoc.cc index dc1f01b9..90b431ad 100644 --- a/poppler/PDFDoc.cc +++ b/poppler/PDFDoc.cc @@ -2130,7 +2130,7 @@ bool PDFDoc::hasJavascript() bool PDFDoc::sign(const char *saveFilename, const char *certNickname, const char *password, GooString *partialFieldName, int page, const PDFRectangle &rect, const GooString &signatureText, const GooString &signatureTextLeft, double fontSize, std::unique_ptr<AnnotColor> &&fontColor, double borderWidth, std::unique_ptr<AnnotColor> &&borderColor, std::unique_ptr<AnnotColor> &&backgroundColor, const GooString *reason, const GooString *location, - const std::string &imagePath) + const std::string &imagePath, const GooString *ownerPassword, const GooString *userPassword) { ::Page *destPage = getPage(page); if (destPage == nullptr) { @@ -2192,7 +2192,7 @@ bool PDFDoc::sign(const char *saveFilename, const char *certNickname, const char FormWidgetSignature *fws = dynamic_cast<FormWidgetSignature *>(formWidget); if (fws) { - const bool res = fws->signDocument(saveFilename, certNickname, "SHA256", password, reason, location); + const bool res = fws->signDocument(saveFilename, certNickname, "SHA256", password, reason, location, ownerPassword, userPassword); // Now remove the signature stuff in case the user wants to continue editing stuff // So the document object is clean diff --git a/poppler/PDFDoc.h b/poppler/PDFDoc.h index 23f9cd28..0a831dc1 100644 --- a/poppler/PDFDoc.h +++ b/poppler/PDFDoc.h @@ -337,7 +337,7 @@ public: // sign() takes ownership of partialFieldName. bool sign(const char *saveFilename, const char *certNickname, const char *password, GooString *partialFieldName, int page, const PDFRectangle &rect, const GooString &signatureText, const GooString &signatureTextLeft, double fontSize, std::unique_ptr<AnnotColor> &&fontColor, double borderWidth, std::unique_ptr<AnnotColor> &&borderColor, std::unique_ptr<AnnotColor> &&backgroundColor, const GooString *reason = nullptr, const GooString *location = nullptr, - const std::string &imagePath = ""); + const std::string &imagePath = "", const GooString *ownerPassword = nullptr, const GooString *userPassword = nullptr); private: // insert referenced objects in XRef diff --git a/utils/pdfsig.cc b/utils/pdfsig.cc index e2d6bff2..56e87d82 100644 --- a/utils/pdfsig.cc +++ b/utils/pdfsig.cc @@ -342,7 +342,7 @@ int main(int argc, char *argv[]) // We don't provide a way to customize the UI from pdfsig for now const bool success = doc->sign(argv[2], certNickname, pw, newSignatureFieldName.copy(), /*page*/ 1, /*rect */ { 0, 0, 0, 0 }, /*signatureText*/ {}, /*signatureTextLeft*/ {}, /*fontSize */ 0, - /*fontColor*/ {}, /*borderWidth*/ 0, /*borderColor*/ {}, /*backgroundColor*/ {}, rs.get()); + /*fontColor*/ {}, /*borderWidth*/ 0, /*borderColor*/ {}, /*backgroundColor*/ {}, rs.get(), /* location */ nullptr, /* image path */ "", ownerPW.get(), userPW.get()); return success ? 0 : 3; }
