This question is admittedly a duplicate of this one but it has no answer. Also, you may be inclined to think that this answer solves the issue, but it doesn't. (I doubt that those answering have actually tried on an Active Directory, they have possible tried on some other LDAP implementation).
The goal is to retrieve the RootDSE without authenticating with a user, i.e. a so-called anonymous connection. (yes, AD supports this)
Here's what I've tried (using Java 8):
import java.util.Properties;
import javax.naming.Context;
import javax.naming.NamingEnumeration;
import javax.naming.NamingException;
import javax.naming.directory.SearchControls;
import javax.naming.directory.SearchResult;
import javax.naming.ldap.InitialLdapContext;
import javax.naming.ldap.LdapContext;
public class MyMain {
public static void main(String[] args) throws NamingException {
Properties props = new Properties();
props.put(Context.INITIAL_CONTEXT_FACTORY, "com.sun.jndi.ldap.LdapCtxFactory");
props.put(Context.PROVIDER_URL, "ldap://myadsrv.mynet.net:389");
props.put(Context.SECURITY_AUTHENTICATION, "none"); // shouldn't be necessary, but just to make a point of it
LdapContext ctx = new InitialLdapContext(props, null);
// Force a bind on the connection
ctx.reconnect(ctx.getConnectControls());
// Get the RootDSE
SearchControls searchControls = new SearchControls();
searchControls.setSearchScope(SearchControls.OBJECT_SCOPE);
searchControls.setReturningAttributes(new String[]{"namingContexts"});
NamingEnumeration<SearchResult> result = ctx.search("", "objectClass=*", searchControls);
}
}
Whatever I do I always end up in below exception. In the example above it will happen on the last line, i.e. the ctx.search(....)
. Exception:
Exception in thread "main" javax.naming.NamingException:
[LDAP: error code 1 - 000004DC: LdapErr: DSID-0C09072B,
comment: In order to perform this operation a successful bind must be completed on the connection., data 0, v2580];
remaining name ''
I have tried other tools such as Apache Directory Studio (open source LDAP browser, written in Java) and ldapsearch (command-line tool from OpenLDAP suite) and those tools are indeed able to retrieve the RootDSE without authenticating. I've used Wireshark to figure out what these tools to do differently than my JNDI implementation and can see some differences, but not quite sure I understand the Wireshark output completely (and wouldn't know how to translate that into something JNDI, as the latter is very high-level but Wireshark is of course quite low-level). But at least it proves that it is possible.