mkazia commented on pull request #1565:
URL: https://github.com/apache/hbase/pull/1565#issuecomment-618760248


   So I took the Sasl sample code from here 
https://docs.oracle.com/javase/8/docs/technotes/guides/security/jgss/lab/src/SaslTestClient.java
 and ran with both IBM and Oracle JDK. It ran successfully. Notice that 
`Sasl.createSaslClient` is called within `Jaas.loginAndAction` which wraps 
everything in `Subject.doAs`. Next I modified the class as below where I moved 
`Sasl.createSaslClient` outside of `Jaas.loginAndAction`. The code ran 
successfully in Oracle JDK but failed in IBM JDK. The stack has some 
commonality with stacktrace I have in jira. 
   
   Is this explanation good enough to change your -1 to +1?
   
   Stack trace:
   ```
   Connected to address nightly6x-1.nightly6x.root.hwx.site/172.27.31.197
   Got connection from client /172.27.31.197
   IBMJGSSProvider Build-Level: -20200127
   [JGSS_DBG_PROV]  main IBMJGSSProvider (version 8.0) loaded
   [JGSS_DBG_PROV]  main Number of system providers=9
   [JGSS_DBG_PROV]  main getMechOidFromProperty: mech oid string = 1.3.6.1.5.5.2
   [JGSS_DBG_PROV]  main getMechOidFromProperty: mech oid string = 
1.2.840.113554.1.2.2
   [JGSS_DBG_PROV]  main getMechOidFromProperty: mech oid string = 1.3.6.1.5.5.2
   [JGSS_DBG_PROV]  main 3 system providers found/added
   [JGSS_DBG_PROV]  main getMechOidFromProperty: mech oid string = 1.3.6.1.5.5.2
   [JGSS_DBG_PROV]  main getMechOidFromProperty: mech oid string = 
1.2.840.113554.1.2.2
   [JGSS_DBG_PROV]  main getMechs: Mechanism(s) supported by provider 
IBMJGSSProvider
   [JGSS_DBG_PROV]  main   1.3.6.1.5.5.2
   [JGSS_DBG_PROV]  main getMechOidFromProperty: mech oid string = 1.3.6.1.5.5.2
   [JGSS_DBG_PROV]  main getMechOidFromProperty: mech oid string = 
1.2.840.113554.1.2.2
   [JGSS_DBG_PROV]  main getMechs: Mechanism(s) supported by provider 
IBMJGSSProvider
   [JGSS_DBG_PROV]  main   1.2.840.113554.1.2.2
   [JGSS_DBG_PROV]  main getMechOidFromProperty: mech oid string = 1.3.6.1.5.5.2
   [JGSS_DBG_PROV]  main getMechs: Mechanism(s) supported by provider IBMSPNEGO
   [JGSS_DBG_PROV]  main   1.3.6.1.5.5.2
   [JGSS_DBG_PROV]  main getMechs: 2 unique mechanism(s) found
   [JGSS_DBG_PROV]  main   [0]: 1.3.6.1.5.5.2
   [JGSS_DBG_PROV]  main   [1]: 1.2.840.113554.1.2.2
   [JGSS_DBG_CRED]  main MN not found; creating one
   [JGSS_DBG_PROV]  main Provider Entry: provider: IBMJGSSProvider, mechanism: 
1.3.6.1.5.5.2 get Factory for mech: 1.2.840.113554.1.2.2 GSSCaller:
   [JGSS_DBG_PROV]  main Provider Entry: provider: IBMJGSSProvider, mechanism: 
1.2.840.113554.1.2.2 get Factory for mech: 1.2.840.113554.1.2.2 GSSCaller:
   [JGSS_DBG_PROV]  main Created new (empty) factory list (size=1) for provider 
IBMJGSSProvider version 8.0
   [JGSS_DBG_PROV]  main Loading factory
   [JGSS_DBG_PROV]  main Factory class name for provider IBMJGSSProvider 
version 8.0 is com.ibm.security.jgss.mech.krb5.Krb5MechFactory
   [JGSS_DBG_PROV]  main IBMJGSSProvider (version 8.0) loaded
   [JGSS_DBG_PROV]  main Prior to load
   [JGSS_DBG_PROV]  main Done to load
   [JGSS_DBG_PROV]  main Loaded factory for provider IBMJGSSProvider version 8.0
   [JGSS_DBG_PROV]  main Loaded factory ok
   [JGSS_DBG_PROV]  main getFactory: index = 1 found factory caller = 
GSSCaller{UNKNOWN}
   [JGSS_DBG_CRED]  main Before Cannonicalizing hostbased service name 
[email protected]
   [KRB_DBG_CFG] Config:main:   readKrb5Properties: defaultRealm = null
   [KRB_DBG_CFG] Config:main:   readKrb5Properties: defaultKDC   = null
   [KRB_DBG_CFG] Config:main:   Java config file: /etc/krb5.conf
   [KRB_DBG_CFG] Config:main:   loadConfigFile: configFile = [logging = {, 
default = FILE:/var/log/krb5libs.log, kdc = FILE:/var/log/krb5kdc.log, 
admin_server = FILE:/var/log/kadmind.log, }, libdefaults = {, renew_lifetime = 
90m, default_realm = ROOT.HWX.SITE, dns_lookup_realm = false, dns_lookup_kdc = 
false, ticket_lifetime = 25m, forwardable = yes, allow_weak_crypto = true, }, 
realms = {, ROOT.HWX.SITE = {, kdc = nightly6x-1.nightly6x.root.hwx.site:88, 
admin_server = nightly6x-1.nightly6x.root.hwx.site:749, default_domain = 
nightly6x.root.hwx.site, }, }, domain_realm = {, .nightly6x.root.hwx.site = 
ROOT.HWX.SITE, nightly6x.root.hwx.site = ROOT.HWX.SITE, }]
   [KRB_DBG_CFG] Config:main:   Loaded from Java config
   [KRB_DBG_CFG] Config:main:   Config: stanzaTable = 
{libdefaults={allow_weak_crypto=[true], ticket_lifetime=[25m], 
default_realm=[ROOT.HWX.SITE], forwardable=[yes], dns_lookup_kdc=[false], 
renew_lifetime=[90m], dns_lookup_realm=[false]}, 
domain_realm={.nightly6x.root.hwx.site=[ROOT.HWX.SITE], 
nightly6x.root.hwx.site=[ROOT.HWX.SITE]}, 
logging={kdc=[FILE:/var/log/krb5kdc.log], default=[FILE:/var/log/krb5libs.log], 
admin_server=[FILE:/var/log/kadmind.log]}, 
realms={ROOT.HWX.SITE={default_domain=[nightly6x.root.hwx.site], 
kdc=[nightly6x-1.nightly6x.root.hwx.site:88], 
admin_server=[nightly6x-1.nightly6x.root.hwx.site:749]}}}
   [KRB_DBG_CFG] Config:main:   get: section     = libdefaults
   [KRB_DBG_CFG] Config:main:   get: name        = dns_lookup_realm
   [KRB_DBG_CFG] Config:main:   get: result      = false
   [JGSS_DBG_CRED]  main Cannonicalizing hostbased service name 
[email protected]
   [JGSS_DBG_CRED]  main Hostname nightly6x-1.nightly6x.root.hwx.site
   [KRB_DBG_CFG] Config:main:   get: section     = domain_realm
   [KRB_DBG_CFG] Config:main:   get: name        = .nightly6x.root.hwx.site
   [KRB_DBG_CFG] Config:main:   get: result      = ROOT.HWX.SITE
   [KRB_DBG_CFG] Config:main:   get: section     = domain_realm
   [KRB_DBG_CFG] Config:main:   get: name        = .nightly6x.root.hwx.site
   [KRB_DBG_CFG] Config:main:   get: result      = ROOT.HWX.SITE
   [JGSS_DBG_CRED]  main Name cannonicalization complete, resulting name 
string=HTTP/[email protected]
   [JGSS_DBG_CTX]  main Creating context, initiator = yes, input cred = null
   [JGSS_DBG_CTX]  main Creating default initiator creds
   [JGSS_DBG_CRED]  main Creating mech cred for null, mech 
1.2.840.113554.1.2.2, usage initiate only
   [JGSS_DBG_PROV]  main Provider Entry: provider: IBMJGSSProvider, mechanism: 
1.3.6.1.5.5.2 get Factory for mech: 1.2.840.113554.1.2.2 GSSCaller:
   [JGSS_DBG_PROV]  main Provider Entry: provider: IBMJGSSProvider, mechanism: 
1.2.840.113554.1.2.2 get Factory for mech: 1.2.840.113554.1.2.2 GSSCaller:
   [JGSS_DBG_PROV]  main getFactory: index = 1 found factory caller = 
GSSCaller{UNKNOWN}
   [JGSS_DBG_CRED]  main Search Subject for Kerberos V5 INIT cred (<<DEF>>, 
com.ibm.security.jgss.mech.krb5.s)
   [JGSS_DBG_CRED]  main No Subject
   [JGSS_DBG_CRED]  main Creating credentials for name null, servName null, 
usage 1
   [JGSS_DBG_CRED]  main Trying to get credentials for null
   [JGSS_DBG_CRED]  main usage: initiator only, check subject, useAllCred : 
false
   [JGSS_DBG_CRED]  main Obtaining Subject creds for default principal
   [JGSS_DBG_CRED]  main SubjectCredFinder: client=null, server=null
   Exception in thread "main" javax.security.sasl.SaslException: Failure to 
initialize security context [Caused by org.ietf.jgss.GSSException, major code: 
13, minor code: 0
           major string: Invalid credentials
           minor string: SubjectCredFinder: no JAAS Subject]
           at 
com.ibm.security.sasl.gsskerb.GssKrb5Client.<init>(GssKrb5Client.java:161)
           at 
com.ibm.security.sasl.gsskerb.FactoryImpl.createSaslClient(FactoryImpl.java:79)
           at javax.security.sasl.Sasl.createSaslClient(Sasl.java:400)
           at SaslTestClient2.main(SaslTestClient2.java:108)
   Caused by: org.ietf.jgss.GSSException, major code: 13, minor code: 0
           major string: Invalid credentials
           minor string: SubjectCredFinder: no JAAS Subject
           at 
com.ibm.security.jgss.i18n.I18NException.throwGSSException(Unknown Source)
           at com.ibm.security.jgss.mech.krb5.v.run(Unknown Source)
           at 
java.security.AccessController.doPrivileged(AccessController.java:734)
           at com.ibm.security.jgss.mech.krb5.s.c(Unknown Source)
           at com.ibm.security.jgss.mech.krb5.s.a(Unknown Source)
           at com.ibm.security.jgss.mech.krb5.s.a(Unknown Source)
           at com.ibm.security.jgss.mech.krb5.s.<init>(Unknown Source)
           at 
com.ibm.security.jgss.mech.krb5.Krb5MechFactory.getCredentialElement(Unknown 
Source)
           at com.ibm.security.jgss.GSSManagerImpl.createMechCredential(Unknown 
Source)
           at com.ibm.security.jgss.GSSCredentialImpl.add(Unknown Source)
           at com.ibm.security.jgss.GSSCredentialImpl.<init>(Unknown Source)
           at com.ibm.security.jgss.GSSManagerImpl.createCredential(Unknown 
Source)
           at com.ibm.security.jgss.GSSContextImpl.a(Unknown Source)
           at com.ibm.security.jgss.GSSContextImpl.<init>(Unknown Source)
           at com.ibm.security.jgss.GSSManagerImpl.createContext(Unknown Source)
           at 
com.ibm.security.sasl.gsskerb.GssKrb5Client.<init>(GssKrb5Client.java:135)
           ... 3 more
   ```
   
   Modified code:
   
   ```
   import javax.security.sasl.*;
   import javax.security.auth.callback.*;
   import java.security.*;
   import javax.security.auth.Subject;
   import javax.security.auth.login.*;
   import com.sun.security.auth.callback.*;
   import java.util.HashMap;
   
   public class SaslTestClient2 {
       private static final String MECH = "GSSAPI"; // SASL name for 
GSS-API/Kerberos
       private static final int PORT = 4568;
   
       private static final byte[] EMPTY = new byte[0];
   
       public static void main(String[] args) throws Exception {
           // Obtain the command-line arguments and parse the server's principal
   
           if (args.length < 2) {
               System.err.println(
                   "Usage: java <options> SaslTestClient2 <service> 
<serverName>");
               System.exit(-1);
           }
   
          // Create application-level connection
          AppConnection conn = new AppConnection(args[1], PORT);
   
          HashMap<String,Object> props = new HashMap<String,Object>();
          // Request confidentiality
          props.put(Sasl.QOP, "auth-conf");
   
           CallbackHandler cbh = null; // Don't need handler for GSSAPI
          // Create SaslClient to perform authentication
          SaslClient clnt = Sasl.createSaslClient(
              new String[]{MECH}, null, args[0], args[1], props, cbh);
   
          if (clnt == null) {
              throw new Exception(
                  "Unable to find client implementation for " + MECH);
          }
   
           PrivilegedExceptionAction action =
               new SaslClientAction(conn, clnt);
   
           Jaas.loginAndAction("client", action);
       }
   
       static class SaslClientAction implements PrivilegedExceptionAction {
           private AppConnection conn;
           private SaslClient clnt;
   
           SaslClientAction(AppConnection conn, SaslClient clnt) {
               this.conn = conn;
               this.clnt = clnt;
           }
   
           public Object run() throws Exception {
               byte[] response;
               byte[] challenge;
   
               // Get initial response for authentication
               response = clnt.hasInitialResponse() ?
                   clnt.evaluateChallenge(EMPTY) : EMPTY;
   
               // Send initial response to server
               AppConnection.AppReply reply =
                   conn.send(AppConnection.AUTH_CMD, response);
   
               // Repeat until authentication terminates
               while (!clnt.isComplete() &&
                   (reply.getStatus() == AppConnection.AUTH_INPROGRESS ||
                    reply.getStatus() == AppConnection.SUCCESS)) {
   
                   // Evaluate challenge to generate response
                   challenge = reply.getBytes();
                   response = clnt.evaluateChallenge(challenge);
   
                   if (reply.getStatus() == AppConnection.SUCCESS) {
                       if (response != null) {
                           throw new Exception("Protocol error interacting with 
SASL");
                       }
                       break;
                   }
   
                   // Send response to server and read server's next challenge
                   reply = conn.send(AppConnection.AUTH_CMD, response);
               }
   
               // Check status of authentication
               if (clnt.isComplete() && reply.getStatus() == 
AppConnection.SUCCESS) {
                   System.out.println("Client authenticated.");
               } else {
                   throw new Exception("Authentication failed: " +
                       " connection status? " + reply.getStatus());
               }
   
               String qop = (String) clnt.getNegotiatedProperty(Sasl.QOP);
               System.out.println("Negotiated QOP: " + qop);
   
               // Try out security layer
               boolean sl = (qop.equals("auth-conf") || qop.equals("auth-int"));
   
               byte[] msg = "Hello There!".getBytes("UTF-8");
               System.out.println("Sending: " + new String(msg, "UTF-8"));
   
               byte[] encrypted = (sl ? clnt.wrap(msg, 0, msg.length) : msg);
   
               reply = conn.send(AppConnection.DATA_CMD, encrypted);
   
               if (reply.getStatus() == AppConnection.SUCCESS) {
                   byte[] encryptedReply = reply.getBytes();
   
                   byte[] clearReply = (sl ? clnt.unwrap(encryptedReply,
                       0, encryptedReply.length) : encryptedReply);
   
                   System.out.println("Received: " + new String(clearReply, 
"UTF-8"));
               } else {
                   System.out.println("Failed exchange: " + reply.getStatus());
               }
   
               conn.close();
   
               return null;
           }
       }
   }
   ```


----------------------------------------------------------------
This is an automated message from the Apache Git Service.
To respond to the message, please log on to GitHub and use the
URL above to go to the specific comment.

For queries about this service, please contact Infrastructure at:
[email protected]


Reply via email to