mirror of
https://github.com/tailscale/tailscale.git
synced 2025-06-10 17:58:38 +00:00
net/tshttpproxy: fix WDAP/PAC proxy detection on Win10 1607 and earlier
Using WINHTTP_AUTOPROXY_ALLOW_AUTOCONFIG on Windows versions older than Windows 10 1703 (build 15063) is not supported and causes WinHttpGetProxyForUrl to fail with ERROR_INVALID_PARAMETER. This results in failures reaching the control on environments where a proxy is required. We use wingoes version detection to conditionally set the WINHTTP_AUTOPROXY_ALLOW_AUTOCONFIG flag on Windows builds greater than 15063. While there, we also update proxy detection to use WINHTTP_AUTO_DETECT_TYPE_DNS_A, as DNS-based proxy discovery might be required with Active Directory and in certain other environments. Updates tailscale/corp#29168 Fixes #879 Signed-off-by: Nick Khyl <nickk@tailscale.com>
This commit is contained in:
parent
4cccd15eeb
commit
191afd3390
@ -12,7 +12,7 @@ tailscale.com/cmd/derper dependencies: (generated by github.com/tailscale/depawa
|
|||||||
github.com/coder/websocket/internal/util from github.com/coder/websocket
|
github.com/coder/websocket/internal/util from github.com/coder/websocket
|
||||||
github.com/coder/websocket/internal/xsync from github.com/coder/websocket
|
github.com/coder/websocket/internal/xsync from github.com/coder/websocket
|
||||||
L github.com/coreos/go-iptables/iptables from tailscale.com/util/linuxfw
|
L github.com/coreos/go-iptables/iptables from tailscale.com/util/linuxfw
|
||||||
W 💣 github.com/dblohm7/wingoes from tailscale.com/util/winutil
|
W 💣 github.com/dblohm7/wingoes from tailscale.com/util/winutil+
|
||||||
github.com/fxamacker/cbor/v2 from tailscale.com/tka
|
github.com/fxamacker/cbor/v2 from tailscale.com/tka
|
||||||
github.com/go-json-experiment/json from tailscale.com/types/opt+
|
github.com/go-json-experiment/json from tailscale.com/types/opt+
|
||||||
github.com/go-json-experiment/json/internal from github.com/go-json-experiment/json+
|
github.com/go-json-experiment/json/internal from github.com/go-json-experiment/json+
|
||||||
|
@ -18,6 +18,7 @@ import (
|
|||||||
"unsafe"
|
"unsafe"
|
||||||
|
|
||||||
"github.com/alexbrainman/sspi/negotiate"
|
"github.com/alexbrainman/sspi/negotiate"
|
||||||
|
"github.com/dblohm7/wingoes"
|
||||||
"golang.org/x/sys/windows"
|
"golang.org/x/sys/windows"
|
||||||
"tailscale.com/hostinfo"
|
"tailscale.com/hostinfo"
|
||||||
"tailscale.com/syncs"
|
"tailscale.com/syncs"
|
||||||
@ -97,9 +98,7 @@ func proxyFromWinHTTPOrCache(req *http.Request) (*url.URL, error) {
|
|||||||
}
|
}
|
||||||
if err == windows.ERROR_INVALID_PARAMETER {
|
if err == windows.ERROR_INVALID_PARAMETER {
|
||||||
metricErrInvalidParameters.Add(1)
|
metricErrInvalidParameters.Add(1)
|
||||||
// Seen on Windows 8.1. (https://github.com/tailscale/tailscale/issues/879)
|
setNoProxyUntil(10 * time.Second)
|
||||||
// TODO(bradfitz): figure this out.
|
|
||||||
setNoProxyUntil(time.Hour)
|
|
||||||
proxyErrorf("tshttpproxy: winhttp: GetProxyForURL(%q): ERROR_INVALID_PARAMETER [unexpected]", urlStr)
|
proxyErrorf("tshttpproxy: winhttp: GetProxyForURL(%q): ERROR_INVALID_PARAMETER [unexpected]", urlStr)
|
||||||
return nil, nil
|
return nil, nil
|
||||||
}
|
}
|
||||||
@ -238,17 +237,30 @@ func (pi *winHTTPProxyInfo) free() {
|
|||||||
}
|
}
|
||||||
}
|
}
|
||||||
|
|
||||||
var proxyForURLOpts = &winHTTPAutoProxyOptions{
|
var getProxyForURLOpts = sync.OnceValue(func() *winHTTPAutoProxyOptions {
|
||||||
DwFlags: winHTTP_AUTOPROXY_ALLOW_AUTOCONFIG | winHTTP_AUTOPROXY_AUTO_DETECT,
|
opts := &winHTTPAutoProxyOptions{
|
||||||
DwAutoDetectFlags: winHTTP_AUTO_DETECT_TYPE_DHCP, // | winHTTP_AUTO_DETECT_TYPE_DNS_A,
|
DwFlags: winHTTP_AUTOPROXY_AUTO_DETECT,
|
||||||
}
|
DwAutoDetectFlags: winHTTP_AUTO_DETECT_TYPE_DHCP | winHTTP_AUTO_DETECT_TYPE_DNS_A,
|
||||||
|
}
|
||||||
|
// Support for the WINHTTP_AUTOPROXY_ALLOW_AUTOCONFIG flag was added in Windows 10, version 1703.
|
||||||
|
//
|
||||||
|
// Using it on earlier versions causes GetProxyForURL to fail with ERROR_INVALID_PARAMETER,
|
||||||
|
// which prevents proxy detection and can lead to failures reaching the control server
|
||||||
|
// on environments where a proxy is required.
|
||||||
|
//
|
||||||
|
// https://web.archive.org/web/20250529044903/https://learn.microsoft.com/en-us/windows/win32/api/winhttp/ns-winhttp-winhttp_autoproxy_options
|
||||||
|
if wingoes.IsWin10BuildOrGreater(wingoes.Win10Build1703) {
|
||||||
|
opts.DwFlags |= winHTTP_AUTOPROXY_ALLOW_AUTOCONFIG
|
||||||
|
}
|
||||||
|
return opts
|
||||||
|
})
|
||||||
|
|
||||||
func (hi winHTTPInternet) GetProxyForURL(urlStr string) (string, error) {
|
func (hi winHTTPInternet) GetProxyForURL(urlStr string) (string, error) {
|
||||||
var out winHTTPProxyInfo
|
var out winHTTPProxyInfo
|
||||||
err := winHTTPGetProxyForURL(
|
err := winHTTPGetProxyForURL(
|
||||||
hi,
|
hi,
|
||||||
windows.StringToUTF16Ptr(urlStr),
|
windows.StringToUTF16Ptr(urlStr),
|
||||||
proxyForURLOpts,
|
getProxyForURLOpts(),
|
||||||
&out,
|
&out,
|
||||||
)
|
)
|
||||||
if err != nil {
|
if err != nil {
|
||||||
|
Loading…
x
Reference in New Issue
Block a user