1 package org.jacorb.security.sas; 2 3 22 23 import java.net.URLDecoder ; 24 import java.util.Hashtable ; 25 26 import org.apache.avalon.framework.configuration.Configurable; 27 import org.apache.avalon.framework.configuration.Configuration; 28 import org.apache.avalon.framework.configuration.ConfigurationException; 29 import org.apache.avalon.framework.logger.Logger; 30 import org.jacorb.orb.CDRInputStream; 31 import org.jacorb.orb.MinorCodes; 32 import org.jacorb.orb.giop.ClientConnection; 33 import org.jacorb.orb.portableInterceptor.ClientRequestInfoImpl; 34 import org.omg.ATLAS.ATLASProfile; 35 import org.omg.ATLAS.ATLASProfileHelper; 36 import org.omg.ATLAS.AuthTokenData; 37 import org.omg.ATLAS.AuthTokenDispenser; 38 import org.omg.ATLAS.AuthTokenDispenserHelper; 39 import org.omg.ATLAS.SCS_ATLAS; 40 import org.omg.CORBA.Any ; 41 import org.omg.CORBA.BAD_PARAM ; 42 import org.omg.CORBA.CompletionStatus ; 43 import org.omg.CSI.AuthorizationElement; 44 import org.omg.CSI.CompleteEstablishContext; 45 import org.omg.CSI.ContextError; 46 import org.omg.CSI.EstablishContext; 47 import org.omg.CSI.IdentityToken; 48 import org.omg.CSI.MTCompleteEstablishContext; 49 import org.omg.CSI.MTContextError; 50 import org.omg.CSI.MessageInContext; 51 import org.omg.CSI.SASContextBody; 52 import org.omg.CSI.SASContextBodyHelper; 53 import org.omg.CSIIOP.CompoundSecMechList; 54 import org.omg.CSIIOP.CompoundSecMechListHelper; 55 import org.omg.CSIIOP.ServiceConfiguration; 56 import org.omg.CSIIOP.TAG_CSI_SEC_MECH_LIST; 57 import org.omg.IOP.Codec ; 58 import org.omg.IOP.ENCODING_CDR_ENCAPS ; 59 import org.omg.IOP.Encoding ; 60 import org.omg.IOP.ServiceContext ; 61 import org.omg.IOP.TaggedComponent ; 62 import org.omg.IOP.CodecFactoryPackage.UnknownEncoding ; 63 import org.omg.PortableInterceptor.ClientRequestInterceptor ; 64 import org.omg.PortableInterceptor.ORBInitInfo ; 65 66 72 73 public class SASClientInterceptor 74 extends org.omg.CORBA.LocalObject 75 implements ClientRequestInterceptor , Configurable 76 { 77 protected static final int SecurityAttributeService = 15; 78 protected final String DEFAULT_NAME = "SASClientInterceptor"; 79 protected Codec codec = null; 80 protected String name = null; 81 82 private Logger logger = null; 83 84 protected byte[] contextToken = new byte[0]; 85 protected boolean useStateful = true; 86 protected Hashtable atlasCache = new Hashtable (); 87 88 protected ISASContext sasContext = null; 89 90 public SASClientInterceptor(ORBInitInfo info) 91 throws UnknownEncoding , ConfigurationException 92 { 93 name = DEFAULT_NAME; 94 Encoding encoding = new Encoding (ENCODING_CDR_ENCAPS.value, (byte) 1, (byte) 0); 95 codec = info.codec_factory().create_codec(encoding); 96 97 org.jacorb.orb.ORB orb = 98 ((org.jacorb.orb.portableInterceptor.ORBInitInfoImpl)info).getORB (); 99 configure( orb.getConfiguration()); 100 } 101 102 public void configure(Configuration configuration) 103 throws ConfigurationException 104 { 105 logger = 106 ((org.jacorb.config.Configuration)configuration).getNamedLogger("jacorb.security.sas.CSS"); 107 108 useStateful = 109 configuration.getAttribute("jacorb.security.sas.stateful","true").equals("true"); 110 111 String contextClass = null; 112 try 113 { 114 contextClass = configuration.getAttribute("jacorb.security.sas.contextClass"); 115 Class c = 116 org.jacorb.util.ObjectUtil.classForName(contextClass); 117 sasContext = (ISASContext)c.newInstance(); 118 } 119 catch(ConfigurationException ce) 120 { 121 if (logger.isDebugEnabled()) 122 logger.debug("ConfigurationException", ce); 123 } 124 catch (Exception e) 125 { 126 if (logger.isErrorEnabled()) 127 logger.error("Could not instantiate class " + contextClass + ": " + e); 128 } 129 130 if (sasContext == null) 131 { 132 if (logger.isErrorEnabled()) 133 logger.error("Could not load SAS context class: "+contextClass); 134 } 135 else 136 { 137 sasContext.configure(configuration); 138 sasContext.initClient(); 139 } 140 } 141 142 public void setContextToken(byte[] contextToken) { 143 this.contextToken = contextToken; 144 } 145 146 public String name() 147 { 148 return name; 149 } 150 151 public void destroy() 152 { 153 } 154 155 public void send_request(org.omg.PortableInterceptor.ClientRequestInfo ri) 156 throws org.omg.PortableInterceptor.ForwardRequest 157 { 158 org.omg.CORBA.ORB orb = ((ClientRequestInfoImpl) ri).orb; 161 162 CompoundSecMechList csmList = null; 164 try 165 { 166 TaggedComponent tc = ri.get_effective_component(TAG_CSI_SEC_MECH_LIST.value); 167 CDRInputStream is = new CDRInputStream( (org.omg.CORBA.ORB )null, tc.component_data); 168 is.openEncapsulatedArray(); 169 csmList = CompoundSecMechListHelper.read( is ); 170 } 171 catch (BAD_PARAM e) 172 { 173 if (logger.isDebugEnabled()) 174 logger.debug("Did not find tagged component TAG_CSI_SEC_MECH_LIST: "+ 175 ri.operation()); 176 } 177 catch (Exception e) 178 { 179 if (logger.isWarnEnabled()) 180 logger.warn("Did not find tagged component TAG_CSI_SEC_MECH_LIST: "+e); 181 } 182 183 if(csmList != null && 184 csmList.mechanism_list[0].as_context_mech.target_supports == 0 && 185 csmList.mechanism_list[0].as_context_mech.target_requires == 0 && 186 csmList.mechanism_list[0].sas_context_mech.target_supports == 0 && 187 csmList.mechanism_list[0].sas_context_mech.target_requires == 0) { 188 return; 189 } 190 191 ClientConnection connection = ((ClientRequestInfoImpl) ri).connection; 193 194 long client_context_id = 0; 195 if (useStateful) 196 client_context_id = connection.cacheSASContext("css".getBytes()); 197 if (client_context_id < 0) 198 { 199 if (logger.isInfoEnabled()) 200 logger.info("New SAS Context: " + (-client_context_id)); 201 } 202 203 AuthorizationElement[] authorizationList = getATLASTokens(orb, csmList); 205 206 try 208 { 209 Any msg = null; 210 if (client_context_id <= 0) 211 { 212 IdentityToken identityToken = new IdentityToken(); 213 identityToken.absent(true); 214 contextToken = sasContext.createClientContext(orb, codec, csmList); 215 msg = makeEstablishContext(orb, 216 -client_context_id, 217 authorizationList, 218 identityToken, 219 contextToken); 220 } 221 else 222 { 223 msg = makeMessageInContext(orb, client_context_id, false); 224 } 225 ri.add_request_service_context(new ServiceContext (SecurityAttributeService, codec.encode_value( msg ) ), true); 226 } 227 catch (Exception e) 228 { 229 if (logger.isWarnEnabled()) 230 logger.warn("Could not set security service context: " + e); 231 throw new org.omg.CORBA.NO_PERMISSION ("SAS Could not set security service context: " + e, 232 MinorCodes.SAS_CSS_FAILURE, 233 CompletionStatus.COMPLETED_NO); 234 } 235 } 236 237 public void send_poll(org.omg.PortableInterceptor.ClientRequestInfo ri) 238 { 239 } 240 241 public void receive_reply(org.omg.PortableInterceptor.ClientRequestInfo ri) 242 { 243 SASContextBody contextBody = null; 245 ServiceContext ctx = null; 246 try 247 { 248 ctx = ri.get_reply_service_context(SecurityAttributeService); 249 } 250 catch (BAD_PARAM e) 251 { 252 if (logger.isDebugEnabled()) 253 logger.debug("No SAS security context found: "+ri.operation()); 254 } 255 catch (Exception e) 256 { 257 if (logger.isWarnEnabled()) 258 logger.warn("No SAS security context found: "+e); 259 } 260 if (ctx == null || ctx.context_data.length <= 1) return; 261 262 try 263 { 264 Any msg = codec.decode_value( ctx.context_data, SASContextBodyHelper.type() ); 265 contextBody = SASContextBodyHelper.extract(msg); 266 } 267 catch (Exception e) 268 { 269 if (logger.isWarnEnabled()) 270 logger.warn("Could not parse SAS reply: " + e);e.printStackTrace(); 271 throw new org.omg.CORBA.NO_PERMISSION ("SAS Could not parse SAS reply: " + e, 272 MinorCodes.SAS_CSS_FAILURE, 273 CompletionStatus.COMPLETED_MAYBE); 274 } 275 ClientConnection connection = ((ClientRequestInfoImpl) ri).connection; 276 277 if (contextBody.discriminator() == MTCompleteEstablishContext.value) 279 { 280 CompleteEstablishContext reply = contextBody.complete_msg(); 281 282 if (reply.client_context_id > 0 && !reply.context_stateful) 284 connection.purgeSASContext(reply.client_context_id); 285 } 286 287 if (contextBody.discriminator() == MTContextError.value) 289 { 290 ContextError reply = contextBody.error_msg(); 291 292 if (reply.client_context_id > 0) 294 connection.purgeSASContext(reply.client_context_id); 295 } 296 } 297 298 public void receive_exception(org.omg.PortableInterceptor.ClientRequestInfo ri) 299 throws org.omg.PortableInterceptor.ForwardRequest 300 { 301 SASContextBody contextBody = null; 303 ServiceContext ctx = null; 304 try 305 { 306 ctx = ri.get_reply_service_context(SecurityAttributeService); 307 } 308 catch (BAD_PARAM e) 309 { 310 if (logger.isDebugEnabled()) 311 logger.debug("No SAS security context found (exception): "+ri.operation()); 312 } 313 catch (Exception e) 314 { 315 if (logger.isWarnEnabled()) 316 logger.warn("No SAS security context found (exception): "+e); 317 } 318 if (ctx == null || ctx.context_data.length <= 1) return; 319 320 try 321 { 322 Any msg = codec.decode_value( ctx.context_data, SASContextBodyHelper.type() ); 323 contextBody = SASContextBodyHelper.extract(msg); 324 } 325 catch (Exception e) 326 { 327 if (logger.isWarnEnabled()) 328 logger.warn("Could not parse SAS reply: " + e); 329 throw new org.omg.CORBA.NO_PERMISSION ("SAS Could not parse SAS reply: " + e, 330 MinorCodes.SAS_CSS_FAILURE, 331 CompletionStatus.COMPLETED_MAYBE); 332 } 333 ClientConnection connection = ((ClientRequestInfoImpl) ri).connection; 334 335 if (contextBody.discriminator() == MTCompleteEstablishContext.value) 337 { 338 CompleteEstablishContext reply = contextBody.complete_msg(); 339 logger.debug("receive_exception MTCompleteEstablishContext: " + reply.client_context_id); 340 341 if (reply.client_context_id > 0 && !reply.context_stateful) 343 connection.purgeSASContext(reply.client_context_id); 344 } 345 346 if (contextBody.discriminator() == MTContextError.value) 348 { 349 ContextError reply = contextBody.error_msg(); 350 logger.debug("receive_exception MTContextError: " + reply.client_context_id); 351 352 if (reply.client_context_id > 0) 354 connection.purgeSASContext(reply.client_context_id); 355 356 if (reply.major_status == 2) throw new org.omg.PortableInterceptor.ForwardRequest (ri.target()); 358 } 359 } 360 361 public void receive_other(org.omg.PortableInterceptor.ClientRequestInfo ri) 362 throws org.omg.PortableInterceptor.ForwardRequest 363 { 364 } 365 366 protected Any makeEstablishContext(org.omg.CORBA.ORB orb, 367 long client_context_id, 368 AuthorizationElement[] authorization_token, 369 IdentityToken identity_token, 370 byte[] client_authentication_token) 371 { 372 EstablishContext msg = new EstablishContext(); 373 msg.client_context_id = client_context_id; 374 msg.client_authentication_token = client_authentication_token; 375 msg.identity_token = identity_token; 376 msg.authorization_token = authorization_token; 377 SASContextBody contextBody = new SASContextBody(); 378 contextBody.establish_msg(msg); 379 Any any = orb.create_any(); 380 SASContextBodyHelper.insert( any, contextBody ); 381 return any; 382 } 383 384 protected Any makeMessageInContext(org.omg.CORBA.ORB orb, 385 long client_context_id, 386 boolean discard_context) 387 { 388 MessageInContext msg = new MessageInContext(); 389 msg.client_context_id = client_context_id; 390 msg.discard_context = discard_context; 391 SASContextBody contextBody = new SASContextBody(); 392 contextBody.in_context_msg(msg); 393 Any any = orb.create_any(); 394 SASContextBodyHelper.insert( any, contextBody ); 395 return any; 396 } 397 398 protected AuthorizationElement[] getATLASTokens(org.omg.CORBA.ORB orb, 399 CompoundSecMechList csmList) 400 throws org.omg.CORBA.NO_PERMISSION 401 { 402 ATLASProfile atlasProfile = null; 404 try 405 { 406 ServiceConfiguration authorities[] = 407 csmList.mechanism_list[0].sas_context_mech.privilege_authorities; 408 for (int i = 0; i < authorities.length; i++) 409 { 410 if (authorities[i].syntax != SCS_ATLAS.value) 411 continue; 412 Any any = codec.decode(authorities[i].name); 413 atlasProfile = ATLASProfileHelper.extract(any); 414 } 415 } 416 catch (Exception e) 417 { 418 if (logger.isWarnEnabled()) 419 logger.warn("Error parsing ATLAS from IOR: " + e); 420 throw new org.omg.CORBA.NO_PERMISSION ("SAS Error parsing ATLAS from IOR: " + e, 421 MinorCodes.SAS_ATLAS_FAILURE, 422 CompletionStatus.COMPLETED_NO); 423 } 424 if (atlasProfile == null) 425 return new AuthorizationElement[0]; 426 427 String cacheID = new String (atlasProfile.the_cache_id); 428 String locator = atlasProfile.the_locator.the_url(); 429 if (locator != null) 430 locator = URLDecoder.decode(locator); 431 432 synchronized (atlasCache) 434 { 435 if (atlasCache.containsKey(cacheID)) 436 { 437 return ((AuthTokenData)atlasCache.get(cacheID)).auth_token; 438 } 439 } 440 441 AuthTokenDispenser dispenser = null; 443 try 444 { 445 org.omg.CORBA.Object obj = orb.string_to_object(locator); 446 dispenser = AuthTokenDispenserHelper.narrow(obj); 447 } 448 catch (Exception e) 449 { 450 logger.warn("Could not find ATLAS server " + locator + ": " + e); 451 throw new org.omg.CORBA.NO_PERMISSION ("SAS Could not find ATLAS server " + locator + ": " + e, MinorCodes.SAS_ATLAS_FAILURE, CompletionStatus.COMPLETED_NO); 452 } 453 if (dispenser == null) 454 { 455 if (logger.isWarnEnabled()) 456 logger.warn("SAS found null ATLAS server " + locator); 457 throw new org.omg.CORBA.NO_PERMISSION ("SAS found null ATLAS server "+locator, 458 MinorCodes.SAS_ATLAS_FAILURE, 459 CompletionStatus.COMPLETED_NO); 460 } 461 462 AuthTokenData data = null; 463 try 464 { 465 data = dispenser.get_my_authorization_token(); 466 } 467 catch (Exception e) 468 { 469 if (logger.isWarnEnabled()) 470 logger.warn("Error getting ATLAS tokens from server " + 471 locator + ": " + e); 472 throw new org.omg.CORBA.NO_PERMISSION ("SAS Error getting ATLAS tokens from server: " + e, 473 MinorCodes.SAS_ATLAS_FAILURE, 474 CompletionStatus.COMPLETED_NO); 475 } 476 synchronized (atlasCache) 477 { 478 atlasCache.put(cacheID, data); 479 } 480 return data.auth_token; 481 } 482 483 } 484 | Popular Tags |