<feed xmlns='http://www.w3.org/2005/Atom'>
<title>nginx.git/src/http/ngx_http_upstream.c, branch release-1.29.5</title>
<subtitle>nginx</subtitle>
<link rel='alternate' type='text/html' href='https://git.sigsegv.uk/nginx.git/'/>
<entry>
<title>Upstream: reinit upstream after reading bad response.</title>
<updated>2026-02-04T15:09:20+00:00</updated>
<author>
<name>Roman Arutyunyan</name>
<email>arut@nginx.com</email>
</author>
<published>2026-01-28T16:38:38+00:00</published>
<link rel='alternate' type='text/html' href='https://git.sigsegv.uk/nginx.git/commit/?id=d7a249470b78a155c7548aea5f4eb959dae9fd03'/>
<id>d7a249470b78a155c7548aea5f4eb959dae9fd03</id>
<content type='text'>
Previously, when connecting to a backend, if the read event handler was
called before the write event handler, and the received response triggered
a next upstream condition, then ngx_http_upstream_reinit() was not called
to clean up the old upstream context.  This had multiple implications.

For all proxy modules, since the last upstream response was not cleaned up,
it was mixed with the next upstream response.  This could result in ignoring
the second response status code, duplicate response headers or reporting
old upstream header errors.

With ngx_http_grpc_module and ngx_http_proxy_v2_module, ctx-&gt;connection
was left dangling since the object it referenced was allocated from the
last upstream connection pool, which was deleted when freeing last upstream.
This lead to use-after-free when trying to reuse this object for the next
upstream.
</content>
<content type='xhtml'>
<div xmlns='http://www.w3.org/1999/xhtml'>
<pre>
Previously, when connecting to a backend, if the read event handler was
called before the write event handler, and the received response triggered
a next upstream condition, then ngx_http_upstream_reinit() was not called
to clean up the old upstream context.  This had multiple implications.

For all proxy modules, since the last upstream response was not cleaned up,
it was mixed with the next upstream response.  This could result in ignoring
the second response status code, duplicate response headers or reporting
old upstream header errors.

With ngx_http_grpc_module and ngx_http_proxy_v2_module, ctx-&gt;connection
was left dangling since the object it referenced was allocated from the
last upstream connection pool, which was deleted when freeing last upstream.
This lead to use-after-free when trying to reuse this object for the next
upstream.
</pre>
</div>
</content>
</entry>
<entry>
<title>Upstream: detect premature plain text response from SSL backend.</title>
<updated>2026-02-04T15:09:20+00:00</updated>
<author>
<name>Roman Arutyunyan</name>
<email>arut@nginx.com</email>
</author>
<published>2026-01-29T09:27:32+00:00</published>
<link rel='alternate' type='text/html' href='https://git.sigsegv.uk/nginx.git/commit/?id=a59f5f099a89dc8eaebd48077292313f9f7e33e3'/>
<id>a59f5f099a89dc8eaebd48077292313f9f7e33e3</id>
<content type='text'>
When connecting to a backend, the connection write event is triggered
first in most cases.  However if a response arrives quickly enough, both
read and write events can be triggered together within the same event loop
iteration.  In this case the read event handler is called first and the
write event handler is called after it.

SSL initialization for backend connections happens only in the write event
handler since SSL handshake starts with sending Client Hello.  Previously,
if a backend sent a quick plain text response, it could be parsed by the
read event handler prior to starting SSL handshake on the connection.
The change adds protection against parsing such responses on SSL-enabled
connections.
</content>
<content type='xhtml'>
<div xmlns='http://www.w3.org/1999/xhtml'>
<pre>
When connecting to a backend, the connection write event is triggered
first in most cases.  However if a response arrives quickly enough, both
read and write events can be triggered together within the same event loop
iteration.  In this case the read event handler is called first and the
write event handler is called after it.

SSL initialization for backend connections happens only in the write event
handler since SSL handshake starts with sending Client Hello.  Previously,
if a backend sent a quick plain text response, it could be parsed by the
read event handler prior to starting SSL handshake on the connection.
The change adds protection against parsing such responses on SSL-enabled
connections.
</pre>
</div>
</content>
</entry>
<entry>
<title>Upstream: add support for connection level ALPN protocol negotiation.</title>
<updated>2025-12-08T03:49:16+00:00</updated>
<author>
<name>Zhidao HONG</name>
<email>z.hong@f5.com</email>
</author>
<published>2025-07-15T14:54:21+00:00</published>
<link rel='alternate' type='text/html' href='https://git.sigsegv.uk/nginx.git/commit/?id=b8492d9c25c34c87419d2ad118fa812fd72da27c'/>
<id>b8492d9c25c34c87419d2ad118fa812fd72da27c</id>
<content type='text'>
This commit is prepared for HTTP/2 and HTTP/3 support.

The ALPN protocol is now set per-connection in
ngx_http_upstream_ssl_init_connection(), allowing proper protocol negotiation
for each individual upstream connection regardless of SSL context sharing.
</content>
<content type='xhtml'>
<div xmlns='http://www.w3.org/1999/xhtml'>
<pre>
This commit is prepared for HTTP/2 and HTTP/3 support.

The ALPN protocol is now set per-connection in
ngx_http_upstream_ssl_init_connection(), allowing proper protocol negotiation
for each individual upstream connection regardless of SSL context sharing.
</pre>
</div>
</content>
</entry>
<entry>
<title>Upstream: reset local address in case of error.</title>
<updated>2025-10-24T13:49:04+00:00</updated>
<author>
<name>Roman Arutyunyan</name>
<email>arut@nginx.com</email>
</author>
<published>2025-10-23T14:21:57+00:00</published>
<link rel='alternate' type='text/html' href='https://git.sigsegv.uk/nginx.git/commit/?id=364a94ecec13037126f28f91cf8f290979ffc229'/>
<id>364a94ecec13037126f28f91cf8f290979ffc229</id>
<content type='text'>
After f10bc5a763bb the address was set to NULL only when local address was
not specified at all.  In case complex value evaluated to an empty or
invalid string, local address remained unchanged.  Currenrly this is not
a problem since the value is only set once.  This change is a preparation
for being able to change the local address after initial setting.
</content>
<content type='xhtml'>
<div xmlns='http://www.w3.org/1999/xhtml'>
<pre>
After f10bc5a763bb the address was set to NULL only when local address was
not specified at all.  In case complex value evaluated to an empty or
invalid string, local address remained unchanged.  Currenrly this is not
a problem since the value is only set once.  This change is a preparation
for being able to change the local address after initial setting.
</pre>
</div>
</content>
</entry>
<entry>
<title>Upstream: overflow detection in Cache-Control delta-seconds.</title>
<updated>2025-09-26T12:50:13+00:00</updated>
<author>
<name>Sergey Kandaurov</name>
<email>pluknet@nginx.com</email>
</author>
<published>2025-09-10T14:39:52+00:00</published>
<link rel='alternate' type='text/html' href='https://git.sigsegv.uk/nginx.git/commit/?id=8255bd29ac9a7bcdc317a8889420554e00d435cb'/>
<id>8255bd29ac9a7bcdc317a8889420554e00d435cb</id>
<content type='text'>
Overflowing calculations are now aligned to the greatest positive integer
as specified in RFC 9111, Section 1.2.2.
</content>
<content type='xhtml'>
<div xmlns='http://www.w3.org/1999/xhtml'>
<pre>
Overflowing calculations are now aligned to the greatest positive integer
as specified in RFC 9111, Section 1.2.2.
</pre>
</div>
</content>
</entry>
<entry>
<title>Upstream: fixed reinit request with gRPC and Early Hints.</title>
<updated>2025-06-23T16:12:21+00:00</updated>
<author>
<name>Sergey Kandaurov</name>
<email>pluknet@nginx.com</email>
</author>
<published>2025-06-23T10:55:32+00:00</published>
<link rel='alternate' type='text/html' href='https://git.sigsegv.uk/nginx.git/commit/?id=cdf7a9c6cb7f344efc80d790fbacdc1c94ab16e3'/>
<id>cdf7a9c6cb7f344efc80d790fbacdc1c94ab16e3</id>
<content type='text'>
The gRPC module context has connection specific state, which can be lost
after request reinitialization when it comes to processing early hints.

The fix is to do only a portion of u-&gt;reinit_request() implementation
required after processing early hints, now inlined in modules.

Now NGX_HTTP_UPSTREAM_EARLY_HINTS is returned from u-&gt;process_header()
for early hints.  When reading a cached response, this code is mapped
to NGX_HTTP_UPSTREAM_INVALID_HEADER to indicate invalid header format.
</content>
<content type='xhtml'>
<div xmlns='http://www.w3.org/1999/xhtml'>
<pre>
The gRPC module context has connection specific state, which can be lost
after request reinitialization when it comes to processing early hints.

The fix is to do only a portion of u-&gt;reinit_request() implementation
required after processing early hints, now inlined in modules.

Now NGX_HTTP_UPSTREAM_EARLY_HINTS is returned from u-&gt;process_header()
for early hints.  When reading a cached response, this code is mapped
to NGX_HTTP_UPSTREAM_INVALID_HEADER to indicate invalid header format.
</pre>
</div>
</content>
</entry>
<entry>
<title>Upstream: early hints support.</title>
<updated>2025-06-19T06:19:57+00:00</updated>
<author>
<name>Roman Arutyunyan</name>
<email>arut@nginx.com</email>
</author>
<published>2024-11-15T04:23:53+00:00</published>
<link rel='alternate' type='text/html' href='https://git.sigsegv.uk/nginx.git/commit/?id=662c1dd2a97afd6c7ca09b8f5a74347ee017b86b'/>
<id>662c1dd2a97afd6c7ca09b8f5a74347ee017b86b</id>
<content type='text'>
The change implements processing upstream early hints response in
ngx_http_proxy_module and ngx_http_grpc_module.  A new directive
"early_hints" enables sending early hints to the client.  By default,
sending early hints is disabled.

Example:

    map $http_sec_fetch_mode $early_hints {
        navigate $http2$http3;
    }

    early_hints $early_hints;

    proxy_pass http://example.com;
</content>
<content type='xhtml'>
<div xmlns='http://www.w3.org/1999/xhtml'>
<pre>
The change implements processing upstream early hints response in
ngx_http_proxy_module and ngx_http_grpc_module.  A new directive
"early_hints" enables sending early hints to the client.  By default,
sending early hints is disabled.

Example:

    map $http_sec_fetch_mode $early_hints {
        navigate $http2$http3;
    }

    early_hints $early_hints;

    proxy_pass http://example.com;
</pre>
</div>
</content>
</entry>
<entry>
<title>Upstream: fixed passwords support for dynamic certificates.</title>
<updated>2025-04-10T13:27:45+00:00</updated>
<author>
<name>Sergey Kandaurov</name>
<email>pluknet@nginx.com</email>
</author>
<published>2025-02-05T15:16:05+00:00</published>
<link rel='alternate' type='text/html' href='https://git.sigsegv.uk/nginx.git/commit/?id=6c3a9d561271ec451f479a84fbe54c81a63dad2e'/>
<id>6c3a9d561271ec451f479a84fbe54c81a63dad2e</id>
<content type='text'>
Passwords were not preserved in optimized SSL contexts, the bug had
appeared in d791b4aab (1.23.1), as in the following configuration:

    server {
        proxy_ssl_password_file password;
        proxy_ssl_certificate $ssl_server_name.crt;
        proxy_ssl_certificate_key $ssl_server_name.key;

        location /original/ {
            proxy_pass https://u1/;
        }

        location /optimized/ {
            proxy_pass https://u2/;
        }
    }

The fix is to always preserve passwords, by copying to the configuration
pool, if dynamic certificates are used.  This is done as part of merging
"ssl_passwords" configuration.

To minimize the number of copies, a preserved version is then used for
inheritance.  A notable exception is inheritance of preserved empty
passwords to the context with statically configured certificates:

    server {
        proxy_ssl_certificate $ssl_server_name.crt;
        proxy_ssl_certificate_key $ssl_server_name.key;

        location / {
            proxy_pass ...;

            proxy_ssl_certificate example.com.crt;
            proxy_ssl_certificate_key example.com.key;
        }
    }

In this case, an unmodified version (NULL) of empty passwords is set,
to allow reading them from the password prompt on nginx startup.

As an additional optimization, a preserved instance of inherited
configured passwords is set to the previous level, to inherit it
to other contexts:

    server {
        proxy_ssl_password_file password;

        location /1/ {
            proxy_pass https://u1/;
            proxy_ssl_certificate $ssl_server_name.crt;
            proxy_ssl_certificate_key $ssl_server_name.key;
        }

        location /2/ {
            proxy_pass https://u2/;
            proxy_ssl_certificate $ssl_server_name.crt;
            proxy_ssl_certificate_key $ssl_server_name.key;
        }
    }
</content>
<content type='xhtml'>
<div xmlns='http://www.w3.org/1999/xhtml'>
<pre>
Passwords were not preserved in optimized SSL contexts, the bug had
appeared in d791b4aab (1.23.1), as in the following configuration:

    server {
        proxy_ssl_password_file password;
        proxy_ssl_certificate $ssl_server_name.crt;
        proxy_ssl_certificate_key $ssl_server_name.key;

        location /original/ {
            proxy_pass https://u1/;
        }

        location /optimized/ {
            proxy_pass https://u2/;
        }
    }

The fix is to always preserve passwords, by copying to the configuration
pool, if dynamic certificates are used.  This is done as part of merging
"ssl_passwords" configuration.

To minimize the number of copies, a preserved version is then used for
inheritance.  A notable exception is inheritance of preserved empty
passwords to the context with statically configured certificates:

    server {
        proxy_ssl_certificate $ssl_server_name.crt;
        proxy_ssl_certificate_key $ssl_server_name.key;

        location / {
            proxy_pass ...;

            proxy_ssl_certificate example.com.crt;
            proxy_ssl_certificate_key example.com.key;
        }
    }

In this case, an unmodified version (NULL) of empty passwords is set,
to allow reading them from the password prompt on nginx startup.

As an additional optimization, a preserved instance of inherited
configured passwords is set to the previous level, to inherit it
to other contexts:

    server {
        proxy_ssl_password_file password;

        location /1/ {
            proxy_pass https://u1/;
            proxy_ssl_certificate $ssl_server_name.crt;
            proxy_ssl_certificate_key $ssl_server_name.key;
        }

        location /2/ {
            proxy_pass https://u2/;
            proxy_ssl_certificate $ssl_server_name.crt;
            proxy_ssl_certificate_key $ssl_server_name.key;
        }
    }
</pre>
</div>
</content>
</entry>
<entry>
<title>Upstream: caching certificates and certificate keys with variables.</title>
<updated>2025-01-17T00:37:46+00:00</updated>
<author>
<name>Sergey Kandaurov</name>
<email>pluknet@nginx.com</email>
</author>
<published>2024-10-29T14:20:53+00:00</published>
<link rel='alternate' type='text/html' href='https://git.sigsegv.uk/nginx.git/commit/?id=454ad0ef33a347eba1a62d18c8fc0498f4dcfd64'/>
<id>454ad0ef33a347eba1a62d18c8fc0498f4dcfd64</id>
<content type='text'>
Caching is enabled with proxy_ssl_certificate_cache and friends.

Co-authored-by: Aleksei Bavshin &lt;a.bavshin@nginx.com&gt;
</content>
<content type='xhtml'>
<div xmlns='http://www.w3.org/1999/xhtml'>
<pre>
Caching is enabled with proxy_ssl_certificate_cache and friends.

Co-authored-by: Aleksei Bavshin &lt;a.bavshin@nginx.com&gt;
</pre>
</div>
</content>
</entry>
<entry>
<title>SSL: caching certificates and certificate keys with variables.</title>
<updated>2025-01-17T00:37:46+00:00</updated>
<author>
<name>Sergey Kandaurov</name>
<email>pluknet@nginx.com</email>
</author>
<published>2024-10-29T12:25:11+00:00</published>
<link rel='alternate' type='text/html' href='https://git.sigsegv.uk/nginx.git/commit/?id=0e756d67aa1e42e3b1b360936eb4d6c06bced2c1'/>
<id>0e756d67aa1e42e3b1b360936eb4d6c06bced2c1</id>
<content type='text'>
A new directive "ssl_certificate_cache max=N [valid=time] [inactive=time]"
enables caching of SSL certificate chain and secret key objects specified
by "ssl_certificate" and "ssl_certificate_key" directives with variables.

Co-authored-by: Aleksei Bavshin &lt;a.bavshin@nginx.com&gt;
</content>
<content type='xhtml'>
<div xmlns='http://www.w3.org/1999/xhtml'>
<pre>
A new directive "ssl_certificate_cache max=N [valid=time] [inactive=time]"
enables caching of SSL certificate chain and secret key objects specified
by "ssl_certificate" and "ssl_certificate_key" directives with variables.

Co-authored-by: Aleksei Bavshin &lt;a.bavshin@nginx.com&gt;
</pre>
</div>
</content>
</entry>
</feed>
