Full_Name: Shou C Version: 2.4.48 OS: URL: ftp://ftp.openldap.org/incoming/ Submission from: (NULL) (98.185.228.137)
Here is the implementation of lutil_memcmp at /libraries/liblutil/memcmp.c int (lutil_memcmp)(const void *v1, const void *v2, size_t n) { if (n != 0) { const unsigned char *s1=v1, *s2=v2; do { if (*s1++ != *s2++) return *--s1 - *--s2; // immediate return after difference } while (--n != 0); } return 0; } Later, it is redefined as memcpy. Then this function is used in the password checking function to compare user password and inputed password. This would lead to a timing attack / side channel attack.
Here are all usages related to comparison of plaintext password /libraries/liblutil/passwd.c: 341 if( is_allowed_scheme("{CLEARTEXT}", schemes ) ) { return ( passwd->bv_len == cred->bv_len ) ? memcmp( passwd->bv_val, cred->bv_val, passwd->bv_len ) : 1; }
Here are all usages related to comparison of hashed password (although this is less exploitable, by bruteforcing based on hash value, with enough time, attacker could still recover the password): /contrib/slapd-modules/passwd/sha2/slapd-sha2.c:262 rc = memcmp((char *)orig_pass, (char *)SHAdigest, sizeof(SHAdigest));
/contrib/slapd-modules/passwd/sha2/slapd-sha2.c:303 rc = memcmp((char *)orig_pass, (char *)SHAdigest, sizeof(SHAdigest));
/contrib/slapd-modules/passwd/sha2/slapd-sha2.c:350 rc = memcmp((char *)orig_pass, (char *)SHAdigest, sizeof(SHAdigest));
/contrib/slapd-modules/passwd/sha2/slapd-sha2.c:391 rc = memcmp((char *)orig_pass, (char *)SHAdigest, sizeof(SHAdigest));
/contrib/slapd-modules/passwd/sha2/slapd-sha2.c:438 rc = memcmp((char *)orig_pass, (char *)SHAdigest, sizeof(SHAdigest));
/contrib/slapd-modules/passwd/sha2/slapd-sha2.c:479 rc = memcmp((char *)orig_pass, (char *)SHAdigest, sizeof(SHAdigest));
/libraries/liblutil/passwd.c: 526 rc = memcmp((char *)orig_pass, (char *)SHA1digest, sizeof(SHA1digest));
/libraries/liblutil/passwd.c: 567 rc = memcmp((char *)orig_pass, (char *)SHA1digest, sizeof(SHA1digest));
/libraries/liblutil/passwd.c: 613 rc = memcmp((char *)orig_pass, (char *)MD5digest, sizeof(MD5digest));
/libraries/liblutil/passwd.c: 654 rc = memcmp((char *)orig_pass, (char *)MD5digest, sizeof(MD5digest));
/libraries/liblutil/passwd.c: 894 return memcmp( PasswordHash, storedPasswordHash, 32) ? LUTIL_PASSWD_ERR : LUTIL_PASSWD_OK;
etc..
A safer implementation is: int (lutil_safe_memcmp)(const void *v1, const void *v2, size_t n) { int c=0; if (n != 0) { const unsigned char *s1=v1, *s2=v2; do { if (*s1++ != *s2++ && c == 0) c += *--s1 - *--s2; } while (--n != 0); } return c; }