]> git.ipfire.org Git - thirdparty/squid.git/commitdiff
Here is my patch to squid-1.1.alpha4 that adds the functionality to
authorwessels <>
Tue, 16 Jul 1996 05:57:49 +0000 (05:57 +0000)
committerwessels <>
Tue, 16 Jul 1996 05:57:49 +0000 (05:57 +0000)
use basic authentication for user&passwd information on non-anonymous
ftp.

If it receives a non-anonymus ftp request without a password, then
Squid responds with 401 Unauthorized with
WWW-Authenticate: Basic realm="ftp <user>"

Notes:
1. This is normal authentication, not proxy authentication. The
   authentication is for the end server and not the proxy (i.e
   it is a translation of the ftp login procedure to HTTP).
2. The realm is always local to the server (string), and therefore
   only the user information is nessecary to make it unique. I added
   "ftp " minimize the risk of collision with a identical realm
   for another protocol (i.e. HTTP) on the same server.
3. This implementation is not fully complete. It needs some further
   work on expiration of generated 401 messages, but this doesn't
   really matter (they are expired immediately anyway).
   Maybe they should be negatively cached, but most browsers cache
   this internally anyway (to avoid unnessesary 401 messages).

/Henrik

src/errorpage.cc
src/ftp.cc

index a06cba7c692f109d9b9fe6cd0dd705105be11543..49b36dc1d3de0ab6c2ce89f2040d3f0191efbcbf 100644 (file)
@@ -1,5 +1,5 @@
 /*
- * $Id: errorpage.cc,v 1.23 1996/07/15 23:12:36 wessels Exp $
+ * $Id: errorpage.cc,v 1.24 1996/07/15 23:57:49 wessels Exp $
  *
  * DEBUG: section 4     Error Generation
  * AUTHOR: Duane Wessels
@@ -127,6 +127,8 @@ void errorInitialize()
     meta_data.misc += MAX_URL * 4;
     tbuf = xmalloc(MAX_URL * 3);
     meta_data.misc += MAX_URL * 3;
+    auth_msg = xmalloc(MAX_URL * 3);
+    meta_data.misc += MAX_URL * 3;
 }
 
 void squid_error_entry(entry, type, msg)
@@ -256,3 +258,38 @@ Generated by %s/%s@%s\n\
        getMyHostname());
     return tmp_error_buf;
 }
+
+char *authorization_needed_msg(request, realm)
+     request_t *request;
+     char *realm;
+{
+    sprintf(auth_msg, "<TITLE>Authorization needed</TITLE>\n\
+Sorry, you have to authorize yourself to request\n\
+<PRE>    ftp://%s@%s%s</PRE>\n\
+from this cache.  Please check with the cache administrator if you\n\
+believe this is incorrect.\n\
+<HR>\n\
+<ADDRESS>\n\
+Generated by %s/%s@%s\n\
+</ADDRESS>\n\
+\n",
+       request->login,
+       request->host,
+       request->urlpath,
+       appname,
+       version_string,
+       getMyHostname());
+
+    mk_mime_hdr(tbuf,
+       (time_t) getNegativeTTL(),
+       strlen(auth_msg),
+       0,
+       "text/html");
+    sprintf(tmp_error_buf, "HTTP/1.0 401 Unauthorized\r\n\
+%s\
+WWW-Authenticate: Basic realm=\"%s\"\r\n\
+\r\n\
+%s",
+       tbuf, realm, auth_msg);
+    return tmp_error_buf;
+}
index fe6739cec93a75e7d864d7b803ae34f4fa2f1498..1afa78343e8e58d2766f6faaedcc4228e28841cd 100644 (file)
@@ -1,5 +1,5 @@
 /*
- * $Id: ftp.cc,v 1.41 1996/07/15 23:13:31 wessels Exp $
+ * $Id: ftp.cc,v 1.42 1996/07/15 23:57:51 wessels Exp $
  *
  * DEBUG: section 9     File Transfer Protocol (FTP)
  * AUTHOR: Harvest Derived
@@ -127,6 +127,7 @@ typedef struct _Ftpdata {
                                 * expires */
     int got_marker;            /* denotes end of successful request */
     int reply_hdr_state;
+    int authenticated;         /* This ftp request is authenticated */
 } FtpData;
 
 /* Local functions */
@@ -143,6 +144,9 @@ void ftpSendRequest _PARAMS((int fd, FtpData * data));
 void ftpConnInProgress _PARAMS((int fd, FtpData * data));
 void ftpServerClose _PARAMS((void));
 
+/* External functions */
+extern char *base64_decode _PARAMS((char *coded));
+
 static int ftpStateFree(fd, ftpState)
      int fd;
      FtpData *ftpState;
@@ -526,6 +530,9 @@ void ftpSendRequest(fd, data)
        sprintf(tbuf, "-H %s ", s);
        strcat(buf, tbuf);
     }
+    if (data->authenticated) {
+       strcat(buf, "-a ");
+    }
     strcat(buf, "-h ");                /* httpify */
     strcat(buf, "- ");         /* stdout */
     strcat(buf, data->request->host);
@@ -585,7 +592,13 @@ int ftpStart(unusedfd, url, request, entry)
      request_t *request;
      StoreEntry *entry;
 {
+    static char realm[8192];
     FtpData *data = NULL;
+    char *req_hdr = entry->mem_obj->mime_hdr;
+    char *auth_hdr;
+    char *response;
+    char *auth;
+
     int status;
 
     debug(9, 3, "FtpStart: FD %d <URL:%s>\n", unusedfd, url);
@@ -594,8 +607,35 @@ int ftpStart(unusedfd, url, request, entry)
     storeLockObject(data->entry = entry, NULL, NULL);
     data->request = requestLink(request);
 
+    auth_hdr = mime_get_header(req_hdr, "Authorization");
+    auth = NULL;
+    if (auth_hdr) {
+       if (strcasecmp(strtok(auth_hdr, " \t"), "Basic") == 0) {
+           auth = base64_decode(strtok(NULL, " \t"));
+       }
+    }
     /* Parse login info. */
-    ftp_login_parser(request->login, data);
+    if (auth) {
+       ftp_login_parser(auth, data);
+       data->authenticated = 1;
+    } else {
+       ftp_login_parser(request->login, data);
+       if (*data->user && !*data->password) {
+           /* This request is not fully authenticated */
+           if (request->port == 21) {
+               sprintf(realm, "ftp %s", data->user);
+           } else {
+               sprintf(realm, "ftp %s port %d",
+                   data->user, request->port);
+           }
+           response = authorization_needed_msg(request, realm);
+           storeAppend(entry, response, strlen(response));
+           httpParseHeaders(response, entry->mem_obj->reply);
+           storeComplete(entry);
+           ftpStateFree(-1, data);
+           return COMM_OK;
+       }
+    }
 
     debug(9, 5, "FtpStart: FD %d, host=%s, path=%s, user=%s, passwd=%s\n",
        unusedfd, data->request->host, data->request->urlpath,