]> git.sur5r.net Git - openldap/commitdiff
Added passwd_exop, added matchedDN rewrite for results.
authorHoward Chu <hyc@openldap.org>
Sun, 16 Feb 2003 09:22:44 +0000 (09:22 +0000)
committerHoward Chu <hyc@openldap.org>
Sun, 16 Feb 2003 09:22:44 +0000 (09:22 +0000)
14 files changed:
servers/slapd/back-ldap/Makefile.in
servers/slapd/back-ldap/add.c
servers/slapd/back-ldap/attribute.c
servers/slapd/back-ldap/back-ldap.h
servers/slapd/back-ldap/bind.c
servers/slapd/back-ldap/compare.c
servers/slapd/back-ldap/delete.c
servers/slapd/back-ldap/extended.c [new file with mode: 0644]
servers/slapd/back-ldap/external.h
servers/slapd/back-ldap/group.c
servers/slapd/back-ldap/init.c
servers/slapd/back-ldap/modify.c
servers/slapd/back-ldap/modrdn.c
servers/slapd/back-ldap/search.c

index 2ce5a7fef38900695bd7d9701936421d73a69401..7122f6e80bf07081c69a9eac41ab4927fc046ea0 100644 (file)
@@ -2,10 +2,10 @@
 
 SRCS   = init.c config.c search.c bind.c unbind.c add.c compare.c \
                delete.c modify.c modrdn.c group.c attribute.c \
-               suffixmassage.c map.c
+               suffixmassage.c map.c extended.c
 OBJS   = init.lo config.lo search.lo bind.lo unbind.lo add.lo compare.lo \
                delete.lo modify.lo modrdn.lo group.lo attribute.lo \
-               suffixmassage.lo map.lo
+               suffixmassage.lo map.lo extended.lo
 
 LDAP_INCDIR= ../../../include       
 LDAP_LIBDIR= ../../../libraries
index cacc1b1dd4401aa802adbabefe30cbf42296b7cd..2b02a50ba33bd59c925231d61e4b83a54d3271f5 100644 (file)
@@ -69,7 +69,7 @@ ldap_back_add(
 #endif /* !NEW_LOGGING */
        
        lc = ldap_back_getconn(li, conn, op);
-       if ( !lc || !ldap_back_dobind( lc, conn, op ) ) {
+       if ( !lc || !ldap_back_dobind( li, lc, conn, op ) ) {
                return( -1 );
        }
 
@@ -187,7 +187,7 @@ ldap_back_add(
                free( mdn.bv_val );
        }
        
-       return( ldap_back_op_result( lc, conn, op, msgid, j ) );
+       return( ldap_back_op_result( li, lc, conn, op, msgid, j ) );
 }
 
 #ifdef ENABLE_REWRITE
index 7b6eebd9a1cbfde069b4e320cf8d218633c8897c..8b572024b62a8cd269948c1cd080f0d4b51ca37d 100644 (file)
@@ -72,7 +72,7 @@ ldap_back_attribute(
        is_oc = op->o_do_not_cache;
        op->o_do_not_cache = 1;
        lc = ldap_back_getconn(li, conn, op);
-       if ( !lc || !ldap_back_dobind(lc, NULL, op) ) {
+       if ( !lc || !ldap_back_dobind(li, lc, NULL, op) ) {
                op->o_do_not_cache = is_oc;
                return 1;
        }
index 77f09561c5eb65fadb33b4babaa6ae78ed5d786b..d2dc6c9f192a1dc3f413db10ff663f67b94d8f27 100644 (file)
@@ -93,9 +93,9 @@ struct ldapinfo {
 
 struct ldapconn *ldap_back_getconn(struct ldapinfo *li, struct slap_conn *conn,
        struct slap_op *op);
-int ldap_back_dobind(struct ldapconn *lc, Connection *conn, Operation *op);
+int ldap_back_dobind(struct ldapinfo *li, struct ldapconn *lc, Connection *conn, Operation *op);
 int ldap_back_map_result(int err);
-int ldap_back_op_result(struct ldapconn *lc, Connection *conn, Operation *op,
+int ldap_back_op_result(struct ldapinfo *li, struct ldapconn *lc, Connection *conn, Operation *op,
        ber_int_t msgid, int rc);
 int    back_ldap_LTX_init_module(int argc, char *argv[]);
 
index e5a26147541b166769408919b8a33ea0bc1647f2..fe6b6e6c039009037cf5326d9b3afe01076e0316 100644 (file)
@@ -116,7 +116,7 @@ ldap_back_bind(
        /* method is always LDAP_AUTH_SIMPLE if we got here */
        rc = ldap_sasl_bind(lc->ld, mdn.bv_val, LDAP_SASL_SIMPLE,
                cred, op->o_ctrls, NULL, &msgid);
-       rc = ldap_back_op_result( lc, conn, op, msgid, rc );
+       rc = ldap_back_op_result( li, lc, conn, op, msgid, rc );
        if (rc == LDAP_SUCCESS) {
                lc->bound = 1;
                if ( mdn.bv_val != dn->bv_val ) {
@@ -410,7 +410,7 @@ ldap_back_getconn(struct ldapinfo *li, Connection *conn, Operation *op)
  * it can be used to simplify the check.
  */
 int
-ldap_back_dobind( struct ldapconn *lc, Connection *conn, Operation *op )
+ldap_back_dobind( struct ldapinfo *li, struct ldapconn *lc, Connection *conn, Operation *op )
 {      
        int rc;
        ber_int_t msgid;
@@ -419,7 +419,7 @@ ldap_back_dobind( struct ldapconn *lc, Connection *conn, Operation *op )
        if ( !lc->bound ) {
                rc = ldap_sasl_bind(lc->ld, lc->bound_dn.bv_val,
                        LDAP_SASL_SIMPLE, &lc->cred, NULL, NULL, &msgid);
-               rc = ldap_back_op_result( lc, conn, op, msgid, rc );
+               rc = ldap_back_op_result( li, lc, conn, op, msgid, rc );
                if (rc == LDAP_SUCCESS) {
                        lc->bound = 1;
                }
@@ -492,8 +492,8 @@ ldap_back_map_result(int err)
 }
 
 int
-ldap_back_op_result(struct ldapconn *lc, Connection *conn, Operation *op,
-       ber_int_t msgid, int err)
+ldap_back_op_result(struct ldapinfo *li, struct ldapconn *lc,
+       Connection *conn, Operation *op, ber_int_t msgid, int err)
 {
        char *msg = NULL;
        char *match = NULL;
@@ -509,34 +509,38 @@ ldap_back_op_result(struct ldapconn *lc, Connection *conn, Operation *op,
                        if (rc != LDAP_SUCCESS) err = rc;
                }
        }
-       err = ldap_back_map_result(err);
-
-       /* internal ops must not reply to client */
-       if ( !conn || op->o_do_not_cache ) goto quiet;
+       if (err != LDAP_SUCCESS) {
+               err = ldap_back_map_result(err);
 
+               /* internal ops must not reply to client */
+               if ( conn && !op->o_do_not_cache ) {
+                       char *mmatch = NULL;
 #ifdef ENABLE_REWRITE
-       
-       /*
-        * FIXME: need rewrite info for match; mmmh ...
-        */
-       send_ldap_result( conn, op, err, match, msg, NULL, NULL );
-       /* better test the pointers before freeing? */
-       if ( match ) {
-               free( match );
-       }
-
-#else /* !ENABLE_REWRITE */
-
-       send_ldap_result( conn, op, err, match, msg, NULL, NULL );
-       /* better test the pointers before freeing? */
-       if ( match ) {
-               free( match );
+                       if (match) {
+                               
+                               switch(rewrite_session(li->rwinfo, "matchedDn", match, conn,
+                                       &mmatch)) {
+                               case REWRITE_REGEXEC_OK:
+                                       if (!mmatch) mmatch = match; break;
+                               case REWRITE_REGEXEC_UNWILLING:
+                               case REWRITE_REGEXEC_ERR:
+                                       break;
+                               }
+                       }
+#else
+                       struct berval dn, mdn;
+                       if (match) {
+                               ber_str2bv(match, 0, 0, &dn);
+                               ldap_back_dn_massage(li, &dn, &mdn, 0, 0);
+                               mmatch = mdn.bv_val;
+                       }
+#endif
+                       send_ldap_result( conn, op, err, mmatch, msg, NULL, NULL );
+                       if (mmatch != match) free(mmatch);
+               }
        }
-
-#endif /* !ENABLE_REWRITE */
-
+       if ( match ) free( match );
        if ( msg ) free( msg );
-quiet:
        return( (err==LDAP_SUCCESS) ? 0 : -1 );
 }
 
index 3b9c101b9234260227e6adf726f171329aab1a46..348736f2f1e42206db0b4b7c035eccd7d98b29bf 100644 (file)
@@ -63,7 +63,7 @@ ldap_back_compare(
        ber_int_t msgid;
 
        lc = ldap_back_getconn(li, conn, op);
-       if (!lc || !ldap_back_dobind( lc, conn, op ) ) {
+       if (!lc || !ldap_back_dobind( li, lc, conn, op ) ) {
                return( -1 );
        }
 
@@ -124,5 +124,5 @@ ldap_back_compare(
                free( mdn.bv_val );
        }
        
-       return( ldap_back_op_result( lc, conn, op, msgid, rc ) );
+       return( ldap_back_op_result( li, lc, conn, op, msgid, rc ) );
 }
index 48ab3c3533a5a8dea8fa144d3cad72cb9ff92e40..a2e737f7a8653b77d5ad1bea3dfa69a522e19a36 100644 (file)
@@ -63,7 +63,7 @@ ldap_back_delete(
 
        lc = ldap_back_getconn( li, conn, op );
        
-       if ( !lc || !ldap_back_dobind( lc, conn, op ) ) {
+       if ( !lc || !ldap_back_dobind( li, lc, conn, op ) ) {
                return( -1 );
        }
 
@@ -105,5 +105,5 @@ ldap_back_delete(
                free( mdn.bv_val );
        }
        
-       return( ldap_back_op_result( lc, conn, op, msgid, rc ) );
+       return( ldap_back_op_result( li, lc, conn, op, msgid, rc ) );
 }
diff --git a/servers/slapd/back-ldap/extended.c b/servers/slapd/back-ldap/extended.c
new file mode 100644 (file)
index 0000000..f5c5df8
--- /dev/null
@@ -0,0 +1,178 @@
+/* extended.c - ldap backend extended routines */
+/* $OpenLDAP$ */
+/*
+ * Copyright 1998-2003 The OpenLDAP Foundation, All Rights Reserved.
+ * COPYING RESTRICTIONS APPLY, see COPYRIGHT file
+ */
+
+#include "portable.h"
+
+#include <stdio.h>
+#include <ac/string.h>
+
+#include "slap.h"
+#include "back-ldap.h"
+#include "lber_pvt.h"
+
+BI_op_extended ldap_back_exop_passwd;
+
+static struct exop {
+       struct berval *oid;
+       BI_op_extended  *extended;
+} exop_table[] = {
+       { (struct berval *)&slap_EXOP_MODIFY_PASSWD, ldap_back_exop_passwd },
+       { NULL, NULL }
+};
+
+int
+ldap_back_extended(
+       Backend         *be,
+       Connection              *conn,
+       Operation               *op,
+       struct berval           *reqoid,
+       struct berval   *reqdata,
+       char            **rspoid,
+       struct berval   **rspdata,
+       LDAPControl *** rspctrls,
+       const char**    text,
+       BerVarray       *refs 
+)
+{
+       int i;
+
+       for( i=0; exop_table[i].extended != NULL; i++ ) {
+               if( ber_bvcmp( exop_table[i].oid, reqoid ) == 0 ) {
+                       return (exop_table[i].extended)(
+                               be, conn, op,
+                               reqoid, reqdata,
+                               rspoid, rspdata, rspctrls,
+                               text, refs );
+               }
+       }
+
+       *text = "not supported within naming context";
+       return LDAP_UNWILLING_TO_PERFORM;
+}
+
+int
+ldap_back_exop_passwd(
+       Backend         *be,
+       Connection              *conn,
+       Operation               *op,
+       struct berval           *reqoid,
+       struct berval   *reqdata,
+       char                    **rspoid,
+       struct berval   **rspdata,
+       LDAPControl             *** rspctrls,
+       const char              **text,
+       BerVarray *refs )
+{
+       struct ldapinfo *li = (struct ldapinfo *) be->be_private;
+       struct ldapconn *lc;
+       struct berval id = { 0, NULL };
+       struct berval old = { 0, NULL };
+       struct berval new = { 0, NULL };
+       struct berval dn, mdn = { 0, NULL }, *newpw = NULL;
+       LDAPMessage *res;
+       ber_int_t msgid;
+       char *msg = NULL, *match = NULL;
+       int rc;
+
+       lc = ldap_back_getconn(li, conn, op);
+       if (!lc || !ldap_back_dobind(li, lc, conn, op) ) {
+               return -1;
+       }
+
+       rc = slap_passwd_parse( reqdata, &id, &old, &new, text );
+       if (rc != LDAP_SUCCESS)
+               return rc;
+       
+       if (id.bv_len) {
+               dn = id;
+       } else {
+               dn = op->o_dn;
+       }
+
+#ifdef NEW_LOGGING
+       LDAP_LOG ( ACL, DETAIL1, "ldap_back_exop_passwd: \"%s\"%s\"\n",
+               dn.bv_val, id.bv_len ? " (proxy)" : "", 0 );
+#else
+       Debug( LDAP_DEBUG_TRACE, "ldap_back_exop_passwd: \"%s\"%s\n",
+               dn.bv_val, id.bv_len ? " (proxy)" : "", 0 );
+#endif
+
+       if (dn.bv_len == 0) {
+               *text = "No password is associated with the Root DSE";
+               return LDAP_UNWILLING_TO_PERFORM;
+       }
+       if (id.bv_len) {
+#ifdef ENABLE_REWRITE
+               switch ( rewrite_session( li->rwinfo, "modifyPwd", dn.bv_val, conn, &mdn.bv_val ) ) {
+               case REWRITE_REGEXEC_OK:
+                       if ( mdn.bv_val == NULL ) {
+                               mdn.bv_val = dn.bv_val;
+                       }
+                       mdn.bv_len = strlen(mdn.bv_val);
+#ifdef NEW_LOGGING
+                       LDAP_LOG( BACK_LDAP, DETAIL1,
+                               "[rw] modifyPwd: \"%s\" -> \"%s\"\n", dn.bv_val, mdn.bv_val, 0 );
+#else /* !NEW_LOGGING */
+                       Debug( LDAP_DEBUG_ARGS, "rw> modifyPwd: \"%s\" -> \"%s\"\n%s",
+                                       dn.bv_val, mdn.bv_val, "" );
+#endif /* !NEW_LOGGING */
+                       break;
+
+               case REWRITE_REGEXEC_UNWILLING:
+                       send_ldap_result( conn, op, LDAP_UNWILLING_TO_PERFORM,
+                                       NULL, "Operation not allowed", NULL, NULL );
+                       return( -1 );
+
+               case REWRITE_REGEXEC_ERR:
+                       send_ldap_result( conn, op, LDAP_OTHER,
+                                       NULL, "Rewrite error", NULL, NULL );
+                       return( -1 );
+               }
+#else /* !ENABLE_REWRITE */
+               ldap_back_dn_massage( li, &dn, &mdn, 0, 1 );
+#endif /* !ENABLE_REWRITE */
+       }
+
+       rc = ldap_passwd(lc->ld, id.bv_len ? &mdn : NULL, old.bv_len ? &old : NULL,
+               new.bv_len ? &new : NULL, op->o_ctrls, NULL, &msgid);
+#ifdef ENABLE_REWRITE
+       if (mdn.bv_val != dn.bv_val)
+#endif
+               free(mdn.bv_val);
+       if (rc == LDAP_SUCCESS) {
+               if (ldap_result(lc->ld, msgid, 1, NULL, &res) == -1) {
+                       ldap_get_option(lc->ld, LDAP_OPT_ERROR_NUMBER, &rc);
+               } else {
+                       /* sigh. parse twice, because parse_passwd doesn't give
+                        * us the err / match / msg info.
+                        */
+                       int err;
+                       rc = ldap_parse_result(lc->ld, res, &err, &match, &msg,
+                               NULL, NULL, 0);
+                       if (rc == LDAP_SUCCESS) {
+                               if (err == LDAP_SUCCESS) {
+                                       rc = ldap_parse_passwd(lc->ld, res, &newpw);
+                                       if (rc == LDAP_SUCCESS && newpw) {
+                                               *rspdata = slap_passwd_return(newpw);
+                                               ber_bvfree(newpw);
+                                       }
+                               } else {
+                                       rc = err;
+                               }
+                       }
+                       ldap_msgfree(res);
+               }
+       }
+       if (rc != LDAP_SUCCESS) {
+               rc = ldap_back_map_result(rc);
+               send_ldap_result(conn, op, rc, match, msg, NULL, NULL);
+               if (match) free(match);
+               if (msg) free(msg);
+               rc = -1;
+       }
+       return rc;
+}
index 2872e0d72a9d1f386592e508f727a34435ccac5f..e12b6b5ecbdcca88003c32d65a9571913bd6be39 100644 (file)
@@ -37,6 +37,8 @@ extern BI_op_delete   ldap_back_delete;
 
 extern BI_op_abandon   ldap_back_abandon;
 
+extern BI_op_extended  ldap_back_extended;
+
 extern BI_acl_group    ldap_back_group;
 
 extern BI_acl_attribute        ldap_back_attribute;
index b6dbe107dd94031dc6fbc5aaa72430a736d6010d..ca1e11c1181657853525307228b16d4e0aaa7529 100644 (file)
@@ -174,7 +174,7 @@ ldap_back_group(
        oc = op->o_do_not_cache;
        op->o_do_not_cache = 1;
        lc = ldap_back_getconn(li, conn, op);
-       if ( !lc || !ldap_back_dobind( lc, NULL, op ) ) {
+       if ( !lc || !ldap_back_dobind( li, lc, NULL, op ) ) {
                op->o_do_not_cache = oc;
                goto cleanup;
        }
index aa76717800666c798d3e575ec96239a01f77349a..5cffa2f67fcda0737d2d4368feb9310ae0d0e5b6 100644 (file)
@@ -87,7 +87,7 @@ ldap_back_initialize(
        bi->bi_op_delete = ldap_back_delete;
        bi->bi_op_abandon = 0;
 
-       bi->bi_extended = 0;
+       bi->bi_extended = ldap_back_extended;
 
        bi->bi_acl_group = ldap_back_group;
        bi->bi_acl_attribute = ldap_back_attribute;
index a44915618dc31536c76c57927849a6d2d2486dcb..83de06937a9649a6b36c769203731c32df2fec52 100644 (file)
@@ -66,7 +66,7 @@ ldap_back_modify(
        ber_int_t msgid;
 
        lc = ldap_back_getconn(li, conn, op);
-       if ( !lc || !ldap_back_dobind( lc, conn, op ) ) {
+       if ( !lc || !ldap_back_dobind( li, lc, conn, op ) ) {
                return( -1 );
        }
 
@@ -171,6 +171,6 @@ cleanup:;
                ch_free(modv[i]->mod_bvalues);
        ch_free(mods);
        ch_free(modv);
-       return( ldap_back_op_result( lc, conn, op, msgid, rc ));
+       return( ldap_back_op_result( li, lc, conn, op, msgid, rc ));
 }
 
index 1dd14ea1fc781fdd6e440a3dcda099e66547c85f..447122920acb13635140f76e8ca45e648add81c3 100644 (file)
@@ -67,7 +67,7 @@ ldap_back_modrdn(
        struct berval mdn = { 0, NULL }, mnewSuperior = { 0, NULL };
 
        lc = ldap_back_getconn( li, conn, op );
-       if ( !lc || !ldap_back_dobind(lc, conn, op) ) {
+       if ( !lc || !ldap_back_dobind(li, lc, conn, op) ) {
                return( -1 );
        }
 
@@ -159,5 +159,5 @@ ldap_back_modrdn(
                free( mnewSuperior.bv_val );
        }
        
-       return( ldap_back_op_result( lc, conn, op, msgid, rc ) );
+       return( ldap_back_op_result( li, lc, conn, op, msgid, rc ) );
 }
index d4d8051a5d0af7593deac070a59545dad5c52be6..3db899345584c37cc45aca93ea936dc895f8ec1c 100644 (file)
@@ -93,7 +93,7 @@ ldap_back_search(
         * FIXME: in case of values return filter, we might want
         * to map attrs and maybe rewrite value
         */
-       if ( !ldap_back_dobind( lc, conn, op ) ) {
+       if ( !ldap_back_dobind( li, lc, conn, op ) ) {
                return( -1 );
        }
 
@@ -265,7 +265,7 @@ ldap_back_search(
                        : NULL, slimit, &msgid);
        if ( rc != LDAP_SUCCESS ) {
 fail:;
-               rc = ldap_back_op_result(lc, conn, op, msgid, rc);
+               rc = ldap_back_op_result(li, lc, conn, op, msgid, rc);
                goto finish;
        }