8042900: Allow com.sun.security.jgss to be in different module than org.ietf.jgss
authorweijun
Wed, 17 Sep 2014 13:55:12 +0800
changeset 26629 3b9ed8175488
parent 26628 47c021955197
child 26630 7973c5ab32da
8042900: Allow com.sun.security.jgss to be in different module than org.ietf.jgss Reviewed-by: valeriep, alanb
jdk/src/java.security.jgss/share/classes/com/sun/security/jgss/ExtendedGSSContext.java
jdk/src/java.security.jgss/share/classes/com/sun/security/jgss/ExtendedGSSCredential.java
jdk/src/java.security.jgss/share/classes/com/sun/security/jgss/Extender.java
jdk/src/java.security.jgss/share/classes/org/ietf/jgss/GSSContext.java
jdk/src/java.security.jgss/share/classes/org/ietf/jgss/GSSName.java
jdk/src/java.security.jgss/share/classes/sun/net/www/protocol/http/spnego/NegotiatorImpl.java
jdk/src/java.security.jgss/share/classes/sun/security/jgss/GSSContextImpl.java
jdk/src/java.security.jgss/share/classes/sun/security/jgss/GSSCredentialImpl.java
jdk/src/java.security.jgss/share/classes/sun/security/jgss/GSSManagerImpl.java
jdk/src/java.security.jgss/share/classes/sun/security/jgss/JgssExtender.java
jdk/src/java.security.jgss/share/classes/sun/security/jgss/krb5/InitSecContextToken.java
jdk/src/java.security.jgss/share/classes/sun/security/jgss/krb5/Krb5Context.java
jdk/src/java.security.jgss/share/classes/sun/security/jgss/spi/GSSContextSpi.java
jdk/src/java.security.jgss/share/classes/sun/security/jgss/spnego/SpNegoContext.java
jdk/src/java.security.jgss/share/classes/sun/security/jgss/spnego/SpNegoCredElement.java
jdk/src/java.security.jgss/share/classes/sun/security/jgss/wrapper/NativeGSSContext.java
jdk/test/sun/security/krb5/auto/Context.java
jdk/test/sun/security/krb5/auto/NewInquireTypes.java
jdk/test/sun/security/krb5/auto/OkAsDelegate.java
jdk/test/sun/security/krb5/auto/OkAsDelegateXRealm.java
jdk/test/sun/security/krb5/auto/SSL.java
--- a/jdk/src/java.security.jgss/share/classes/com/sun/security/jgss/ExtendedGSSContext.java	Tue Sep 16 23:04:13 2014 +0400
+++ b/jdk/src/java.security.jgss/share/classes/com/sun/security/jgss/ExtendedGSSContext.java	Wed Sep 17 13:55:12 2014 +0800
@@ -26,6 +26,8 @@
 package com.sun.security.jgss;
 
 import org.ietf.jgss.*;
+import sun.security.jgss.GSSContextImpl;
+import sun.security.krb5.internal.AuthorizationData;
 
 /**
  * The extended GSSContext interface for supporting additional
@@ -34,13 +36,48 @@
  */
 @jdk.Exported
 public interface ExtendedGSSContext extends GSSContext {
+
+    // The impl is almost identical to GSSContextImpl with only 2 differences:
+    // 1. It implements the extended interface
+    // 2. It translates result to data types here in inquireSecContext
+    static class ExtendedGSSContextImpl extends GSSContextImpl
+            implements ExtendedGSSContext {
+
+        public ExtendedGSSContextImpl(GSSContextImpl old) {
+            super(old);
+        }
+
+        @Override
+        public Object inquireSecContext(InquireType type) throws GSSException {
+            SecurityManager security = System.getSecurityManager();
+            if (security != null) {
+                security.checkPermission(
+                        new InquireSecContextPermission(type.toString()));
+            }
+            Object output = super.inquireSecContext(type.name());
+            if (output != null) {
+                if (type == InquireType.KRB5_GET_AUTHZ_DATA) {
+                    AuthorizationData ad = (AuthorizationData) output;
+                    AuthorizationDataEntry[] authzData =
+                            new AuthorizationDataEntry[ad.count()];
+                    for (int i = 0; i < ad.count(); i++) {
+                        authzData[i] = new AuthorizationDataEntry(
+                                ad.item(i).adType, ad.item(i).adData);
+                    }
+                    output = authzData;
+                }
+            }
+            return output;
+        }
+    }
+
     /**
      * Return the mechanism-specific attribute associated with {@code type}.
      * <p>
      * If there is a security manager, an {@link InquireSecContextPermission}
      * with the name {@code type.mech} must be granted. Otherwise, this could
-     * result in a {@link SecurityException}.<p>
-     *
+     * result in a {@link SecurityException}.
+     * <p>
      * Example:
      * <pre>
      *      GSSContext ctxt = m.createContext(...)
--- a/jdk/src/java.security.jgss/share/classes/com/sun/security/jgss/ExtendedGSSCredential.java	Tue Sep 16 23:04:13 2014 +0400
+++ b/jdk/src/java.security.jgss/share/classes/com/sun/security/jgss/ExtendedGSSCredential.java	Wed Sep 17 13:55:12 2014 +0800
@@ -26,6 +26,7 @@
 package com.sun.security.jgss;
 
 import org.ietf.jgss.*;
+import sun.security.jgss.GSSCredentialImpl;
 
 /**
  * The extended GSSCredential interface for supporting additional
@@ -34,6 +35,15 @@
  */
 @jdk.Exported
 public interface ExtendedGSSCredential extends GSSCredential {
+
+    static class ExtendedGSSCredentialImpl extends GSSCredentialImpl
+            implements ExtendedGSSCredential {
+
+        public ExtendedGSSCredentialImpl(GSSCredentialImpl old) {
+            super(old);
+        }
+    }
+
     /**
      * Impersonates a principal. In Kerberos, this can be implemented
      * using the Microsoft S4U2self extension.
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.security.jgss/share/classes/com/sun/security/jgss/Extender.java	Wed Sep 17 13:55:12 2014 +0800
@@ -0,0 +1,56 @@
+/*
+ * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package com.sun.security.jgss;
+
+import org.ietf.jgss.GSSContext;
+import org.ietf.jgss.GSSCredential;
+import sun.security.jgss.GSSContextImpl;
+import sun.security.jgss.GSSCredentialImpl;
+import sun.security.jgss.JgssExtender;
+
+// The com.sun.security.jgss extension to JGSS-API
+class Extender extends JgssExtender {
+
+    static {
+        JgssExtender.setExtender(new Extender());
+    }
+
+    public GSSCredential wrap(GSSCredential cred) {
+        if (cred instanceof ExtendedGSSCredential.ExtendedGSSCredentialImpl) {
+            return cred;
+        } else {
+            return new ExtendedGSSCredential.ExtendedGSSCredentialImpl((GSSCredentialImpl)cred);
+        }
+    }
+
+    public GSSContext wrap(GSSContext ctxt) {
+        if (ctxt instanceof ExtendedGSSContext.ExtendedGSSContextImpl) {
+            return ctxt;
+        } else {
+            return new ExtendedGSSContext.ExtendedGSSContextImpl((GSSContextImpl)ctxt);
+        }
+    }
+}
--- a/jdk/src/java.security.jgss/share/classes/org/ietf/jgss/GSSContext.java	Tue Sep 16 23:04:13 2014 +0400
+++ b/jdk/src/java.security.jgss/share/classes/org/ietf/jgss/GSSContext.java	Wed Sep 17 13:55:12 2014 +0800
@@ -25,7 +25,6 @@
 
 package org.ietf.jgss;
 
-import sun.security.jgss.spi.*;
 import java.io.InputStream;
 import java.io.OutputStream;
 
--- a/jdk/src/java.security.jgss/share/classes/org/ietf/jgss/GSSName.java	Tue Sep 16 23:04:13 2014 +0400
+++ b/jdk/src/java.security.jgss/share/classes/org/ietf/jgss/GSSName.java	Wed Sep 17 13:55:12 2014 +0800
@@ -25,10 +25,6 @@
 
 package org.ietf.jgss;
 
-import sun.security.jgss.spi.*;
-import java.util.Vector;
-import java.util.Enumeration;
-
 /**
  * This interface encapsulates a single GSS-API principal entity. The
  * application obtains an implementation of this interface
--- a/jdk/src/java.security.jgss/share/classes/sun/net/www/protocol/http/spnego/NegotiatorImpl.java	Tue Sep 16 23:04:13 2014 +0400
+++ b/jdk/src/java.security.jgss/share/classes/sun/net/www/protocol/http/spnego/NegotiatorImpl.java	Wed Sep 17 13:55:12 2014 +0800
@@ -25,7 +25,6 @@
 
 package sun.net.www.protocol.http.spnego;
 
-import com.sun.security.jgss.ExtendedGSSContext;
 import java.io.IOException;
 
 import org.ietf.jgss.GSSContext;
@@ -36,6 +35,7 @@
 import sun.net.www.protocol.http.HttpCallerInfo;
 import sun.net.www.protocol.http.Negotiator;
 import sun.security.jgss.GSSManagerImpl;
+import sun.security.jgss.GSSContextImpl;
 import sun.security.jgss.GSSUtil;
 import sun.security.jgss.HttpCaller;
 
@@ -102,8 +102,8 @@
                                         GSSContext.DEFAULT_LIFETIME);
 
         // Always respect delegation policy in HTTP/SPNEGO.
-        if (context instanceof ExtendedGSSContext) {
-            ((ExtendedGSSContext)context).requestDelegPolicy(true);
+        if (context instanceof GSSContextImpl) {
+            ((GSSContextImpl)context).requestDelegPolicy(true);
         }
         oneToken = context.initSecContext(new byte[0], 0, 0);
     }
--- a/jdk/src/java.security.jgss/share/classes/sun/security/jgss/GSSContextImpl.java	Tue Sep 16 23:04:13 2014 +0400
+++ b/jdk/src/java.security.jgss/share/classes/sun/security/jgss/GSSContextImpl.java	Wed Sep 17 13:55:12 2014 +0800
@@ -33,7 +33,8 @@
 import java.io.ByteArrayInputStream;
 import java.io.ByteArrayOutputStream;
 import java.io.IOException;
-import com.sun.security.jgss.*;
+import java.lang.reflect.Field;
+import java.lang.reflect.Modifier;
 
 /**
  * This class represents the JGSS security context and its associated
@@ -87,10 +88,10 @@
  * per-message operations are returned in an instance of the MessageProp
  * class, which is used as an argument in these calls.</dl>
  */
-class GSSContextImpl implements ExtendedGSSContext {
+public class GSSContextImpl implements GSSContext {
 
-    private final GSSManagerImpl gssManager;
-    private final boolean initiator;
+    private GSSManagerImpl gssManager;
+    private boolean initiator;
 
     // private flags for the context state
     private static final int PRE_INIT = 1;
@@ -122,6 +123,22 @@
     private boolean reqAnonState = false;
     private boolean reqDelegPolicyState = false;
 
+    public GSSContextImpl() {
+        // Useless
+    }
+
+    // Used by new ExtendedGSSContext.ExtendedGSSContextImpl(ctxt)
+    protected GSSContextImpl(GSSContextImpl src) {
+        for (Field f: GSSContextImpl.class.getDeclaredFields()) {
+            if (!Modifier.isStatic(f.getModifiers())) {
+                try {
+                    f.set(this, f.get(src));
+                } catch (Exception e) {
+                    throw new RuntimeException(e);
+                }
+            }
+        }
+    }
     /**
      * Creates a GSSContextImp on the context initiator's side.
      */
@@ -613,7 +630,7 @@
                                    "No mechanism context yet!");
         GSSCredentialSpi delCredElement = mechCtxt.getDelegCred();
         return (delCredElement == null ?
-            null : new GSSCredentialImpl(gssManager, delCredElement));
+            null : GSSManagerImpl.wrap(new GSSCredentialImpl(gssManager, delCredElement)));
     }
 
     public boolean isInitiator() throws GSSException {
@@ -633,25 +650,18 @@
 
     // ExtendedGSSContext methods:
 
-    @Override
-    public Object inquireSecContext(InquireType type) throws GSSException {
-        SecurityManager security = System.getSecurityManager();
-        if (security != null) {
-            security.checkPermission(new InquireSecContextPermission(type.toString()));
-        }
+    public Object inquireSecContext(String type) throws GSSException {
         if (mechCtxt == null) {
             throw new GSSException(GSSException.NO_CONTEXT);
         }
         return mechCtxt.inquireSecContext(type);
     }
 
-    @Override
     public void requestDelegPolicy(boolean state) throws GSSException {
         if (mechCtxt == null && initiator)
             reqDelegPolicyState = state;
     }
 
-    @Override
     public boolean getDelegPolicyState() {
         if (mechCtxt != null)
             return mechCtxt.getDelegPolicyState();
--- a/jdk/src/java.security.jgss/share/classes/sun/security/jgss/GSSCredentialImpl.java	Tue Sep 16 23:04:13 2014 +0400
+++ b/jdk/src/java.security.jgss/share/classes/sun/security/jgss/GSSCredentialImpl.java	Wed Sep 17 13:55:12 2014 +0800
@@ -27,11 +27,11 @@
 
 import org.ietf.jgss.*;
 import sun.security.jgss.spi.*;
+
 import java.util.*;
-import com.sun.security.jgss.*;
 import sun.security.jgss.spnego.SpNegoCredElement;
 
-public class GSSCredentialImpl implements ExtendedGSSCredential {
+public class GSSCredentialImpl implements GSSCredential {
 
     private GSSManagerImpl gssManager = null;
     private boolean destroyed = false;
@@ -47,6 +47,18 @@
     // XXX Optimization for single mech usage
     private GSSCredentialSpi tempCred = null;
 
+    public GSSCredentialImpl() {
+        // Useless
+    }
+
+    // Used by new ExtendedGSSCredential.ExtendedGSSCredentialImpl(cred)
+    protected GSSCredentialImpl(GSSCredentialImpl src) {
+        this.gssManager = src.gssManager;
+        this.destroyed = src.destroyed;
+        this.hashtable = src.hashtable;
+        this.tempCred = src.tempCred;
+    }
+
     GSSCredentialImpl(GSSManagerImpl gssManager, int usage)
         throws GSSException {
         this(gssManager, null, GSSCredential.DEFAULT_LIFETIME,
@@ -140,7 +152,7 @@
                                   ((GSSNameImpl)name).getElement(mech));
         GSSCredentialSpi cred = tempCred.impersonate(nameElement);
         return (cred == null ?
-            null : new GSSCredentialImpl(gssManager, cred));
+            null : GSSManagerImpl.wrap(new GSSCredentialImpl(gssManager, cred)));
     }
 
     public GSSName getName() throws GSSException {
--- a/jdk/src/java.security.jgss/share/classes/sun/security/jgss/GSSManagerImpl.java	Tue Sep 16 23:04:13 2014 +0400
+++ b/jdk/src/java.security.jgss/share/classes/sun/security/jgss/GSSManagerImpl.java	Wed Sep 17 13:55:12 2014 +0800
@@ -145,35 +145,35 @@
 
     public GSSCredential createCredential(int usage)
         throws GSSException {
-        return new GSSCredentialImpl(this, usage);
+        return wrap(new GSSCredentialImpl(this, usage));
     }
 
     public GSSCredential createCredential(GSSName aName,
                                           int lifetime, Oid mech, int usage)
         throws GSSException {
-        return new GSSCredentialImpl(this, aName, lifetime, mech, usage);
+        return wrap(new GSSCredentialImpl(this, aName, lifetime, mech, usage));
     }
 
     public GSSCredential createCredential(GSSName aName,
                                           int lifetime, Oid mechs[], int usage)
         throws GSSException {
-        return new GSSCredentialImpl(this, aName, lifetime, mechs, usage);
+        return wrap(new GSSCredentialImpl(this, aName, lifetime, mechs, usage));
     }
 
     public GSSContext createContext(GSSName peer, Oid mech,
                                     GSSCredential myCred, int lifetime)
         throws GSSException {
-        return new GSSContextImpl(this, peer, mech, myCred, lifetime);
+        return wrap(new GSSContextImpl(this, peer, mech, myCred, lifetime));
     }
 
     public GSSContext createContext(GSSCredential myCred)
         throws GSSException {
-        return new GSSContextImpl(this, myCred);
+        return wrap(new GSSContextImpl(this, myCred));
     }
 
     public GSSContext createContext(byte[] interProcessToken)
         throws GSSException {
-        return new GSSContextImpl(this, interProcessToken);
+        return wrap(new GSSContextImpl(this, interProcessToken));
     }
 
     public void addProviderAtFront(Provider p, Oid mech)
@@ -257,4 +257,20 @@
         }
         return result;
     }
+
+    static {
+        // Load the extended JGSS interfaces if exist
+        try {
+            Class.forName("com.sun.security.jgss.Extender");
+        } catch (Exception e) {
+        }
+    }
+
+    static GSSCredential wrap(GSSCredentialImpl cred) {
+        return sun.security.jgss.JgssExtender.getExtender().wrap(cred);
+    }
+
+    static GSSContext wrap(GSSContextImpl ctxt) {
+        return sun.security.jgss.JgssExtender.getExtender().wrap(ctxt);
+    }
 }
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/jdk/src/java.security.jgss/share/classes/sun/security/jgss/JgssExtender.java	Wed Sep 17 13:55:12 2014 +0800
@@ -0,0 +1,81 @@
+/*
+ * Copyright (c) 2014, Oracle and/or its affiliates. All rights reserved.
+ * DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
+ *
+ * This code is free software; you can redistribute it and/or modify it
+ * under the terms of the GNU General Public License version 2 only, as
+ * published by the Free Software Foundation.  Oracle designates this
+ * particular file as subject to the "Classpath" exception as provided
+ * by Oracle in the LICENSE file that accompanied this code.
+ *
+ * This code is distributed in the hope that it will be useful, but WITHOUT
+ * ANY WARRANTY; without even the implied warranty of MERCHANTABILITY or
+ * FITNESS FOR A PARTICULAR PURPOSE.  See the GNU General Public License
+ * version 2 for more details (a copy is included in the LICENSE file that
+ * accompanied this code).
+ *
+ * You should have received a copy of the GNU General Public License version
+ * 2 along with this work; if not, write to the Free Software Foundation,
+ * Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA.
+ *
+ * Please contact Oracle, 500 Oracle Parkway, Redwood Shores, CA 94065 USA
+ * or visit www.oracle.com if you need additional information or have any
+ * questions.
+ */
+
+package sun.security.jgss;
+
+import org.ietf.jgss.GSSContext;
+import org.ietf.jgss.GSSCredential;
+
+/**
+ * The extending point of basic JGSS-API.
+ * <p>
+ * If a module wants to extend basic JGSS-API classes, it should extends this
+ * class and register itself as "the extender" using the setExtender method.
+ * When various GSSManager.createXXX methods are called, they will call
+ * "the extender"'s wrap methods to create objects of extended types
+ * instead of basic types.
+ * <p>
+ * We have only one extension now defined in com.sun.security.jgss, and the
+ * registering process is triggered in {@link GSSManagerImpl} by calling
+ * Class.forName("com.sun.security.jgss.Extender"). Only GSSContext
+ * and GSSCredential are extended now.
+ * <p>
+ * The setExtender method should be called before any JGSS call.
+ */
+public class JgssExtender {
+
+    // "The extender"
+    private static volatile JgssExtender theOne = new JgssExtender();
+
+    /**
+     * Gets "the extender". GSSManager calls this method so that it can
+     * wrap basic objects into extended objects.
+     * @return the extender
+     */
+    public static JgssExtender getExtender() {
+        return theOne;
+    }
+
+    /**
+     * Set "the extender" so that GSSManager can create extended objects.
+     */
+    protected static void setExtender(JgssExtender theOne) {
+        JgssExtender.theOne = theOne;
+    }
+
+    /**
+     * Wraps a plain GSSCredential object into an extended type.
+     */
+    public GSSCredential wrap(GSSCredential cred) {
+        return cred;
+    }
+
+    /**
+     * Wraps a plain GSSContext object into an extended type.
+     */
+    public GSSContext wrap(GSSContext ctxt) {
+        return ctxt;
+    }
+}
--- a/jdk/src/java.security.jgss/share/classes/sun/security/jgss/krb5/InitSecContextToken.java	Tue Sep 16 23:04:13 2014 +0400
+++ b/jdk/src/java.security.jgss/share/classes/sun/security/jgss/krb5/InitSecContextToken.java	Wed Sep 17 13:55:12 2014 +0800
@@ -25,7 +25,6 @@
 
 package sun.security.jgss.krb5;
 
-import com.sun.security.jgss.AuthorizationDataEntry;
 import org.ietf.jgss.*;
 import java.io.InputStream;
 import java.io.IOException;
@@ -152,17 +151,7 @@
                 new KerberosTime(apReq.getCreds().getAuthTime()).toString());
         context.setTktFlags(apReq.getCreds().getFlags());
         AuthorizationData ad = apReq.getCreds().getAuthzData();
-        if (ad == null) {
-            context.setAuthzData(null);
-        } else {
-            AuthorizationDataEntry[] authzData =
-                    new AuthorizationDataEntry[ad.count()];
-            for (int i=0; i<ad.count(); i++) {
-                authzData[i] = new AuthorizationDataEntry(
-                        ad.item(i).adType, ad.item(i).adData);
-            }
-            context.setAuthzData(authzData);
-        }
+        context.setAuthzData(ad);
     }
 
     public final KrbApReq getKrbApReq() {
--- a/jdk/src/java.security.jgss/share/classes/sun/security/jgss/krb5/Krb5Context.java	Tue Sep 16 23:04:13 2014 +0400
+++ b/jdk/src/java.security.jgss/share/classes/sun/security/jgss/krb5/Krb5Context.java	Wed Sep 17 13:55:12 2014 +0800
@@ -25,7 +25,6 @@
 
 package sun.security.jgss.krb5;
 
-import com.sun.security.jgss.InquireType;
 import org.ietf.jgss.*;
 import sun.misc.HexDumpEncoder;
 import sun.security.jgss.GSSUtil;
@@ -48,6 +47,7 @@
 import javax.security.auth.kerberos.KerberosPrincipal;
 import javax.security.auth.kerberos.KerberosTicket;
 import sun.security.krb5.internal.Ticket;
+import sun.security.krb5.internal.AuthorizationData;
 
 /**
  * Implements the mechanism specific context class for the Kerberos v5
@@ -1419,30 +1419,30 @@
     /**
      * Return the mechanism-specific attribute associated with {@code type}.
      */
-    public Object inquireSecContext(InquireType type)
+    public Object inquireSecContext(String type)
             throws GSSException {
         if (!isEstablished()) {
              throw new GSSException(GSSException.NO_CONTEXT, -1,
                      "Security context not established.");
         }
         switch (type) {
-            case KRB5_GET_SESSION_KEY:
+            case "KRB5_GET_SESSION_KEY":
                 return new KerberosSessionKey(key);
-            case KRB5_GET_SESSION_KEY_EX:
+            case "KRB5_GET_SESSION_KEY_EX":
                 return new javax.security.auth.kerberos.EncryptionKey(
                         key.getBytes(), key.getEType());
-            case KRB5_GET_TKT_FLAGS:
+            case "KRB5_GET_TKT_FLAGS":
                 return tktFlags.clone();
-            case KRB5_GET_AUTHZ_DATA:
+            case "KRB5_GET_AUTHZ_DATA":
                 if (isInitiator()) {
                     throw new GSSException(GSSException.UNAVAILABLE, -1,
                             "AuthzData not available on initiator side.");
                 } else {
-                    return (authzData==null)?null:authzData.clone();
+                    return authzData;
                 }
-            case KRB5_GET_AUTHTIME:
+            case "KRB5_GET_AUTHTIME":
                 return authTime;
-            case KRB5_GET_KRB_CRED:
+            case "KRB5_GET_KRB_CRED":
                 if (!isInitiator()) {
                     throw new GSSException(GSSException.UNAVAILABLE, -1,
                             "KRB_CRED not available on acceptor side.");
@@ -1470,7 +1470,7 @@
     // Helpers for inquireSecContext
     private boolean[] tktFlags;
     private String authTime;
-    private com.sun.security.jgss.AuthorizationDataEntry[] authzData;
+    private AuthorizationData authzData;
 
     public void setTktFlags(boolean[] tktFlags) {
         this.tktFlags = tktFlags;
@@ -1480,7 +1480,7 @@
         this.authTime = authTime;
     }
 
-    public void setAuthzData(com.sun.security.jgss.AuthorizationDataEntry[] authzData) {
+    public void setAuthzData(AuthorizationData authzData) {
         this.authzData = authzData;
     }
 
--- a/jdk/src/java.security.jgss/share/classes/sun/security/jgss/spi/GSSContextSpi.java	Tue Sep 16 23:04:13 2014 +0400
+++ b/jdk/src/java.security.jgss/share/classes/sun/security/jgss/spi/GSSContextSpi.java	Wed Sep 17 13:55:12 2014 +0800
@@ -34,7 +34,6 @@
 import java.io.InputStream;
 import java.io.OutputStream;
 import java.security.Provider;
-import com.sun.security.jgss.*;
 
 /**
  * This interface is implemented by a mechanism specific instance of a GSS
@@ -403,6 +402,6 @@
      * @throws GSSException see {@link ExtendedGSSContext#inquireSecContext}
      * for details
      */
-    public Object inquireSecContext(InquireType type)
+    public Object inquireSecContext(String type)
             throws GSSException;
 }
--- a/jdk/src/java.security.jgss/share/classes/sun/security/jgss/spnego/SpNegoContext.java	Tue Sep 16 23:04:13 2014 +0400
+++ b/jdk/src/java.security.jgss/share/classes/sun/security/jgss/spnego/SpNegoContext.java	Wed Sep 17 13:55:12 2014 +0800
@@ -25,8 +25,6 @@
 
 package sun.security.jgss.spnego;
 
-import com.sun.security.jgss.ExtendedGSSContext;
-import com.sun.security.jgss.InquireType;
 import java.io.*;
 import java.security.Provider;
 import org.ietf.jgss.*;
@@ -174,9 +172,9 @@
      */
     public final boolean getDelegPolicyState() {
         if (isInitiator() && mechContext != null &&
-                mechContext instanceof ExtendedGSSContext &&
+                mechContext instanceof GSSContextImpl &&
                 (state == STATE_IN_PROCESS || state == STATE_DONE)) {
-            return ((ExtendedGSSContext)mechContext).getDelegPolicyState();
+            return ((GSSContextImpl)mechContext).getDelegPolicyState();
         } else {
             return delegPolicyState;
         }
@@ -850,7 +848,7 @@
                     myCred.getInternalCred());
             }
             mechContext =
-                factory.manager.createContext(serverName,
+                    factory.manager.createContext(serverName,
                     internal_mech, cred, GSSContext.DEFAULT_LIFETIME);
             mechContext.requestConf(confState);
             mechContext.requestInteg(integState);
@@ -858,8 +856,8 @@
             mechContext.requestMutualAuth(mutualAuthState);
             mechContext.requestReplayDet(replayDetState);
             mechContext.requestSequenceDet(sequenceDetState);
-            if (mechContext instanceof ExtendedGSSContext) {
-                ((ExtendedGSSContext)mechContext).requestDelegPolicy(
+            if (mechContext instanceof GSSContextImpl) {
+                ((GSSContextImpl)mechContext).requestDelegPolicy(
                         delegPolicyState);
             }
         }
@@ -890,8 +888,7 @@
                 cred = new GSSCredentialImpl(factory.manager,
                 myCred.getInternalCred());
             }
-            mechContext =
-                factory.manager.createContext(cred);
+            mechContext = factory.manager.createContext(cred);
         }
 
         // pass token to mechanism acceptSecContext
@@ -1217,14 +1214,14 @@
     /**
      * Retrieve attribute of the context for {@code type}.
      */
-    public Object inquireSecContext(InquireType type)
+    public Object inquireSecContext(String type)
             throws GSSException {
         if (mechContext == null) {
             throw new GSSException(GSSException.NO_CONTEXT, -1,
                     "Underlying mech not established.");
         }
-        if (mechContext instanceof ExtendedGSSContext) {
-            return ((ExtendedGSSContext)mechContext).inquireSecContext(type);
+        if (mechContext instanceof GSSContextImpl) {
+            return ((GSSContextImpl)mechContext).inquireSecContext(type);
         } else {
             throw new GSSException(GSSException.BAD_MECH, -1,
                     "inquireSecContext not supported by underlying mech.");
--- a/jdk/src/java.security.jgss/share/classes/sun/security/jgss/spnego/SpNegoCredElement.java	Tue Sep 16 23:04:13 2014 +0400
+++ b/jdk/src/java.security.jgss/share/classes/sun/security/jgss/spnego/SpNegoCredElement.java	Wed Sep 17 13:55:12 2014 +0800
@@ -27,8 +27,6 @@
 import org.ietf.jgss.*;
 import java.security.Provider;
 import sun.security.jgss.GSSUtil;
-import sun.security.jgss.ProviderList;
-import sun.security.jgss.GSSCredentialImpl;
 import sun.security.jgss.spi.GSSNameSpi;
 import sun.security.jgss.spi.GSSCredentialSpi;
 
--- a/jdk/src/java.security.jgss/share/classes/sun/security/jgss/wrapper/NativeGSSContext.java	Tue Sep 16 23:04:13 2014 +0400
+++ b/jdk/src/java.security.jgss/share/classes/sun/security/jgss/wrapper/NativeGSSContext.java	Wed Sep 17 13:55:12 2014 +0800
@@ -36,7 +36,6 @@
 import sun.security.jgss.spnego.NegTokenInit;
 import sun.security.jgss.spnego.NegTokenTarg;
 import javax.security.auth.kerberos.DelegationPermission;
-import com.sun.security.jgss.InquireType;
 import java.io.*;
 
 
@@ -623,7 +622,7 @@
         dispose();
     }
 
-    public Object inquireSecContext(InquireType type)
+    public Object inquireSecContext(String type)
             throws GSSException {
         throw new GSSException(GSSException.UNAVAILABLE, -1,
                 "Inquire type not supported.");
--- a/jdk/test/sun/security/krb5/auto/Context.java	Tue Sep 16 23:04:13 2014 +0400
+++ b/jdk/test/sun/security/krb5/auto/Context.java	Wed Sep 17 13:55:12 2014 +0800
@@ -22,15 +22,14 @@
  */
 
 import com.sun.security.auth.module.Krb5LoginModule;
-import java.security.Key;
+
+import java.lang.reflect.Method;
 import java.security.PrivilegedActionException;
 import java.security.PrivilegedExceptionAction;
 import java.util.Arrays;
-import java.util.Base64;
 import java.util.HashMap;
 import java.util.Map;
 import javax.security.auth.Subject;
-import javax.security.auth.kerberos.KerberosCredMessage;
 import javax.security.auth.kerberos.KerberosKey;
 import javax.security.auth.kerberos.KerberosTicket;
 import javax.security.auth.login.LoginContext;
@@ -41,10 +40,6 @@
 import org.ietf.jgss.GSSName;
 import org.ietf.jgss.MessageProp;
 import org.ietf.jgss.Oid;
-import com.sun.security.jgss.ExtendedGSSContext;
-import com.sun.security.jgss.InquireType;
-import com.sun.security.jgss.AuthorizationDataEntry;
-import com.sun.security.jgss.ExtendedGSSCredential;
 import java.io.ByteArrayInputStream;
 import java.io.ByteArrayOutputStream;
 import java.security.Principal;
@@ -78,7 +73,7 @@
 public class Context {
 
     private Subject s;
-    private ExtendedGSSContext x;
+    private GSSContext x;
     private String name;
     private GSSCredential cred;     // see static method delegated().
 
@@ -143,7 +138,6 @@
     /**
      * Logins with username/password as an existing Subject. The
      * same subject can be used multiple times to simulate multiple logins.
-     * @param s existing subject
      */
     public static Context fromUserPass(Subject s,
             String user, char[] pass, boolean storeKey) throws Exception {
@@ -222,7 +216,7 @@
             @Override
             public byte[] run(Context me, byte[] dummy) throws Exception {
                 GSSManager m = GSSManager.getInstance();
-                me.x = (ExtendedGSSContext)m.createContext(
+                me.x = m.createContext(
                           target.indexOf('@') < 0 ?
                             m.createName(target, null) :
                             m.createName(target, GSSName.NT_HOSTBASED_SERVICE),
@@ -267,7 +261,7 @@
                         asInitiator?
                                 GSSCredential.INITIATE_AND_ACCEPT:
                                 GSSCredential.ACCEPT_ONLY);
-                me.x = (ExtendedGSSContext)m.createContext(me.cred);
+                me.x = m.createContext(me.cred);
                 return null;
             }
         }, null);
@@ -285,7 +279,7 @@
      *
      * @return the GSSContext object
      */
-    public ExtendedGSSContext x() {
+    public GSSContext x() {
         return x;
     }
 
@@ -339,7 +333,7 @@
      */
     public void status() throws Exception {
         System.out.println("STATUS OF " + name.toUpperCase());
-        try {
+        if (x != null) {
             StringBuffer sb = new StringBuffer();
             if (x.getAnonymityState()) {
                 sb.append("anon, ");
@@ -362,19 +356,15 @@
             if (x.getSequenceDetState()) {
                 sb.append("seq det, ");
             }
-            if (x instanceof ExtendedGSSContext) {
-                if (((ExtendedGSSContext)x).getDelegPolicyState()) {
-                    sb.append("deleg policy, ");
-                }
+            System.out.println("   Context status of " + name + ": " + sb.toString());
+            if (x.isProtReady() || x.isEstablished()) {
+                System.out.println("   " + x.getSrcName() + " -> " + x.getTargName());
             }
-            System.out.println("Context status of " + name + ": " + sb.toString());
-            System.out.println(x.getSrcName() + " -> " + x.getTargName());
-        } catch (Exception e) {
-            ;// Don't care
         }
+        xstatus();
         if (s != null) {
             System.out.println("====== START SUBJECT CONTENT =====");
-            for (Principal p: s.getPrincipals()) {
+            for (Principal p : s.getPrincipals()) {
                 System.out.println("    Principal: " + p);
             }
             for (Object o : s.getPublicCredentials()) {
@@ -405,51 +395,42 @@
             }
             System.out.println("====== END SUBJECT CONTENT =====");
         }
-        if (x != null && x instanceof ExtendedGSSContext) {
-            if (x.isEstablished()) {
-                ExtendedGSSContext ex = (ExtendedGSSContext)x;
-                Key k = (Key)ex.inquireSecContext(
-                        InquireType.KRB5_GET_SESSION_KEY);
-                if (k == null) {
-                    throw new Exception("(Old) Session key cannot be null");
-                }
-                System.out.println("(Old) Session key is: " + k);
-                Key k2 = (Key)ex.inquireSecContext(
-                        InquireType.KRB5_GET_SESSION_KEY_EX);
-                if (k2 == null) {
-                    throw new Exception("Session key cannot be null");
-                }
-                System.out.println("Session key is: " + k);
-                boolean[] flags = (boolean[])ex.inquireSecContext(
-                        InquireType.KRB5_GET_TKT_FLAGS);
-                if (flags == null) {
-                    throw new Exception("Ticket flags cannot be null");
+    }
+
+    public void xstatus() throws Exception {
+        System.out.println("   Extended context status:");
+        if (x != null) {
+            try {
+                Class<?> clazz = Class.forName("com.sun.security.jgss.ExtendedGSSContext");
+                if (clazz.isAssignableFrom(x.getClass())) {
+                    if (clazz.getMethod("getDelegPolicyState").invoke(x) == Boolean.TRUE) {
+                        System.out.println("   deleg policy");
+                    }
+                    if (x.isEstablished()) {
+                        Class<?> inqType = Class.forName("com.sun.security.jgss.InquireType");
+                        Method inqMethod = clazz.getMethod("inquireSecContext", inqType);
+                        for (Object o : inqType.getEnumConstants()) {
+                            System.out.println("   " + o + ":");
+                            try {
+                                System.out.println("      " + inqMethod.invoke(x, o));
+                            } catch (Exception e) {
+                                System.out.println(e.getCause());
+                            }
+                        }
+                    }
                 }
-                System.out.println("Ticket flags is: " + Arrays.toString(flags));
-                String authTime = (String)ex.inquireSecContext(
-                        InquireType.KRB5_GET_AUTHTIME);
-                if (authTime == null) {
-                    throw new Exception("Auth time cannot be null");
-                }
-                System.out.println("AuthTime is: " + authTime);
-                if (!x.isInitiator()) {
-                    AuthorizationDataEntry[] ad = (AuthorizationDataEntry[])ex.inquireSecContext(
-                            InquireType.KRB5_GET_AUTHZ_DATA);
-                    System.out.println("AuthzData is: " + Arrays.toString(ad));
+            } catch (ClassNotFoundException cnfe) {
+                System.out.println("   -- ExtendedGSSContext not available");
+            }
+        }
+        if (cred != null) {
+            try {
+                Class<?> clazz2 = Class.forName("com.sun.security.jgss.ExtendedGSSCredential");
+                if (!clazz2.isAssignableFrom(cred.getClass())) {
+                    throw new Exception("cred is not extended");
                 }
-                try {
-                    KerberosCredMessage tok = (KerberosCredMessage)ex.inquireSecContext(
-                            InquireType.KRB5_GET_KRB_CRED);
-                    System.out.println("KRB_CRED is " +
-                            (tok == null?"not ":"") + "available");
-                    if (tok != null) {
-                        System.out.println("From " + tok.getSender() + " to "
-                                + tok.getRecipient());
-                        System.out.println(Base64.getEncoder().encodeToString(tok.getEncoded()));
-                    }
-                } catch (Exception e) {
-                    System.out.println("KRB_CRED is not available: " + e);
-                }
+            } catch (ClassNotFoundException cnfe) {
+                System.out.println("   -- ExtendedGSSCredential not available");
             }
         }
     }
@@ -591,7 +572,10 @@
                     if (Context.this.cred == null) {
                         Context.this.cred = m.createCredential(GSSCredential.INITIATE_ONLY);
                     }
-                    return ((ExtendedGSSCredential)Context.this.cred).impersonate(other);
+                    return (GSSCredential)
+                            Class.forName("com.sun.security.jgss.ExtendedGSSCredential")
+                            .getMethod("impersonate", GSSName.class)
+                            .invoke(Context.this.cred, other);
                 }
             });
             Context out = new Context();
--- a/jdk/test/sun/security/krb5/auto/NewInquireTypes.java	Tue Sep 16 23:04:13 2014 +0400
+++ b/jdk/test/sun/security/krb5/auto/NewInquireTypes.java	Wed Sep 17 13:55:12 2014 +0800
@@ -29,6 +29,7 @@
  * @run main/othervm NewInquireTypes
  */
 
+import com.sun.security.jgss.ExtendedGSSContext;
 import com.sun.security.jgss.InquireType;
 import sun.security.jgss.GSSUtil;
 import sun.security.krb5.internal.KRBCred;
@@ -52,10 +53,12 @@
 
         Context.handshake(c, s);
 
+        ExtendedGSSContext ctxt = (ExtendedGSSContext)c.x();
         EncryptionKey key = (EncryptionKey)
-                c.x().inquireSecContext(InquireType.KRB5_GET_SESSION_KEY_EX);
+                ctxt.inquireSecContext(InquireType.KRB5_GET_SESSION_KEY_EX);
         KerberosCredMessage cred = (KerberosCredMessage)
-                c.x().inquireSecContext(InquireType.KRB5_GET_KRB_CRED);
+                ctxt.inquireSecContext(InquireType.KRB5_GET_KRB_CRED);
+        c.status();
 
         // Confirm the KRB_CRED message is encrypted with the session key.
         new KRBCred(cred.getEncoded()).encPart.decrypt(
--- a/jdk/test/sun/security/krb5/auto/OkAsDelegate.java	Tue Sep 16 23:04:13 2014 +0400
+++ b/jdk/test/sun/security/krb5/auto/OkAsDelegate.java	Wed Sep 17 13:55:12 2014 +0800
@@ -48,6 +48,7 @@
  * @summary Support OK-AS-DELEGATE flag
  */
 import com.sun.security.jgss.ExtendedGSSContext;
+import org.ietf.jgss.GSSContext;
 import org.ietf.jgss.GSSCredential;
 import org.ietf.jgss.GSSException;
 import org.ietf.jgss.Oid;
@@ -102,7 +103,7 @@
         cx.requestCredDeleg(requestDelegState);
         cx.requestDelegPolicy(requestDelegPolicyState);
         s.startAsServer(mech);
-        ExtendedGSSContext sx = (ExtendedGSSContext)s.x();
+        GSSContext sx = s.x();
 
         Context.handshake(c, s);
 
--- a/jdk/test/sun/security/krb5/auto/OkAsDelegateXRealm.java	Tue Sep 16 23:04:13 2014 +0400
+++ b/jdk/test/sun/security/krb5/auto/OkAsDelegateXRealm.java	Wed Sep 17 13:55:12 2014 +0800
@@ -42,6 +42,8 @@
 import javax.security.auth.callback.NameCallback;
 import javax.security.auth.callback.PasswordCallback;
 import javax.security.auth.callback.UnsupportedCallbackException;
+
+import com.sun.security.jgss.ExtendedGSSContext;
 import org.ietf.jgss.GSSException;
 import sun.security.jgss.GSSUtil;
 import sun.security.krb5.Config;
@@ -129,7 +131,7 @@
         for (int i=0; i<2; i++) {
             c.startAsClient("host@host.r3.local", GSSUtil.GSS_KRB5_MECH_OID);
             s.startAsServer(GSSUtil.GSS_KRB5_MECH_OID);
-            c.x().requestDelegPolicy(true);
+            ((ExtendedGSSContext)c.x()).requestDelegPolicy(true);
 
             Context.handshake(c, s);
             boolean succeed = true;
--- a/jdk/test/sun/security/krb5/auto/SSL.java	Tue Sep 16 23:04:13 2014 +0400
+++ b/jdk/test/sun/security/krb5/auto/SSL.java	Wed Sep 17 13:55:12 2014 +0800
@@ -186,13 +186,13 @@
             // Client checks "initiate", then server gets the name
             // and checks "accept". Second connection resume.
             if (!permChecks.equals("IA")) {
-                throw new Exception();
+                throw new Exception(permChecks);
             }
         } else {
             // For bound, JAAS checks "accept" once. Server checks again,
             // client then checks "initiate". Second connection resume.
             if (!permChecks.equals("AAI")) {
-                throw new Exception();
+                throw new Exception(permChecks);
             }
         }
     }