graygnuorg / pound

Light-weight reverse proxy, load balancer and HTTPS front-end for Web servers.
GNU General Public License v3.0
43 stars 13 forks source link

Different behaviour (or bug) in URL parsing between Pound 2.8 and 4.12 #34

Closed johndoe7000 closed 1 month ago

johndoe7000 commented 1 month ago

Hello, I'm also hitting this problem.

With Pound 2.8 (compiled with libpcre3-dev) "curl -I https://test.example.com/test" results into...

HTTP/1.1 301 Moved Permanently Date: Mon, 19 Aug 2024 16:25:57 GMT Server: Apache Location: https://test.example.com/test/ Content-Type: text/html; charset=iso-8859-1

Pound 2.8 config: ListenHTTPS Address x.x.x.x Port 443 xHTTP 2 Cert "xxxxxxxxxxxxxxxx" Disable TLSv1_1 SSLHonorCipherOrder 1 Ciphers "xxxxxxxxxxxxxxxxx"

    Service
        Url "/test"
        HeadRequire "Host:.*test.example.com.*"
            BackEnd
                    Address x.x.x.x
                    Port    80
                    TimeOut 60
            End
            Session
                    Type IP
                    TTL 300
            End
    End

....

With Pound 4.12 (commit d657f059c68f27e06ea741d045e7b656191d6ac9, compiled with libpcre2-dev) "curl -I https://test.example.com/test" results into...

HTTP/1.1 301 Moved Permanently Date: Mon, 19 Aug 2024 16:57:14 GMT Server: Apache Location: http://test.example.com/test/ Content-Type: text/html; charset=iso-8859-1

Pound 4.12 config: ListenHTTPS Address x.x.x.x Port 443 xHTTP 2 Cert "xxxxxxxxxxxxx" Disable TLSv1_1 SSLHonorCipherOrder 1 Ciphers "xxxxxxxxxxxxxx"

    Service
        Url "/test"
        Header "Host:.*test.example.com.*"
            BackEnd
                    Address x.x.x.x
                    Port    80
                    TimeOut 60
            End
            Session
                    Type IP
                    TTL 300
            End
    End

....

As you can see the configs are the same... only Header is used instead of deprecated HeadRequire.

The difference between both systems is: Pound 2.8 is installed on Debian 11 and libpcre3. Pound 4.12 is installed on Debian 12 and libpcre2.

I've 4 backends that behave wrong with Pound 4.12 but work flawlessly with Pound 2.8... 2 with Apache and 2 with IIS. All these backends have NO ListenHTTP Redirection. The only solution to this problem is adding a ListenHTTP Service to simply redirect http to https for these backends.

Originally posted by @johndoe7000 in https://github.com/graygnuorg/pound/issues/8#issuecomment-2297088993

graygnuorg commented 1 month ago

Note this:

HTTP/1.1 301 Moved Permanently Date: Mon, 19 Aug 2024 16:25:57 GMT Server: Apache

That is, the redirect is not generated by pound, it is generated by Apache.

graygnuorg commented 1 month ago

This looks like a duplicate of https://github.com/graygnuorg/pound/issues/8. See the discussion for details. Please pay special attention to https://github.com/graygnuorg/pound/issues/8#issuecomment-1491007422. This must be the reason of the observed behavior. Consequently, there may be two ways to fix it. The first is to fix backend settings so that it properly handles incoming requests. The second one is to tweak pound to include only headers sent by version 2.8 to keep the backend happy.

johndoe7000 commented 1 month ago

I see your point. But why does it work with Pound 2.8? Has Robert Segall build a workaround for these broken backends?

All these backends are proprietary software... don't wanna even talk about the IIS/MS bull*hit backends... I will not touch them;)

If I do the following... "curl -I https://test.example.com/test/" (take notice of the trailing slash!) The answer is even without redirection...

HTTP/1.1 200 OK Date: Mon, 19 Aug 2024 19:55:23 GMT Server: Apache Set-Cookie: xxxx_sessid=01i2ml1av096dndq8jgq8bblps; path=/; HttpOnly Expires: Mon, 19 Aug 2024 19:55:23 GMT Cache-Control: private, no-cache, no-store, must-revalidate, post-check=0, pre-check=0 Pragma: no-cache Last-Modified: Mon, 19 Aug 2024 19:55:23 GMT X-Frame-Options: sameorigin Content-Language: en Vary: Accept-Encoding Content-Type: text/html; charset=UTF-8

The dilemma is.. nobody enters an URL in a browser and finishes the string with a trailing slash! This leads me to guess, that Robert has somehow build a workaround for such buggy backends,

In the meantime I've discovered that "chrome" based Browsers do circumvent the problem as they always "force" https connections. This means that if you get a http answer (or simply enter URL without https) they try to (re)connect with https... ergo you don't see a problem.... very bad!!! But when you use Firefox ESR and have enabled "Don’t enable HTTPS-Only Mode" under "Privacy & Security" you get the usual Pound "Service Unavailable" Error.

johndoe7000 commented 1 month ago

I've already tried all possibilities in https://github.com/graygnuorg/pound/issues/8#issuecomment-1491007422 without success.

graygnuorg commented 1 month ago

You said you have four backends. Are the corresponding Service sections similar to the one you've shown? Do you use RewriteLocation in your config file?

graygnuorg commented 1 month ago

Never mind. I've pushed this: https://github.com/graygnuorg/pound/commit/f91b175163e2867953c2baf0a9ffd385030d6674. Please pull, that should fix it.

johndoe7000 commented 1 month ago

You said you have four backends. Are the corresponding Service sections similar to the one you've shown? Do you use RewriteLocation in your config file?

Yes, all backends are similar to my example above. No, I don't use RewriteLocation in my config, but all four backends use "Rewrite rules" by themselves.

johndoe7000 commented 1 month ago

Your patch https://github.com/graygnuorg/pound/commit/f91b175163e2867953c2baf0a9ffd385030d6674 works like a charm. You made my day... thanks again.

graygnuorg commented 1 month ago

Great. I'm closing the issue.