Package: apache2-common Version: 2.0.54-2 Severity: normal Tags: patch Currently it is not possible to successfully issue an HTTP CONNECT request to apache2 with mod_ssl; mod_proxy_connect talks directly to the client socket and bypasses mod_ssl.
Further discussion of this bug is at: http://issues.apache.org/bugzilla/show_bug.cgi?id=29744 I have included a patch by Brad Boyer (see above discussion) which fixes this problem for me. -- System Information: Debian Release: 3.1 APT prefers testing APT policy: (990, 'testing'), (500, 'unstable'), (1, 'experimental') Architecture: i386 (i586) Kernel: Linux 2.6.11.7-grsec Locale: LANG=en_US, LC_CTYPE=en_US (charmap=ISO-8859-1) Versions of packages apache2-common depends on: ii apache2-utils 2.0.54-2 utility programs for webservers ii debconf 1.4.30.13 Debian configuration management sy ii debianutils 2.8.4 Miscellaneous utilities specific t ii libc6 2.3.2.ds1-21 GNU C Library: Shared libraries an ii libdb4.2 4.2.52-18 Berkeley v4.2 Database Libraries [ ii libexpat1 1.95.8-3 XML parsing C library - runtime li ii libgcc1 1:3.4.3-12 GCC support library ii libmagic1 4.12-1 File type determination library us ii mime-support 3.28-1 MIME files 'mime.types' & 'mailcap ii net-tools 1.60-10 The NET-3 networking toolkit ii openssl 0.9.7e-3 Secure Socket Layer (SSL) binary a ii ssl-cert 1.0-11 Simple debconf wrapper for openssl -- no debconf information
--- build-tree.orig/apache2/modules/proxy/proxy_connect.c 2004-02-09 12:53:19.000000000 -0800 +++ build-tree/apache2/modules/proxy/proxy_connect.c 2004-10-20 16:09:26.000000000 -0700 @@ -83,10 +83,14 @@ { apr_pool_t *p = r->pool; apr_socket_t *sock; + conn_rec *c = r->connection; + conn_rec *backconn; + apr_bucket_brigade *bb = apr_brigade_create(p, c->bucket_alloc); + apr_status_t err, rv; apr_size_t i, o, nbytes; char buffer[HUGE_STRING_LEN]; - apr_socket_t *client_socket = ap_get_module_config(r->connection->conn_config, &core_module); + apr_socket_t *client_socket = ap_get_module_config(c->conn_config, &core_module); int failed; apr_pollfd_t *pollfd; apr_int32_t pollcnt; @@ -211,7 +215,23 @@ * We add the NULL filter to the stack to do this... */ r->output_filters = NULL; - r->connection->output_filters = NULL; + + backconn = ap_run_create_connection(c->pool, r->server, sock, + c->id, c->sbh, c->bucket_alloc); + if(!backconn) { + /* peer reset */ + ap_log_error(APLOG_MARK, APLOG_DEBUG, 0, r->server, + "proxy: an error occurred creating a new connection " + "to %pI (%s)", connect_addr, connectname); + apr_socket_close(sock); + return HTTP_INTERNAL_SERVER_ERROR; + } + ap_proxy_ssl_disable(backconn); + ap_run_pre_connection(backconn, sock); + + ap_log_error(APLOG_MARK, APLOG_DEBUG, 0, r->server, + "proxy: connection complete to %pI (%s)", + connect_addr, connectname); /* If we are connecting through a remote proxy, we need to pass @@ -222,12 +242,12 @@ */ ap_log_error(APLOG_MARK, APLOG_DEBUG, 0, r->server, "proxy: CONNECT: sending the CONNECT request to the remote proxy"); - nbytes = apr_snprintf(buffer, sizeof(buffer), + + ap_fprintf(backconn->output_filters, bb, "CONNECT %s HTTP/1.0" CRLF, r->uri); - apr_send(sock, buffer, &nbytes); - nbytes = apr_snprintf(buffer, sizeof(buffer), - "Proxy-agent: %s" CRLF CRLF, ap_get_server_version()); - apr_send(sock, buffer, &nbytes); + ap_fprintf(backconn->output_filters, bb, + "Proxy-agent: %s" CRLF CRLF, ap_get_server_version()); + ap_fflush(backconn->output_filters, bb); } else { ap_log_error(APLOG_MARK, APLOG_DEBUG, 0, r->server, @@ -235,11 +255,12 @@ nbytes = apr_snprintf(buffer, sizeof(buffer), "HTTP/1.0 200 Connection Established" CRLF); ap_xlate_proto_to_ascii(buffer, nbytes); - apr_send(client_socket, buffer, &nbytes); + ap_fwrite(c->output_filters, bb, buffer, nbytes); nbytes = apr_snprintf(buffer, sizeof(buffer), "Proxy-agent: %s" CRLF CRLF, ap_get_server_version()); ap_xlate_proto_to_ascii(buffer, nbytes); - apr_send(client_socket, buffer, &nbytes); + ap_fwrite(c->output_filters, bb, buffer, nbytes); + ap_fflush(c->output_filters, bb); #if 0 /* This is safer code, but it doesn't work yet. I'm leaving it * here so that I can fix it later. @@ -293,23 +314,13 @@ /* ap_log_error(APLOG_MARK, APLOG_DEBUG, 0, r->server, "proxy: CONNECT: sock was set");*/ nbytes = sizeof(buffer); - if (apr_recv(sock, buffer, &nbytes) == APR_SUCCESS) { - o = 0; - i = nbytes; - while(i > 0) - { - nbytes = i; - /* This is just plain wrong. No module should ever write directly - * to the client. For now, this works, but this is high on my list of - * things to fix. The correct line is: - * if ((nbytes = ap_rwrite(buffer + o, nbytes, r)) < 0) - * rbb - */ - if (apr_send(client_socket, buffer + o, &nbytes) != APR_SUCCESS) - break; - o += nbytes; - i -= nbytes; - } + apr_brigade_cleanup(bb); + if (ap_get_brigade(backconn->input_filters, bb, + AP_MODE_READBYTES, APR_NONBLOCK_READ, + nbytes) == APR_SUCCESS) { + if (ap_pass_brigade(c->output_filters, bb) != APR_SUCCESS) + break; + ap_fflush(c->output_filters, bb); } else break; @@ -323,17 +334,13 @@ /* ap_log_error(APLOG_MARK, APLOG_DEBUG, 0, r->server, "proxy: CONNECT: client was set");*/ nbytes = sizeof(buffer); - if (apr_recv(client_socket, buffer, &nbytes) == APR_SUCCESS) { - o = 0; - i = nbytes; - while(i > 0) - { - nbytes = i; - if (apr_send(sock, buffer + o, &nbytes) != APR_SUCCESS) - break; - o += nbytes; - i -= nbytes; - } + apr_brigade_cleanup(bb); + if (ap_get_brigade(c->input_filters, bb, AP_MODE_READBYTES, + APR_NONBLOCK_READ, nbytes) == APR_SUCCESS) { + if (ap_pass_brigade(backconn->output_filters, bb) + != APR_SUCCESS) + break; + ap_fflush(backconn->output_filters, bb); } else break;