Docjar: A Java Source and Docuemnt Enginecom.*    java.*    javax.*    org.*    all    new    plug-in

Quick Search    Search Deep

Source code: org/activemq/security/jassjacc/JassJaccSecurityAdapter.java


1   /** 
2    * 
3    * Copyright 2004 Hiram Chirino
4    * 
5    * Licensed under the Apache License, Version 2.0 (the "License"); 
6    * you may not use this file except in compliance with the License. 
7    * 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  package org.activemq.security.jassjacc;
19  
20  import java.security.AccessControlContext;
21  import java.security.AccessControlException;
22  import java.security.AccessController;
23  import java.security.Permission;
24  import java.security.PrivilegedAction;
25  import java.util.Iterator;
26  
27  import javax.jms.JMSException;
28  import javax.security.auth.Subject;
29  import javax.security.auth.login.LoginContext;
30  import javax.security.jacc.PolicyConfiguration;
31  import javax.security.jacc.PolicyConfigurationFactory;
32  import javax.security.jacc.PolicyContext;
33  import javax.security.jacc.PolicyContextException;
34  
35  import org.activemq.broker.BrokerClient;
36  import org.activemq.message.ActiveMQDestination;
37  import org.activemq.message.ActiveMQMessage;
38  import org.activemq.message.ConnectionInfo;
39  import org.activemq.message.ConsumerInfo;
40  import org.activemq.message.ProducerInfo;
41  import org.activemq.security.SecurityAdapter;
42  
43  /**
44   * Implements SecurityAdapter that uses JASS to authenticate and
45   * JACC to authorize the user operations.
46   * 
47   * @version $Revision: 1.1.1.1 $
48   */
49  public class JassJaccSecurityAdapter implements SecurityAdapter {
50    
51    private String jassConfiguration;
52  
53    /**
54     * @param jassConfiguration
55     */
56    public JassJaccSecurityAdapter(String jassConfiguration) {
57      this.jassConfiguration = jassConfiguration;
58    }
59    
60    
61    protected AccessControlContext getAccessControlContext(BrokerClient client) {
62      
63      Subject subject = client.getSubject();
64          if (subject == null) throw new IllegalArgumentException("Subject must not be null");
65  
66          AccessControlContext acc = (AccessControlContext) Subject.doAsPrivileged(subject, new PrivilegedAction() {
67              public Object run() {
68                  return AccessController.getContext();
69              }
70          }, null);        
71          
72      return acc;
73    }
74    
75    static protected String getBrokerName(BrokerClient client) {
76      return client.getBrokerConnector().getBrokerInfo().getBrokerName();
77    }
78  
79    public void authorizeConnection(BrokerClient client, ConnectionInfo info) throws JMSException {
80  
81      // Set the TCCL since it seems JAAS needs it to find the login module classes.
82      Thread.currentThread().setContextClassLoader(JassJaccSecurityAdapter.class.getClassLoader());
83      
84      // Do the login.
85          Subject subject = doJassLogin(info);
86          client.setSubject(subject);        
87      
88          // Can the user really use the broker?
89      PolicyContext.setContextID(getBrokerPoicyContextId(client));
90          AccessControlContext accessContext = getAccessControlContext(client);
91          if (accessContext != null) {
92              Permission permission = new JMSBrokerPermission(getBrokerName(client),JMSBrokerPermission.CONNECT_ACTION);
93              accessContext.checkPermission(permission);
94          }
95      }
96  
97    /**
98     * @param client
99     * @return
100    */
101   static private String getBrokerPoicyContextId(BrokerClient client) {
102     return getBrokerPolicyContextId(getBrokerName(client));
103   }
104 
105   /**
106    * @param client
107    * @return
108    */
109   static private String getBrokerPolicyContextId(String brokerName) {
110     return "org.activemq.broker:"+brokerName;
111   }
112 
113   /**
114    * @param info
115    * @param subject
116    * @return
117    */
118   private Subject doJassLogin(ConnectionInfo info) throws JMSException {
119     try {
120       LoginContext lc = new LoginContext(jassConfiguration,
121           new UsernamePasswordCallback(info.getUserName(), info
122               .getPassword()));
123       lc.login();
124       return lc.getSubject();
125     } catch (Exception e) {
126       throw (JMSException)new JMSException("Login failed: "+e.getMessage()).initCause(e);
127     }
128   }
129 
130   public void authorizeConsumer(BrokerClient client, ConsumerInfo info) throws JMSException {
131       PolicyContext.setContextID(getDestinationPoicyContextId(client, info.getDestination()));
132         AccessControlContext accessContext = getAccessControlContext(client);
133         if (accessContext != null) {
134             Permission permission = new JMSDestinationPermission(info.getDestination().getPhysicalName(),JMSDestinationPermission.CONSUME_ACTION);
135             accessContext.checkPermission(permission);
136         }
137     }
138 
139     public boolean authorizeReceive(BrokerClient client, ActiveMQMessage message) {
140         try {
141             PolicyContext.setContextID(getDestinationPoicyContextId(client, message.getJMSActiveMQDestination()));
142             AccessControlContext accessContext = getAccessControlContext(client);
143             if (accessContext != null) {
144                 Permission permission = new JMSDestinationPermission(message.getJMSActiveMQDestination().getPhysicalName(),JMSDestinationPermission.CONSUME_ACTION);
145                 accessContext.checkPermission(permission);
146             }
147         }
148         catch (AccessControlException e) {
149             return false;
150         }
151         return true;
152     }
153 
154 
155   /**
156    * @param client
157    * @param destination
158    * @return
159    */
160   static private String getDestinationPoicyContextId(BrokerClient client, ActiveMQDestination destination) {
161     return getDestinationPoicyContextId(getBrokerName(client), destination);
162   }
163   
164   static private String getDestinationPoicyContextId(String brokerName, ActiveMQDestination destination) {
165     ActiveMQDestination activeMQDestination = ((ActiveMQDestination)destination);
166     return (activeMQDestination.isTopic()?"org.activemq.topic:":"org.activemq.queue:")+brokerName+":"+activeMQDestination.getPhysicalName();
167   }
168 
169   public void authorizeProducer(BrokerClient client, ProducerInfo info) throws JMSException {
170       PolicyContext.setContextID(getDestinationPoicyContextId(client, info.getDestination()));
171         AccessControlContext accessContext = getAccessControlContext(client);
172         if (accessContext != null) {
173             Permission permission = new JMSDestinationPermission(info.getDestination().getPhysicalName(),JMSDestinationPermission.PRODUCE_ACTION);
174             accessContext.checkPermission(permission);
175         }
176     }
177 
178   public void authorizeSendMessage(BrokerClient client, ActiveMQMessage message) throws JMSException {
179       PolicyContext.setContextID(getDestinationPoicyContextId(client, message.getJMSActiveMQDestination()));
180         AccessControlContext accessContext = getAccessControlContext(client);
181         if (accessContext != null) {
182             String physicalName = ((ActiveMQDestination)message.getJMSDestination()).getPhysicalName();
183       Permission permission = new JMSDestinationPermission(message.getJMSActiveMQDestination().getPhysicalName(),JMSDestinationPermission.SEND_ACTION);
184             accessContext.checkPermission(permission);
185         }
186     }
187     
188   /**
189    * Creates a JACC PolicyConfiguration for the broker security.
190    * 
191    * @param brokerSecurity
192    */
193   static public void secure(BrokerSecurityConfig brokerSecurity) {
194 
195         try {
196           
197       PolicyConfigurationFactory factory = PolicyConfigurationFactory.getPolicyConfigurationFactory();
198       PolicyConfiguration policyConfiguration = factory.getPolicyConfiguration(
199           getBrokerPolicyContextId(brokerSecurity.getBrokerName()), true);
200 
201       for (Iterator iter = brokerSecurity.getConnectRoles().iterator(); iter.hasNext();) {
202         String role = (String) iter.next();
203         policyConfiguration.addToRole(role, new JMSBrokerPermission(
204             brokerSecurity.getBrokerName(), JMSBrokerPermission.CONNECT_ACTION));
205       }
206 
207       policyConfiguration.commit();
208 
209         } catch (ClassNotFoundException e) {
210       e.printStackTrace();
211     } catch (PolicyContextException e) {
212       e.printStackTrace();
213     }
214     
215   }
216 
217   /**
218    * Creates a JACC PolicyConfiguration for the broker security.
219    * 
220    * @param brokerSecurity
221    */
222   static public void secure(DestinationSecurityConfig destinationSecurity) {
223 
224         try {
225           
226           String policyId = getDestinationPoicyContextId(destinationSecurity.getBrokerName(), destinationSecurity.getDestination());
227       PolicyConfigurationFactory factory = PolicyConfigurationFactory.getPolicyConfigurationFactory();
228       PolicyConfiguration policyConfiguration = factory.getPolicyConfiguration(policyId, true);
229 
230       for (Iterator iter = destinationSecurity.getConsumeRoles().iterator(); iter.hasNext();) {
231         String role = (String) iter.next();
232         policyConfiguration.addToRole(role, new JMSDestinationPermission(
233             destinationSecurity.getDestination().getPhysicalName(), JMSDestinationPermission.CONSUME_ACTION));
234       }
235       for (Iterator iter = destinationSecurity.getProduceRoles().iterator(); iter.hasNext();) {
236         String role = (String) iter.next();
237         policyConfiguration.addToRole(role, new JMSDestinationPermission(
238             destinationSecurity.getDestination().getPhysicalName(), JMSDestinationPermission.PRODUCE_ACTION));
239       }
240       for (Iterator iter = destinationSecurity.getSendRoles().iterator(); iter.hasNext();) {
241         String role = (String) iter.next();
242         policyConfiguration.addToRole(role, new JMSDestinationPermission(
243             destinationSecurity.getDestination().getPhysicalName(), JMSDestinationPermission.SEND_ACTION));
244       }
245       
246       policyConfiguration.commit();
247 
248         } catch (ClassNotFoundException e) {
249       e.printStackTrace();
250     } catch (PolicyContextException e) {
251       e.printStackTrace();
252     }
253     
254   }
255 
256 }