[Date Prev][Date Next] [Chronological] [Thread] [Top]

Re: Cyrus-IMAPD and LDAP



Hi,
   I attached a patch for Cyrus SASL to make it do LDAP authentication.
The difference between this patch and the patch listed on the website
below is my patch allows people to authenticate via cyrus-sasl and the
user doesn't have to be able to log into the LDAP server. If anyone has
any questions about this, feel free to contact me

Brian

On Tue, 31 Jul 2001, Tarjei Huse wrote:

> www.surf.co.uk -> cyrus sasl patch.
> Tarjei
>
> > Hi !
> >
> > I had installed cyrus-Imapd with Cyrus-sysl-authentfication - how can I
> > implement a auth against my ldap-database ?
> >
> > Regards
> >
> > Marc Schöchlin
>
>
> ____________________
> Tarjei Huse
> 920 63 413
>
>
--- /usr/src/cyrus-sasl-orig/lib/checkpw.c	Wed Jul 19 21:24:13 2000
+++ checkpw.c	Sat Jul  7 07:14:40 2001
@@ -49,10 +49,16 @@
 #include <saslint.h>
 #include <saslutil.h>
 #include <assert.h>
+#include <syslog.h>
 #ifdef HAVE_UNISTD_H
 #include <unistd.h>
 #endif
 
+#ifdef HAVE_LDAP
+#include <lber.h>
+#include <ldap.h>
+#endif /* HAVE_LDAP */
+
 #ifdef HAVE_KRB
 #include <krb.h>
 #endif
@@ -902,8 +908,132 @@
 
 #endif
 
+#ifdef HAVE_LDAP
+
+/* simon@surf.org.uk LDAP auth 07/11/2000
+ * Updated to 1.5.24 by SWH 09/12/2000
+ * changed to use malloc and simplify the auth by Simon@surf.org.uk 10/21/2000
+*/
+
+/* masneyb@seul.org LDAP auth 01/15/2001
+ * Updated to make it do a search for the entry in LDAP 
+*/
+
+static int ldap_verify_password(sasl_conn_t *conn,
+                               const char *userid,
+                               const char *password,
+                               const char *service __attribute__((unused)),
+                               const char *user_realm __attribute__((unused)),
+                               const char **reply)
+{
+  char *ldap_server="", *ldap_basedn="", *ldap_filter="", *port_num="", *ldap_user="", *ldap_pass="";
+  char **tempstr, buf[1024], salt[2], *attrs[] = {"userPassword", NULL}, *pos;
+  int ldap_port = LDAP_PORT, found;
+  LDAPMessage * res, * ent;
+  sasl_getopt_t * getopt;
+  void *context;
+  LDAP * ld;
+
+  if (strcmp(password,"") == 0 || strcmp(userid,"") == 0) 
+    return SASL_BADPARAM;
+
+  if (reply)
+    *reply = NULL;
+
+  if (_sasl_getcallback (conn, SASL_CB_GETOPT, &getopt, &context) == SASL_OK) 
+    {
+      getopt (context, NULL, "ldap_server", (const char **) &ldap_server, NULL);
+      getopt (context, NULL, "ldap_user", (const char **) &ldap_user, NULL);
+      getopt (context, NULL, "ldap_pass", (const char **) &ldap_pass, NULL);
+      getopt (context, NULL, "ldap_basedn", (const char **) &ldap_basedn, NULL);
+      getopt (context, NULL, "ldap_filter", (const char **) &ldap_filter, NULL);
+      getopt (context, NULL, "ldap_port", (const char **) &port_num, NULL);
+      if (port_num)
+        ldap_port = atoi (port_num);
+      if (ldap_port == 0)
+        ldap_port = LDAP_PORT;
+     
+    }
+
+  if ((ld = ldap_init (ldap_server, ldap_port)) == NULL) 
+    {
+      if (reply) 
+        *reply = "cannot connect to LDAP server";
+      return SASL_FAIL;
+    }
+
+  if (ldap_simple_bind_s (ld, ldap_user, ldap_pass) != LDAP_SUCCESS)
+    {
+      ldap_unbind (ld);
+      if (reply)
+        *reply = "cannot login into LDAP server";
+      return SASL_FAIL;
+    }
+
+  snprintf (buf, sizeof (buf), ldap_filter, userid);
+  if (ldap_search_s (ld, ldap_basedn, LDAP_SCOPE_SUBTREE, buf, attrs, 0,
+                     &res) != LDAP_SUCCESS)
+    {
+      ldap_unbind (ld);
+      if (reply)
+        *reply = "invalid username/password";
+      return SASL_FAIL;
+    }
+
+  found = 0;
+  for (ent = ldap_first_entry (ld, res); ent != NULL;
+       ent = ldap_next_entry (ld, ent))
+    {
+      if ((tempstr = ldap_get_values (ld, ent, "userPassword")) == NULL)
+        continue;
+
+      if (strncmp (*tempstr, "{crypt}", 7) == 0)
+        {
+          salt[0] = (*tempstr)[7];
+          salt[1] = (*tempstr)[8];
+          if (strcmp ((*tempstr)+7, crypt (password, salt)) != 0)
+            {
+              ldap_value_free (tempstr);
+              continue;
+            }
+        }
+      else
+        {
+          strncpy (buf, password, sizeof (buf));
+          for (pos = buf; *pos != '\0'; pos++)
+            *pos = tolower (*pos);
+          if (strcmp (*tempstr, buf) != 0)
+            {
+              ldap_value_free (tempstr);
+              continue;
+            }
+        }
+      found = 1;
+      ldap_value_free (tempstr);
+      break;
+    }
+
+  if (res != NULL)
+    ldap_msgfree (res);
+
+  ldap_unbind (ld);
+  if (!found)
+    {
+      if (reply)
+        *reply = "invalid username/password";
+      return SASL_FAIL;
+    }
+  return SASL_OK;
+}
+
+#endif /* HAVE_LDAP */
+
+
 struct sasl_verify_password_s _sasl_verify_password[] = {
     { "sasldb", &sasldb_verify_password },
+#ifdef HAVE_LDAP
+    { "ldap", &ldap_verify_password },
+#endif
 #ifdef HAVE_KRB
     { "kerberos_v4", &kerberos_verify_password },
 #endif