View Javadoc
1   /*
2    * Copyright (C) 2021, Thomas Wolf <thomas.wolf@paranor.ch> and others
3    *
4    * This program and the accompanying materials are made available under the
5    * terms of the Eclipse Distribution License v. 1.0 which is available at
6    * https://www.eclipse.org/org/documents/edl-v10.php.
7    *
8    * SPDX-License-Identifier: BSD-3-Clause
9    */
10  package org.eclipse.jgit.gpg.bc.internal.keys;
11  
12  import static org.junit.Assert.assertEquals;
13  import static org.junit.Assert.assertTrue;
14  
15  import java.io.IOException;
16  import java.io.InputStream;
17  import java.security.Security;
18  import java.util.Iterator;
19  import java.util.Locale;
20  import java.util.function.Consumer;
21  
22  import org.bouncycastle.jce.provider.BouncyCastleProvider;
23  import org.bouncycastle.openpgp.PGPException;
24  import org.bouncycastle.openpgp.PGPPublicKey;
25  import org.bouncycastle.openpgp.PGPPublicKeyRing;
26  import org.bouncycastle.openpgp.PGPPublicKeyRingCollection;
27  import org.bouncycastle.openpgp.PGPUtil;
28  import org.bouncycastle.openpgp.operator.jcajce.JcaKeyFingerprintCalculator;
29  import org.bouncycastle.util.encoders.Hex;
30  import org.junit.BeforeClass;
31  import org.junit.Test;
32  import org.junit.runner.RunWith;
33  import org.junit.runners.Parameterized;
34  import org.junit.runners.Parameterized.Parameter;
35  import org.junit.runners.Parameterized.Parameters;
36  
37  @RunWith(Parameterized.class)
38  public class KeyGripTest {
39  
40  	@BeforeClass
41  	public static void ensureBC() {
42  		if (Security.getProvider(BouncyCastleProvider.PROVIDER_NAME) == null) {
43  			Security.addProvider(new BouncyCastleProvider());
44  		}
45  	}
46  
47  	protected static class TestData {
48  
49  		String filename;
50  
51  		String[] expectedKeyGrips;
52  
53  		TestData(String filename, String... keyGrips) {
54  			this.filename = filename;
55  			this.expectedKeyGrips = keyGrips;
56  		}
57  
58  		@Override
59  		public String toString() {
60  			return filename;
61  		}
62  	}
63  
64  	@Parameters(name = "{0}")
65  	public static TestData[] initTestData() {
66  		return new TestData[] {
67  				new TestData("rsa.asc",
68  						"D148210FAF36468055B83D0F5A6DEB83FBC8E864",
69  						"A5E4CD2CBBE44A16E4D6EC05C2E3C3A599DC763C"),
70  				new TestData("dsa-elgamal.asc",
71  						"552286BEB2999F0A9E26A50385B90D9724001187",
72  						"CED7034A8EB5F4CE90DF99147EC33D86FCD3296C"),
73  				new TestData("brainpool256.asc",
74  						"A01BAA22A72F09A0FF0A1D4CBCE70844DD52DDD7",
75  						"C1678B7DE5F144C93B89468D5F9764ACE182ED36"),
76  				new TestData("brainpool384.asc",
77  						"2F25DB025DEBF3EA2715350209B985829B04F50A",
78  						"B6BD8B81F75AF914163D97DF8DE8F6FC64C283F8"),
79  				new TestData("brainpool512.asc",
80  						"5A484F56AB4B8B6583B6365034999F6543FAE1AE",
81  						"9133E4A7E8FC8515518DF444C3F2F247EEBBADEC"),
82  				new TestData("nistp256.asc",
83  						"FC81AECE90BCE6E54D0D637D266109783AC8DAC0",
84  						"A56DC8DB8355747A809037459B4258B8A743EAB5"),
85  				new TestData("nistp384.asc",
86  						"A1338230AED1C9C125663518470B49056C9D1733",
87  						"797A83FE041FFE06A7F4B1D32C6F4AE0F6D87ADF"),
88  				new TestData("nistp521.asc",
89  						"D91B789603EC9138AA20342A2B6DC86C81B70F5D",
90  						"FD048B2CA1919CB241DC8A2C7FA3E742EF343DCA"),
91  				new TestData("secp256k1.asc",
92  						"498B89C485489BA16B40755C0EBA580166393074",
93  						"48FFED40D018747363BDEFFDD404D1F4870F8064"),
94  				new TestData("ed25519.asc",
95  						"940D97D75C306D737A59A98EAFF1272832CEDC0B"),
96  				new TestData("x25519.asc",
97  						"A77DC8173DA6BEE126F5BD6F5A14E01200B52FCE",
98  						"636C983EDB558527BA82780B52CB5DAE011BE46B")
99  		};
100 	}
101 
102 	// Injected by JUnit
103 	@Parameter
104 	public TestData data;
105 
106 	private void readAsc(InputStream in, Consumer<PGPPublicKey> process)
107 			throws IOException, PGPException {
108 		PGPPublicKeyRingCollection pgpPub = new PGPPublicKeyRingCollection(
109 			PGPUtil.getDecoderStream(in), new JcaKeyFingerprintCalculator());
110 
111 		Iterator<PGPPublicKeyRing> keyRings = pgpPub.getKeyRings();
112 		while (keyRings.hasNext()) {
113 			PGPPublicKeyRing keyRing = keyRings.next();
114 
115 			Iterator<PGPPublicKey> keys = keyRing.getPublicKeys();
116 			while (keys.hasNext()) {
117 				process.accept(keys.next());
118 			}
119 		}
120 	}
121 
122 	@Test
123 	public void testGrip() throws Exception {
124 		try (InputStream in = this.getClass()
125 				.getResourceAsStream(data.filename)) {
126 			int index[] = { 0 };
127 			readAsc(in, key -> {
128 				byte[] keyGrip = null;
129 				try {
130 					keyGrip = KeyGrip.getKeyGrip(key);
131 				} catch (PGPException e) {
132 					throw new RuntimeException(e);
133 				}
134 				assertTrue("More keys than expected",
135 						index[0] < data.expectedKeyGrips.length);
136 				assertEquals("Wrong keygrip", data.expectedKeyGrips[index[0]++],
137 						Hex.toHexString(keyGrip).toUpperCase(Locale.ROOT));
138 			});
139 			assertEquals("Missing keys", data.expectedKeyGrips.length,
140 					index[0]);
141 		}
142 	}
143 }