The LDAP Result Codes Reference is a fast, searchable lookup for the numeric
result codes returned by every LDAP operation. When a bind, search, add, modify
or delete completes, the server returns an LDAPResult whose resultCode field
tells you exactly what happened — and the difference between code 32 and code
49 is the difference between a missing entry and a wrong password.
How it works
Every LDAP response carries an integer result code defined by RFC 4511 (the
LDAPv3 protocol) in section 4.1.9 and Appendix A. Codes are not strictly grouped
by range, but they fall into three practical categories: success (such as
0 success, 5 compareFalse, 6 compareTrue, 14 saslBindInProgress),
referral (10 referral, which redirects the client to another server), and
error (everything else). This tool stores the full table locally and filters
it as you type — match on the number, the camelCase name, or any word in the
description.
Common codes worth memorizing
0 success— the operation worked.32 noSuchObject— the target DN does not exist.49 invalidCredentials— wrong DN/password or a locked account.50 insufficientAccessRights— authenticated but not authorized.53 unwillingToPerform— the server refuses on policy grounds.65 objectClassViolation— the entry breaks its schema.68 entryAlreadyExists— an add collided with an existing entry.
Active Directory sub-codes under 49
Active Directory uses result code 49 as a catch-all authentication failure, then encodes the real reason in the ldapControlResponses diagnostic message as a hex sub-code. Reading the sub-code is essential because 49 alone does not tell you whether to re-prompt the user, contact IT, or check account configuration:
| Sub-code | Meaning | Action |
|---|---|---|
52e | Invalid credentials (bad password) | Re-prompt user |
525 | User not found | Check the bind DN or username format |
52f | Account restrictions (logon hours, workstation) | Contact administrator |
530 | Account not permitted to log on at this time | Check logon hour policy |
531 | Account not permitted to log on from this workstation | IP or machine policy issue |
532 | Password expired | Force password reset |
533 | Account disabled | Enable account or contact administrator |
701 | Account expired | Renew account or contact administrator |
773 | User must reset password at next logon | Trigger password reset flow |
775 | Account locked out | Wait for lockout policy to clear or unlock manually |
To read the sub-code in practice, look at the data field in the server’s diagnostic message. In Python-ldap it appears in the info field of the INVALID_CREDENTIALS exception; in .NET’s System.DirectoryServices it surfaces in the ErrorCode property with 0x80070 prefix.
Debugging a failed bind — diagnostic checklist
When a bind returns an error code that is not immediately obvious:
- Check code 49 sub-codes first if against Active Directory (see table above).
- Code 32 — verify the full Distinguished Name (DN) exists:
ldapsearch -x -H ldap://server -D "cn=admin,dc=example,dc=com" -w password -b "dc=example,dc=com" "(cn=username)". - Code 50 — the bind succeeded but the read/modify failed on ACL. Check directory ACLs or service account permissions.
- Code 34 — the DN string itself is malformed. Look for unescaped special characters (
,,+,",\,<,>,;). - Code 53 — server-side policy blocked the operation. Common cause: attempting to set a password that does not meet complexity requirements.
- Code 65 — schema violation. The entry is missing a required attribute or has an attribute not permitted by its objectClass.
Notes
Active Directory frequently returns code 49 for many distinct failures and
encodes the real reason in the diagnostic message as a hex sub-code — for example
52e (bad password), 525 (user not found), 530 (logon time restriction),
532 (password expired) and 533 (account disabled). Always read the diagnostic
string, not just the numeric code. Codes such as 9, 15, 35 and several
ranges are unused or reserved and should never appear in a conformant response.