Book a Demo!
CoCalc Logo Icon
StoreFeaturesDocsShareSupportNewsAboutPoliciesSign UpSign In
PojavLauncherTeam
GitHub Repository: PojavLauncherTeam/mobile
Path: blob/master/test/jdk/com/sun/crypto/provider/Cipher/AES/TestGCMKeyAndIvCheck.java
41161 views
1
/*
2
* Copyright (c) 2013, Oracle and/or its affiliates. All rights reserved.
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 it
6
* under the terms of the GNU General Public License version 2 only, as
7
* published by the Free Software Foundation.
8
*
9
* This code is distributed in the hope that it will be useful, but WITHOUT
10
* ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
11
* FITNESS FOR A PARTICULAR PURPOSE. See the GNU General Public License
12
* version 2 for more details (a copy is included in the LICENSE file that
13
* accompanied this code).
14
*
15
* You should have received a copy of the GNU General Public License version
16
* 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 USA
20
* or visit www.oracle.com if you need additional information or have any
21
* questions.
22
*/
23
24
/*
25
* @test
26
* @bug 6996769
27
* @library ../UTIL
28
* @build TestUtil
29
* @run main TestGCMKeyAndIvCheck
30
* @summary Ensure that same key+iv can't be repeated used for encryption.
31
* @author Valerie Peng
32
*/
33
34
35
import java.security.*;
36
import javax.crypto.*;
37
import javax.crypto.spec.*;
38
import java.math.*;
39
40
import java.util.*;
41
42
public class TestGCMKeyAndIvCheck {
43
44
private static final byte[] AAD = new byte[5];
45
private static final byte[] PT = new byte[18];
46
47
private static void checkISE(Cipher c) throws Exception {
48
// Subsequent encryptions should fail
49
try {
50
c.updateAAD(AAD);
51
throw new Exception("Should throw ISE for updateAAD()");
52
} catch (IllegalStateException ise) {
53
// expected
54
}
55
56
try {
57
c.update(PT);
58
throw new Exception("Should throw ISE for update()");
59
} catch (IllegalStateException ise) {
60
// expected
61
}
62
try {
63
c.doFinal(PT);
64
throw new Exception("Should throw ISE for doFinal()");
65
} catch (IllegalStateException ise) {
66
// expected
67
}
68
}
69
70
public void test() throws Exception {
71
Cipher c = Cipher.getInstance("AES/GCM/NoPadding", "SunJCE");
72
73
SecretKey key = new SecretKeySpec(new byte[16], "AES");
74
// First try parameter-less init.
75
c.init(Cipher.ENCRYPT_MODE, key);
76
c.updateAAD(AAD);
77
byte[] ctPlusTag = c.doFinal(PT);
78
79
// subsequent encryption should fail unless re-init w/ different key+iv
80
checkISE(c);
81
82
// Validate the retrieved parameters against the IV and tag length.
83
AlgorithmParameters params = c.getParameters();
84
if (params == null) {
85
throw new Exception("getParameters() should not return null");
86
}
87
GCMParameterSpec spec = params.getParameterSpec(GCMParameterSpec.class);
88
if (spec.getTLen() != (ctPlusTag.length - PT.length)*8) {
89
throw new Exception("Parameters contains incorrect TLen value");
90
}
91
if (!Arrays.equals(spec.getIV(), c.getIV())) {
92
throw new Exception("Parameters contains incorrect IV value");
93
}
94
95
// Should be ok to use the same key+iv for decryption
96
c.init(Cipher.DECRYPT_MODE, key, params);
97
c.updateAAD(AAD);
98
byte[] recovered = c.doFinal(ctPlusTag);
99
if (!Arrays.equals(recovered, PT)) {
100
throw new Exception("decryption result mismatch");
101
}
102
103
// Now try to encrypt again using the same key+iv; should fail also
104
try {
105
c.init(Cipher.ENCRYPT_MODE, key, params);
106
throw new Exception("Should throw exception when same key+iv is used");
107
} catch (InvalidAlgorithmParameterException iape) {
108
// expected
109
}
110
111
// Now try to encrypt again using parameter-less init; should work
112
c.init(Cipher.ENCRYPT_MODE, key);
113
c.doFinal(PT);
114
115
// make sure a different iv is used
116
byte[] iv = c.getIV();
117
if (Arrays.equals(spec.getIV(), iv)) {
118
throw new Exception("IV should be different now");
119
}
120
121
// Now try to encrypt again using a different parameter; should work
122
c.init(Cipher.ENCRYPT_MODE, key, new GCMParameterSpec(128, new byte[30]));
123
c.updateAAD(AAD);
124
c.doFinal(PT);
125
// subsequent encryption should fail unless re-init w/ different key+iv
126
checkISE(c);
127
128
// Now try decryption twice in a row; no re-init required and
129
// same parameters is used.
130
c.init(Cipher.DECRYPT_MODE, key, params);
131
c.updateAAD(AAD);
132
recovered = c.doFinal(ctPlusTag);
133
134
c.updateAAD(AAD);
135
recovered = c.doFinal(ctPlusTag);
136
if (!Arrays.equals(recovered, PT)) {
137
throw new Exception("decryption result mismatch");
138
}
139
140
// Now try decryption again and re-init using the same parameters
141
c.init(Cipher.DECRYPT_MODE, key, params);
142
c.updateAAD(AAD);
143
recovered = c.doFinal(ctPlusTag);
144
145
// init to decrypt w/o parameters; should fail with IKE as
146
// javadoc specified
147
try {
148
c.init(Cipher.DECRYPT_MODE, key);
149
throw new Exception("Should throw IKE for dec w/o params");
150
} catch (InvalidKeyException ike) {
151
// expected
152
}
153
154
// Lastly, try encryption AND decryption w/ wrong type of parameters,
155
// e.g. IvParameterSpec
156
try {
157
c.init(Cipher.ENCRYPT_MODE, key, new IvParameterSpec(iv));
158
throw new Exception("Should throw IAPE");
159
} catch (InvalidAlgorithmParameterException iape) {
160
// expected
161
}
162
try {
163
c.init(Cipher.DECRYPT_MODE, key, new IvParameterSpec(iv));
164
throw new Exception("Should throw IAPE");
165
} catch (InvalidAlgorithmParameterException iape) {
166
// expected
167
}
168
169
System.out.println("Test Passed!");
170
}
171
172
public static void main (String[] args) throws Exception {
173
TestGCMKeyAndIvCheck t = new TestGCMKeyAndIvCheck();
174
t.test();
175
}
176
}
177
178
179