]> git.ipfire.org Git - thirdparty/squid.git/commitdiff
develop urlParse() and request_t structure to avoid sscanf'ing the URL
authorwessels <>
Tue, 16 Apr 1996 10:23:12 +0000 (10:23 +0000)
committerwessels <>
Tue, 16 Apr 1996 10:23:12 +0000 (10:23 +0000)
too frequently.

src/http.cc
src/main.cc
src/neighbors.cc
src/url.cc
src/wais.cc

index 216bf8ae20038e65374cd9e75798a60f470bac53..ad69daafbf21fcef2496bd1a8cf589b57c270937 100644 (file)
@@ -1,4 +1,4 @@
-/* $Id: http.cc,v 1.47 1996/04/15 23:02:26 wessels Exp $ */
+/* $Id: http.cc,v 1.48 1996/04/16 04:23:12 wessels Exp $ */
 
 /*
  * DEBUG: Section 11          http: HTTP
 
 typedef struct _httpdata {
     StoreEntry *entry;
-    char host[SQUIDHOSTNAMELEN + 1];
-    int port;
-    int method;
+    request_t *REQ;
     char *req_hdr;
-    char request[MAX_URL + 1];
     char *icp_page_ptr;                /* Used to send proxy-http request: 
                                 * put_free_8k_page(me) if the lifetime
                                 * expires */
@@ -24,6 +21,7 @@ typedef struct _httpdata {
                                 * icpReadWriteData */
     char *reply_hdr;
     int reply_hdr_state;
+    int free_request;
 } HttpData;
 
 static void httpCloseAndFree(fd, data)
@@ -43,44 +41,15 @@ static void httpCloseAndFree(fd, data)
        }
        if (data->icp_rwd_ptr)
            safe_free(data->icp_rwd_ptr);
+       if (data->free_request)
+           safe_free(data->REQ);
        xfree(data);
     }
 }
 
-static int http_url_parser(url, host, port, request)
-     char *url;
-     char *host;
-     int *port;
-     char *request;
-{
-    static char hostbuf[MAX_URL];
-    static char proto[MAX_URL];
-    int t;
-    char *s = NULL;
-
-    /* initialize everything */
-    (*port) = urlDefaultPort(PROTO_HTTP);
-    proto[0] = hostbuf[0] = request[0] = host[0] = '\0';
-
-    t = sscanf(url, "%[a-zA-Z]://%[^/]%s", proto, hostbuf, request);
-    if (t < 2)
-       return -1;
-    if (strcasecmp(proto, "http") != 0) {
-       return -1;
-    } else if (t == 2)
-       strcpy(request, "/");
-    if ((s = strchr(hostbuf, ':')) && *(s + 1)) {
-       *s = '\0';
-       *port = atoi(s + 1);
-    }
-    strncpy(host, hostbuf, SQUIDHOSTNAMELEN);
-    return 0;
-}
-
-int httpCachable(url, method, req_hdr)
+int httpCachable(url, method)
      char *url;
      int method;
-     char *req_hdr;
 {
     wordlist *p = NULL;
 
@@ -421,15 +390,16 @@ static void httpSendRequest(fd, data)
     int len = 0;
     int buflen;
     int cfd = -1;
-    char *Method = RequestMethodStr[data->method];
+    request_t *req = data->REQ;
+    char *Method = RequestMethodStr[req->method];
 
     debug(11, 5, "httpSendRequest: FD %d: data %p.\n", fd, data);
-    buflen = strlen(Method) + strlen(data->request);
+    buflen = strlen(Method) + strlen(req->urlpath);
     if (data->req_hdr)
        buflen += strlen(data->req_hdr);
     buflen += 512;             /* lots of extra */
 
-    if (data->method == METHOD_POST && data->req_hdr) {
+    if (req->method == METHOD_POST && data->req_hdr) {
        if ((t = strstr(data->req_hdr, "\r\n\r\n"))) {
            post_buf = xstrdup(t + 4);
            *(t + 4) = '\0';
@@ -444,7 +414,7 @@ static void httpSendRequest(fd, data)
     }
     memset(buf, '\0', buflen);
 
-    sprintf(buf, "%s %s HTTP/1.0\r\n", Method, data->request);
+    sprintf(buf, "%s %s HTTP/1.0\r\n", Method, req->urlpath);
     len = strlen(buf);
     if (data->req_hdr) {       /* we have to parse the request header */
        xbuf = xstrdup(data->req_hdr);
@@ -504,10 +474,11 @@ static void httpConnInProgress(fd, data)
      HttpData *data;
 {
     StoreEntry *entry = data->entry;
+    request_t *req = data->REQ;
 
     debug(11, 5, "httpConnInProgress: FD %d data=%p\n", fd, data);
 
-    if (comm_connect(fd, data->host, data->port) != COMM_OK) {
+    if (comm_connect(fd, req->host, req->port) != COMM_OK) {
        debug(11, 5, "httpConnInProgress: FD %d errno=%d\n", fd, errno);
        switch (errno) {
        case EINPROGRESS:
@@ -539,19 +510,23 @@ int proxyhttpStart(e, url, entry)
     int sock;
     int status;
     HttpData *data = NULL;
+    request_t *request = NULL;
 
-    debug(11, 3, "proxyhttpStart: <URL:%s>\n", url);
+    debug(11, 3, "proxyhttpStart: \"%s %s\"\n",
+       RequestMethodStr[request->method], url);
     debug(11, 10, "proxyhttpStart: HTTP request header:\n%s\n",
        entry->mem_obj->mime_hdr);
 
     data = (HttpData *) xcalloc(1, sizeof(HttpData));
     data->entry = entry;
-
-    strncpy(data->request, url, sizeof(data->request) - 1);
-    data->method = entry->method;
-    data->port = e->ascii_port;
     data->req_hdr = entry->mem_obj->mime_hdr;
-    strncpy(data->host, e->host, sizeof(data->host) - 1);
+    request = (request_t *) xcalloc (1, sizeof(request_t));
+    data->free_request = 1;
+    data->REQ = request;
+
+    strncpy(request->host, e->host, SQUIDHOSTNAMELEN);
+    request->port = e->ascii_port;
+    strncpy(request->urlpath, url, MAX_URL);
 
     if (e->proxy_only)
        storeStartDeleteBehind(entry);
@@ -567,14 +542,14 @@ int proxyhttpStart(e, url, entry)
     /* check if IP is already in cache. It must be. 
      * It should be done before this route is called. 
      * Otherwise, we cannot check return code for connect. */
-    if (!ipcache_gethostbyname(data->host)) {
+    if (!ipcache_gethostbyname(request->host)) {
        debug(11, 4, "proxyhttpstart: Called without IP entry in ipcache. OR lookup failed.\n");
        cached_error_entry(entry, ERR_DNS_FAIL, dns_error_message);
        httpCloseAndFree(sock, data);
        return COMM_ERROR;
     }
     /* Open connection. */
-    if ((status = comm_connect(sock, data->host, data->port))) {
+    if ((status = comm_connect(sock, request->host, request->port))) {
        if (status != EINPROGRESS) {
            cached_error_entry(entry, ERR_CONNECT_FAIL, xstrerror());
            httpCloseAndFree(sock, data);
@@ -597,13 +572,12 @@ int proxyhttpStart(e, url, entry)
     comm_set_select_handler(sock, COMM_SELECT_WRITE,
        (PF) httpSendRequest, (void *) data);
     return COMM_OK;
-
 }
 
-int httpStart(unusedfd, url, method, req_hdr, entry)
+int httpStart(unusedfd, url, request, req_hdr, entry)
      int unusedfd;
      char *url;
-     int method;
+     request_t *request;
      char *req_hdr;
      StoreEntry *entry;
 {
@@ -611,20 +585,15 @@ int httpStart(unusedfd, url, method, req_hdr, entry)
     int sock, status;
     HttpData *data = NULL;
 
-    debug(11, 3, "httpStart: %s <URL:%s>\n", RequestMethodStr[method], url);
+    debug(11, 3, "httpStart: \"%s %s\"\n",
+       RequestMethodStr[request->method], url);
     debug(11, 10, "httpStart: req_hdr '%s'\n", req_hdr);
 
     data = (HttpData *) xcalloc(1, sizeof(HttpData));
     data->entry = entry;
-    data->method = method;
     data->req_hdr = req_hdr;
+    data->REQ = request;
 
-    /* Parse url. */
-    if (http_url_parser(url, data->host, &data->port, data->request)) {
-       cached_error_entry(entry, ERR_INVALID_URL, NULL);
-       safe_free(data);
-       return COMM_ERROR;
-    }
     /* Create socket. */
     sock = comm_open(COMM_NONBLOCKING, 0, 0, url);
     if (sock == COMM_ERROR) {
@@ -636,14 +605,14 @@ int httpStart(unusedfd, url, method, req_hdr, entry)
     /* check if IP is already in cache. It must be. 
      * It should be done before this route is called. 
      * Otherwise, we cannot check return code for connect. */
-    if (!ipcache_gethostbyname(data->host)) {
+    if (!ipcache_gethostbyname(request->host)) {
        debug(11, 4, "httpstart: Called without IP entry in ipcache. OR lookup failed.\n");
        cached_error_entry(entry, ERR_DNS_FAIL, dns_error_message);
        httpCloseAndFree(sock, data);
        return COMM_ERROR;
     }
     /* Open connection. */
-    if ((status = comm_connect(sock, data->host, data->port))) {
+    if ((status = comm_connect(sock, request->host, request->port))) {
        if (status != EINPROGRESS) {
            cached_error_entry(entry, ERR_CONNECT_FAIL, xstrerror());
            httpCloseAndFree(sock, data);
index 16875009781f92d4d8cbed1e31cafa3238555e40..6af0e1644ba2f62a9e2bb6c53b68e71ea41d7224 100644 (file)
@@ -1,4 +1,4 @@
-/* $Id: main.cc,v 1.33 1996/04/15 22:53:35 wessels Exp $ */
+/* $Id: main.cc,v 1.34 1996/04/16 04:23:14 wessels Exp $ */
 
 /* DEBUG: Section 1             main: startup and main loop */
 
@@ -220,6 +220,7 @@ static void mainInitialize()
     if (first_time) {
        first_time = 0;
        /* module initialization */
+       urlInitialize();
        disk_init();
        stat_init(&CacheInfo, getAccessLogFile());
        storeInit();
index 8ad856ecb9c555f85c9540bbd190044dcae42ffb..55782c5c7122de47f58287e833009f8a6a7741b7 100644 (file)
@@ -1,4 +1,4 @@
-/* $Id: neighbors.cc,v 1.19 1996/04/15 22:53:46 wessels Exp $ */
+/* $Id: neighbors.cc,v 1.20 1996/04/16 04:23:15 wessels Exp $ */
 
 /* TODO:
  * - change 'neighbor' to 'sibling'
@@ -341,7 +341,7 @@ int neighborsUdpPing(proto)
      protodispatch_data *proto;
 {
     char *t = NULL;
-    char *host = proto->host;
+    char *host = proto->request->host;
     char *url = proto->url;
     StoreEntry *entry = proto->entry;
     struct hostent *hep = NULL;
@@ -532,7 +532,7 @@ void neighborsUdpAck(fd, url, header, from, entry)
                inet_ntoa(from->sin_addr));
            BIT_SET(entry->flag, ENTRY_DISPATCHED);
            entry->ping_status = DONE;
-           getFromOrgSource(0, entry);
+           getFromCache(0, entry, NULL, entry->mem_obj->request);
        }
        return;
     }
@@ -552,7 +552,7 @@ void neighborsUdpAck(fd, url, header, from, entry)
        }
        BIT_SET(entry->flag, ENTRY_DISPATCHED);
        entry->ping_status = DONE;
-       getFromCache(0, entry, e);
+       getFromCache(0, entry, e, entry->mem_obj->request);
        e->hits++;
        return;
     } else if ((header->opcode == ICP_OP_MISS) || (header->opcode == ICP_OP_DECHO)) {
@@ -600,7 +600,7 @@ void neighborsUdpAck(fd, url, header, from, entry)
            debug(15, 6, "Receive MISSes from all neighbors and parents\n");
            /* pass in fd=0 here so getFromCache() looks up the real FD
             * and resets the timeout handler */
-           getFromDefaultSource(0, entry);
+           getFromCache(0, entry, NULL, entry->mem_obj->request);
            return;
        }
     } else {
index 1e95be1c494430b05d621740889336e98d4aeec7..bf9c2e492f6b066b6619ded22b34794994dd663e 100644 (file)
@@ -1,4 +1,4 @@
-/* $Id: url.cc,v 1.16 1996/04/16 01:51:20 wessels Exp $ */
+/* $Id: url.cc,v 1.17 1996/04/16 04:23:17 wessels Exp $ */
 
 /* 
  * DEBUG: Section 23          url
@@ -29,7 +29,6 @@ char *ProtocolStr[] =
 };
 
 static int url_acceptable[256];
-static int url_acceptable_init = 0;
 static char hex[17] = "0123456789abcdef";
 
 /* convert %xx in url string to a character 
@@ -67,7 +66,7 @@ char *url_convert_hex(org_url, allocate)
 
 /* INIT Acceptable table. 
  * Borrow from libwww2 with Mosaic2.4 Distribution   */
-static void init_url_acceptable()
+void urlInitialize()
 {
     unsigned int i;
     char *good =
@@ -76,7 +75,6 @@ static void init_url_acceptable()
        url_acceptable[i] = 0;
     for (; *good; good++)
        url_acceptable[(unsigned int) *good] = 1;
-    url_acceptable_init = 1;
 }
 
 
@@ -88,9 +86,6 @@ char *url_escape(url)
     char *p, *q;
     char *tmpline = xcalloc(1, MAX_URL);
 
-    if (!url_acceptable_init)
-       init_url_acceptable();
-
     q = tmpline;
     for (p = url; *p; p++) {
        if (url_acceptable[(int) (*p)])
@@ -128,6 +123,10 @@ protocol_t urlParseProtocol(s)
        return PROTO_HTTP;
     if (strncasecmp(s, "ftp", 3) == 0)
        return PROTO_FTP;
+#ifndef NO_FTP_FOR_FILE
+    if (strncasecmp(s, "file", 4) == 0)
+       return PROTO_FTP;
+#endif
     if (strncasecmp(s, "gopher", 6) == 0)
        return PROTO_GOPHER;
     if (strncasecmp(s, "cache_object", 12) == 0)
@@ -156,9 +155,80 @@ int urlDefaultPort(p)
        return CACHE_HTTP_PORT;
 #ifdef NEED_PROTO_CONNECT
     case PROTO_CONNECT:
-       return 443;
+       return CONNECT_PORT;
 #endif
     default:
        return 0;
     }
 }
+
+request_t *urlParse(method, url)
+       method_t method;
+       char *url;
+{
+    static char proto[MAX_URL+1];
+    static char host[MAX_URL+1];
+    static char urlpath[MAX_URL+1];
+    request_t *request = NULL;
+    char *t = NULL;
+    int port;
+    protocol_t protocol = PROTO_NONE;
+    proto[0] = host[0] = urlpath[0] = '\0';
+
+    if (method == METHOD_CONNECT) {
+       port = CONNECT_PORT;
+       if (sscanf(url, "%[^:]:%d", host, &port) < 1)
+           return NULL;
+        if (!aclMatchInteger(connect_port_list, port))
+           return NULL;
+    } else {
+       if (sscanf(url, "%[^:]://%[^/]%s", proto, host, urlpath) < 2)
+           return NULL;
+       protocol = urlParseProtocol(proto);
+       port = urlDefaultPort(protocol);
+       if ((t = strchr(host, ':')) && *(t+1) != '\0') {
+           *t = '\0';
+           port = atoi(t + 1);
+       }
+    }
+    for (t = host; *t; t++)
+        *t = tolower(*t);
+    if (port == 0) {
+       debug(23,0,"urlParse: Invalid port == 0\n");
+       return NULL;
+    }
+
+    request = (request_t *) xcalloc (1, sizeof(request_t));
+    request->method = method;
+    request->protocol = protocol;
+    strncpy(request->host, host, SQUIDHOSTNAMELEN);
+    request->port = port;
+    strncpy(request->urlpath, urlpath, MAX_URL);
+    return request;
+}
+
+char *urlCanonical (request, buf)
+    request_t *request;
+    char *buf;
+{
+    static char urlbuf[MAX_URL+1];
+    static char portbuf[32];
+    if (buf == NULL)
+       buf = urlbuf;
+    switch (request->method) {
+    case METHOD_CONNECT:
+        sprintf(buf, "%s:%d", request->host, request->port);
+       break;
+    default:
+       portbuf[0] = '\0';
+       if (request->port != urlDefaultPort(request->protocol))
+               sprintf(portbuf, ":%d", request->port);
+        sprintf(buf, "%s://%s%s%s",
+               ProtocolStr[request->protocol],
+               request->host,
+               portbuf,
+               request->urlpath);
+       break;
+    }
+    return buf;
+}
index 8d74b56c50d332d3bbb160ae81e3a4294b5d1ff4..023027bc95313d54e7c38c8ca0281b8ad6e6d8c9 100644 (file)
@@ -1,4 +1,4 @@
-/* $Id: wais.cc,v 1.24 1996/04/12 21:41:44 wessels Exp $ */
+/* $Id: wais.cc,v 1.25 1996/04/16 04:23:18 wessels Exp $ */
 
 /*
  * DEBUG: Section 24          wais
@@ -10,9 +10,9 @@
 
 typedef struct _waisdata {
     StoreEntry *entry;
-    char host[SQUIDHOSTNAMELEN + 1];
-    int port;
-    int method;
+    method_t method;
+    char *relayhost;
+    int relayport;
     char *mime_hdr;
     char request[MAX_URL];
 } WAISData;
@@ -26,20 +26,6 @@ static void waisCloseAndFree(fd, data)
     xfree(data);
 }
 
-
-static int wais_url_parser(url, host, port, request)
-     char *url;
-     char *host;
-     int *port;
-     char *request;
-{
-    strcpy(host, getWaisRelayHost());
-    *port = getWaisRelayPort();
-    strcpy(request, url);
-
-    return 0;
-}
-
 /* This will be called when timeout on read. */
 static void waisReadReplyTimeout(fd, data)
      int fd;
@@ -239,7 +225,7 @@ void waisSendRequest(fd, data)
 int waisStart(unusedfd, url, method, mime_hdr, entry)
      int unusedfd;
      char *url;
-     int method;
+     method_t method;
      char *mime_hdr;
      StoreEntry *entry;
 {
@@ -247,11 +233,16 @@ int waisStart(unusedfd, url, method, mime_hdr, entry)
     int sock, status;
     WAISData *data = NULL;
 
-    debug(24, 3, "waisStart - url:%s, type:%s\n", url, RequestMethodStr[method]);
+    debug(24, 3, "waisStart: \"%s %s\"\n",
+       RequestMethodStr[method], url);
     debug(24, 4, "            header: %s\n", mime_hdr);
 
     data = (WAISData *) xcalloc(1, sizeof(WAISData));
     data->entry = entry;
+    data->method = method;
+    data->relayhost = getWaisRelayHost();
+    data->relayport = getWaisRelayPort();
+    data->mime_hdr = mime_hdr;
 
     if (!getWaisRelayHost()) {
        debug(24, 0, "waisStart: Failed because no relay host defined!\n");
@@ -259,10 +250,6 @@ int waisStart(unusedfd, url, method, mime_hdr, entry)
        safe_free(data);
        return COMM_ERROR;
     }
-    /* Parse url. */
-    (void) wais_url_parser(url, data->host, &data->port, data->request);
-    data->method = method;
-    data->mime_hdr = mime_hdr;
 
     /* Create socket. */
     sock = comm_open(COMM_NONBLOCKING, 0, 0, url);
@@ -275,20 +262,20 @@ int waisStart(unusedfd, url, method, mime_hdr, entry)
     /* check if IP is already in cache. It must be. 
      * It should be done before this route is called. 
      * Otherwise, we cannot check return code for connect. */
-    if (!ipcache_gethostbyname(data->host)) {
+    if (!ipcache_gethostbyname(data->relayhost)) {
        debug(24, 4, "waisstart: Called without IP entry in ipcache. OR lookup failed.\n");
        cached_error_entry(entry, ERR_DNS_FAIL, dns_error_message);
        waisCloseAndFree(sock, data);
        return COMM_ERROR;
     }
     /* Open connection. */
-    if ((status = comm_connect(sock, data->host, data->port))) {
+    if ((status = comm_connect(sock, data->relayhost, data->relayport))) {
        if (status != EINPROGRESS) {
            cached_error_entry(entry, ERR_CONNECT_FAIL, xstrerror());
            waisCloseAndFree(sock, data);
            return COMM_ERROR;
        } else {
-           debug(24, 5, "waisStart - conn %d EINPROGRESS\n", sock);
+           debug(24, 5, "waisStart: FD %d EINPROGRESS\n", sock);
        }
     }
     /* Install connection complete handler. */