]> git.sur5r.net Git - openldap/commitdiff
ITS#3846 don't use hashed passwords on SASL bind
authorHoward Chu <hyc@openldap.org>
Tue, 9 Aug 2005 23:03:21 +0000 (23:03 +0000)
committerHoward Chu <hyc@openldap.org>
Tue, 9 Aug 2005 23:03:21 +0000 (23:03 +0000)
libraries/liblutil/passwd.c
servers/slapd/sasl.c

index 8fe4673aadd184725eff458e7c6f0a4a8d791f42..fa39c55b9a0b0ae94745da34f9a0300af81f22cd 100644 (file)
@@ -211,11 +211,21 @@ static const struct pw_scheme *get_scheme(
        const char* scheme )
 {
        struct pw_slist *pws;
+       struct berval bv;
 
        if (!pw_inited) lutil_passwd_init();
 
+       bv.bv_val = strchr( scheme, '}' );
+       if ( !bv.bv_val )
+               return NULL;
+
+       bv.bv_len = bv.bv_val - scheme + 1;
+       bv.bv_val = (char *) scheme;
+
        for( pws=pw_schemes; pws; pws=pws->next ) {
-               if( strcasecmp(scheme, pws->s.name.bv_val ) == 0 ) {
+               if( bv.bv_len != pws->s.name.bv_len )
+                       continue;
+               if( strncasecmp(bv.bv_val, pws->s.name.bv_val, bv.bv_len ) == 0 ) {
                        return &(pws->s);
                }
        }
@@ -686,18 +696,21 @@ static int chk_md5(
  */
 
 static void lmPasswd_to_key(
-       const unsigned char *lmPasswd,
+       const char *lmPasswd,
        des_cblock *key)
 {
+       const unsigned char *lpw = (const unsigned char *) lmPasswd;
+       unsigned char *k = (unsigned char *) key;
+
        /* make room for parity bits */
-       ((char *)key)[0] = lmPasswd[0];
-       ((char *)key)[1] = ((lmPasswd[0]&0x01)<<7) | (lmPasswd[1]>>1);
-       ((char *)key)[2] = ((lmPasswd[1]&0x03)<<6) | (lmPasswd[2]>>2);
-       ((char *)key)[3] = ((lmPasswd[2]&0x07)<<5) | (lmPasswd[3]>>3);
-       ((char *)key)[4] = ((lmPasswd[3]&0x0F)<<4) | (lmPasswd[4]>>4);
-       ((char *)key)[5] = ((lmPasswd[4]&0x1F)<<3) | (lmPasswd[5]>>5);
-       ((char *)key)[6] = ((lmPasswd[5]&0x3F)<<2) | (lmPasswd[6]>>6);
-       ((char *)key)[7] = ((lmPasswd[6]&0x7F)<<1);
+       k[0] = lpw[0];
+       k[1] = ((lpw[0] & 0x01) << 7) | (lpw[1] >> 1);
+       k[2] = ((lpw[1] & 0x03) << 6) | (lpw[2] >> 2);
+       k[3] = ((lpw[2] & 0x07) << 5) | (lpw[3] >> 3);
+       k[4] = ((lpw[3] & 0x0F) << 4) | (lpw[4] >> 4);
+       k[5] = ((lpw[4] & 0x1F) << 3) | (lpw[5] >> 5);
+       k[6] = ((lpw[5] & 0x3F) << 2) | (lpw[6] >> 6);
+       k[7] = ((lpw[6] & 0x7F) << 1);
                
        des_set_odd_parity( key );
 }      
@@ -817,7 +830,6 @@ static int chk_crypt(
        const struct berval * cred,
        const char **text )
 {
-       char *cr;
        unsigned int i;
 
        for( i=0; i<cred->bv_len; i++) {
@@ -862,7 +874,7 @@ static int chk_unix(
        const char **text )
 {
        unsigned int i;
-       char *pw,*cr;
+       char *pw;
 
        for( i=0; i<cred->bv_len; i++) {
                if(cred->bv_val[i] == '\0') {
index 74f895886e27de4aa3295bf6b1a3779246b91265..5fcfa544dbee745665945a855ce7c7ab7c9d5dd5 100644 (file)
@@ -336,6 +336,8 @@ typedef struct lookup_info {
 
 static slap_response sasl_ap_lookup;
 
+static struct berval sc_cleartext = BER_BVC("{CLEARTEXT}");
+
 static int
 sasl_ap_lookup( Operation *op, SlapReply *rs )
 {
@@ -388,6 +390,34 @@ sasl_ap_lookup( Operation *op, SlapReply *rs )
                        sl->list[i].name );
                }
                for ( bv = a->a_vals; bv->bv_val; bv++ ) {
+                       /* ITS#3846 don't give hashed passwords to SASL */
+                       if ( ad == slap_schema.si_ad_userPassword &&
+                               bv->bv_val[0] == '{' ) {
+                               rc = lutil_passwd_scheme( bv->bv_val );
+                               if ( rc ) {
+                                       /* If it's not a recognized scheme, just assume it's
+                                        * a cleartext password that happened to include brackets.
+                                        *
+                                        * If it's a recognized scheme, skip this value, unless the
+                                        * scheme is {CLEARTEXT}. In that case, skip over the
+                                        * scheme name and use the remainder. If there is nothing
+                                        * past the scheme name, skip this value.
+                                        */
+#ifdef SLAPD_CLEARTEXT
+                                       if ( !strncasecmp( bv->bv_val, sc_cleartext.bv_val,
+                                               sc_cleartext.bv_len )) {
+                                               struct berval cbv;
+                                               cbv.bv_len = bv->bv_len - sc_cleartext.bv_len;
+                                               if ( cbv.bv_len ) {
+                                                       cbv.bv_val = bv->bv_val + sc_cleartext.bv_len;
+                                                       sl->sparams->utils->prop_set( sl->sparams->propctx,
+                                                               sl->list[i].name, cbv.bv_val, cbv.bv_len );
+                                               }
+                                       }
+#endif
+                                       continue;
+                               }
+                       }
                        sl->sparams->utils->prop_set( sl->sparams->propctx,
                                sl->list[i].name, bv->bv_val, bv->bv_len );
                }