1 /*
2 * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS HEADER.
3 *
4 * Copyright 1997-2007 Sun Microsystems, Inc. All rights reserved.
5 *
6 * The contents of this file are subject to the terms of either the GNU
7 * General Public License Version 2 only ("GPL") or the Common Development
8 * and Distribution License("CDDL") (collectively, the "License"). You
9 * may not use this file except in compliance with the License. You can obtain
10 * a copy of the License at https://glassfish.dev.java.net/public/CDDL+GPL.html
11 * or glassfish/bootstrap/legal/LICENSE.txt. See the License for the specific
12 * language governing permissions and limitations under the License.
13 *
14 * When distributing the software, include this License Header Notice in each
15 * file and include the License file at glassfish/bootstrap/legal/LICENSE.txt.
16 * Sun designates this particular file as subject to the "Classpath" exception
17 * as provided by Sun in the GPL Version 2 section of the License file that
18 * accompanied this code. If applicable, add the following below the License
19 * Header, with the fields enclosed by brackets [] replaced by your own
20 * identifying information: "Portions Copyrighted [year]
21 * [name of copyright owner]"
22 *
23 * Contributor(s):
24 *
25 * If you wish your version of this file to be governed by only the CDDL or
26 * only the GPL Version 2, indicate your decision by adding "[Contributor]
27 * elects to include this software in this distribution under the [CDDL or GPL
28 * Version 2] license." If you don't indicate a single choice of license, a
29 * recipient has the option to distribute your version of this file under
30 * either the CDDL, the GPL Version 2 or to extend the choice of license to
31 * its licensees as provided above. However, if you add GPL Version 2 code
32 * and therefore, elected the GPL Version 2 license, then the option applies
33 * only if the new code is made subject to such option by the copyright
34 * holder.
35 */
36
37 package javax.security.jacc;
38
39
40 import java.security.AccessController;
41 import java.security.AccessControlException;
42 import java.security.PrivilegedExceptionAction;
43 import java.security.PrivilegedActionException;
44 import java.security.SecurityPermission;
45
46 import javax.security.jacc.PolicyConfiguration;
47
48 import javax.security.jacc.PolicyContextException;
49
50 /**
51 * Abstract factory and finder class for obtaining
52 * the instance of the class that implements the PolicyConfigurationFactory
53 * of a provider. The factory will be used to instantiate PolicyConfiguration
54 * objects that will be used by the deployment tools of the container
55 * to create and manage policy contexts within the Policy Provider.
56 * <P>
57 * Implementation classes must have a public no argument constructor that
58 * may be used to create an operational instance of the factory implementation
59 * class.
60 *
61 * @see java.security.Permission
62 * @see javax.security.jacc.PolicyConfiguration
63 * @see javax.security.jacc.PolicyContextException
64 *
65 * @author Ron Monzillo
66 * @author Gary Ellison
67 * @author Harpreet Singh
68 */
69
70 public abstract class PolicyConfigurationFactory
71 {
72 private static String FACTORY_NAME =
73 "javax.security.jacc.PolicyConfigurationFactory.provider";
74
75 private static PolicyConfigurationFactory pcFactory;
76
77 /**
78 * This static method uses a system property to find and instantiate
79 * (via a public constructor) a provider specific factory implementation
80 * class. The name of the provider specific factory implementation class is
81 * obtained from the value of the system property,
82 * <P><code><Pre>
83 * javax.security.jacc.PolicyConfigurationFactory.provider.
84 * </Pre></code><P>
85 *
86 * @return the singleton instance of the provider specific
87 * PolicyConfigurationFactory implementation class.
88 *
89 * @throws java.lang.SecurityException
90 * when called by an AccessControlContext that has not been
91 * granted the "setPolicy" SecurityPermission.
92 *
93 * @throws java.lang.ClassNotFoundException
94 * when the class named by the system property could not be found
95 * including because the value of the system property has not be set.
96 *
97 * @throws javax.security.jacc.PolicyContextException
98 * if the implementation throws a checked exception that has not been
99 * accounted for by the getPolicyConfigurationFactory method signature.
100 * The exception thrown
101 * by the implementation class will be encapsulated (during construction)
102 * in the thrown PolicyContextException
103 */
104
105 public static PolicyConfigurationFactory getPolicyConfigurationFactory()
106 throws java.lang.ClassNotFoundException,
107 javax.security.jacc.PolicyContextException
108 {
109
110 SecurityManager sm = System.getSecurityManager();
111 if (sm != null) sm.checkPermission(new
112 java.security.SecurityPermission("setPolicy"));
113 if(pcFactory != null)
114 return pcFactory;
115
116 String msg;
117 final String classname[] = { null };
118
119 try {
120
121 Class clazz = null;
122
123 if (sm != null){
124 try{
125 clazz = (Class)AccessController.doPrivileged
126 (new PrivilegedExceptionAction(){
127 public Object run() throws java.lang.Exception{
128
129 classname[0] = System.getProperty(FACTORY_NAME);
130
131 if(classname[0] == null){
132 String msg = new String
133 ("JACC:Error PolicyConfigurationFactory : property not set : "+ FACTORY_NAME);
134 throw new ClassNotFoundException(msg);
135 }
136
137 return Class.forName(classname[0],true,
138 Thread.currentThread().getContextClassLoader());
139 }
140 });
141 } catch (PrivilegedActionException ex){
142 Exception e = ex.getException() ;
143 if ( e instanceof java.lang.ClassNotFoundException){
144 throw (java.lang.ClassNotFoundException)e;
145 } else if ( e instanceof java.lang.InstantiationException){
146 throw (java.lang.InstantiationException)e;
147 } else if ( e instanceof java.lang.IllegalAccessException){
148 throw (java.lang.IllegalAccessException)e;
149 }
150 }
151 } else {
152 classname[0] = System.getProperty(FACTORY_NAME);
153
154 if (classname[0] == null){
155 msg = new String
156 ("JACC:Error PolicyConfigurationFactory : property not set : "+ FACTORY_NAME);
157 throw new ClassNotFoundException(msg);
158 }
159
160 clazz = Class.forName(classname[0],true,
161 Thread.currentThread().getContextClassLoader());
162 }
163
164 Object factory = clazz.newInstance();
165
166 pcFactory = (PolicyConfigurationFactory) factory;
167
168 } catch(java.lang.ClassNotFoundException cnfe){
169 msg = new String
170 ("JACC:Error PolicyConfigurationFactory : cannot find class : "
171 + classname[0]);
172 throw new ClassNotFoundException(msg,cnfe);
173 } catch(java.lang.IllegalAccessException iae){
174 msg = new String
175 ("JACC:Error PolicyConfigurationFactory : cannot access class : "
176 + classname[0]);
177 throw new PolicyContextException(msg,iae);
178 } catch(java.lang.InstantiationException ie){
179 msg = new String
180 ("JACC:Error PolicyConfigurationFactory : cannot instantiate : "
181 + classname[0]);
182 throw new PolicyContextException(msg,ie);
183 } catch(java.lang.ClassCastException cce){
184 msg = new String
185 ("JACC:Error PolicyConfigurationFactory : class not PolicyConfigurationFactory : "+ classname[0]);
186 throw new ClassCastException(msg);
187 }
188
189 return pcFactory;
190
191 }
192
193 /**
194 * This method is used to obtain an instance of the provider specific
195 * class that implements the PolicyConfiguration interface that
196 * corresponds to the identified policy context within the provider.
197 * The methods of the PolicyConfiguration interface are used to
198 * define the policy statements of the identified policy context.
199 * <P>
200 * If at the time of the call, the identified policy context does not
201 * exist in the provider, then the policy context will be created
202 * in the provider and the Object that implements the context's
203 * PolicyConfiguration Interface will be returned. If the state of the
204 * identified context is "deleted" or "inService" it will be transitioned to
205 * the "open" state as a result of the call. The states in the lifecycle
206 * of a policy context are defined by the PolicyConfiguration interface.
207 * <P>
208 * For a given value of policy context identifier, this method
209 * must always return the same instance of PolicyConfiguration
210 * and there must be at most one actual instance of a
211 * PolicyConfiguration with a given policy context identifier
212 * (during a process context).
213 * <P>
214 * To preserve the invariant that there be at most one
215 * PolicyConfiguration object for a given policy context,
216 * it may be necessary for this method to be thread safe.
217 * <P>
218 * @param contextID A String identifying the policy context whose
219 * PolicyConfiguration interface is to be returned. The value passed to
220 * this parameter must not be null.
221 * <P>
222 * @param remove A boolean value that establishes whether or not the
223 * policy statements of an existing policy context are to be
224 * removed before its PolicyConfiguration object is returned. If the value
225 * passed to this parameter is true, the policy statements of
226 * an existing policy context will be removed. If the value is false,
227 * they will not be removed.
228 *
229 * @return an Object that implements the PolicyConfiguration
230 * Interface matched to the Policy provider and corresponding to the
231 * identified policy context.
232 *
233 * @throws java.lang.SecurityException
234 * when called by an AccessControlContext that has not been
235 * granted the "setPolicy" SecurityPermission.
236 *
237 * @throws javax.security.jacc.PolicyContextException
238 * if the implementation throws a checked exception that has not been
239 * accounted for by the getPolicyConfiguration method signature.
240 * The exception thrown
241 * by the implementation class will be encapsulated (during construction)
242 * in the thrown PolicyContextException.
243 */
244
245 public abstract PolicyConfiguration
246 getPolicyConfiguration(String contextID, boolean remove)
247 throws javax.security.jacc.PolicyContextException;
248
249 /**
250 * This method determines if the identified policy context
251 * exists with state "inService" in the Policy provider
252 * associated with the factory.
253 * <P>
254 * @param contextID A string identifying a policy context
255 *
256 * @return true if the identified policy context exists within the
257 * provider and its state is "inService", false otherwise.
258 *
259 * @throws java.lang.SecurityException
260 * when called by an AccessControlContext that has not been
261 * granted the "setPolicy" SecurityPermission.
262 *
263 * @throws javax.security.jacc.PolicyContextException
264 * if the implementation throws a checked exception that has not been
265 * accounted for by the inService method signature. The exception thrown
266 * by the implementation class will be encapsulated (during construction)
267 * in the thrown PolicyContextException.
268 */
269
270 public abstract boolean inService(String contextID)
271 throws javax.security.jacc.PolicyContextException;
272
273 }