1 /*
   2  * Copyright (c) 1999, 2003, Oracle and/or its affiliates. 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.  Oracle designates this
   8  * particular file as subject to the "Classpath" exception as provided
   9  * by Oracle 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 Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
  22  * or visit www.oracle.com if you need additional information or have any
  23  * questions.
  24  */
  25 
  26 package com.sun.security.sasl;
  27 
  28 import javax.security.sasl.*;
  29 
  30 /**
  31   * Implements the EXTERNAL SASL client mechanism.
  32   * (<A HREF="ftp://ftp.isi.edu/in-notes/rfc2222.txt">RFC 2222</A>).
  33   * The EXTERNAL mechanism returns the optional authorization ID as
  34   * the initial response. It processes no challenges.
  35   *
  36   * @author Rosanna Lee
  37   */
  38 final class ExternalClient implements SaslClient {
  39     private byte[] username;
  40     private boolean completed = false;
  41 
  42     /**
  43      * Constructs an External mechanism with optional authorization ID.
  44      *
  45      * @param authorizationID If non-null, used to specify authorization ID.
  46      * @throws SaslException if cannot convert authorizationID into UTF-8
  47      *     representation.
  48      */
  49     ExternalClient(String authorizationID) throws SaslException {
  50         if (authorizationID != null) {
  51             try {
  52                 username = authorizationID.getBytes("UTF8");
  53             } catch (java.io.UnsupportedEncodingException e) {
  54                 throw new SaslException("Cannot convert " + authorizationID +
  55                     " into UTF-8", e);
  56             }
  57         } else {
  58             username = new byte[0];
  59         }
  60     }
  61 
  62     /**
  63      * Retrieves this mechanism's name for initiating the "EXTERNAL" protocol
  64      * exchange.
  65      *
  66      * @return  The string "EXTERNAL".
  67      */
  68     public String getMechanismName() {
  69         return "EXTERNAL";
  70     }
  71 
  72     /**
  73      * This mechanism has an initial response.
  74      */
  75     public boolean hasInitialResponse() {
  76         return true;
  77     }
  78 
  79     public void dispose() throws SaslException {
  80     }
  81 
  82     /**
  83      * Processes the challenge data.
  84      * It returns the EXTERNAL mechanism's initial response,
  85      * which is the authorization id encoded in UTF-8.
  86      * This is the optional information that is sent along with the SASL command.
  87      * After this method is called, isComplete() returns true.
  88      *
  89      * @param challengeData Ignored.
  90      * @return The possible empty initial response.
  91      * @throws SaslException If authentication has already been called.
  92      */
  93     public byte[] evaluateChallenge(byte[] challengeData)
  94         throws SaslException {
  95         if (completed) {
  96             throw new IllegalStateException(
  97                 "EXTERNAL authentication already completed");
  98         }
  99         completed = true;
 100         return username;
 101     }
 102 
 103     /**
 104      * Returns whether this mechanism is complete.
 105      * @return true if initial response has been sent; false otherwise.
 106      */
 107     public boolean isComplete() {
 108         return completed;
 109     }
 110 
 111     /**
 112       * Unwraps the incoming buffer.
 113       *
 114       * @throws SaslException Not applicable to this mechanism.
 115       */
 116     public byte[] unwrap(byte[] incoming, int offset, int len)
 117         throws SaslException {
 118         if (completed) {
 119             throw new SaslException("EXTERNAL has no supported QOP");
 120         } else {
 121             throw new IllegalStateException(
 122                 "EXTERNAL authentication Not completed");
 123         }
 124     }
 125 
 126     /**
 127       * Wraps the outgoing buffer.
 128       *
 129       * @throws SaslException Not applicable to this mechanism.
 130       */
 131     public byte[] wrap(byte[] outgoing, int offset, int len)
 132         throws SaslException {
 133         if (completed) {
 134             throw new SaslException("EXTERNAL has no supported QOP");
 135         } else {
 136             throw new IllegalStateException(
 137                 "EXTERNAL authentication not completed");
 138         }
 139     }
 140 
 141     /**
 142      * Retrieves the negotiated property.
 143      * This method can be called only after the authentication exchange has
 144      * completed (i.e., when <tt>isComplete()</tt> returns true); otherwise, a
 145      * <tt>IllegalStateException</tt> is thrown.
 146      *
 147      * @return null No property is applicable to this mechanism.
 148      * @exception IllegalStateException if this authentication exchange
 149      * has not completed
 150      */
 151     public Object getNegotiatedProperty(String propName) {
 152         if (completed) {
 153             return null;
 154         } else {
 155             throw new IllegalStateException(
 156                 "EXTERNAL authentication not completed");
 157         }
 158     }
 159 }