1/* 2 * Licensed to the Apache Software Foundation (ASF) under one or more 3 * contributor license agreements. See the NOTICE file distributed with 4 * this work for additional information regarding copyright ownership. 5 * The ASF licenses this file to You under the Apache License, Version 2.0 6 * (the "License"); you may not use this file except in compliance with 7 * the License. You may obtain a copy of the License at 8 * 9 * http://www.apache.org/licenses/LICENSE-2.0 10 * 11 * Unless required by applicable law or agreed to in writing, software 12 * distributed under the License is distributed on an "AS IS" BASIS, 13 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. 14 * See the License for the specific language governing permissions and 15 * limitations under the License. 16 */ 17 18/** 19 * @author Vera Y. Petrashkova 20 */ 21 22package javax.crypto; 23 24import java.security.spec.AlgorithmParameterSpec; 25import java.security.InvalidAlgorithmParameterException; 26import java.security.InvalidKeyException; 27import java.security.Key; 28import java.security.NoSuchAlgorithmException; 29import java.security.SecureRandom; 30import java.security.AlgorithmParameters; 31import java.nio.ByteBuffer; 32 33import junit.framework.TestCase; 34 35 36/** 37 * Tests for <code>CipherSpi</code> class constructors and methods. 38 */ 39 40public class CipherSpiTest extends TestCase { 41 42 /** 43 * Constructor for CipherSpiTests. 44 * 45 * @param arg0 46 */ 47 public CipherSpiTest(String arg0) { 48 super(arg0); 49 } 50 51 /** 52 * Test for <code>CipherSpi</code> constructor 53 * Assertion: constructs CipherSpi 54 */ 55 public void testCipherSpiTests01() throws IllegalBlockSizeException, 56 BadPaddingException, ShortBufferException { 57 58 CipherSpi cSpi = new myCipherSpi(); 59 assertEquals("BlockSize is not 0", cSpi.engineGetBlockSize(), 0); 60 assertEquals("OutputSize is not 0", cSpi.engineGetOutputSize(1), 0); 61 byte[] bb = cSpi.engineGetIV(); 62 assertEquals("Length of result byte array is not 0", bb.length, 0); 63 assertNull("Not null result", cSpi.engineGetParameters()); 64 byte[] bb1 = new byte[10]; 65 byte[] bb2 = new byte[10]; 66 bb = cSpi.engineUpdate(bb1, 1, 2); 67 assertEquals("Incorrect result of engineUpdate(byte, int, int)", 68 bb.length, 2); 69 bb = cSpi.engineDoFinal(bb1, 1, 2); 70 assertEquals("Incorrect result of engineDoFinal(byte, int, int)", 2, 71 bb.length); 72 assertEquals( 73 "Incorrect result of engineUpdate(byte, int, int, byte, int)", 74 cSpi.engineUpdate(bb1, 1, 2, bb2, 7), 2); 75 assertEquals( 76 "Incorrect result of engineDoFinal(byte, int, int, byte, int)", 77 2, cSpi.engineDoFinal(bb1, 1, 2, bb2, 0)); 78 } 79 80 /** 81 * Test for <code>engineGetKeySize(Key)</code> method 82 * Assertion: It throws UnsupportedOperationException if it is not overridden 83 */ 84 public void testCipherSpi02() throws Exception { 85 CipherSpi cSpi = new myCipherSpi(); 86 try { 87 cSpi.engineGetKeySize(null); 88 fail("UnsupportedOperationException must be thrown"); 89 } catch (UnsupportedOperationException e) { 90 } 91 } 92 93 /** 94 * Test for <code>engineWrap(Key)</code> method 95 * Assertion: It throws UnsupportedOperationException if it is not overridden 96 */ 97 public void testCipherSpi03() throws Exception { 98 CipherSpi cSpi = new myCipherSpi(); 99 try { 100 cSpi.engineWrap(null); 101 fail("UnsupportedOperationException must be thrown"); 102 } catch (UnsupportedOperationException e) { 103 } 104 } 105 106 /** 107 * Test for <code>engineUnwrap(byte[], String, int)</code> method 108 * Assertion: It throws UnsupportedOperationException if it is not overridden 109 */ 110 public void testCipherSpi04() throws Exception { 111 CipherSpi cSpi = new myCipherSpi(); 112 try { 113 cSpi.engineUnwrap(new byte[0], "", 0); 114 fail("UnsupportedOperationException must be thrown"); 115 } catch (UnsupportedOperationException e) { 116 } 117 } 118 119 /** 120 * Test for <code>engineUpdate(ByteBuffer, ByteBuffer)</code> method 121 * Assertions: 122 * throws NullPointerException if one of these buffers is null; 123 * throws ShortBufferException is there is no space in output to hold result 124 */ 125 public void testCipherSpi05() throws ShortBufferException { 126 CipherSpi cSpi = new myCipherSpi(); 127 byte[] bb = { (byte) 0, (byte) 1, (byte) 2, (byte) 3, (byte) 4, 128 (byte) 5, (byte) 6, (byte) 7, (byte) 8, (byte) 9, (byte) 10 }; 129 int pos = 5; 130 int len = bb.length; 131 ByteBuffer bbNull = null; 132 ByteBuffer bb1 = ByteBuffer.allocate(len); 133 bb1.put(bb); 134 bb1.position(0); 135 try { 136 cSpi.engineUpdate(bbNull, bb1); 137 fail("NullPointerException must be thrown"); 138 } catch (NullPointerException e) { 139 } 140 try { 141 cSpi.engineUpdate(bb1, bbNull); 142 fail("NullPointerException must be thrown"); 143 } catch (NullPointerException e) { 144 } 145 ByteBuffer bb2 = ByteBuffer.allocate(bb.length); 146 bb1.position(len); 147 assertEquals("Incorrect number of stored bytes", 0, cSpi.engineUpdate( 148 bb1, bb2)); 149 150 bb1.position(0); 151 bb2.position(len - 2); 152 try { 153 cSpi.engineUpdate(bb1, bb2); 154 fail("ShortBufferException bust be thrown. Output buffer remaining: " 155 .concat(Integer.toString(bb2.remaining()))); 156 } catch (ShortBufferException e) { 157 } 158 bb1.position(10); 159 bb2.position(0); 160 assertTrue("Incorrect number of stored bytes", cSpi.engineUpdate(bb1, 161 bb2) > 0); 162 bb1.position(bb.length); 163 cSpi.engineUpdate(bb1, bb2); 164 165 bb1.position(pos); 166 bb2.position(0); 167 int res = cSpi.engineUpdate(bb1, bb2); 168 assertTrue("Incorrect result", res > 0); 169 } 170 171 /** 172 * Test for <code>engineDoFinal(ByteBuffer, ByteBuffer)</code> method 173 * Assertions: 174 * throws NullPointerException if one of these buffers is null; 175 * throws ShortBufferException is there is no space in output to hold result 176 */ 177 public void testCipherSpi06() throws BadPaddingException, 178 ShortBufferException, IllegalBlockSizeException { 179 CipherSpi cSpi = new myCipherSpi(); 180 int len = 10; 181 byte[] bbuf = new byte[len]; 182 for (int i = 0; i < bbuf.length; i++) { 183 bbuf[i] = (byte) i; 184 } 185 ByteBuffer bb1 = ByteBuffer.wrap(bbuf); 186 ByteBuffer bbNull = null; 187 try { 188 cSpi.engineDoFinal(bbNull, bb1); 189 fail("NullPointerException must be thrown"); 190 } catch (NullPointerException e) { 191 } 192 try { 193 cSpi.engineDoFinal(bb1, bbNull); 194 fail("NullPointerException must be thrown"); 195 } catch (NullPointerException e) { 196 } 197 ByteBuffer bb2 = ByteBuffer.allocate(len); 198 bb1.position(bb1.limit()); 199 assertEquals("Incorrect result", 0, cSpi.engineDoFinal(bb1, bb2)); 200 201 bb1.position(0); 202 bb2.position(len - 2); 203 try { 204 cSpi.engineDoFinal(bb1, bb2); 205 fail("ShortBufferException must be thrown. Output buffer remaining: " 206 .concat(Integer.toString(bb2.remaining()))); 207 } catch (ShortBufferException e) { 208 } 209 int pos = 5; 210 bb1.position(pos); 211 bb2.position(0); 212 assertTrue("Incorrect result", cSpi.engineDoFinal(bb1, bb2) > 0); 213 } 214} 215 216/** 217 * Additional class for CipherGeneratorSpi constructor verification 218 */ 219 220class myCipherSpi extends CipherSpi { 221 private byte[] initV; 222 223 private static byte[] resV = { (byte) 7, (byte) 6, (byte) 5, (byte) 4, 224 (byte) 3, (byte) 2, (byte) 1, (byte) 0 }; 225 226 public myCipherSpi() { 227 this.initV = new byte[0]; 228 } 229 230 protected void engineSetMode(String mode) throws NoSuchAlgorithmException { 231 } 232 233 protected void engineSetPadding(String padding) 234 throws NoSuchPaddingException { 235 } 236 237 protected int engineGetBlockSize() { 238 return 0; 239 } 240 241 protected int engineGetOutputSize(int inputLen) { 242 return 0; 243 } 244 245 protected byte[] engineGetIV() { 246 return new byte[0]; 247 } 248 249 protected AlgorithmParameters engineGetParameters() { 250 return null; 251 } 252 253 protected void engineInit(int opmode, Key key, SecureRandom random) 254 throws InvalidKeyException { 255 } 256 257 protected void engineInit(int opmode, Key key, 258 AlgorithmParameterSpec params, SecureRandom random) 259 throws InvalidKeyException, InvalidAlgorithmParameterException { 260 } 261 262 protected void engineInit(int opmode, Key key, AlgorithmParameters params, 263 SecureRandom random) throws InvalidKeyException, 264 InvalidAlgorithmParameterException { 265 } 266 267 protected byte[] engineUpdate(byte[] input, int inputOffset, int inputLen) { 268 if (initV.length < inputLen) { 269 initV = new byte[inputLen]; 270 } 271 for (int i = 0; i < inputLen; i++) { 272 initV[i] = input[inputOffset + i]; 273 } 274 return initV; 275 } 276 277 protected int engineUpdate(byte[] input, int inputOffset, int inputLen, 278 byte[] output, int outputOffset) throws ShortBufferException { 279 byte[] res = engineUpdate(input, inputOffset, inputLen); 280 int t = res.length; 281 if ((output.length - outputOffset) < t) { 282 throw new ShortBufferException("Update"); 283 } 284 for (int i = 0; i < t; i++) { 285 output[i + outputOffset] = initV[i]; 286 } 287 return t; 288 } 289 290 protected byte[] engineDoFinal(byte[] input, int inputOffset, int inputLen) 291 throws IllegalBlockSizeException, BadPaddingException { 292 if (resV.length > inputLen) { 293 byte[] bb = new byte[inputLen]; 294 for (int i = 0; i < inputLen; i++) { 295 bb[i] = resV[i]; 296 } 297 return bb; 298 } 299 return resV; 300 } 301 302 protected int engineDoFinal(byte[] input, int inputOffset, int inputLen, 303 byte[] output, int outputOffset) throws ShortBufferException, 304 IllegalBlockSizeException, BadPaddingException { 305 byte[] res = engineDoFinal(input, inputOffset, inputLen); 306 307 int t = res.length; 308 if ((output.length - outputOffset) < t) { 309 throw new ShortBufferException("DoFinal"); 310 } 311 for (int i = 0; i < t; i++) { 312 output[i + outputOffset] = res[i]; 313 } 314 return t; 315 } 316 317 318 protected int engineUpdate(ByteBuffer input, ByteBuffer output) 319 throws ShortBufferException { 320 return super.engineUpdate(input, output); 321 } 322 323 protected int engineDoFinal(ByteBuffer input, ByteBuffer output) 324 throws ShortBufferException, IllegalBlockSizeException, 325 BadPaddingException { 326 return super.engineDoFinal(input, output); 327 } 328} 329