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 org.apache.harmony.auth.tests.javax.security.sasl; 23 24import java.io.IOException; 25import java.security.Provider; 26import java.security.Security; 27import java.util.Map; 28 29import javax.security.auth.callback.Callback; 30import javax.security.auth.callback.CallbackHandler; 31import javax.security.auth.callback.NameCallback; 32import javax.security.auth.callback.PasswordCallback; 33import javax.security.auth.callback.TextOutputCallback; 34import javax.security.auth.callback.UnsupportedCallbackException; 35import javax.security.sasl.Sasl; 36import javax.security.sasl.SaslClient; 37import javax.security.sasl.SaslClientFactory; 38import javax.security.sasl.SaslException; 39 40import junit.framework.TestCase; 41 42import org.apache.harmony.auth.tests.support.SpiEngUtils; 43 44/** 45 * Test for Sasl class 46 */ 47public class Sasl3Test extends TestCase { 48 private static final String CLNTSRV = "SaslClientFactory."; 49 50 private static final String fClientClass = mySaslClientFactory.class.getName();; 51 52 private Provider [] provs; 53 private boolean initProvs; 54 55 @Override 56 protected void setUp() throws Exception { 57 super.setUp(); 58 if (!initProvs) { 59 provs = Security.getProviders(); 60 initProvs = true; 61 } 62 if (provs != null) { 63 for (Provider element : provs) { 64 Security.removeProvider(element.getName()); 65 } 66 } 67 } 68 69 protected Provider[] mProv; 70 71 private void addProviders() { 72 for (Provider element : mProv) { 73 Security.insertProviderAt(element, 1); 74 } 75 } 76 77 /* 78 * @see TestCase#tearDown() 79 */ 80 @Override 81 protected void tearDown() throws Exception { 82 super.tearDown(); 83 if (mProv != null) { 84 for (Provider element : mProv) { 85 Security.removeProvider(element.getName()); 86 } 87 } 88 if (provs != null) { 89 for (int i = 0; i < provs.length; i++) { 90 Security.insertProviderAt(provs[i], (i+1)); 91 } 92 } 93 } 94 95 /** 96 * Test for <code>createSaslClient(String[] mechanisms, 97 * String authanticationID, String protocol, String serverName, 98 * Map prop, CallbackHandler cbh))</code> 99 * method Assertions: throws NullPointerException when mechanisms is null; 100 * throws SaslException when parameters (protocol, cbh, mechanisms) are 101 * wrong. 102 * 103 * All providers are previously removed and 2 new providers were added. 104 */ 105 public void testCreateClient01() throws SaslException { 106 mProv = new Provider[] { 107 (new SpiEngUtils()).new MyProvider("MySaslClientProvider1", 108 "Testing provider SaslClientFactory - 1", CLNTSRV 109 .concat("NAME-1"), fClientClass), 110 (new SpiEngUtils()).new MyProvider("MySaslClientProvider2", 111 "Testing provider SaslClientFactory - 2", CLNTSRV 112 .concat("NAME-2"), fClientClass) }; 113 addProviders(); 114 115 CallbackHandler cbH = new cbHand(); 116 try { 117 Sasl.createSaslClient(null, null, null, null, null, cbH); 118 fail("NullPointerException should be thrown when mechanisms is null"); 119 } catch (NullPointerException e) { 120 } 121 try { 122 Sasl.createSaslClient(new String[] { "NAME-2" }, null, "protocol", 123 null, null, cbH); 124 fail("SaslException should be thrown when CallbackHandler is wrong"); 125 } catch (SaslException e) { 126 } 127 cbH = new cbHandN(); 128 try { 129 Sasl.createSaslClient(new String[] { "NAME-1" }, null, "protocol", 130 null, null, cbH); 131 fail("SaslException should be thrown when mechanisms is wrong"); 132 } catch (SaslException e) { 133 } 134 try { 135 Sasl.createSaslClient(new String[] { "NAME-2" }, null, null, null, 136 null, cbH); 137 fail("SaslException should be thrown when protocol is null"); 138 } catch (SaslException e) { 139 } 140 } 141 142 /** 143 * Test for <code>createSaslClient(String[] mechanisms, 144 * String authanticationID, String protocol, String serverName, 145 * Map prop, CallbackHandler cbh))</code> 146 * method Assertions: throws NullPointerException when mechanisms is null; 147 * returns null SaslClient. 148 * 149 * All providers are previously removed. 150 */ 151 public void testCreateClient02() throws SaslException { 152 try { 153 Sasl.createSaslClient(null, null, null, null, null, null); 154 fail("NullPointerException should be thrown when mechanisms is null"); 155 } catch (NullPointerException e) { 156 } 157 assertNull("Not null result", Sasl.createSaslClient( 158 new String[] { "NAME-999" }, null, null, null, null, null)); 159 } 160 161 /** 162 * Test for <code>createSaslClient(String[] mechanisms, 163 * String authanticationID, String protocol, String serverName, 164 * Map prop, CallbackHandler cbh))</code> 165 * method 166 * 167 * Assertions: returns SaslClient; throws SaslClient for NAME-1 mechanism 168 * 169 * All providers are previously removed and 2 new providers were added. 170 */ 171 public void testCreateClient03() throws SaslException { 172 mProv = new Provider[] { 173 (new SpiEngUtils()).new MyProvider("MySaslClientProvider1", 174 "Testing provider SaslClientFactory - 1", CLNTSRV 175 .concat("NAME-1"), fClientClass), 176 (new SpiEngUtils()).new MyProvider("MySaslClientProvider2", 177 "Testing provider SaslClientFactory - 2", CLNTSRV 178 .concat("NAME-2"), fClientClass) }; 179 addProviders(); 180 181 CallbackHandler cbH = new cbHandN(); 182 SaslClient saslC = Sasl.createSaslClient(new String[] { "NAME-2" }, 183 null, "protocol", null, null, cbH); 184 assertNotNull("Null result", saslC); 185 try { 186 saslC.unwrap(null, 1, 1); 187 fail("SaslException sould be thrown"); 188 } catch (SaslException e) { 189 } 190 assertFalse("Incorrect isComplete() result", saslC.isComplete()); 191 // try to create client for wrong mechanism 192 try { 193 saslC = Sasl.createSaslClient(new String[] { "NAME-1" }, null, 194 "protocol", null, null, cbH); 195 fail("SaslException sould be thrown"); 196 } catch (SaslException e) { 197 } 198 } 199 200 /** 201 * Test for <code>createSaslClient(String[] mechanisms, 202 * String authanticationID, String protocol, String serverName, 203 * Map prop, CallbackHandler cbh))</code> 204 * method 205 * 206 * Assertions: returns SaslClient; throws SaslClient for NAME-1 mechanism 207 * 208 * All providers are previously removed and 1 new provider was added. 209 */ 210 public void testCreateClient04() throws SaslException { 211 mProv = new Provider[] { (new SpiEngUtils()).new MyProvider( 212 "MySaslClientProvider1", 213 "Testing provider SaslClientFactory - 1", CLNTSRV 214 .concat("NAME-1"), fClientClass) }; 215 mProv[0].put(CLNTSRV.concat("NAME-2"), fClientClass); 216 addProviders(); 217 CallbackHandler cbH = new cbHandN(); 218 SaslClient saslC = Sasl.createSaslClient(new String[] { "NAME-2" }, 219 null, "protocol", null, null, cbH); 220 assertNotNull("Null result for NAME-2", saslC); 221 assertFalse("Incorrect isComplete() result", saslC.isComplete()); 222 // try to create client for wrong mechanism 223 try { 224 saslC = Sasl.createSaslClient(new String[] { "NAME-1" }, null, 225 "protocol", null, null, cbH); 226 fail("SaslException sould be thrown"); 227 } catch (SaslException e) { 228 } 229 } 230 231 /** 232 * Test for <code>createSaslClient(String[] mechanisms, 233 * String authanticationID, String protocol, String serverName, 234 * Map prop, CallbackHandler cbh))</code> 235 * method 236 * 237 * Assertions: return null client when there is no provider supported some 238 * mechanism returns SaslClient when incorrect mechanism is used 239 * 240 * All providers are previously removed and 2 new providers were added. 241 */ 242 public void testCreateClient05() throws SaslException { 243 mProv = new Provider[] { 244 (new SpiEngUtils()).new MyProvider("MySaslClientProvider1", 245 "Testing provider SaslClientFactory - 1", CLNTSRV 246 .concat("NAME-2"), fClientClass.concat("Ext")), 247 (new SpiEngUtils()).new MyProvider("MySaslClientProvider2", 248 "Testing provider SaslClientFactory - 2", CLNTSRV 249 .concat("NAME-1"), fClientClass), 250 (new SpiEngUtils()).new MyProvider("MySaslClientProvider3", 251 "Testing provider SaslClientFactory - 3", CLNTSRV 252 .concat("NAME-6"), fClientClass) }; 253 addProviders(); 254 255 CallbackHandler cbH = new cbHandN(); 256 257 SaslClient saslC; 258 // try to create SaslClient for wrong mechanism 259 // there is no provider supported NAME-77, NAME-66 mechanisms 260 261 assertNull("Not null object was created for wrong mechanism", Sasl 262 .createSaslClient(new String[] { "NAME-77", "NAME-66" }, null, 263 "protocol", null, null, cbH)); 264 265 saslC = Sasl.createSaslClient(new String[] { "NAME-2" }, null, 266 "protocol", null, null, cbH); 267 assertNotNull("Null result for NAME-2", saslC); 268 try { 269 saslC.unwrap(null, 1, 1); 270 fail("SaslException sould be thrown"); 271 } catch (SaslException e) { 272 } 273 assertFalse("Incorrect isComplete() result", saslC.isComplete()); 274 // NAME-1 was defined in some provider but it is supported in 275 // another provider 276 try { 277 Sasl.createSaslClient(new String[] { "NAME-1" }, null, "protocol", 278 null, null, cbH); 279 fail("SaslException sould be thrown"); 280 } catch (SaslException e) { 281 } 282 // NAME-6 and NAME-5 were defined in one provider but they are 283 // supported 284 // in another provider 285 saslC = Sasl.createSaslClient(new String[] { "NAME-6", "NAME-5" }, 286 null, "protocol", null, null, cbH); 287 assertNotNull("Null result for NAME-6 and NAME-5", saslC); 288 } 289 290 /* 291 * Additional classes for creating SaslClient and SaslServer objects 292 */ 293 294 public static class mySaslClientFactory implements SaslClientFactory { 295 public mySaslClientFactory() { 296 super(); 297 } 298 299 public String[] getMechanismNames(Map<String, ?> prop) { 300 return new String[] { "NAME-1", "NAME-2", "NAME-3", "NAME-4" }; 301 } 302 303 public SaslClient createSaslClient(String[] mech, String id, 304 String protocol, String srvName, Map<String, ?> prop, CallbackHandler hnd) 305 throws SaslException { 306 if (mech == null) { 307 throw new SaslException(); 308 } 309 if ("NAME-1".equals(mech[0])) { 310 throw new SaslException("Incorrect mechanisms"); 311 } 312 if (protocol == null) { 313 throw new SaslException("Protocol is null"); 314 } 315 TextOutputCallback[] cb = { new TextOutputCallback( 316 TextOutputCallback.INFORMATION, "Information") }; 317 try { 318 hnd.handle(cb); 319 } catch (UnsupportedCallbackException e) { 320 throw new SaslException("Incorrect callback handlere", e); 321 } catch (IOException e) { 322 throw new SaslException("Incorrect callback handlere", e); 323 } 324 return new mySaslClient(); 325 } 326 327 public class mySaslClient implements SaslClient { 328 public mySaslClient() { 329 super(); 330 } 331 332 public Object getNegotiatedProperty(String s) { 333 return ""; 334 } 335 336 public String getMechanismName() { 337 return "Proba"; 338 } 339 340 public boolean isComplete() { 341 return false; 342 } 343 344 public boolean hasInitialResponse() { 345 return false; 346 } 347 348 public void dispose() throws SaslException { 349 } 350 351 public byte[] evaluateChallenge(byte[] challenge) throws SaslException { 352 return new byte[0]; 353 } 354 355 public byte[] unwrap(byte[] incoming, int offset, int len) 356 throws SaslException { 357 throw new SaslException(); 358 } 359 360 public byte[] wrap(byte[] outgoing, int offset, int len) 361 throws SaslException { 362 return new byte[0]; 363 } 364 } 365 } 366 367 public static class mySaslClientFactoryExt extends mySaslClientFactory { 368 @Override 369 public String[] getMechanismNames(Map<String, ?> prop) { 370 return new String[] { "NAME-5", "NAME-6" }; 371 } 372 373 @Override 374 public SaslClient createSaslClient(String[] mech, String id, 375 String protocol, String srvName, Map<String, ?> prop, CallbackHandler hnd) 376 throws SaslException { 377 if (mech == null) { 378 throw new SaslException(); 379 } 380 return new mySaslClient(); 381 } 382 } 383 384 public static class cbHand implements CallbackHandler { 385 public cbHand() { 386 } 387 388 public void handle(Callback[] callbacks) throws IOException, 389 UnsupportedCallbackException { 390 for (Callback element : callbacks) { 391 if (element instanceof NameCallback) { 392 NameCallback nc = (NameCallback) element; 393 nc.setName("Ok"); 394 } else if (element instanceof PasswordCallback) { 395 PasswordCallback pc = (PasswordCallback) element; 396 System.err.print(pc.getPrompt()); 397 System.err.flush(); 398 pc.setPassword(new char[] { 'O', 'k' }); 399 } else { 400 throw new UnsupportedCallbackException(element, 401 "Callback should be NamCallback or PasswordCallback"); 402 } 403 } 404 } 405 } 406 407 public static class cbHandN implements CallbackHandler { 408 public cbHandN() { 409 } 410 411 public void handle(Callback[] callbacks) throws IOException, 412 UnsupportedCallbackException { 413 for (Callback element : callbacks) { 414 if (element instanceof TextOutputCallback) { 415 TextOutputCallback toc = (TextOutputCallback) element; 416 if (toc.getMessageType() != TextOutputCallback.INFORMATION) { 417 throw new IOException("Unsupported message type: " 418 + toc.getMessageType()); 419 } 420 } else { 421 throw new UnsupportedCallbackException(element, 422 "Callback should be TextOutputCallback"); 423 } 424 } 425 } 426 } 427} 428