JPolicy.java

00001 
00027 package org.objectweb.jonas_lib.security.jacc;
00028 
00029 import java.security.CodeSource;
00030 import java.security.Permission;
00031 import java.security.PermissionCollection;
00032 import java.security.Policy;
00033 import java.security.Principal;
00034 import java.security.ProtectionDomain;
00035 import java.security.SecurityPermission;
00036 
00037 import javax.security.jacc.EJBMethodPermission;
00038 import javax.security.jacc.EJBRoleRefPermission;
00039 import javax.security.jacc.PolicyConfiguration;
00040 import javax.security.jacc.PolicyConfigurationFactory;
00041 import javax.security.jacc.PolicyContext;
00042 import javax.security.jacc.PolicyContextException;
00043 import javax.security.jacc.WebResourcePermission;
00044 import javax.security.jacc.WebRoleRefPermission;
00045 import javax.security.jacc.WebUserDataPermission;
00046 
00047 import org.objectweb.common.TraceCore;
00048 
00049 import org.objectweb.jonas_lib.I18n;
00050 
00051 import org.objectweb.util.monolog.api.BasicLevel;
00052 import org.objectweb.util.monolog.api.Logger;
00053 
00069 public class JPolicy extends Policy {
00070 
00074     private static Logger logger = null;
00075 
00079     private static JPolicy unique = null;
00080 
00084     private static Policy initialPolicy = null;
00085 
00089     private static I18n i18n = I18n.getInstance(JPolicy.class);
00090 
00096     private static PolicyConfigurationFactory policyConfigurationFactory = null;
00097 
00098 
00103     public JPolicy() {
00104         // Retrieve existing policy
00105         initialPolicy = Policy.getPolicy();
00106 
00107         // init logger
00108         logger = TraceCore.sec;
00109     }
00110 
00115     private void initPolicyConfigurationFactory() throws JPolicyException {
00116         // Check that factory is the JOnAS policy configuration factory
00117         try {
00118             policyConfigurationFactory = PolicyConfigurationFactory.getPolicyConfigurationFactory();
00119         } catch (ClassNotFoundException cnfe) {
00120             throw new JPolicyException("PolicyConfigurationFactory class implementation was not found : '" + cnfe.getMessage() + "'.");
00121         } catch (PolicyContextException pce) {
00122             throw new JPolicyException("PolicyContextException in PolicyConfigurationFactory : '" + pce.getMessage() + "'.");
00123         }
00124 
00125     }
00126 
00127 
00132     public static JPolicy getInstance() {
00133         if (unique == null) {
00134             unique = new JPolicy();
00135         }
00136         return unique;
00137     }
00138 
00139 
00140 
00141     // Section 4.8
00142     // J2EE 1.4 container can call Policy.implies or Policy.getPermissions
00143     // with an argument ProtectionDomain that was constructed with the
00144     // principals of the caller.
00145     // Then the caller must call implies method on the returned PermissionCollection
00146 
00147 
00156     public boolean implies(ProtectionDomain domain, Permission permission) {
00157         String contextID = PolicyContext.getContextID();
00158 
00159         // Delegating model
00160         if (contextID == null) {
00161             return initialPolicy.implies(domain, permission);
00162         }
00163 
00164         // See 2.5 of JACC. A replacement Policy object may accomplish this
00165         // by delegating non-javax.security.jacc policy decisions to the
00166         // corresponding default system Policy implementation class.
00167         //TODO : change to not instanceof EJB and Web permissions (JACC permissions)
00168         if (permission instanceof SecurityPermission) {
00169             return initialPolicy.implies(domain, permission);
00170         }
00171 
00172         if (!(permission instanceof EJBMethodPermission || permission instanceof EJBRoleRefPermission
00173               || permission instanceof WebUserDataPermission || permission instanceof WebRoleRefPermission
00174               || permission instanceof WebResourcePermission)) {
00175             return initialPolicy.implies(domain, permission);
00176         }
00177 
00178         if (logger.isLoggable(BasicLevel.DEBUG)) {
00179             logger.log(BasicLevel.DEBUG, "!= null, Permission being checked = " + permission);
00180         }
00181 
00182         // configuration was committed ?
00183         try {
00184             if (policyConfigurationFactory == null) {
00185                 initPolicyConfigurationFactory();
00186             }
00187 
00188             if (!policyConfigurationFactory.inService(contextID)) {
00189                 if (logger.isLoggable(BasicLevel.DEBUG)) {
00190                     logger.log(BasicLevel.DEBUG, "Not in service, return false");
00191                 }
00192                 return false;
00193             }
00194         } catch (JPolicyException jpe) {
00195             if (logger.isLoggable(BasicLevel.ERROR)) {
00196                 logger.log(BasicLevel.ERROR, i18n.getMessage("JPolicy.implies.canNotCheck", jpe.getMessage()));
00197             }
00198             return false;
00199         } catch (PolicyContextException pce) {
00200             if (logger.isLoggable(BasicLevel.ERROR)) {
00201                 logger.log(BasicLevel.ERROR, i18n.getMessage("JPolicy.implies.canNotCheck", pce.getMessage()));
00202             }
00203             return false;
00204         }
00205 
00206         JPolicyConfiguration jPolicyConfiguration = null;
00207         try {
00208             PolicyConfiguration pc = policyConfigurationFactory.getPolicyConfiguration(contextID, false);
00209             if (pc instanceof JPolicyConfiguration) {
00210                 jPolicyConfiguration = (JPolicyConfiguration) pc;
00211             } else {
00212                 //Maybe it's a delegating policy configuration and we have a configuration for this object
00213                 jPolicyConfiguration = JPolicyConfigurationKeeper.getConfiguration(contextID);
00214                 if (jPolicyConfiguration == null) {
00215                     throw new RuntimeException("This policy provider can only manage JPolicyConfiguration objects");
00216                 }
00217             }
00218         } catch (PolicyContextException pce) {
00219             if (logger.isLoggable(BasicLevel.ERROR)) {
00220                 logger.log(BasicLevel.ERROR, i18n.getMessage("JPolicy.implies.canNotRetrieve", contextID, pce.getMessage()));
00221             }
00222             return false;
00223         }
00224 
00225         /* JACC 3.2
00226            The provider must ensure that excluded policy statements take precedence
00227            over overlapping unchecked policy statements, and that both excluded and
00228            unchecked policy statements take precedence over overlapping role based policy
00229            statements.
00230         */
00231         PermissionCollection excludedPermissions = jPolicyConfiguration.getExcludedPermissions();
00232         PermissionCollection uncheckedPermissions = jPolicyConfiguration.getUncheckedPermissions();
00233 
00234         logger.log(BasicLevel.DEBUG, "Check permission");
00235         logger.log(BasicLevel.DEBUG, "Excluded permissions = " + excludedPermissions);
00236         logger.log(BasicLevel.DEBUG, "unchecked permissions = " + uncheckedPermissions);
00237 
00238         // excluded ?
00239         if (excludedPermissions.implies(permission)) {
00240             if (logger.isLoggable(BasicLevel.DEBUG)) {
00241                 logger.log(BasicLevel.DEBUG, "Permission '" + permission + "' is excluded, return false");
00242             }
00243             return false;
00244         } else if (uncheckedPermissions.implies(permission)) { // unchecked
00245             if (logger.isLoggable(BasicLevel.DEBUG)) {
00246                 logger.log(BasicLevel.DEBUG, "Permission '" + permission + "' is unchecked, return true");
00247             }
00248             return true;
00249         } else {
00250             // per role if any or false
00251             if (domain.getPrincipals().length > 0) {
00252                 logger.log(BasicLevel.DEBUG, "There are principals, checking principals...");
00253                 // check roles
00254                 return isImpliedPermissionForPrincipals(jPolicyConfiguration, permission, domain.getPrincipals());
00255             } else {
00256                 if (logger.isLoggable(BasicLevel.DEBUG)) {
00257                     logger.log(BasicLevel.DEBUG, "Principals length = 0, there is no principal on this domain");
00258                 }
00259                 // permission not found
00260                 if (logger.isLoggable(BasicLevel.DEBUG)) {
00261                     logger.log(BasicLevel.DEBUG, "Permission '" + permission + "' not found, return false");
00262                 }
00263                 return false;
00264             }
00265         }
00266     }
00267 
00268 
00279     public PermissionCollection getPermissions(ProtectionDomain domain) {
00280 
00281          // Always use delegating model
00282         return initialPolicy.getPermissions(domain);
00283 
00284         //TODO : retrieve all permissions for a given ProtectionDomain
00285         //JPolicyConfiguration jPolicyConfiguration = policyConfigurationFactory.getPolicyConfiguration(contextID);
00286         //return jPolicyConfiguration.getPermissionsForDomain(domain);
00287         //         String contextID = PolicyContext.getContextID();
00288         //         // Delegating model
00289         //         if (contextID == null) {
00290         //             return initialPolicy.getPermissions(domain);
00291         //         } else {
00292         //             // not implemented as not recommended in section 4.8
00293         //             throw new UnsupportedOperationException("Method getPermissions with a given protection domain is not supported");
00294         //         }
00295 
00296     }
00297 
00298 
00312     public PermissionCollection getPermissions(CodeSource codeSource) {
00313 
00314         // Always use delegating model
00315         return initialPolicy.getPermissions(codeSource);
00316 
00317         //TODO : retrieve all permissions for a given codesource
00318         //         String contextID = PolicyContext.getContextID();
00319         //         if (contextID == null) {
00320         //             return initialPolicy.getPermissions(codeSource);
00321         //         } else {
00322         //             // not implemented
00323         //             throw new UnsupportedOperationException("Method getPermissions with a given codeSource is not implemented");
00324         //         }
00325     }
00326 
00327 
00331     public void refresh() {
00332         initialPolicy.refresh();
00333     }
00334 
00335 
00336 
00344     private boolean isImpliedPermissionForPrincipals(JPolicyConfiguration jPolicyConfiguration, Permission permission, Principal[] principals) {
00345         //if (logger.isLoggable(BasicLevel.DEBUG)) {
00346         //    logger.log(BasicLevel.DEBUG, "");
00347         //}
00348         PermissionCollection permissions = null;
00349         int i = 0;
00350         boolean implied = false;
00351         // for each principal's permissions check if the given permission is implied
00352         while (i < principals.length && !implied) {
00353             if (logger.isLoggable(BasicLevel.DEBUG)) {
00354                 logger.log(BasicLevel.DEBUG, "Checking permission '" + permission + "' with permissions of Principal '" + principals[i].getName() + "'.");
00355             }
00356             permissions = jPolicyConfiguration.getPermissionsForPrincipal(principals[i]);
00357 
00358             if (permissions.implies(permission)) {
00359                 if (logger.isLoggable(BasicLevel.DEBUG)) {
00360                     logger.log(BasicLevel.DEBUG, "Permission implied with principal '" + principals[i].getName() + "'.");
00361                 }
00362                 implied = true;
00363             }
00364             i++;
00365         }
00366         if (logger.isLoggable(BasicLevel.DEBUG)) {
00367             if (!implied) {
00368                 logger.log(BasicLevel.DEBUG, "Permission '" + permission + "' was not found in each permissions of the given roles, return false");
00369             }
00370         }
00371         return implied;
00372     }
00373 
00374 }
00375 

Generated on Tue Feb 15 15:05:56 2005 for JOnAS by  doxygen 1.3.9.1