In case that AllowEncodedSlashes is set to NoDecode do not double encode
encoded slashes in the URL sent by the reverse proxy to the backend.
* include/ap_mmn.h: Document the addition of ap_proxy_canonenc_ex to the API.
* modules/proxy/mod_proxy.h: Declare ap_proxy_canonenc_ex and define flag
values.
* modules/proxy/proxy_util.c: Implement ap_proxy_canonenc_ex by modifying
ap_proxy_canonenc accordingly and reimplement ap_proxy_canonenc to
use ap_proxy_canonenc_ex with the appropriate flag.
* modules/http2/mod_proxy_http2.c, modules/proxy/mod_proxy_*.c: Set the
correct flag based on the AllowEncodedSlashes configuration and use
ap_proxy_canonenc_ex instead of ap_proxy_canonenc.
git-svn-id: https://svn.apache.org/repos/asf/httpd/httpd/trunk@1908341 13f79535-47bb-0310-9956-ffa450edef68
Decoding was not done for mapping=servlet only (a subset), but overlooked for
mapping=encoded. To avoid double-encoding in the canon_handler hook, use a new
"proxy-noencode" (similarly to "proxy-nocanon") entry in r->notes.
* proxy/mod_proxy.c(ap_proxy_trans_match):
Set "proxy-noencode" in r->notes for PROXYPASS_MAP_ENCODED, and return DONE
to avoid decoding in ap_process_request_internal().
* proxy/mod_proxy_http.c, proxy/mod_proxy_ajp.c, proxy/mod_proxy_wstunnel.c,
proxy/mod_proxy_fcgi.c, proxy/mod_proxy_ajp.c, http2/mod_proxy_http2.c:
Don't process the url through ap_proxy_canonenc() in canon_handler if
"proxy-noencode" is set.
git-svn-id: https://svn.apache.org/repos/asf/httpd/httpd/trunk@1907972 13f79535-47bb-0310-9956-ffa450edef68
Allows to opt-out the fallback to mod_proxy_http to handle WebSocket upgrade,
and let mod_proxy_wstunnel handle the requests as in 2.4.46 and earlier.
Update docs.
git-svn-id: https://svn.apache.org/repos/asf/httpd/httpd/trunk@1889792 13f79535-47bb-0310-9956-ffa450edef68
Let mod_proxy_http's canon and scheme handlers accept "ws[s]:" schemes so that
mod_proxy_wstunnel can decline requests when mod_proxy_http is loaded.
* modules/proxy/{mod_proxy.h,proxy_util.c} (ap_proxy_worker_can_upgrade):
Add a "dflt" argument to ap_proxy_worker_can_upgrade() which, if not NULL,
is matched when no worker upgrade= parameter is configured. This allows to
handle the default "Upgrade: websocket" case for "ws[s]:" schemes.
* modules/proxy/mod_proxy_http.c (proxy_http_canon, proxy_http_handler):
Add and use the new get_url_scheme() helper to parse URL schemes handled by
mod_proxy_http and use it in canon and scheme handlers. This helper now
accepts ws[s] schemes.
* modules/proxy/mod_proxy_wstunnel.c (proxy_wstunnel_post_config):
New post_config hook to detect whether mod_proxy_http is loaded and set
global fallback_to_mod_proxy_http flag in this case.
* modules/proxy/mod_proxy_wstunnel.c (proxy_wstunnel_check_trans,
proxy_wstunnel_canon,
proxy_wstunnel_handler):
These hooks now early return DECLINED if fallback_to_mod_proxy_http is set.
git-svn-id: https://svn.apache.org/repos/asf/httpd/httpd/trunk@1885239 13f79535-47bb-0310-9956-ffa450edef68
This is cleaner API than using pfds->pool implicitely.
MAJOR bump but reusing the existing hooks (with an API/ABI breakage) because
it's trunk material only.
git-svn-id: https://svn.apache.org/repos/asf/httpd/httpd/trunk@1879449 13f79535-47bb-0310-9956-ffa450edef68
Create the dedicated pfds and subpool in proxy_wstunnel_request() too, for
the first call to ap_mpm_register_poll_callback_timeout().
While at it, add comments about why we need the dedicated pfds/subpool.
git-svn-id: https://svn.apache.org/repos/asf/httpd/httpd/trunk@1879438 13f79535-47bb-0310-9956-ffa450edef68
Since event_register_poll_callback_ex() allocates its data on pfds->pool,
we need a subpool to be cleared at each proxy_wstunnel_callback() call.
git-svn-id: https://svn.apache.org/repos/asf/httpd/httpd/trunk@1879418 13f79535-47bb-0310-9956-ffa450edef68
modules/proxy/mod_proxy.h:
Rename AP_PROXY_TRANSFER_SHOULD_YIELD to AP_PROXY_TRANSFER_YIELD_PENDING
and add AP_PROXY_TRANSFER_YIELD_MAX_READS.
modules/proxy/mod_proxy_http.c:
modules/proxy/mod_proxy_wstunnel.c:
Removing of reqtimeout filter is now handled by ap_proxy_tunnel_create().
modules/proxy/proxy_util.c:
ap_proxy_transfer_between_connections():
Reorganize loop to break out early.
When AP_PROXY_TRANSFER_YIELD_PENDING, if !ap_filter_should_yield() we
still need to run and check ap_filter_output_pending() since it may
release pending data.
When AP_PROXY_TRANSFER_YIELD_MAX_READS, stop the loop after too much
reads (PROXY_TRANSFER_MAX_READS = 10000) to release the thread and
give the caller a chance to schedule the other direction.
Don't return APR_INCOMPLETE when it comes from an incomplete body
detected by ap_http_filter().
ap_proxy_tunnel_create():
Start with POLLOUT on both directions so that any pending output data
is flushed first.
ap_proxy_tunnel_run():
Remove re-init/clear of the pollset for each call so that the function
is reentrant.
Handle POLLOUT before POLLIN so that we can read in the same pass once
all buffered output data are flushed, using ap_filter_input_pending()
to drain buffered input data.
This is preparatory patch for async websocket tunneling is mod_proxy_http.
git-svn-id: https://svn.apache.org/repos/asf/httpd/httpd/trunk@1879401 13f79535-47bb-0310-9956-ffa450edef68
If the request Upgrade header matches the worker upgrade= parameter and
the backend switches the protocol, do the tunneling in mod_proxy_http.
This allows to keep the protocol to HTTP until the backend really
switches the protocol, and apply usual output filters.
When configured to forward Upgrade mechanism, we want the backend to be
able to announce its Upgrade protocol to the client (e.g. with 426
Upgrade Required response) and thus forward back the Upgrade header that
matches the one(s) configured in the worker upgrade= parameter.
modules/proxy/mod_proxy.h:
modules/proxy/proxy_util.c:
ap_proxy_worker_can_upgrade(): added helper to determine whether a
proxy worker is configured to forward an Upgrade protocol.
include/ap_mmn.h:
Bump MMN minor for ap_proxy_worker_can_upgrade().
modules/proxy/mod_proxy.c:
set_worker_param(): handle worker parameter upgrade=ANY as upgrade=*
(should the "any" protocol scheme be something some day..).
modules/proxy/mod_proxy_wstunnel.c:
proxy_wstunnel_handler(): use ap_proxy_worker_can_upgrade() to match
the Upgrade header. Axe handling of upgrade=NONE, it makes no sense to
Upgrade a connection if the client did not ask for it, nor to configure
mod_proxy_wstunnel to use a worker with upgrade=NONE by the way.
modules/proxy/mod_proxy_http.c:
proxy_http_req_t: add fields force10 (force HTTP/1.0) and upgrade (value
of the Upgrade header sent by the client if it matches the configuration,
NULL otherwise).
proxy_http_handler(): use ap_proxy_worker_can_upgrade() to determine
whether the request is electable for end to end protocol upgrading and set
req->upgrade accordingly.
terminate_headers(): handle Connection and Upgrade headers to send to the
backend, according to req->force10 and req->upgrade set before.
ap_proxy_http_prefetch(): use req->force10 and terminate_headers().
send_continue_body(): added helper to send the body retained for end to
end 100-continue handling.
ap_proxy_http_process_response(): use ap_proxy_worker_can_upgrade() to
match the response Upgrade header and forward it back if it matches the
configured one(s). That is for 101 Switching Protocol obviously but also
any other status code which is not overidden, at the backend wish. If the
protocol is switching, create a proxy tunnel and run it, using the minimal
timeout from the client or backend connection.
Github: closes#125
git-svn-id: https://svn.apache.org/repos/asf/httpd/httpd/trunk@1877646 13f79535-47bb-0310-9956-ffa450edef68
Support half closed connections and pending data draining (for protocols like
rsync). PR 61616.
When reading on one side goes faster than writing on the other side, the output
filters chain may start buffering data and finally block, which will break
bidirectional tunneling for some protocols.
To avoid this, proxy_tunnel_run() now stops polling/reading until pending data
are drained, and recovers appropriately.
git-svn-id: https://svn.apache.org/repos/asf/httpd/httpd/trunk@1869420 13f79535-47bb-0310-9956-ffa450edef68
This allows proxy modules to decline request handling at early stage.
Then mod_proxy_wstunnel can implement that hook to verify that an Upgrade
is requested, and otherwise hand over to mod_proxy_http.
git-svn-id: https://svn.apache.org/repos/asf/httpd/httpd/trunk@1869399 13f79535-47bb-0310-9956-ffa450edef68
This commit adds struct proxy_tunnel_rec that contains the fields needed for a
poll() loop through the filters chains, plus functions ap_proxy_tunnel_create()
and ap_proxy_tunnel_run() to respectively initialize a tunnel and (re)start it.
Proxy connect and wstunnel modules now make use of this new API to avoid
duplicating logic and code.
git-svn-id: https://svn.apache.org/repos/asf/httpd/httpd/trunk@1869338 13f79535-47bb-0310-9956-ffa450edef68
Let's call stream_reqbody() for all rb_methods, no RB_SPOOL_CL special case.
This both simplifies code and allows to keep EOS into the input_brigade until
it's sent, and thus detect whether we already fetched the whole body if/when
proxy_http_handler() re-enters for different balancer members.
git-svn-id: https://svn.apache.org/repos/asf/httpd/httpd/trunk@1869222 13f79535-47bb-0310-9956-ffa450edef68
This function now now handles SSL reuse as well as the "proxy-request-hostname"
note (SNI), so let's also call it unconditionnaly in all proxy modules.
On the mod_ssl side, since this note has the lifetime of the connection, don't
reset/unset it during handshake (ssl_io_filter_handshake).
git-svn-id: https://svn.apache.org/repos/asf/httpd/httpd/trunk@1859422 13f79535-47bb-0310-9956-ffa450edef68
configuration example:
<Location "/apis">
ProxyPass unix:/var/run/unix.sock|ws://127.0.0.1/api
</Location>
Currently 'ap_proxy_get_worker()' can't get matched pre-defined worker because
of different uri formatting in 'proxy_wstunnel_canon()' and ap_proxy_define_worker()'
PR 62932 <pavel dcmsys.com>
git-svn-id: https://svn.apache.org/repos/asf/httpd/httpd/trunk@1851093 13f79535-47bb-0310-9956-ffa450edef68
construction for error handling/jump (as suggested by Ruediger).
Hence we can move backend->close = 1 (for mod_proxy_wstunnel) and
proxy_run_detach_backend() (for mod_proxy_http2) in the cleanup fallback.
git-svn-id: https://svn.apache.org/repos/asf/httpd/httpd/trunk@1729749 13f79535-47bb-0310-9956-ffa450edef68
This used to check for the backend connection readability only (instead of
the full ping/100-continue round-trip), but the case is already handled by
ap_proxy_connect_backend() which is always called.
git-svn-id: https://svn.apache.org/repos/asf/httpd/httpd/trunk@1729507 13f79535-47bb-0310-9956-ffa450edef68