Пример #1
0
        /// <summary>Switches to the previous revision.</summary>
        /// <exception cref="System.IO.IOException"/>
        /// <exception cref="Org.BouncyCastle.Security.GeneralSecurityException"/>
        public virtual void SwitchToPreviousRevision()
        {
            LOGGER.Info("Switching to previous revision.");
            latestRevision = false;
            dss            = document.GetCatalog().GetPdfObject().GetAsDictionary(PdfName.DSS);
            DateTime cal = pkcs7.GetTimeStampDate();

            if (cal == SignUtils.UNDEFINED_TIMESTAMP_DATE)
            {
                cal = pkcs7.GetSignDate();
            }
            // TODO: get date from signature
            signDate = cal.ToUniversalTime();
            IList <String> names = sgnUtil.GetSignatureNames();

            if (names.Count > 1)
            {
                signatureName = names[names.Count - 2];
                document      = new PdfDocument(new PdfReader(sgnUtil.ExtractRevision(signatureName)), new DocumentProperties()
                                                .SetEventCountingMetaInfo(metaInfo));
                this.acroForm = PdfAcroForm.GetAcroForm(document, true);
                this.sgnUtil  = new SignatureUtil(document);
                names         = sgnUtil.GetSignatureNames();
                signatureName = names[names.Count - 1];
                pkcs7         = CoversWholeDocument();
                LOGGER.Info(MessageFormatUtil.Format("Checking {0}signature {1}", pkcs7.IsTsp() ? "document-level timestamp "
                     : "", signatureName));
            }
            else
            {
                LOGGER.Info("No signatures in revision");
                pkcs7 = null;
            }
        }
Пример #2
0
        public virtual void LastBytesNotCoveredTest01()
        {
            String        inPdf         = sourceFolder + "lastBytesNotCoveredTest01.pdf";
            PdfDocument   pdfDocument   = new PdfDocument(new PdfReader(inPdf));
            SignatureUtil signatureUtil = new SignatureUtil(pdfDocument);

            NUnit.Framework.Assert.IsFalse(signatureUtil.SignatureCoversWholeDocument("Signature1"));
        }
Пример #3
0
        public virtual void NotIndirectSigDictionaryTest()
        {
            String        inPdf         = sourceFolder + "notIndirectSigDictionaryTest.pdf";
            PdfDocument   pdfDocument   = new PdfDocument(new PdfReader(inPdf));
            SignatureUtil signatureUtil = new SignatureUtil(pdfDocument);

            NUnit.Framework.Assert.IsTrue(signatureUtil.SignatureCoversWholeDocument("Signature1"));
        }
Пример #4
0
        public virtual void SpacesBeforeContentsTest02()
        {
            String        inPdf         = sourceFolder + "spacesBeforeContentsTest02.pdf";
            PdfDocument   pdfDocument   = new PdfDocument(new PdfReader(inPdf));
            SignatureUtil signatureUtil = new SignatureUtil(pdfDocument);

            NUnit.Framework.Assert.IsTrue(signatureUtil.SignatureCoversWholeDocument("Signature1"));
        }
Пример #5
0
        public virtual void BytesAreCoveredTest02()
        {
            String        inPdf         = sourceFolder + "bytesAreCoveredTest02.pdf";
            PdfDocument   pdfDocument   = new PdfDocument(new PdfReader(inPdf));
            SignatureUtil signatureUtil = new SignatureUtil(pdfDocument);

            NUnit.Framework.Assert.IsTrue(signatureUtil.SignatureCoversWholeDocument("sig"));
        }
Пример #6
0
        public virtual void GetSignaturesTest02()
        {
            String         inPdf          = sourceFolder + "simpleDocument.pdf";
            PdfDocument    pdfDocument    = new PdfDocument(new PdfReader(inPdf));
            SignatureUtil  signatureUtil  = new SignatureUtil(pdfDocument);
            IList <String> signatureNames = signatureUtil.GetSignatureNames();

            NUnit.Framework.Assert.AreEqual(0, signatureNames.Count);
        }
Пример #7
0
        /// <summary>Signs a PDF where space was already reserved.</summary>
        /// <param name="document">the original PDF</param>
        /// <param name="fieldName">the field to sign. It must be the last field</param>
        /// <param name="outs">the output PDF</param>
        /// <param name="externalSignatureContainer">
        /// the signature container doing the actual signing. Only the
        /// method ExternalSignatureContainer.sign is used
        /// </param>
        /// <exception cref="System.IO.IOException"/>
        /// <exception cref="Org.BouncyCastle.Security.GeneralSecurityException"/>
        public static void SignDeferred(PdfDocument document, String fieldName, Stream outs, IExternalSignatureContainer
                                        externalSignatureContainer)
        {
            SignatureUtil signatureUtil = new SignatureUtil(document);
            PdfDictionary v             = signatureUtil.GetSignatureDictionary(fieldName);

            if (v == null)
            {
                throw new PdfException(PdfException.ThereIsNoFieldInTheDocumentWithSuchName1).SetMessageParams(fieldName);
            }
            if (!signatureUtil.SignatureCoversWholeDocument(fieldName))
            {
                new PdfException(PdfException.SignatureWithName1IsNotTheLastItDoesntCoverWholeDocument).SetMessageParams(fieldName
                                                                                                                         );
            }
            PdfArray b = v.GetAsArray(PdfName.ByteRange);

            long[] gaps = SignatureUtil.AsLongArray(b);
            // TODO: refactor
            if (b.Size() != 4 || gaps[0] != 0)
            {
                throw new ArgumentException("Single exclusion space supported");
            }
            IRandomAccessSource readerSource = document.GetReader().GetSafeFile().CreateSourceView();
            Stream rg = new RASInputStream(new RandomAccessSourceFactory().CreateRanged(readerSource, gaps));

            byte[] signedContent  = externalSignatureContainer.Sign(rg);
            int    spaceAvailable = (int)(gaps[2] - gaps[1]) - 2;

            if ((spaceAvailable & 1) != 0)
            {
                throw new ArgumentException("Gap is not a multiple of 2");
            }
            spaceAvailable /= 2;
            if (spaceAvailable < signedContent.Length)
            {
                throw new PdfException(PdfException.AvailableSpaceIsNotEnoughForSignature);
            }
            StreamUtil.CopyBytes(readerSource, 0, gaps[1] + 1, outs);
            ByteBuffer bb = new ByteBuffer(spaceAvailable * 2);

            foreach (byte bi in signedContent)
            {
                bb.AppendHex(bi);
            }
            int remain = (spaceAvailable - signedContent.Length) * 2;

            for (int k = 0; k < remain; ++k)
            {
                bb.Append((byte)48);
            }
            byte[] bbArr = bb.ToByteArray();
            outs.Write(bbArr);
            StreamUtil.CopyBytes(readerSource, gaps[2] - 1, gaps[3] + 1, outs);
        }
Пример #8
0
        /// <exception cref="Org.BouncyCastle.Security.GeneralSecurityException"/>
        protected internal virtual void InitLtvVerifier(PdfDocument document)
        {
            this.document = document;
            this.acroForm = PdfAcroForm.GetAcroForm(document, true);
            this.sgnUtil  = new SignatureUtil(document);
            IList <String> names = sgnUtil.GetSignatureNames();

            signatureName = names[names.Count - 1];
            this.signDate = DateTimeUtil.GetCurrentUtcTime();
            pkcs7         = CoversWholeDocument();
            LOGGER.Info(MessageFormatUtil.Format("Checking {0}signature {1}", pkcs7.IsTsp() ? "document-level timestamp "
                 : "", signatureName));
        }
Пример #9
0
        /// <summary>This is the first method to be called when using external signatures.</summary>
        /// <remarks>
        /// This is the first method to be called when using external signatures. The general sequence is:
        /// preClose(), getDocumentBytes() and close().
        /// <p>
        /// <CODE>exclusionSizes</CODE> must contain at least
        /// the <CODE>PdfName.CONTENTS</CODE> key with the size that it will take in the
        /// document. Note that due to the hex string coding this size should be byte_size*2+2.
        /// </remarks>
        /// <param name="exclusionSizes">
        /// Map with names and sizes to be excluded in the signature
        /// calculation. The key is a PdfName and the value an Integer. At least the /Contents must be present
        /// </param>
        /// <exception cref="System.IO.IOException">on error</exception>
        protected internal virtual void PreClose(IDictionary <PdfName, int?> exclusionSizes)
        {
            if (preClosed)
            {
                throw new PdfException(PdfException.DocumentAlreadyPreClosed);
            }
            // TODO: add mergeVerification functionality
            preClosed = true;
            PdfAcroForm   acroForm   = PdfAcroForm.GetAcroForm(document, true);
            SignatureUtil sgnUtil    = new SignatureUtil(document);
            String        name       = GetFieldName();
            bool          fieldExist = sgnUtil.DoesSignatureFieldExist(name);

            acroForm.SetSignatureFlags(PdfAcroForm.SIGNATURE_EXIST | PdfAcroForm.APPEND_ONLY);
            PdfSigFieldLockDictionary fieldLock = null;

            if (cryptoDictionary == null)
            {
                throw new PdfException(PdfException.NoCryptoDictionaryDefined);
            }
            cryptoDictionary.GetPdfObject().MakeIndirect(document);
            if (fieldExist)
            {
                PdfSignatureFormField sigField = (PdfSignatureFormField)acroForm.GetField(fieldName);
                sigField.Put(PdfName.V, cryptoDictionary.GetPdfObject());
                fieldLock = sigField.GetSigFieldLockDictionary();
                if (fieldLock == null && this.fieldLock != null)
                {
                    this.fieldLock.GetPdfObject().MakeIndirect(document);
                    sigField.Put(PdfName.Lock, this.fieldLock.GetPdfObject());
                    fieldLock = this.fieldLock;
                }
                sigField.Put(PdfName.P, document.GetPage(appearance.GetPageNumber()).GetPdfObject());
                sigField.Put(PdfName.V, cryptoDictionary.GetPdfObject());
                PdfObject obj   = sigField.GetPdfObject().Get(PdfName.F);
                int       flags = 0;
                if (obj != null && obj.IsNumber())
                {
                    flags = ((PdfNumber)obj).IntValue();
                }
                flags |= PdfAnnotation.LOCKED;
                sigField.Put(PdfName.F, new PdfNumber(flags));
                PdfDictionary ap = new PdfDictionary();
                ap.Put(PdfName.N, appearance.GetAppearance().GetPdfObject());
                sigField.Put(PdfName.AP, ap);
                sigField.SetModified();
            }
            else
            {
                PdfWidgetAnnotation widget = new PdfWidgetAnnotation(appearance.GetPageRect());
                widget.SetFlags(PdfAnnotation.PRINT | PdfAnnotation.LOCKED);
                PdfSignatureFormField sigField = PdfFormField.CreateSignature(document);
                sigField.SetFieldName(name);
                sigField.Put(PdfName.V, cryptoDictionary.GetPdfObject());
                sigField.AddKid(widget);
                if (this.fieldLock != null)
                {
                    this.fieldLock.GetPdfObject().MakeIndirect(document);
                    sigField.Put(PdfName.Lock, this.fieldLock.GetPdfObject());
                    fieldLock = this.fieldLock;
                }
                int pagen = appearance.GetPageNumber();
                widget.SetPage(document.GetPage(pagen));
                PdfDictionary ap = widget.GetAppearanceDictionary();
                if (ap == null)
                {
                    ap = new PdfDictionary();
                    widget.Put(PdfName.AP, ap);
                }
                ap.Put(PdfName.N, appearance.GetAppearance().GetPdfObject());
                acroForm.AddField(sigField, document.GetPage(pagen));
                if (acroForm.GetPdfObject().IsIndirect())
                {
                    acroForm.SetModified();
                }
                else
                {
                    //Acroform dictionary is a Direct dictionary,
                    //for proper flushing, catalog needs to be marked as modified
                    document.GetCatalog().SetModified();
                }
            }
            exclusionLocations = new Dictionary <PdfName, PdfLiteral>();
            PdfLiteral lit = new PdfLiteral(80);

            exclusionLocations[PdfName.ByteRange] = lit;
            cryptoDictionary.Put(PdfName.ByteRange, lit);
            foreach (KeyValuePair <PdfName, int?> entry in exclusionSizes)
            {
                PdfName key = entry.Key;
                lit = new PdfLiteral((int)entry.Value);
                exclusionLocations[key] = lit;
                cryptoDictionary.Put(key, lit);
            }
            if (certificationLevel > 0)
            {
                AddDocMDP(cryptoDictionary);
            }
            if (fieldLock != null)
            {
                AddFieldMDP(cryptoDictionary, fieldLock);
            }
            if (signatureEvent != null)
            {
                signatureEvent.GetSignatureDictionary(cryptoDictionary);
            }
            if (certificationLevel > 0)
            {
                // add DocMDP entry to root
                PdfDictionary docmdp = new PdfDictionary();
                docmdp.Put(PdfName.DocMDP, cryptoDictionary.GetPdfObject());
                document.GetCatalog().Put(PdfName.Perms, docmdp);
                document.GetCatalog().SetModified();
            }
            cryptoDictionary.GetPdfObject().Flush(false);
            document.Close();
            range = new long[exclusionLocations.Count * 2];
            long byteRangePosition = exclusionLocations.Get(PdfName.ByteRange).GetPosition();

            exclusionLocations.JRemove(PdfName.ByteRange);
            int idx = 1;

            foreach (PdfLiteral lit1 in exclusionLocations.Values)
            {
                long n = lit1.GetPosition();
                range[idx++] = n;
                range[idx++] = lit1.GetBytesCount() + n;
            }
            iText.IO.Util.JavaUtil.Sort(range, 1, range.Length - 1);
            for (int k = 3; k < range.Length - 2; k += 2)
            {
                range[k] -= range[k - 1];
            }
            if (tempFile == null)
            {
                bout = temporaryOS.ToArray();
                range[range.Length - 1] = bout.Length - range[range.Length - 2];
                MemoryStream    bos = new MemoryStream();
                PdfOutputStream os  = new PdfOutputStream(bos);
                os.Write('[');
                for (int k_1 = 0; k_1 < range.Length; ++k_1)
                {
                    os.WriteLong(range[k_1]).Write(' ');
                }
                os.Write(']');
                System.Array.Copy(bos.ToArray(), 0, bout, (int)byteRangePosition, bos.Length);
            }
            else
            {
                try {
                    raf = FileUtil.GetRandomAccessFile(tempFile);
                    long len = raf.Length;
                    range[range.Length - 1] = len - range[range.Length - 2];
                    MemoryStream    bos = new MemoryStream();
                    PdfOutputStream os  = new PdfOutputStream(bos);
                    os.Write('[');
                    for (int k_1 = 0; k_1 < range.Length; ++k_1)
                    {
                        os.WriteLong(range[k_1]).Write(' ');
                    }
                    os.Write(']');
                    raf.Seek(byteRangePosition);
                    raf.Write(bos.ToArray(), 0, (int)bos.Length);
                }
                catch (System.IO.IOException e) {
                    try {
                        raf.Close();
                    }
                    catch (Exception) {
                    }
                    try {
                        tempFile.Delete();
                    }
                    catch (Exception) {
                    }
                    throw;
                }
            }
        }
Пример #10
0
 /// <summary>The verification constructor.</summary>
 /// <remarks>
 /// The verification constructor. This class should only be created with
 /// PdfStamper.getLtvVerification() otherwise the information will not be
 /// added to the Pdf.
 /// </remarks>
 /// <param name="document">
 /// The
 /// <see cref="iText.Kernel.Pdf.PdfDocument"/>
 /// to apply the validation to.
 /// </param>
 public LtvVerification(PdfDocument document)
 {
     this.document = document;
     this.acroForm = PdfAcroForm.GetAcroForm(document, true);
     this.sgnUtil  = new SignatureUtil(document);
 }