37#if _SQUID_WINDOWS_ && !_SQUID_CYGWIN_
39#define snprintf _snprintf
44#define LDAPAPI __cdecl
48#define LDAP_OPT_X_TLS 0x6000
50#define ber_alloc() ber_alloc_t(0)
63#define NMASLDAP_GET_LOGIN_CONFIG_REQUEST "2.16.840.1.113719.1.39.42.100.3"
64#define NMASLDAP_GET_LOGIN_CONFIG_RESPONSE "2.16.840.1.113719.1.39.42.100.4"
65#define NMASLDAP_SET_PASSWORD_REQUEST "2.16.840.1.113719.1.39.42.100.11"
66#define NMASLDAP_SET_PASSWORD_RESPONSE "2.16.840.1.113719.1.39.42.100.12"
67#define NMASLDAP_GET_PASSWORD_REQUEST "2.16.840.1.113719.1.39.42.100.13"
68#define NMASLDAP_GET_PASSWORD_RESPONSE "2.16.840.1.113719.1.39.42.100.14"
70#define NMAS_LDAP_EXT_VERSION 1
72#define SMB_MALLOC_ARRAY(type, nelem) calloc(nelem, sizeof(type))
73#define DEBUG(level, args)
81 struct berval **requestBV,
84 const char *password2)
87 BerElement *requestBer =
nullptr;
89 const char * utf8ObjPtr =
nullptr;
91 const char * utf8PwdPtr =
nullptr;
93 const char * utf8Pwd2Ptr =
nullptr;
97 utf8ObjSize = strlen(objectDN)+1;
98 utf8ObjPtr = objectDN;
100 if (password !=
nullptr) {
101 utf8PwdSize = strlen(password)+1;
102 utf8PwdPtr = password;
105 if (password2 !=
nullptr) {
106 utf8Pwd2Size = strlen(password2)+1;
107 utf8Pwd2Ptr = password2;
111 if ((requestBer = ber_alloc()) ==
nullptr) {
112 err = LDAP_ENCODING_ERROR;
116 if (password !=
nullptr && password2 !=
nullptr) {
118 rc = ber_printf(requestBer,
"{iooo}",
NMAS_LDAP_EXT_VERSION, utf8ObjPtr, utf8ObjSize, utf8PwdPtr, utf8PwdSize, utf8Pwd2Ptr, utf8Pwd2Size);
119 }
else if (password !=
nullptr) {
121 rc = ber_printf(requestBer,
"{ioo}",
NMAS_LDAP_EXT_VERSION, utf8ObjPtr, utf8ObjSize, utf8PwdPtr, utf8PwdSize);
128 err = LDAP_ENCODING_ERROR;
132 if ((ber_tag_t)ber_flatten(requestBer, requestBV) == LBER_ERROR) {
133 err = LDAP_ENCODING_ERROR;
138 ber_free(requestBer, 1);
150 struct berval **requestBV,
152 unsigned int methodIDLen,
153 unsigned int *methodID,
158 unsigned int elemCnt = methodIDLen /
sizeof(
unsigned int);
160 char *utf8ObjPtr=
nullptr;
163 char *utf8TagPtr =
nullptr;
166 utf8ObjPtr = objectDN;
167 utf8ObjSize = strlen(utf8ObjPtr)+1;
170 utf8TagSize = strlen(utf8TagPtr)+1;
173 BerElement *requestBer = ber_alloc();
175 return LDAP_ENCODING_ERROR;
179 ber_free(requestBer, 1);
180 return LDAP_ENCODING_ERROR;
184 if (ber_printf(requestBer,
"{i{", methodIDLen) < 0) {
185 ber_free(requestBer, 1);
186 return LDAP_ENCODING_ERROR;
189 for (
unsigned int i = 0; i < elemCnt; ++i) {
190 if (ber_printf(requestBer,
"i", methodID[i]) < 0) {
191 ber_free(requestBer, 1);
192 return LDAP_ENCODING_ERROR;
196 if (ber_printf(requestBer,
"}}", 0) < 0) {
197 ber_free(requestBer, 1);
198 return LDAP_ENCODING_ERROR;
203 if (ber_printf(requestBer,
"oio}", utf8TagPtr, utf8TagSize, putDataLen, putData, putDataLen) < 0) {
204 ber_free(requestBer, 1);
205 return LDAP_ENCODING_ERROR;
209 if (ber_printf(requestBer,
"o}", utf8TagPtr, utf8TagSize) < 0) {
210 ber_free(requestBer, 1);
211 return LDAP_ENCODING_ERROR;
216 if (
static_cast<ber_tag_t
>(ber_flatten(requestBer, requestBV)) == LBER_ERROR) {
217 ber_free(requestBer, 1);
218 return LDAP_ENCODING_ERROR;
221 ber_free(requestBer, 1);
232 struct berval *replyBV,
238 BerElement *replyBer =
nullptr;
239 char *retOctStr =
nullptr;
240 size_t retOctStrLen = 0;
242 if ((replyBer = ber_init(replyBV)) ==
nullptr) {
243 err = LDAP_OPERATIONS_ERROR;
244 }
else if (retData) {
245 retOctStrLen = *retDataLen + 1;
248 err = LDAP_OPERATIONS_ERROR;
249 }
else if (ber_scanf(replyBer,
"{iis}", serverVersion, &err, retOctStr, &retOctStrLen) != LBER_ERROR) {
250 if (*retDataLen >= retOctStrLen) {
251 memcpy(retData, retOctStr, retOctStrLen);
253 err = LDAP_NO_MEMORY;
256 *retDataLen = retOctStrLen;
258 err = LDAP_DECODING_ERROR;
261 if (ber_scanf(replyBer,
"{ii}", serverVersion, &err) == LBER_ERROR) {
263 err = LDAP_DECODING_ERROR;
269 ber_free(replyBer, 1);
272 if (retOctStr !=
nullptr) {
273 memset(retOctStr, 0, retOctStrLen);
288 unsigned int methodIDLen,
289 unsigned int *methodID,
295 struct berval *requestBV =
nullptr;
296 char *replyOID =
nullptr;
297 struct berval *replyBV =
nullptr;
298 int serverVersion = 0;
301 if ((strlen(objectDN) == 0) ||
ld ==
nullptr) {
302 return LDAP_NO_SUCH_ATTRIBUTE;
305 err =
berEncodeLoginData(&requestBV, objectDN, methodIDLen, methodID, tag, 0,
nullptr);
309 requestBV,
nullptr,
nullptr, &replyOID, &replyBV))) {
312 }
else if (!replyOID) {
314 err = LDAP_NOT_SUPPORTED;
317 err = LDAP_NOT_SUPPORTED;
318 }
else if (!replyBV) {
323 err = LDAP_OPERATIONS_ERROR;
329 err = LDAP_OPERATIONS_ERROR;
339 ldap_memfree(replyOID);
344 ber_bvfree(requestBV);
362 unsigned int methodID = 0;
363 unsigned int methodIDLen =
sizeof(methodID);
364 char tag[] = {
'P',
'A',
'S',
'S',
'W',
'O',
'R',
'D',
' ',
'H',
'A',
'S',
'H',0};
365 char *pwdBuf=
nullptr;
366 size_t pwdBufLen, bufferLen;
368 bufferLen = pwdBufLen = pwdLen+2;
370 if (pwdBuf ==
nullptr) {
371 return LDAP_NO_MEMORY;
374 err =
getLoginConfig(
ld, objectDN, methodIDLen, &methodID, tag, &pwdBufLen, pwdBuf);
385 err = LDAP_INAPPROPRIATE_AUTH;
389 if (pwdLen >= pwdBufLen) {
390 memcpy(pwd, &pwdBuf[1], pwdBufLen-1);
391 pwd[pwdBufLen - 1] =
'\0';
393 err = LDAP_NO_MEMORY;
399 if (pwdBuf !=
nullptr) {
419 struct berval *requestBV =
nullptr;
420 char *replyOID =
nullptr;
421 struct berval *replyBV =
nullptr;
424 size_t pwdBufLen, bufferLen;
427 if (objectDN ==
nullptr || (strlen(objectDN) == 0) || pwdSize ==
nullptr ||
ld ==
nullptr) {
428 return LDAP_NO_SUCH_ATTRIBUTE;
431 bufferLen = pwdBufLen = *pwdSize;
433 if (pwdBuf ==
nullptr) {
434 return LDAP_NO_MEMORY;
442 }
else if (!replyOID) {
444 err = LDAP_NOT_SUPPORTED;
447 err = LDAP_NOT_SUPPORTED;
448 }
else if (!replyBV) {
452 err = LDAP_OPERATIONS_ERROR;
457 err = LDAP_OPERATIONS_ERROR;
459 }
else if (!err && pwdBufLen != 0) {
460 if (*pwdSize >= pwdBufLen+1 && pwd !=
nullptr) {
461 memcpy(pwd, pwdBuf, pwdBufLen);
464 err = LDAP_OPERATIONS_ERROR;
466 *pwdSize = pwdBufLen;
476 ldap_memfree(replyOID);
481 ber_bvfree(requestBV);
484 if (pwdBuf !=
nullptr) {
506 if (rc == LDAP_SUCCESS) {
507 DEBUG(5, (
"NDS Universal Password retrieved for %s\n", object_dn));
509 DEBUG(3, (
"NDS Universal Password NOT retrieved for %s\n", object_dn));
512 if (rc != LDAP_SUCCESS) {
514 if (rc == LDAP_SUCCESS) {
515 DEBUG(5, (
"NDS Simple Password retrieved for %s\n", object_dn));
518 DEBUG(3, (
"NDS Simple Password NOT retrieved for %s\n", object_dn));
519 return LDAP_INVALID_CREDENTIALS;
static int nmasldap_get_simple_pwd(LDAP *ld, char *objectDN, size_t pwdLen, char *pwd)
#define SMB_MALLOC_ARRAY(type, nelem)
#define NMASLDAP_GET_LOGIN_CONFIG_REQUEST
static int berEncodeLoginData(struct berval **requestBV, char *objectDN, unsigned int methodIDLen, unsigned int *methodID, char *tag, size_t putDataLen, void *putData)
static int berEncodePasswordData(struct berval **requestBV, const char *objectDN, const char *password, const char *password2)
static int getLoginConfig(LDAP *ld, char *objectDN, unsigned int methodIDLen, unsigned int *methodID, char *tag, size_t *dataLen, void *data)
#define NMASLDAP_GET_PASSWORD_REQUEST
#define DEBUG(level, args)
int nds_get_password(LDAP *ld, char *object_dn, size_t *pwd_len, char *pwd)
#define NMASLDAP_GET_PASSWORD_RESPONSE
static int nmasldap_get_password(LDAP *ld, char *objectDN, size_t *pwdSize, unsigned char *pwd)
#define NMASLDAP_GET_LOGIN_CONFIG_RESPONSE
#define NMAS_LDAP_EXT_VERSION
static int berDecodeLoginData(struct berval *replyBV, int *serverVersion, size_t *retDataLen, void *retData)
void ZeroSensitiveMemory(void *dst, const size_t len)