gnunet-svn
[Top][All Lists]
Advanced

[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]

[GNUnet-SVN] r12799 - in libmicrohttpd: . src/daemon src/examples src/in


From: gnunet
Subject: [GNUnet-SVN] r12799 - in libmicrohttpd: . src/daemon src/examples src/include
Date: Wed, 1 Sep 2010 15:43:14 +0200

Author: grothoff
Date: 2010-09-01 15:43:14 +0200 (Wed, 01 Sep 2010)
New Revision: 12799

Modified:
   libmicrohttpd/configure.ac
   libmicrohttpd/src/daemon/daemon.c
   libmicrohttpd/src/daemon/digestauth.c
   libmicrohttpd/src/daemon/internal.h
   libmicrohttpd/src/examples/digest_auth_example.c
   libmicrohttpd/src/include/microhttpd.h
Log:
From: 
Amr Ali <address@hidden>
  To: 
Christian Grothoff <address@hidden>
  Date: 
Today 15:24:06
  Attachments: 
 http_dauth_r5.patch

Attached is a patch for all points discussed below.



Modified: libmicrohttpd/configure.ac
===================================================================
--- libmicrohttpd/configure.ac  2010-09-01 13:36:01 UTC (rev 12798)
+++ libmicrohttpd/configure.ac  2010-09-01 13:43:14 UTC (rev 12799)
@@ -338,20 +338,15 @@
 
 if test "x$disable_dauth" != "xyes"
 then
- if test "$gcrypt" = "true"
- then
-   enable_dauth="yes"
-   MHD_LIBDEPS="$LIBGCRYPT_LIBS"
- else
-   disable_dauth="yes (lacking libgcrypt)"
-   enable_dauth="no (lacking libgcrypt)"
- fi
+ AC_DEFINE([DAUTH_SUPPORT],[1],[include Digest Auth support])
+ enable_dauth="yes"
 else
+ AC_DEFINE([DAUTH_SUPPORT],[0],[disable Digest Auth support])
  enable_dauth="no"
 fi
 AC_MSG_RESULT($disable_dauth)
 
-AM_CONDITIONAL(ENABLE_DAUTH, [test "x$disable_dauth" != "xyes" -a "$gcrypt" = 
"true"])
+AM_CONDITIONAL(ENABLE_DAUTH, [test "x$disable_dauth" != "xyes"])
 
 MHD_LIB_LDFLAGS="-export-dynamic -no-undefined"
 

Modified: libmicrohttpd/src/daemon/daemon.c
===================================================================
--- libmicrohttpd/src/daemon/daemon.c   2010-09-01 13:36:01 UTC (rev 12798)
+++ libmicrohttpd/src/daemon/daemon.c   2010-09-01 13:43:14 UTC (rev 12799)
@@ -1367,6 +1367,11 @@
            return MHD_NO;
           break;
 #endif
+#ifdef DAUTH_SUPPORT
+       case MHD_OPTION_DIGEST_AUTH_RANDOM:
+         daemon->digest_auth_random = va_arg (ap, const char *);
+         break;
+#endif
        case MHD_OPTION_LISTEN_SOCKET:
          daemon->socket_fd = va_arg (ap, int);   
          break;
@@ -1423,6 +1428,7 @@
                case MHD_OPTION_HTTPS_MEM_KEY:
                case MHD_OPTION_HTTPS_MEM_CERT:
                case MHD_OPTION_HTTPS_PRIORITIES:
+               case MHD_OPTION_DIGEST_AUTH_RANDOM:
                case MHD_OPTION_ARRAY:
                  if (MHD_YES != parse_options (daemon,
                                                servaddr,

Modified: libmicrohttpd/src/daemon/digestauth.c
===================================================================
--- libmicrohttpd/src/daemon/digestauth.c       2010-09-01 13:36:01 UTC (rev 
12798)
+++ libmicrohttpd/src/daemon/digestauth.c       2010-09-01 13:43:14 UTC (rev 
12799)
@@ -25,10 +25,8 @@
 
 #include "internal.h"
 #include "md5.h"
-#include "sha1.h"
 
 #define HASH_MD5_HEX_LEN (2 * MD5_DIGEST_SIZE)
-#define HASH_SHA1_HEX_LEN (2 * SHA1_DIGEST_SIZE)
 
 #define _BASE          "Digest "
 
@@ -57,7 +55,6 @@
   hex[len * 2] = '\0';
 }
 
-
 /**
  * calculate H(A1) as per RFC2617 spec and store the
  * result in 'sessionkey'.
@@ -109,9 +106,8 @@
  * @param uri requested URL
  * @param hentity H(entity body) if qop="auth-int"
  * @param response request-digest or response-digest
- * @return 0 on success, 1 on error
  */
-static int
+static void
 digest_calc_response(const char *ha1,
                     const char *nonce,
                     const char *noncecount,
@@ -133,8 +129,6 @@
   MD5Update (&md5, uri, strlen(uri));  
   if (strcasecmp(qop, "auth-int") == 0) 
     {
-      if (hentity == NULL)
-       return 1;
       MD5Update (&md5, ":", 1);
       MD5Update (&md5, hentity, strlen(hentity));
     }  
@@ -158,61 +152,50 @@
   MD5Update (&md5, ha2hex, HASH_MD5_HEX_LEN);
   MD5Final (resphash, &md5);
   cvthex(resphash, sizeof (resphash), response);
-  return 0;
 }
 
-
-static const char *
-lookup_sub_value(char *data, 
-                size_t len,
-                const char *key)
+/**
+ * Lookup subvalue off of the HTTP Authorization header
+ *
+ * @param dest A pointer to char * to store the result
+ * @param size The size of dst
+ * @param data A pointer to char * of the Authorization header
+ * @param key A pointer to char * of the key in the header
+ * @return size of the located value, 0 if otherwise
+ */
+static int
+lookup_sub_value(char *dest,
+               size_t size,
+               const char *data,
+               const char *key)
 {
-  char *tmp = data;
-  char *value = NULL;
-  size_t keylen;
-  size_t i;
-  
-  keylen = strlen(key);
-  for (i = 0; i < len; ++i) {
-    if (strncmp(tmp, key, keylen) == 0 &&
-       strncmp(tmp + keylen, "=", 1) == 0) 
-      {
-       tmp += keylen;
-       break;
-      }
-    else 
-      {
-       tmp++;
-      }    
-    if ((i + 1) == len) 
-      return NULL;
-  }  
-  while (1) 
-    {
-      tmp++;
-      
-      if (*tmp == '"' && *(tmp + 1) == ',') 
-       {
-         *tmp = '\0';
-         break;
-       }      
-      if (*tmp == '"' && *(tmp + 1) == '\0') 
-       {
-         *tmp = '\0';
-         break;
-       }      
-      if (*tmp == ',' || *tmp == '\0') 
-       {
-         *tmp = '\0';
-         break;
-       }      
-      if (*tmp == '"')
-       continue;      
-      if (value == NULL)
-       value = tmp;
-    }
-  
-  return value;
+       size_t keylen = strlen(key);
+       const char *ptr = data;
+       char field[size];
+       char fmt[24 + keylen + 1];
+       int items_read;
+
+       ptr += strstr(ptr, key) - ptr;
+
+       if (*(ptr + keylen) != ' ' && *(ptr + keylen) != '=') {
+               ++ptr;
+               ptr += strstr(ptr, key) - ptr;
+       }
+
+       if (!ptr)
+               return 0;
+
+       snprintf(fmt, 24 + keylen + 1,
+                       "%s%%*[ =\"]%%%u[^, \"]", key, (unsigned int) size - 1);
+
+       items_read = sscanf(ptr, fmt, field);
+
+       if (items_read == 1) {
+               strcpy(dest, field);
+               return strlen(dest);
+       }
+
+       return 0;
 }
 
 
@@ -227,7 +210,7 @@
 MHD_digest_auth_get_username(struct MHD_Connection *connection)
 {
   size_t len;
-  const char *user;
+  char user[50];
   const char *header;
   
   header = MHD_lookup_connection_value(connection,
@@ -236,53 +219,44 @@
   if (header == NULL)
     return NULL;
   if (strncmp(header, _BASE, strlen(_BASE)) != 0)
-    return NULL;  
-  len = strlen(header) - strlen(_BASE) + 1;
-  {
-    char buffer[len];
-  
-    memcpy (buffer,
-           header + strlen(_BASE), 
-           len);  
-    user = lookup_sub_value(buffer, len, "username");  
-    if (NULL == user) 
-      return NULL;
-    return strdup (user);
-  }
-}
+    return NULL;
 
+  len = lookup_sub_value(user, 50, header, "username");
 
-/**
- * FIXME: password should probably not be here!
- */
+  if (!len)
+         return NULL;
+
+  return strdup(user);
+}
+
 static void
 calculate_nonce (uint32_t nonce_time,
                 const char *method,
-                const char *password,
+                const char *rnd,
                 const char *uri,
                 const char *realm,
                 char *nonce)
 {
-  struct SHA1Context sha1;
+  struct MD5Context md5;
   unsigned char timestamp[4];
-  unsigned char tmpnonce[SHA1_DIGEST_SIZE];
+  unsigned char tmpnonce[MD5_DIGEST_SIZE];
   char timestamphex[sizeof(timestamp)*2+1];
 
-  SHA1Init (&sha1);
+  MD5Init (&md5);
   timestamp[0] = (nonce_time & 0xff000000) >> 0x18;
   timestamp[1] = (nonce_time & 0x00ff0000) >> 0x10;
   timestamp[2] = (nonce_time & 0x0000ff00) >> 0x08;
   timestamp[3] = (nonce_time & 0x000000ff);    
-  SHA1Update(&sha1, timestamp, 4);
-  SHA1Update(&sha1, ":", 1);
-  SHA1Update(&sha1, method, strlen(method));
-  SHA1Update(&sha1, ":", 1);
-  SHA1Update(&sha1, password, strlen(password));
-  SHA1Update(&sha1, ":", 1);
-  SHA1Update(&sha1, uri, strlen(uri));
-  SHA1Update(&sha1, ":", 1);
-  SHA1Update(&sha1, realm, strlen(realm));
-  SHA1Final (tmpnonce, &sha1);  
+  MD5Update(&md5, timestamp, 4);
+  MD5Update(&md5, ":", 1);
+  MD5Update(&md5, method, strlen(method));
+  MD5Update(&md5, ":", 1);
+  MD5Update(&md5, rnd, strlen(rnd));
+  MD5Update(&md5, ":", 1);
+  MD5Update(&md5, uri, strlen(uri));
+  MD5Update(&md5, ":", 1);
+  MD5Update(&md5, realm, strlen(realm));
+  MD5Final (tmpnonce, &md5);  
   cvthex(tmpnonce, sizeof (tmpnonce), nonce);  
   cvthex(timestamp, 4, timestamphex);
   strncat(nonce, timestamphex, 8);
@@ -311,17 +285,19 @@
   int auth;
   size_t len;
   const char *header;
-  const char *ret;
-  const char *nonce;
-  const char *cnonce;
-  const char *uri;
-  const char *qop;
-  const char *nc;
-  const char *response;
+  const char *rnd;
+  char ret[60];
+  char nonce[50];
+  char cnonce[50];
+  char uri[100];
+/*char qop[15]; // Uncomment when supporting "auth-int" */  
+  char qop[] = "auth"; /* "auth-int" is not supported */
+  char nc[10];
+  char response[35];
   char *hentity = NULL; /* "auth-int" is not supported */
   char ha1[HASH_MD5_HEX_LEN + 1];
   char respexp[HASH_MD5_HEX_LEN + 1];
-  char noncehashexp[HASH_SHA1_HEX_LEN + 9];
+  char noncehashexp[HASH_MD5_HEX_LEN + 9];
   uint32_t nonce_time;
   uint32_t t;
 
@@ -332,28 +308,24 @@
   if (header == NULL) 
     return MHD_NO;
   if (strncmp(header, _BASE, strlen(_BASE)) != 0) 
-    return MHD_NO;  
-  len = strlen(header) - strlen(_BASE) + 1;  
-  {
-    char buffer[len];
+    return MHD_NO;
 
-    memcpy (buffer, 
-           header + strlen(_BASE), 
-           len);
-    ret = lookup_sub_value(buffer, len, "username");  
-    if ( (ret == NULL) ||
+  rnd = connection->daemon->digest_auth_random;
+
+       len = lookup_sub_value(ret, 60, header, "username");
+    if ( (!len) ||
         (strcmp(username, ret) != 0) ) 
       return MHD_NO;
-    ret = lookup_sub_value(buffer, len, "realm");  
-    if ( (ret == NULL) || 
+    len = lookup_sub_value(ret, 60, header, "realm");  
+    if ( (!len) || 
         (strcmp(realm, ret) != 0) )
       return MHD_NO;
-    if ( (NULL == (uri = lookup_sub_value(buffer, len, "uri"))) ||
-        (NULL == (nonce = lookup_sub_value(buffer, len, "nonce"))) )
+    if ( (0 == lookup_sub_value(uri, 100, header, "uri")) ||
+        (0 == (len = lookup_sub_value(nonce, 50, header, "nonce"))) )
       return MHD_NO;
   
     /* 8 = 4 hexadecimal numbers for the timestamp */  
-    nonce_time = strtoul(nonce + strlen(nonce) - 8, 0, 16);  
+    nonce_time = strtoul(nonce + len - 8, 0, 16);  
     t = (uint32_t) time(NULL);    
     /*
      * First level vetting for the nonce validity
@@ -365,7 +337,7 @@
       return MHD_INVALID_NONCE;    
     calculate_nonce (nonce_time,
                     connection->method,
-                    password,
+                    rnd,
                     uri,
                     realm,
                     noncehashexp);
@@ -381,19 +353,20 @@
     
     if (0 != strcmp(nonce, noncehashexp))
       return MHD_INVALID_NONCE;
-    if ( (NULL == (cnonce = lookup_sub_value(buffer, len, "cnonce"))) ||
-        (NULL == (qop = lookup_sub_value(buffer, len, "qop"))) ||
-        (NULL == (nc = lookup_sub_value(buffer, len, "nc")))  ||
-        (NULL == (response = lookup_sub_value(buffer, len, "response"))) )
+    if ( (0 == lookup_sub_value(cnonce, 50, header, "cnonce")) ||
+/*      (0 == lookup_sub_value(qop, 15, header, "qop")) || // Uncomment when 
supporting "auth-int" */
+        (0 == lookup_sub_value(nc, 10, header, "nc"))  ||
+        (0 == lookup_sub_value(response, 35, header, "response")) )
       return MHD_NO;
-    digest_calc_ha1("md5",
+
+       digest_calc_ha1("md5",
                    username,
                    realm,
                    password,
                    nonce,
                    cnonce,
                    ha1);
-    auth = digest_calc_response(ha1,
+    digest_calc_response(ha1,
                                nonce,
                                nc,
                                cnonce,
@@ -402,10 +375,9 @@
                                uri,
                                hentity,
                                respexp);  
-    if (0 != auth) 
-      return MHD_NO;
-    auth = strcmp(response, respexp) == 0 ? MHD_YES : MHD_NO;
-  }
+
+       auth = strcmp(response, respexp) == 0 ? MHD_YES : MHD_NO;
+
   return auth;
 }
 
@@ -415,7 +387,7 @@
  *
  * @param connection The MHD connection structure
  * @param realm the realm presented to the client
- * @param password the password used in authentication FIXME!
+ * @param opaque string to user for opaque value
  * @param signal_stale MHD_YES if the nonce is invalid to add
  *                     'stale=true' to the authentication header
  * @return MHD_YES on success, MHD_NO otherwise
@@ -423,23 +395,25 @@
 int
 MHD_queue_auth_fail_response(struct MHD_Connection *connection,
                             const char *realm,
-                            const char *password,
                             const char *opaque,
                             int signal_stale)
 {
   int ret;
   size_t hlen;
-  char nonce[HASH_SHA1_HEX_LEN + 9];
+  const char *rnd;
+  char nonce[HASH_MD5_HEX_LEN + 9];
   struct MHD_Response *response;
 
   response = MHD_create_response_from_data(0, NULL, MHD_NO, MHD_NO);  
   if (NULL == response) 
     return MHD_NO;
+
+  rnd = connection->daemon->digest_auth_random;
   
   /* Generating the server nonce */  
   calculate_nonce ((uint32_t) time(NULL),
                   connection->method,
-                  password,
+                  rnd,
                   connection->url,
                   realm,
                   nonce);

Modified: libmicrohttpd/src/daemon/internal.h
===================================================================
--- libmicrohttpd/src/daemon/internal.h 2010-09-01 13:36:01 UTC (rev 12798)
+++ libmicrohttpd/src/daemon/internal.h 2010-09-01 13:43:14 UTC (rev 12799)
@@ -865,7 +865,14 @@
 
 #endif
 
+#ifdef DAUTH_SUPPORT
   /**
+   * Character array of random values.
+   */
+  const char *digest_auth_random;
+
+#endif
+  /**
    * Pointer to master daemon (NULL if this is the master)
    */
   struct MHD_Daemon *master;

Modified: libmicrohttpd/src/examples/digest_auth_example.c
===================================================================
--- libmicrohttpd/src/examples/digest_auth_example.c    2010-09-01 13:36:01 UTC 
(rev 12798)
+++ libmicrohttpd/src/examples/digest_auth_example.c    2010-09-01 13:43:14 UTC 
(rev 12799)
@@ -48,7 +48,6 @@
 
   if (username == NULL) {
          ret = MHD_queue_auth_fail_response(connection, realm,
-                                            password, 
                                             OPAQUE,
                                             MHD_NO);
 
@@ -62,7 +61,6 @@
 
   if (ret == MHD_INVALID_NONCE) {
          ret = MHD_queue_auth_fail_response(connection, realm,
-                                            password,
                                             OPAQUE, MHD_YES);
 
          return ret;
@@ -70,7 +68,7 @@
 
   if (ret == MHD_NO) {
          ret = MHD_queue_auth_fail_response(connection, realm,
-                                            password, OPAQUE, MHD_NO);
+                                            OPAQUE, MHD_NO);
          
          return ret;
   }
@@ -87,6 +85,9 @@
 int
 main (int argc, char *const *argv)
 {
+  int fd;
+  char rnd[9];
+  size_t len;
   struct MHD_Daemon *d;
 
   if (argc != 2)
@@ -94,9 +95,18 @@
       printf ("%s PORT\n", argv[0]);
       return 1;
     }
+
+  fd = open("/dev/urandom", O_RDONLY);
+  len = read(fd, rnd, 8);
+  close(fd);
+
+  rnd[8] = '\0';
+
   d = MHD_start_daemon (MHD_USE_THREAD_PER_CONNECTION | MHD_USE_DEBUG,
                         atoi (argv[1]),
-                        NULL, NULL, &ahc_echo, PAGE, MHD_OPTION_END);
+                        NULL, NULL, &ahc_echo, PAGE,
+                                               MHD_OPTION_DIGEST_AUTH_RANDOM, 
rnd,
+                                               MHD_OPTION_END);
   if (d == NULL)
     return 1;
   (void) getc (stdin);

Modified: libmicrohttpd/src/include/microhttpd.h
===================================================================
--- libmicrohttpd/src/include/microhttpd.h      2010-09-01 13:36:01 UTC (rev 
12798)
+++ libmicrohttpd/src/include/microhttpd.h      2010-09-01 13:43:14 UTC (rev 
12799)
@@ -520,7 +520,15 @@
    * "cls" will be set to the second argument following
    * MHD_OPTION_UNESCAPE_CALLBACK.
    */
-  MHD_OPTION_UNESCAPE_CALLBACK = 16
+  MHD_OPTION_UNESCAPE_CALLBACK = 16,
+
+  /**
+   * Memory pointer for the random values to be used by the Digest
+   * Auth module. This option should be followed by an "const char *"
+   * argument.
+   */
+  MHD_OPTION_DIGEST_AUTH_RANDOM = 17
+
 };
 
 
@@ -1307,7 +1315,6 @@
  *
  * @param connection The MHD connection structure
  * @param realm The realm presented to the client
- * @param password the password used in authentication FIXME!
  * @param opaque string to user for opaque value
  * @param signal_stale MHD_YES if the nonce is invalid to add
  *                     'stale=true' to the authentication header
@@ -1316,7 +1323,6 @@
 int
 MHD_queue_auth_fail_response(struct MHD_Connection *connection,
                             const char *realm,
-                            const char *password,
                             const char *opaque,
                             int signal_stale);
 




reply via email to

[Prev in Thread] Current Thread [Next in Thread]