Path: blob/aarch64-shenandoah-jdk8u272-b10/jdk/test/javax/xml/crypto/dsig/LineFeedOnlyTest.java
38853 views
/*1* Copyright (c) 2005, 2020, Oracle and/or its affiliates. All rights reserved.2* Copyright (c) 2020 Red Hat, Inc.3* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.4*5* This code is free software; you can redistribute it and/or modify it6* under the terms of the GNU General Public License version 2 only, as7* published by the Free Software Foundation.8*9* This code is distributed in the hope that it will be useful, but WITHOUT10* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or11* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License12* version 2 for more details (a copy is included in the LICENSE file that13* accompanied this code).14*15* You should have received a copy of the GNU General Public License version16* 2 along with this work; if not, write to the Free Software Foundation,17* Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.18*19* Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA20* or visit www.oracle.com if you need additional information or have any21* questions.22*/2324import java.io.File;25import java.io.FileInputStream;26import java.io.StringWriter;27import java.security.Key;28import java.security.KeyStore;29import java.security.cert.Certificate;30import java.util.Base64;31import java.util.Collections;3233import javax.xml.crypto.Data;34import javax.xml.crypto.OctetStreamData;35import javax.xml.crypto.URIDereferencer;36import javax.xml.crypto.URIReference;37import javax.xml.crypto.URIReferenceException;38import javax.xml.crypto.XMLCryptoContext;39import javax.xml.crypto.dsig.CanonicalizationMethod;40import javax.xml.crypto.dsig.DigestMethod;41import javax.xml.crypto.dsig.Reference;42import javax.xml.crypto.dsig.SignatureMethod;43import javax.xml.crypto.dsig.SignedInfo;44import javax.xml.crypto.dsig.XMLSignature;45import javax.xml.crypto.dsig.XMLSignatureFactory;46import javax.xml.crypto.dsig.dom.DOMSignContext;47import javax.xml.crypto.dsig.keyinfo.KeyInfo;48import javax.xml.crypto.dsig.keyinfo.KeyInfoFactory;49import javax.xml.crypto.dsig.spec.C14NMethodParameterSpec;50import javax.xml.parsers.DocumentBuilder;51import javax.xml.parsers.DocumentBuilderFactory;52import javax.xml.transform.OutputKeys;53import javax.xml.transform.Transformer;54import javax.xml.transform.TransformerFactory;55import javax.xml.transform.dom.DOMSource;56import javax.xml.transform.stream.StreamResult;5758import org.w3c.dom.Document;59import org.w3c.dom.Node;60import org.w3c.dom.NodeList;6162/* @test63* @bug 823664564* @summary Test "lineFeedOnly" property prevents CR in Base64 encoded output65* @run main/othervm/timeout=300 -Dcom.sun.org.apache.xml.internal.security.lineFeedOnly=false LineFeedOnlyTest66* @run main/othervm/timeout=300 -Dcom.sun.org.apache.xml.internal.security.lineFeedOnly=true LineFeedOnlyTest67* @run main/othervm/timeout=300 -Dcom.sun.org.apache.xml.internal.security.lineFeedOnly=true68* -Dcom.sun.org.apache.xml.internal.security.ignoreLineBreaks=true LineFeedOnlyTest69* @run main/othervm/timeout=300 LineFeedOnlyTest70*/71public class LineFeedOnlyTest {7273private final static String DIR = System.getProperty("test.src", ".");74private final static String DATA_DIR =75DIR + System.getProperty("file.separator") + "data";76private final static String KEYSTORE =77DATA_DIR + System.getProperty("file.separator") + "certs" +78System.getProperty("file.separator") + "test.jks";79private final static String STYLESHEET =80"http://www.w3.org/TR/xml-stylesheet";8182private static XMLSignatureFactory fac;83private static KeyInfoFactory kifac;84private static DocumentBuilder db;85private static CanonicalizationMethod withoutComments;86private static SignatureMethod dsaSha1;87private static DigestMethod sha1;88private static Key signingKey;89private static Certificate signingCert;90private static KeyStore ks;91private static URIDereferencer httpUd;9293// Much of this test is derived from GenerationTests. We use a separate file in order to test94// when the system property "com.sun.org.apache.xml.internal.security.lineFeedOnly" is enabled/disabled.95public static void main(String[] args) throws Exception {96boolean lineFeedOnly = Boolean.getBoolean("com.sun.org.apache.xml.internal.security.lineFeedOnly");97boolean ignoreLineBreaks = Boolean.getBoolean("com.sun.org.apache.xml.internal.security.ignoreLineBreaks");9899setup();100test_create_signature_line_endings(lineFeedOnly, ignoreLineBreaks);101}102103private static void setup() throws Exception {104fac = XMLSignatureFactory.getInstance();105kifac = fac.getKeyInfoFactory();106DocumentBuilderFactory dbf = DocumentBuilderFactory.newInstance();107dbf.setNamespaceAware(true);108db = dbf.newDocumentBuilder();109110// get key & self-signed certificate from keystore111FileInputStream fis = new FileInputStream(KEYSTORE);112ks = KeyStore.getInstance("JKS");113ks.load(fis, "changeit".toCharArray());114signingKey = ks.getKey("user", "changeit".toCharArray());115signingCert = ks.getCertificate("user");116117// create common objects118withoutComments = fac.newCanonicalizationMethod119(CanonicalizationMethod.INCLUSIVE, (C14NMethodParameterSpec)null);120dsaSha1 = fac.newSignatureMethod(SignatureMethod.DSA_SHA1, null);121sha1 = fac.newDigestMethod(DigestMethod.SHA1, null);122123httpUd = new HttpURIDereferencer();124}125126private static void test_create_signature_line_endings(boolean lineFeedOnly,127boolean ignoreLineBreaks) throws Exception {128System.out.println("* Generating signature-line-endings.xml");129System.out.println("* com.sun.org.apache.xml.internal.security.lineFeedOnly is "130+ String.valueOf(lineFeedOnly));131System.out.println("* com.sun.org.apache.xml.internal.security.ignoreLineBreaks is "132+ String.valueOf(ignoreLineBreaks));133134// create reference135Reference ref = fac.newReference(STYLESHEET, sha1);136137// create SignedInfo138SignedInfo si = fac.newSignedInfo(withoutComments, dsaSha1,139Collections.singletonList(ref));140141Document doc = db.newDocument();142143// create XMLSignature144KeyInfo crt = kifac.newKeyInfo(Collections.singletonList145(kifac.newX509Data(Collections.singletonList(signingCert))));146XMLSignature sig = fac.newXMLSignature(si, crt);147148DOMSignContext dsc = new DOMSignContext(signingKey, doc);149dsc.setURIDereferencer(httpUd);150151sig.sign(dsc);152153NodeList list = doc.getElementsByTagName("X509Certificate");154if (list.getLength() != 1) {155throw new Exception("Expected exactly one X509Certificate tag");156}157Node item = list.item(0);158StringWriter writer = new StringWriter();159Transformer tr = TransformerFactory.newInstance().newTransformer();160tr.setOutputProperty(OutputKeys.METHOD, "xml");161tr.setOutputProperty(OutputKeys.OMIT_XML_DECLARATION, "yes");162tr.transform(new DOMSource(item.getFirstChild()), new StreamResult(writer));163String actual = writer.toString();164165String expected;166if (ignoreLineBreaks) {167expected = Base64.getEncoder().encodeToString(signingCert.getEncoded());168} else if (lineFeedOnly) {169expected = Base64.getMimeEncoder(76, new byte[] {'\n'}).encodeToString(signingCert.getEncoded());170} else {171expected = Base64.getMimeEncoder().encodeToString(signingCert.getEncoded());172}173174if (!expected.equals(actual)) {175if (ignoreLineBreaks && actual.contains("\n")) {176throw new Exception("ignoreLineBreaks did not take precedence over lineFeedOnly");177} else if (lineFeedOnly && actual.contains("\r\n")) {178throw new Exception("Expected LF only, but found CRLF");179} else if (!lineFeedOnly && !actual.contains("\r\n")) {180throw new Exception("Expected CRLF, but found LF only");181}182throw new Exception("Unexpected output in encoded certificate");183}184}185186/**187* This URIDereferencer returns locally cached copies of http content to188* avoid test failures due to network glitches, etc.189*/190private static class HttpURIDereferencer implements URIDereferencer {191private URIDereferencer defaultUd;192193HttpURIDereferencer() {194defaultUd = XMLSignatureFactory.getInstance().getURIDereferencer();195}196197public Data dereference(final URIReference ref, XMLCryptoContext ctx)198throws URIReferenceException {199String uri = ref.getURI();200if (uri.equals(STYLESHEET)) {201try {202FileInputStream fis = new FileInputStream(new File203(DATA_DIR, uri.substring(uri.lastIndexOf('/'))));204return new OctetStreamData(fis,ref.getURI(),ref.getType());205} catch (Exception e) { throw new URIReferenceException(e); }206}207208// fallback on builtin deref209return defaultUd.dereference(ref, ctx);210}211}212213}214215216