Skip to main content
Skip table of contents

FIPS & SHA3 Examples for iText Core 8.0.0

With the release of iText Core version 8.0.0, direct support for the Java and .NET Bouncy Castle FIPS APIs has been added. Below you can find Java and C# examples for using FIPS in approved mode and the SHA3-512 algorithm.

For more information on the FIPS implementation see our Bouncy Castle changes page, or refer to the iText 8.0.0 release notes.

FIPS with SHA3 example

Java

JAVA
package org.example;

import com.itextpdf.kernel.pdf.PdfReader;
import com.itextpdf.kernel.pdf.StampingProperties;
import com.itextpdf.signatures.*;
import org.bouncycastle.crypto.CryptoServicesRegistrar;
import org.bouncycastle.jcajce.provider.BouncyCastleFipsProvider;

import java.io.FileInputStream;
import java.io.FileOutputStream;
import java.io.IOException;
import java.security.GeneralSecurityException;
import java.security.KeyStore;
import java.security.PrivateKey;
import java.security.Security;
import java.security.cert.Certificate;

public class SignExample {
    public static final String BASE_URI = "src/main/resources/";
    public static final String INPUT_FILE = BASE_URI + "input.pdf";
    public static final String OUTPUT_FILE = BASE_URI + "signed.pdf";
    public static final String KEYSTORE_PATH = "path/to/keystore";
    public static final char[] PASSWORD_CHARS = "testpassphrase".toCharArray();

    public static void main(String[] args) throws Exception {
        var signExample = new SignExample();
        signExample.fipsExample(INPUT_FILE, OUTPUT_FILE, KEYSTORE_PATH, PASSWORD_CHARS);
    }

    public void fipsExample(String inFile, String outFile, String keyStorePath, char[] password) throws GeneralSecurityException, IOException {
        CryptoServicesRegistrar.setApprovedOnlyMode(true);
        BouncyCastleFipsProvider provider = new BouncyCastleFipsProvider();
        Security.addProvider(provider);

        KeyStore ks = KeyStore.getInstance(KeyStore.getDefaultType());
        ks.load(new FileInputStream(keyStorePath), password);
        String alias = ks.aliases().nextElement();
        PrivateKey pk = (PrivateKey) ks.getKey(alias, password);
        Certificate[] chain = ks.getCertificateChain(alias);
        PdfSigner signer = new PdfSigner(new PdfReader(inFile), new FileOutputStream(outFile),
                new StampingProperties().useAppendMode());

        PdfSignatureAppearance sap = signer.getSignatureAppearance();
        sap.setReason("Test 1");
        sap.setLocation("Ghent");

        IExternalDigest digest = new BouncyCastleDigest();
        IExternalSignature signature = new PrivateKeySignature(pk, DigestAlgorithms.SHA3_512, provider.getName());

        signer.signDetached(digest, signature, chain, null, null, null, 0, PdfSigner.CryptoStandard.CADES);
    }
} 


C#

C#
using iText.Bouncycastleconnector;
using iText.Commons.Bouncycastle;
using iText.Commons.Bouncycastle.Cert;
using iText.Commons.Bouncycastle.Crypto;
using iText.Commons.Bouncycastle.Openssl;
using iText.Kernel.Pdf;
using iText.Signatures;
using itext8_project.s81866;
using Org.BouncyCastle.Crypto;

namespace itext8_project.ReleaseExample;

public class SignTest
{
    public void FipsExample(string inFile, String outFile, string pemPath, string pw) {
        CryptoServicesRegistrar.SetApprovedOnlyMode(true);
        var chain = PemFileHelper.ReadFirstChain(pemPath);
        var privateKey = PemFileHelper.ReadFirstKey(pemPath, pw.ToCharArray());
        var pk = new PrivateKeySignature(privateKey, DigestAlgorithms.SHA256);
        var signer = new PdfSigner(new PdfReader(inFile), new FileStream(outFile, FileMode.Create),
            new StampingProperties().UseAppendMode());


        signer.SignDetached(pk, chain, null, null, null, 0, PdfSigner.CryptoStandard.CMS);
    }
    
    
    class PemFileHelper {
        private static readonly IBouncyCastleFactory FACTORY = BouncyCastleFactoryCreator.GetFactory();
        private PemFileHelper() {
            // Empty constructor.
        }
        public static IX509Certificate[] ReadFirstChain(String pemFileName) {
            return ReadCertificates(pemFileName).ToArray(new IX509Certificate[0]);
        }
        public static IPrivateKey ReadFirstKey(String pemFileName, char[] keyPass) {
            return ReadPrivateKey(pemFileName, keyPass);
        }
        public static List<IX509Certificate> InitStore(String pemFileName) {
            IX509Certificate[] chain = ReadFirstChain(pemFileName);
            return chain.Length > 0 ? new List<IX509Certificate> { chain[0] } : chain.ToList();
        }
        private static IList<IX509Certificate> ReadCertificates(String pemFileName) {
            using (TextReader file = new StreamReader(pemFileName)) {
                IPemReader parser = FACTORY.CreatePEMParser(file, null);
                Object readObject = parser.ReadObject();
                IList<IX509Certificate> certificates = new List<IX509Certificate>();
                while (readObject != null) {
                    if (readObject is IX509Certificate) {
                        certificates.Add((IX509Certificate)readObject);
                    }
                    readObject = parser.ReadObject();
                }
                return certificates;
            }
        }
        private static IPrivateKey ReadPrivateKey(String pemFileName, char[] keyPass) {
            using (TextReader file = new StreamReader(pemFileName)) {
                IPemReader parser = FACTORY.CreatePEMParser(file, keyPass);
                Object readObject = parser.ReadObject();
                while (!(readObject is IPrivateKey) && readObject != null) {
                    readObject = parser.ReadObject();
                }
                return (IPrivateKey)readObject;
            }
        }
    }
}
JavaScript errors detected

Please note, these errors can depend on your browser setup.

If this problem persists, please contact our support.