Kerberos and LDAP: Why does Java 6 truncate LDAP host names when using Kerberos? -


my task connect kerberized ldap server through java gss api. have small sample app use test connection, kerberos configuration, connection parameters, etc, sure can connect ldap server , retrieve data. code given below:

import java.io.fileinputstream; import java.io.ioexception; import java.security.privilegedactionexception; import java.security.privilegedexceptionaction; import java.util.hashmap; import java.util.hashtable; import java.util.map; import java.util.properties;  import javax.naming.context; import javax.naming.namingenumeration; import javax.naming.namingexception; import javax.naming.directory.attributes; import javax.naming.directory.dircontext; import javax.naming.directory.searchcontrols; import javax.naming.directory.searchresult; import javax.naming.ldap.control; import javax.naming.ldap.initialldapcontext; import javax.security.auth.subject; import javax.security.auth.login.logincontext; import javax.security.auth.login.loginexception; import javax.security.auth.spi.loginmodule;  public class testkerberizedldap implements runnable {      public static void main(string[] args) {         runnable rn = null;         if (args.length == 1) {             rn = new testkerberizedldap(args[0]);         }         else if (args.length == 0) {             rn = new testkerberizedldap("c:/dev/projects/testkerberizedldap/src/testkerberizedldap.properties");         }         else {             printusage();             return;         }          rn.run();     }      private static final string loginmoduleclassname = "com.sun.security.auth.module.krb5loginmodule";     private static final string koid = "1.2.840.113554.1.2.2";     private static final string soid = "1.3.6.1.5.5.2";      private subject subject;     private dircontext ldapcontext;     private string username;     private string password;     private string ldaphost;      private testkerberizedldap(string propfilename) {         properties prop = new properties();         try {             fileinputstream istream = new fileinputstream(propfilename);             prop.load(istream);             istream.close();         }         catch (ioexception e) {             e.printstacktrace();         }          system.out.println("properties found:");         (string propname : prop.stringpropertynames()) {             system.out.println(propname + " = " + prop.getproperty(propname));         }         system.out.println();          system.setproperty("java.security.krb5.conf", prop.getproperty("krbconf"));         system.setproperty("java.security.krb5.debug", "true");         system.setproperty("sun.security.krb5.debug", "true");          ldaphost = prop.getproperty("ldaphost");         username = prop.getproperty("user");         password = prop.getproperty("password");         subject = null;         ldapcontext = null;     }      public void run() {         try {             initsubject();             if (subject != null) {                 initcontextkerberized();             }         }         catch (exception ex) {             ex.printstacktrace();         }     }      private void initcontextkerberized() throws exception {         subject.doas(subject, new privilegedexceptionaction<object>() {             public object run() throws exception {                 hashtable<string, string> env = new hashtable<string, string>();                 env.put(context.initial_context_factory, "com.sun.jndi.ldap.ldapctxfactory");                 env.put(context.provider_url, ldaphost);                 env.put(context.security_authentication, "gssapi");                 ldapcontext = new initialldapcontext(env, new control[0]);                  // stuff ldapcontext here...                 searchldapdirectory();                  return null;             }         });     }      private void searchldapdirectory() throws namingexception {         string base = "cn=users";         string filter = "(objectclass=user)";         searchcontrols sc = new searchcontrols();         sc.setsearchscope(searchcontrols.subtree_scope);         namingenumeration<searchresult> ne = ldapcontext.search(base, filter, sc);         int numelements = 0;         system.out.println();         while (ne.hasmoreelements()) {             searchresult sr = ne.nextelement();             attributes attr = sr.getattributes();             system.out.println(attr.get("name").get());             numelements++;         }         system.out.println("the number of elements returned " + numelements);     }      private void initsubject() throws instantiationexception, classnotfoundexception, illegalaccessexception {         loginmodule module = null;         try {             module = (loginmodule) class.forname(loginmoduleclassname).newinstance();             subject = new subject();             map<string, string> options = new hashmap<string, string>();             map<string, object> sharedstate = new hashmap<string, object>();              if ((username != null) && (password != null)) {                 sharedstate.put("javax.security.auth.login.password", password.tochararray());                 sharedstate.put("javax.security.auth.login.name", username);                 options.put("principal", username);                 options.put("storekey", "true");                 options.put("usefirstpass", "true");             }             else {                 options.put("principal", username);                 options.put("useticketcache", "true");                 options.put("donotprompt", "true");                 options.put("renewtgt", "true");             }             options.put("debug", "true");             options.put("refreshkrb5config", "true");              module.initialize(subject, null, sharedstate, options);             module.login();             module.commit();         }         catch (loginexception ex) {             ex.printstacktrace();             subject = null;             if (module != null) {                 try {                     module.abort();                 }                 catch (loginexception ex2) {                     ex2.printstacktrace();                 }             }         }     }      private static void printusage() {         system.out.println();         system.out.println("usage: testkerberizedldap <property file name>");         system.out.println();     } } 

within testkerberized.properties file, "ldaphost" property defined "ldap://dv2k8ad.2k8.hlp.net:389/dc=2k8,dc=hlp,dc=net".

now, when run app java 7, works charm. kerberos authentication succeeds, , data retrieved ldap server. however, cant run java 6. keeps giving me following exception:

    found ticket user1@2k8.hlp.net go krbtgt/2k8.hlp.net@2k8.hlp.net expiring on thu jun 04 00:47:07 pdt 2015 entered krb5context.initseccontext state=state_new found ticket user1@2k8.hlp.net go krbtgt/2k8.hlp.net@2k8.hlp.net expiring on thu jun 04 00:47:07 pdt 2015 service ticket not found in subject >>> credentials acquireservicecreds: same realm default etypes default_tgs_enctypes: 23 16 3 1. >>> cksumtype: sun.security.krb5.internal.crypto.rsamd5cksumtype >>> etype: sun.security.krb5.internal.crypto.arcfourhmacetype >>> krbkdcreq send: kdc=172.23.5.151 udp:88, timeout=30000, number of retries =3, #bytes=1289 >>> kdccommunication: kdc=172.23.5.151 udp:88, timeout=30000,attempt =1, #bytes=1289 >>> krbkdcreq send: #bytes read=92 >>> krbkdcreq send: #bytes read=92 >>> kdcaccessibility: remove 172.23.5.151:88 >>> kdcrep: init() encoding tag 126 req type 13 >>>krberror:      stime wed jun 03 14:47:07 pdt 2015 1433368027000      susec 109093      error code 7      error message server not found in kerberos database      realm 2k8.hlp.net      sname ldap/2k8.hlp.net      msgtype 30 java.security.privilegedactionexception: javax.naming.authenticationexception: gssapi [root exception javax.security.sasl.saslexception: gss initiate failed [caused gssexception: no valid credentials provided (mechanism level: server not found in kerberos database (7))]]     @ java.security.accesscontroller.doprivileged(native method)     @ javax.security.auth.subject.doas(subject.java:396)     @ testkerberizedldap.initcontextkerberized(testkerberizedldap.java:95)     @ testkerberizedldap.run(testkerberizedldap.java:85)     @ testkerberizedldap.main(testkerberizedldap.java:39) caused by: javax.naming.authenticationexception: gssapi [root exception javax.security.sasl.saslexception: gss initiate failed [caused gssexception: no valid credentials provided (mechanism level: server not found in kerberos database (7))]]     @ com.sun.jndi.ldap.sasl.ldapsasl.saslbind(ldapsasl.java:150)     @ com.sun.jndi.ldap.ldapclient.authenticate(ldapclient.java:214)     @ com.sun.jndi.ldap.ldapctx.connect(ldapctx.java:2694)     @ com.sun.jndi.ldap.ldapctx.<init>(ldapctx.java:293)     @ com.sun.jndi.ldap.ldapctxfactory.getusingurl(ldapctxfactory.java:175)     @ com.sun.jndi.ldap.ldapctxfactory.getusingurls(ldapctxfactory.java:193)     @ com.sun.jndi.ldap.ldapctxfactory.getldapctxinstance(ldapctxfactory.java:136)     @ com.sun.jndi.ldap.ldapctxfactory.getinitialcontext(ldapctxfactory.java:66)     @ javax.naming.spi.namingmanager.getinitialcontext(namingmanager.java:667)     @ javax.naming.initialcontext.getdefaultinitctx(initialcontext.java:288)     @ javax.naming.initialcontext.init(initialcontext.java:223)     @ javax.naming.ldap.initialldapcontext.<init>(initialldapcontext.java:134)     @ testkerberizedldap$1.run(testkerberizedldap.java:101)     ... 5 more caused by: javax.security.sasl.saslexception: gss initiate failed [caused gssexception: no valid credentials provided (mechanism level: server not found in kerberos database (7))]     @ com.sun.security.sasl.gsskerb.gsskrb5client.evaluatechallenge(gsskrb5client.java:194)     @ com.sun.jndi.ldap.sasl.ldapsasl.saslbind(ldapsasl.java:105)     ... 17 more caused by: gssexception: no valid credentials provided (mechanism level: server not found in kerberos database (7))     @ sun.security.jgss.krb5.krb5context.initseccontext(krb5context.java:663)     @ sun.security.jgss.gsscontextimpl.initseccontext(gsscontextimpl.java:230)     @ sun.security.jgss.gsscontextimpl.initseccontext(gsscontextimpl.java:162)     @ com.sun.security.sasl.gsskerb.gsskrb5client.evaluatechallenge(gsskrb5client.java:175)     ... 18 more caused by: krbexception: server not found in kerberos database (7)     @ sun.security.krb5.krbtgsrep.<init>(krbtgsrep.java:61)     @ sun.security.krb5.krbtgsreq.getreply(krbtgsreq.java:185)     @ sun.security.krb5.internal.credentialsutil.servicecreds(credentialsutil.java:294)     @ sun.security.krb5.internal.credentialsutil.acquireservicecreds(credentialsutil.java:106)     @ sun.security.krb5.credentials.acquireservicecreds(credentials.java:557)     @ sun.security.jgss.krb5.krb5context.initseccontext(krb5context.java:594)     ... 21 more caused by: krbexception: identifier doesn't match expected value (906)     @ sun.security.krb5.internal.kdcrep.init(kdcrep.java:133)     @ sun.security.krb5.internal.tgsrep.init(tgsrep.java:58)     @ sun.security.krb5.internal.tgsrep.<init>(tgsrep.java:53)     @ sun.security.krb5.krbtgsrep.<init>(krbtgsrep.java:46)     ... 26 more 

it's worth noting module.commit() succeeded, , subject obtained, no issues there. noticed sname field in krberror message off. says ldap/2k8.hlp.net whereas should have been ldap/dv2k8ad.2k8.hlp.net.

following this, ran wireshark session capture kerberos packets being sent, , captured packets while running testkerberizedldap on both java 6 , java 7. tgt acquired successfully, because program got successful as-rep in both cases. however, tgs-req being sent kdc had different values. server name sent java 6 ldap/2k8.hlp.net , 1 sent java 7 ldap/dv2k8ad.2k8.hlp.net

i dont know why java 6 choosing trim ldap host name. if knows workaround, or fix (short of updating java), i'd grateful help.

yay, resolved!

this bug in java 1.6.0_22. switched using java 1.6.0_45, , worked charm :)


Comments

Popular posts from this blog

javascript - Bootstrap Popover: iOS Safari strange behaviour -

Magento/PHP - Get phones on all members in a customer group -

session - Logging Out Using PHP -