Save This Page
Home » openjdk-7 » javax.security » auth » kerberos » [javadoc | source]
    1   /*
    2    * Copyright 2000-2006 Sun Microsystems, Inc.  All Rights Reserved.
    3    * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
    4    *
    5    * This code is free software; you can redistribute it and/or modify it
    6    * under the terms of the GNU General Public License version 2 only, as
    7    * published by the Free Software Foundation.  Sun designates this
    8    * particular file as subject to the "Classpath" exception as provided
    9    * by Sun in the LICENSE file that accompanied this code.
   10    *
   11    * This code is distributed in the hope that it will be useful, but WITHOUT
   12    * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
   13    * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
   14    * version 2 for more details (a copy is included in the LICENSE file that
   15    * accompanied this code).
   16    *
   17    * You should have received a copy of the GNU General Public License version
   18    * 2 along with this work; if not, write to the Free Software Foundation,
   19    * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
   20    *
   21    * Please contact Sun Microsystems, Inc., 4150 Network Circle, Santa Clara,
   22    * CA 95054 USA or visit www.sun.com if you need additional information or
   23    * have any questions.
   24    */
   25   
   26   package javax.security.auth.kerberos;
   27   
   28   import java.util;
   29   import java.security.Permission;
   30   import java.security.BasicPermission;
   31   import java.security.PermissionCollection;
   32   import java.io.ObjectStreamField;
   33   import java.io.ObjectOutputStream;
   34   import java.io.ObjectInputStream;
   35   import java.io.IOException;
   36   
   37   /**
   38    * This class is used to restrict the usage of the Kerberos
   39    * delegation model, ie: forwardable and proxiable tickets.
   40    * <p>
   41    * The target name of this <code>Permission</code> specifies a pair of
   42    * kerberos service principals. The first is the subordinate service principal
   43    * being entrusted to use the TGT. The second service principal designates
   44    * the target service the subordinate service principal is to
   45    * interact with on behalf of the initiating KerberosPrincipal. This
   46    * latter service principal is specified to restrict the use of a
   47    * proxiable ticket.
   48    * <p>
   49    * For example, to specify the "host" service use of a forwardable TGT the
   50    * target permission is specified as follows:
   51    * <p>
   52    * <pre>
   53    *  DelegationPermission("\"host/foo.example.com@EXAMPLE.COM\" \"krbtgt/EXAMPLE.COM@EXAMPLE.COM\"");
   54    * </pre>
   55    * <p>
   56    * To give the "backup" service a proxiable nfs service ticket the target permission
   57    * might be specified:
   58    * <p>
   59    * <pre>
   60    *  DelegationPermission("\"backup/bar.example.com@EXAMPLE.COM\" \"nfs/home.EXAMPLE.COM@EXAMPLE.COM\"");
   61    * </pre>
   62    *
   63    * @since 1.4
   64    */
   65   
   66   public final class DelegationPermission extends BasicPermission
   67       implements java.io.Serializable {
   68   
   69       private static final long serialVersionUID = 883133252142523922L;
   70   
   71       private transient String subordinate, service;
   72   
   73       /**
   74        * Create a new <code>DelegationPermission</code>
   75        * with the specified subordinate and target principals.
   76        *
   77        * <p>
   78        *
   79        * @param principals the name of the subordinate and target principals
   80        *
   81        * @throws NullPointerException if <code>principals</code> is <code>null</code>.
   82        * @throws IllegalArgumentException if <code>principals</code> is empty.
   83        */
   84       public DelegationPermission(String principals) {
   85           super(principals);
   86           init(principals);
   87       }
   88   
   89       /**
   90        * Create a new <code>DelegationPermission</code>
   91        * with the specified subordinate and target principals.
   92        * <p>
   93        *
   94        * @param principals the name of the subordinate and target principals
   95        * <p>
   96        * @param actions should be null.
   97        *
   98        * @throws NullPointerException if <code>principals</code> is <code>null</code>.
   99        * @throws IllegalArgumentException if <code>principals</code> is empty.
  100        */
  101       public DelegationPermission(String principals, String actions) {
  102           super(principals, actions);
  103           init(principals);
  104       }
  105   
  106   
  107       /**
  108        * Initialize the DelegationPermission object.
  109        */
  110       private void init(String target) {
  111   
  112           StringTokenizer t = null;
  113           if (!target.startsWith("\"")) {
  114               throw new IllegalArgumentException
  115                   ("service principal [" + target +
  116                    "] syntax invalid: " +
  117                    "improperly quoted");
  118           } else {
  119               t = new StringTokenizer(target, "\"", false);
  120               subordinate = t.nextToken();
  121               if (t.countTokens() == 2) {
  122                   t.nextToken();  // bypass whitespace
  123                   service = t.nextToken();
  124               } else if (t.countTokens() > 0) {
  125                   throw new IllegalArgumentException
  126                       ("service principal [" + t.nextToken() +
  127                        "] syntax invalid: " +
  128                        "improperly quoted");
  129               }
  130           }
  131       }
  132   
  133       /**
  134        * Checks if this Kerberos delegation permission object "implies" the
  135        * specified permission.
  136        * <P>
  137        * If none of the above are true, <code>implies</code> returns false.
  138        * @param p the permission to check against.
  139        *
  140        * @return true if the specified permission is implied by this object,
  141        * false if not.
  142        */
  143       public boolean implies(Permission p) {
  144           if (!(p instanceof DelegationPermission))
  145               return false;
  146   
  147           DelegationPermission that = (DelegationPermission) p;
  148           if (this.subordinate.equals(that.subordinate) &&
  149               this.service.equals(that.service))
  150               return true;
  151   
  152           return false;
  153       }
  154   
  155   
  156       /**
  157        * Checks two DelegationPermission objects for equality.
  158        * <P>
  159        * @param obj the object to test for equality with this object.
  160        *
  161        * @return true if <i>obj</i> is a DelegationPermission, and
  162        *  has the same subordinate and service principal as this.
  163        *  DelegationPermission object.
  164        */
  165       public boolean equals(Object obj) {
  166           if (obj == this)
  167               return true;
  168   
  169           if (! (obj instanceof DelegationPermission))
  170               return false;
  171   
  172           DelegationPermission that = (DelegationPermission) obj;
  173           return implies(that);
  174       }
  175   
  176       /**
  177        * Returns the hash code value for this object.
  178        *
  179        * @return a hash code value for this object.
  180        */
  181   
  182       public int hashCode() {
  183           return getName().hashCode();
  184       }
  185   
  186   
  187       /**
  188        * Returns a PermissionCollection object for storing
  189        * DelegationPermission objects.
  190        * <br>
  191        * DelegationPermission objects must be stored in a manner that
  192        * allows them to be inserted into the collection in any order, but
  193        * that also enables the PermissionCollection implies method to
  194        * be implemented in an efficient (and consistent) manner.
  195        *
  196        * @return a new PermissionCollection object suitable for storing
  197        * DelegationPermissions.
  198        */
  199   
  200       public PermissionCollection newPermissionCollection() {
  201           return new KrbDelegationPermissionCollection();
  202       }
  203   
  204       /**
  205        * WriteObject is called to save the state of the DelegationPermission
  206        * to a stream. The actions are serialized, and the superclass
  207        * takes care of the name.
  208        */
  209       private synchronized void writeObject(java.io.ObjectOutputStream s)
  210           throws IOException
  211       {
  212           s.defaultWriteObject();
  213       }
  214   
  215       /**
  216        * readObject is called to restore the state of the
  217        * DelegationPermission from a stream.
  218        */
  219       private synchronized void readObject(java.io.ObjectInputStream s)
  220            throws IOException, ClassNotFoundException
  221       {
  222           // Read in the action, then initialize the rest
  223           s.defaultReadObject();
  224           init(getName());
  225       }
  226   
  227       /*
  228         public static void main(String args[]) throws Exception {
  229         DelegationPermission this_ =
  230         new DelegationPermission(args[0]);
  231         DelegationPermission that_ =
  232         new DelegationPermission(args[1]);
  233         System.out.println("-----\n");
  234         System.out.println("this.implies(that) = " + this_.implies(that_));
  235         System.out.println("-----\n");
  236         System.out.println("this = "+this_);
  237         System.out.println("-----\n");
  238         System.out.println("that = "+that_);
  239         System.out.println("-----\n");
  240   
  241         KrbDelegationPermissionCollection nps =
  242         new KrbDelegationPermissionCollection();
  243         nps.add(this_);
  244         nps.add(new DelegationPermission("\"host/foo.example.com@EXAMPLE.COM\" \"CN=Gary Ellison/OU=JSN/O=SUNW/L=Palo Alto/ST=CA/C=US\""));
  245         try {
  246         nps.add(new DelegationPermission("host/foo.example.com@EXAMPLE.COM \"CN=Gary Ellison/OU=JSN/O=SUNW/L=Palo Alto/ST=CA/C=US\""));
  247         } catch (Exception e) {
  248         System.err.println(e);
  249         }
  250   
  251         System.out.println("nps.implies(that) = " + nps.implies(that_));
  252         System.out.println("-----\n");
  253   
  254         Enumeration e = nps.elements();
  255   
  256         while (e.hasMoreElements()) {
  257         DelegationPermission x =
  258         (DelegationPermission) e.nextElement();
  259         System.out.println("nps.e = " + x);
  260         }
  261         }
  262       */
  263   }
  264   
  265   
  266   final class KrbDelegationPermissionCollection extends PermissionCollection
  267       implements java.io.Serializable {
  268   
  269       // Not serialized; see serialization section at end of class.
  270       private transient List<Permission> perms;
  271   
  272       public KrbDelegationPermissionCollection() {
  273           perms = new ArrayList<Permission>();
  274       }
  275   
  276   
  277       /**
  278        * Check and see if this collection of permissions implies the permissions
  279        * expressed in "permission".
  280        *
  281        * @param p the Permission object to compare
  282        *
  283        * @return true if "permission" is a proper subset of a permission in
  284        * the collection, false if not.
  285        */
  286   
  287       public boolean implies(Permission permission) {
  288           if (! (permission instanceof DelegationPermission))
  289                   return false;
  290   
  291           synchronized (this) {
  292               for (Permission x : perms) {
  293                   if (x.implies(permission))
  294                       return true;
  295               }
  296           }
  297           return false;
  298   
  299       }
  300   
  301       /**
  302        * Adds a permission to the DelegationPermissions. The key for
  303        * the hash is the name.
  304        *
  305        * @param permission the Permission object to add.
  306        *
  307        * @exception IllegalArgumentException - if the permission is not a
  308        *                                       DelegationPermission
  309        *
  310        * @exception SecurityException - if this PermissionCollection object
  311        *                                has been marked readonly
  312        */
  313   
  314       public void add(Permission permission) {
  315           if (! (permission instanceof DelegationPermission))
  316               throw new IllegalArgumentException("invalid permission: "+
  317                                                  permission);
  318           if (isReadOnly())
  319               throw new SecurityException("attempt to add a Permission to a readonly PermissionCollection");
  320   
  321           synchronized (this) {
  322               perms.add(0, permission);
  323           }
  324       }
  325   
  326       /**
  327        * Returns an enumeration of all the DelegationPermission objects
  328        * in the container.
  329        *
  330        * @return an enumeration of all the DelegationPermission objects.
  331        */
  332   
  333       public Enumeration<Permission> elements() {
  334           // Convert Iterator into Enumeration
  335           synchronized (this) {
  336               return Collections.enumeration(perms);
  337           }
  338       }
  339   
  340       private static final long serialVersionUID = -3383936936589966948L;
  341   
  342       // Need to maintain serialization interoperability with earlier releases,
  343       // which had the serializable field:
  344       //    private Vector permissions;
  345       /**
  346        * @serialField permissions java.util.Vector
  347        *     A list of DelegationPermission objects.
  348        */
  349       private static final ObjectStreamField[] serialPersistentFields = {
  350           new ObjectStreamField("permissions", Vector.class),
  351       };
  352   
  353       /**
  354        * @serialData "permissions" field (a Vector containing the DelegationPermissions).
  355        */
  356       /*
  357        * Writes the contents of the perms field out as a Vector for
  358        * serialization compatibility with earlier releases.
  359        */
  360       private void writeObject(ObjectOutputStream out) throws IOException {
  361           // Don't call out.defaultWriteObject()
  362   
  363           // Write out Vector
  364           Vector<Permission> permissions = new Vector<Permission>(perms.size());
  365   
  366           synchronized (this) {
  367               permissions.addAll(perms);
  368           }
  369   
  370           ObjectOutputStream.PutField pfields = out.putFields();
  371           pfields.put("permissions", permissions);
  372           out.writeFields();
  373       }
  374   
  375       /*
  376        * Reads in a Vector of DelegationPermissions and saves them in the perms field.
  377        */
  378       private void readObject(ObjectInputStream in) throws IOException,
  379       ClassNotFoundException {
  380           // Don't call defaultReadObject()
  381   
  382           // Read in serialized fields
  383           ObjectInputStream.GetField gfields = in.readFields();
  384   
  385           // Get the one we want
  386           Vector<Permission> permissions =
  387                   (Vector<Permission>)gfields.get("permissions", null);
  388           perms = new ArrayList<Permission>(permissions.size());
  389           perms.addAll(permissions);
  390       }
  391   }

Save This Page
Home » openjdk-7 » javax.security » auth » kerberos » [javadoc | source]