Re: [users@httpd] SNI with apache 2.4.1 reverse proxy
Hello Karspar, Hi all, On Wed, Apr 18, 2012 at 10:16:51AM +0200, Kaspar Brand wrote: So implementation-wise this will most likely have two parts of code: 1. Determining the hostname to put into SNI data depending on ProxyPreserveHost somewhere in the reverse proxy module. 2. Putting that value into the SNI data in mod_ssl's ssl_engine_io.c. I'm not too familiar with the history/motivation of the ProxyPreserveHost directve (which dates to as far as 2002, see r93089), but in the context of proxy SSL requests, I think it isn't a particularly good idea to support this feature... because essentially, it opens up the door to MitM attacks: you're asking mod_proxy_http to, say, request URI https://foo.example.org/index.html, but directing it via TLS to a host configured with certificate bar.example.org. I don't think so: I'm not directing the Proxy to connect to a different host. I just make it send different SNI data to the configured backend server and accept a different CN in the server's certificate. The MitM would still have to hijack the server's IP or DNS entry and present a certificate issued by a trusted CA for that CN, just that it now has to read bar.example.org instead of foo.example.org. I don't see, how the attack gets simpler by that. I am, however, not sure how the change will affect forward proxying (if at all). I have only thought about reverse proxying where I have SSLProxyVerify set to require on the reverse proxy and run both servers with a self-signed CA for just that purpose. All the client-side presentation is done by the reverse proxy with the official certificates. mod_proxy_http's blindness for MitM attacks was also the reason for introducing SSLProxyCheckPeerCN in r760866/r768504, I assume. In addition to dealing with SNI extension / Host header mismatches you would also have to accommodate for the case of CN / Host header mismatches. That's done automatically since the same note is used for CN check and SNI data. By setting that note to the hostname from the Host header, all there items are in sync automatically. I've put together a small patch doing just that (admittedly without much knowing what I'm doing since its my very first time hacking apache). I've opened a bug report for it: https://issues.apache.org/bugzilla/show_bug.cgi?id=53134. Feel free to have a look at it and tell me what you think. Perhaps it also helps to make clear, what I mean. With that patch name based virtual hosts work with SSL through an httpd-2.4/trunk reverse proxy with a single virtual host and no rewrite rules whatsoever on both servers. To solve your immediate problem in 2.4, what you could try is: ProxyPass / https://127.0.0.1:12443/ ProxyPreserveHost On SSLProxyCheckPeerCN off This prevents mod_ssl in 2.4 from adding an SNI extension to the proxy request (it will skip IP addresses), and will pass the Host reader from the original request to the backend. You need to turn off SSLProxyCheckPeerCN at the same time (unless your backend cert has CN=127.0.0.1) - but in the end, this just reflects what you're asking mod_proxy_http to do: connect via TLS to host with cert X and request resource from host Y. I've chosen the second possible workaround: Setting SSLProxyProtocol to SSLv3. If you look at the code in ssl_engine_io.c you'll see that its the second condition for disabling SNI towards the backend server. This way, SSLProxyCheckPeerCN can stay enabled. -- Micha I hate forms!
Re: [users@httpd] SNI with apache 2.4.1 reverse proxy
Hi, On Tue, Apr 10, 2012 at 10:01:11AM +0200, Michael Weiser wrote: A solution might be something like: ProxyPass / https://www.example.com:12443/ no-sni ProxyPassReverse / https://www.example.com:12443/ no-sni , disabling SNI towards the backend server. Or can I tell the 2.2.14 apache inside the VM to ignore the SNI data it sees in the requests? The best solution I can think of would be some switch like ProxyPass / https://www.example.com:12443/ pass-host-as-sni ProxyPassReverse / https://www.example.com:12443/ pass-host-as-sni that makes mod_ssl put the content of the host header into the sni data structures instead of the hostname from the URL used in the ProxyPass(Reverse) configuration itself. This way even name-based virtual hosts should work behind the reverse proxy. I haven't heard anything back: What's the general opinion on this? -- bye, Micha
Re: [users@httpd] SNI with apache 2.4.1 reverse proxy
Hi there, On Mon, Apr 16, 2012 at 01:45:16PM +0200, Peter Sylvester wrote: that makes mod_ssl put the content of the host header into the sni data structures instead of the hostname from the URL used in the ProxyPass(Reverse) configuration itself. This way even name-based virtual hosts should work behind the reverse proxy. I haven't heard anything back: What's the general opinion on this? - If a configuration parameter can be avoided, this divides the possibilities of errors by at least 3. I don't think that a configuration parameter is necessary. I agree (or at least don't care as long as I get the behaviour I need ;). - If something is put into the SNI, it must be identical to what is in the Host:header. This could be a side-effect of ProxyPreserveHost On since only with ProxyPreserveHost On does it make any sense anyways. With ProxyPreserveHost Off, the SNI data should contain the hostname from the ProxyPassReverse directive. So implementation-wise this will most likely have two parts of code: 1. Determining the hostname to put into SNI data depending on ProxyPreserveHost somewhere in the reverse proxy module. 2. Putting that value into the SNI data in mod_ssl's ssl_engine_io.c. ssl_engine_io.c already uses an apr_table_get with a name of proxy-request-hostname which is apr_table_set'd in mod_proxy_http.c. So point 2 seems to be taken care of already. Host header preservation seems to be done done in mod_proxy_http.c as well. Now setting proxy-request-hostname based on that shouldn't be too hard. Shall I have a go at that? -- bye, Michael Elephants don't play chess!
Re: [users@httpd] SNI with apache 2.4.1 reverse proxy
Hi Tom, On Mon, Apr 16, 2012 at 04:02:00PM +0100, Tom Evans wrote: This could be a side-effect of ProxyPreserveHost On since only with ProxyPreserveHost On does it make any sense anyways. With ProxyPreserveHost Off, the SNI data should contain the hostname from the ProxyPassReverse directive. Er, surely you mean ProxyPass directive here. The ProxyPassReverse directive is only used for rewriting response headers, it has nothing to do with altering the proxied request. To be honest, I'm making this all up as I go along. Thanks for pointing me in the right direction. -- Thanks, Micha
Re: [users@httpd] SNI with apache 2.4.1 reverse proxy
Hi Igor, Hi Daniel, On Mon, Apr 09, 2012 at 08:56:12AM -, Igor Gali? wrote: Then it looks like mod_proxy_http determines the value for proxy-request-hostname from the remote URL in ProxyPass, but is passing on the Host header from the original request. That would imply ProxyPreserveHost on -- which is off by default I also don't see it in Micha's paste. Uh, I am very sorry to have wasted your time, but I actually do have ProxyPreserveHost On in my config. It was inbetween some comments and I must have removed it together with them. I have checked and it seems to be the only statement missing from my mail. I have it in there because wordpress has a feature of automatically using the host name from the request in all links in the HTML it generates. Unfortunately, it insists on creating absolute instead of relative links. This is also why I access wordpress inside the VM via HTTPS at all: This way it automatically (or at least with only a very small patch to it's config.php) generates https:// links in its responses when accessed via HTTPS, making the reverse proxy very simple (apart from the SSL bit) and almost transparent. At first I tried to configure the reverse proxy to plain http:// (SSL termination, so to speak) and rewrite all links using mod_proxy_html for performance and because it seemed the straightforward thing to do. But I had various detail problems within wordpress I couldn't solve (with links to uploaded files for example). So I switched to just passing on the original requests as unchanged as possible. As for the SNI bit: So I tell the reverse proxy to access https://www.example.com:12433/ but pass on the Host header unchanged. The wordpress VM's apache 2.2.14 gets upset with this discrepancy and denies to serve the requests. As I perhaps poorly explained in the second part of my mail, I tried to tell the reverse proxy to access https://Host-header:12443/ instead but couldn't make it work. A solution might be something like: ProxyPass / https://www.example.com:12443/ no-sni ProxyPassReverse / https://www.example.com:12443/ no-sni , disabling SNI towards the backend server. Or can I tell the 2.2.14 apache inside the VM to ignore the SNI data it sees in the requests? The best solution I can think of would be some switch like ProxyPass / https://www.example.com:12443/ pass-host-as-sni ProxyPassReverse / https://www.example.com:12443/ pass-host-as-sni that makes mod_ssl put the content of the host header into the sni data structures instead of the hostname from the URL used in the ProxyPass(Reverse) configuration itself. This way even name-based virtual hosts should work behind the reverse proxy. -- Thanks for your patience, Micha
Re: server push CGI problem
On Mon, 12 Aug 2002, Justin Erenkrantz wrote: I've got an update problem regarding apache 1.3.24/2.0.39 and a home-grown server-push webcam CGI. The CGI continuously reads images from the cam, Can you try 2.0.40 as I believe some of the CGI handling was been rewritten since .39? So, this already may have been resolved. -- justin I just did - without any effect. The normal CGI still continues to run after the connection to the browser has been closed with apache reading and discarding its output. The nph- variant doesn't seem to give a mime-type at all so that mozilla tries to download it as application/octet-stream and navigator 4.79 is showing the output literally. If someone could point me at the piece of source to look for that output-discarding I could start hacking about myself. I found something in mod_cgi.c already but that seems to apply to redirects only. The output discard after connection break seems to happen at the end of the filter stack. If it's of any relevance to the problem: The whole thing is running on an SGI Indigo2 with IRIX 6.5.16f and was compiled using MIPSpro cc 7.2.3.1 and linked against various precompiled open source libs from freeware.sgi.com. (without any problems BTW) -- bye, Micha
server push CGI problem
Hi, I've got an update problem regarding apache 1.3.24/2.0.39 and a home-grown server-push webcam CGI. The CGI continuously reads images from the cam, compresses them into JPEGs and puts them together into a multipart/x-mixed-replace stream to produce a poor-man's video with netscape-browsers. With apache-1.3.x the CGI detected that the connection to the browser was closed by getting an error back when writing to standard output because apache automatically closed down the pipe to the CGI as well. Now after upgrading to apache-2.0.39 the cgi never gets the error and therefore never stops delivering pictures to nowhere. My guess is that apache tries to discard all remaining script output by reading until EOF before closing the pipe which in my case results in the script carrying on forever. I've tried to install the script as nph- but that resulted in the browser showing the data literally because it somehow got the MIME type wrong/not at all. Now my questions are: Is my guess regarding the discard of remaining output right? Can it be switched off? How can I get the nph- approach get to work properly? Thanks in advance for your help. -- bye, Micha