You are viewing a plain text version of this content. The canonical link for it is here.
Posted to dev@httpd.apache.org by Troy Morrison <sp...@zoom.com> on 1996/06/01 20:11:24 UTC
Apache Proxy CONNECT support diff
diff -5 -u apache_1.1b2/src/http_core.c apache_1.1b2-new/src/http_core.c
--- apache_1.1b2/src/http_core.c Thu Apr 11 00:00:19 1996
+++ apache_1.1b2-new/src/http_core.c Sun May 19 19:23:11 1996
@@ -476,10 +476,11 @@
char *method = getword_conf (cmd->pool, &limited_methods);
if(!strcasecmp(method,"GET")) limited |= (1 << M_GET);
else if(!strcasecmp(method,"PUT")) limited |= (1 << M_PUT);
else if(!strcasecmp(method,"POST")) limited |= (1 << M_POST);
else if(!strcasecmp(method,"DELETE")) limited |= (1 << M_DELETE);
+ else if(!strcasecmp(method,"CONNECT")) limited |= (1 << M_CONNECT);
else return "unknown method in <Limit>";
}
cmd->limited = limited;
return NULL;
@@ -860,10 +861,11 @@
(core_dir_config *)get_module_config(r->per_dir_config, &core_module);
int errstatus;
FILE *f;
if (r->method_number != M_GET) return DECLINED;
+
if (r->finfo.st_mode == 0 || (r->path_info && *r->path_info)) {
log_reason("File does not exist", r->filename, r);
return NOT_FOUND;
}
diff -5 -u apache_1.1b2/src/http_protocol.c apache_1.1b2-new/src/http_protocol.c
--- apache_1.1b2/src/http_protocol.c Tue Apr 16 06:00:10 1996
+++ apache_1.1b2-new/src/http_protocol.c Sun May 19 19:26:40 1996
@@ -437,10 +437,12 @@
r->method_number = M_POST;
else if(!strcmp(r->method,"PUT"))
r->method_number = M_PUT;
else if(!strcmp(r->method,"DELETE"))
r->method_number = M_DELETE;
+ else if(!strcmp(r->method,"CONNECT"))
+ r->method_number = M_CONNECT;
else
r->method_number = M_INVALID; /* Will eventually croak. */
return r;
}
diff -5 -u apache_1.1b2/src/httpd.h apache_1.1b2-new/src/httpd.h
--- apache_1.1b2/src/httpd.h Tue Apr 23 20:08:13 1996
+++ apache_1.1b2-new/src/httpd.h Sun May 19 12:20:58 1996
@@ -237,16 +237,17 @@
#define NOT_IMPLEMENTED 501
#define BAD_GATEWAY 502
#define SERVICE_UNAVAILABLE 503
#define RESPONSE_CODES 10
-#define METHODS 5
+#define METHODS 6
#define M_GET 0
#define M_PUT 1
#define M_POST 2
#define M_DELETE 3
-#define M_INVALID 4
+#define M_CONNECT 4
+#define M_INVALID 5
#define CGI_MAGIC_TYPE "application/x-httpd-cgi"
#define INCLUDES_MAGIC_TYPE "text/x-server-parsed-html"
#define INCLUDES_MAGIC_TYPE3 "text/x-server-parsed-html3"
#define MAP_FILE_MAGIC_TYPE "application/x-type-map"
diff -5 -u apache_1.1b2/src/mod_mime.c apache_1.1b2-new/src/mod_mime.c
--- apache_1.1b2/src/mod_mime.c Sat Apr 13 00:00:17 1996
+++ apache_1.1b2-new/src/mod_mime.c Thu May 16 14:52:22 1996
@@ -226,10 +226,18 @@
if (S_ISDIR(r->finfo.st_mode)) {
r->content_type = DIR_MAGIC_TYPE;
return OK;
}
+ /* TM -- FIXME
+ *
+ * if r->filename does not contain a '/', the following passes a null
+ * pointer to getword, causing a SEGV ..
+ */
+
+ if(fn == NULL) fn = r->filename;
+
/* Parse filename extensions, which can be in any order */
while ((ext = getword(r->pool, &fn, '.')) && *ext) {
int found = 0;
/* Check for Content-Type */
diff -5 -u apache_1.1b2/src/mod_proxy.c apache_1.1b2-new/src/mod_proxy.c
--- apache_1.1b2/src/mod_proxy.c Thu Apr 11 12:00:11 1996
+++ apache_1.1b2-new/src/mod_proxy.c Mon May 20 12:02:43 1996
@@ -70,11 +70,12 @@
two passes). Consider doing them the first time round.
Ben Laurie <be...@algroup.co.uk> 30 Mar 96
*/
-#define TESTING 1
+#define TESTING 0
+#undef EXPLAIN
#include "httpd.h"
#include "http_config.h"
#include "http_log.h"
#include "http_main.h"
@@ -197,11 +198,11 @@
static int ftp_canon(request_rec *r, char *url);
static int http_handler(request_rec *r, struct cache_req *c, char *url,
const char *proxyhost, int proxyport);
static int ftp_handler(request_rec *r, struct cache_req *c, char *url);
-
+static int connect_handler(request_rec *r, struct cache_req *c, char *url);
static BUFF *cache_error(struct cache_req *r);
/* -------------------------------------------------------------- */
/* Translate the URL into a 'filename' */
@@ -2126,13 +2127,20 @@
/* otherwise, try it direct */
/* N.B. what if we're behind a firewall, where we must use a proxy or
* give up??
*/
+
/* handle the scheme */
if (strcmp(scheme, "http") == 0) return http_handler(r, cr, url, NULL, 0);
if (strcmp(scheme, "ftp") == 0) return ftp_handler(r, cr, url);
+
+ /* This handles Netscape's Secure CONNECT method... it is a bit of a kludge
+ * But works, sort of :-)
+ */
+
+ if (r->method_number == M_CONNECT) return connect_handler(r, cr, url);
else return NOT_IMPLEMENTED;
}
static int
@@ -2565,10 +2573,128 @@
pclosef(pool, sock);
return OK;
}
+/*
+ * This handles Netscape-SSL style "CONNECT" proxy requests.
+ * A connection is opened to the specified host and data is
+ * passed through between the WWW site and the browser.
+ * This code is based on the IETF document at
+ * http://www.netscape.com/docs/std/tunnelling_ssl.html.
+ *
+ * FIXME: this is bad, because it does its own socket I/O
+ * instead of using the I/O in buff.c. However,
+ * the I/O in buff.c blocks on reads, and because
+ * this function doesn't know how much data will
+ * be sent either way (or when) it can't use blocking
+ * I/O. This may be very implementation-specific
+ * (to Linux). Any suggestions?
+ * FIXME: this doesn't log the number of bytes sent, but
+ * that may be okay, since the data is supposed to
+ * be transparent.
+ * FIXME: doesn't check any headers initally sent from the
+ * client.
+ * FIXME: according to netscape docs, should only connect
+ * to well-known SSL ports (https, snews, etc.)
+ * FIXME: should allow authentication, but hopefully the
+ * generic proxy authentication is good enough.
+ * FIXME: no check for r->assbackwards, whatever that is.
+ */
+
+static int
+connect_handler(request_rec *r, struct cache_req *c, char *url)
+{
+ struct sockaddr_in server;
+ const char *host, *err;
+ char *p;
+ int port, sock;
+ char buffer[HUGE_STRING_LEN];
+ int nbytes, i;
+ fd_set fds;
+
+ memset(&server, '\0', sizeof(server));
+ server.sin_family=AF_INET;
+
+ /* Break the URL into host:port pairs */
+
+ host = url;
+ p = strchr(url, ':');
+ if (p==NULL) port = DEFAULT_HTTPS_PORT;
+ else
+ {
+ port = atoi(p+1);
+ *p='\0';
+ }
+
+ Explain2("CONNECT to %s on port %d", host, port);
+
+ server.sin_port = htons(port);
+ err = host2addr(host, &server.sin_addr);
+ if (err != NULL) return proxyerror(r, err); /* give up */
+
+ sock = socket(PF_INET, SOCK_STREAM, IPPROTO_TCP);
+ if (sock == -1)
+ {
+ log_error("proxy: error creating socket", r->server);
+ return SERVER_ERROR;
+ }
+ note_cleanups_for_fd(r->pool, sock);
+
+ i = doconnect(sock, &server, r);
+ if (i == -1 )
+ return proxyerror(r, "Could not connect to remote machine");
+
+ Explain0("Returning 200 OK Status");
+
+ rvputs(r, "HTTP/1.0 200 Connection established\015\012", NULL);
+ rvputs(r, "Proxy-agent: ", SERVER_VERSION, "\015\012\015\012", NULL);
+ bflush(r->connection->client);
+
+ while (1) /* Infinite loop until error (one side closes the connection) */
+ {
+ FD_ZERO(&fds);
+ FD_SET(sock, &fds);
+ FD_SET(r->connection->client->fd, &fds);
+
+ Explain0("Going to sleep (select)");
+ i = select((r->connection->client->fd > sock ? r->connection->client->fd+1 : sock+1), &fds, NULL, NULL, NULL);
+ Explain1("Woke from select(), i=%d",i);
+
+ if (i)
+ {
+ if (FD_ISSET(sock, &fds))
+ {
+ Explain0("sock was set");
+ if((nbytes=read(sock,buffer,HUGE_STRING_LEN))!=0)
+ {
+ if(nbytes==-1) break;
+ if(write(r->connection->client->fd, buffer, nbytes)==EOF)break;
+ Explain1("Wrote %d bytes to client", nbytes);
+ }
+ else break;
+ }
+ else if (FD_ISSET(r->connection->client->fd, &fds))
+ {
+ Explain0("client->fd was set");
+ if((nbytes=read(r->connection->client->fd,buffer,HUGE_STRING_LEN))!=0)
+ {
+ if(nbytes==-1) break;
+ if(write(sock,buffer,nbytes)==EOF) break;
+ Explain1("Wrote %d bytes to server", nbytes);
+ }
+ else break;
+ }
+ else break; /* Must be done waiting */
+ }
+ else break;
+ }
+
+ pclosef(r->pool,sock);
+
+ return OK;
+}
/*
* This handles http:// URLs, and other URLs using a remote proxy over http
* If proxyhost is NULL, then contact the server directly, otherwise
* go via the proxy.
--
Ben Laurie Phone: +44 (181) 994 6435
Freelance Consultant and Fax: +44 (181) 994 6472
Technical Director Email: ben@algroup.co.uk
A.L. Digital Ltd, URL: http://www.algroup.co.uk
London, England.