Compare commits

...

3801 Commits

Author SHA1 Message Date
Tyler Smalley
16c59d2294 VERSION.txt: this is v1.52.1
Signed-off-by: Tyler Smalley <tyler@tailscale.com>
2023-11-02 13:31:04 -07:00
Andrew Lytvynov
e5d93d37bf clientupdate: do not recursively delete dirs in cleanupOldDownloads (#10093)
In case there's a wild symlink in one of the target paths, we don't want
to accidentally delete too much. Limit `cleanupOldDownloads` to deleting
individual files only.

Updates https://github.com/tailscale/tailscale/issues/10082

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
(cherry picked from commit 7145016414)
2023-11-02 13:30:38 -07:00
Andrew Lytvynov
741b63479e clientupdate: cleanup SPK and MSI downloads (#10085)
After we're done installing, clean up the temp files. This prevents temp
volumes from filling up on hosts that don't reboot often.

Fixes https://github.com/tailscale/tailscale/issues/10082

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
(cherry picked from commit 6c0ac8bef3)
2023-11-02 12:49:04 -07:00
Aaron Klotz
2855ad959c cmd/tailscaled: pre-load wintun.dll using a fully-qualified path
In corp PR #14970 I updated the installer to set a security mitigation that
always forces system32 to the front of the Windows dynamic linker's search
path.

Unfortunately there are other products out there that, partying like it's
1995, drop their own, older version of wintun.dll into system32. Since we
look there first, we end up loading that old version.

We can fix this by preloading wintun using a fully-qualified path. When
wintun-go then loads wintun, the dynamic linker will hand it the module
that was previously loaded by us.

Fixes #10023, #10025, #10052

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
(cherry picked from commit 47019ce1f1)
2023-11-02 09:48:35 -06:00
Tyler Smalley
31e1690f38 VERSION.txt: this is v1.52.0
Signed-off-by: Tyler Smalley <tyler@tailscale.com>
2023-10-30 10:13:53 -07:00
Maisem Ali
62d580f0e8 util/linuxfw: add missing error checks in tests
This would surface as panics when run on Fly. Still fail, but at least don't panic.

Updates #10003

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-10-28 09:44:53 -07:00
Rhea Ghosh
387a98fe28 ipn/ipnlocal: exclude tvOS devices from taildrop file targets (#10002) 2023-10-27 16:35:18 -05:00
Chris Palmer
f66dc8dc0a clientupdate: check for privileges earlier (#9964)
Fixes #9963

Signed-off-by: Chris Palmer <cpalmer@tailscale.com>
2023-10-27 10:43:50 -07:00
Flakes Updater
f9fafe269a go.mod.sri: update SRI hash for go.mod changes
Signed-off-by: Flakes Updater <noreply+flakes-updater@tailscale.com>
2023-10-27 10:37:26 -07:00
Cole Helbling
087260734b flake: drop unnecessary git input
Signed-off-by: Cole Helbling <cole.helbling@determinate.systems>
2023-10-27 10:33:50 -07:00
Cole Helbling
561e7b61c3 flake: fix systemd service by hardcoding $PORT
Another solution would be to copy the `.defaults` file alongside the
service file, and set the `EnvironmentFile` to point to that, but it
would still be hardcoded (as the `.defaults` file would be stored in the
Nix store), so I figured that this is a good solution until there is a
proper NixOS module.

Fixes #9995.

Signed-off-by: Cole Helbling <cole.helbling@determinate.systems>
2023-10-27 10:33:50 -07:00
Cole Helbling
9e71851a36 go.mod.sri: update
Signed-off-by: Cole Helbling <cole.helbling@determinate.systems>
2023-10-27 10:33:50 -07:00
Cole Helbling
4f62a2ed99 flake: set a default package
This allows `nix build` to run, without needing to use `nix build
.#tailscale`.

Signed-off-by: Cole Helbling <cole.helbling@determinate.systems>
2023-10-27 10:33:50 -07:00
Cole Helbling
f737496d7c flake: drop unnecessary fileContents binding
Since the tailscale derivation already has a `pkgs` binding, we can
use `pkgs.lib`. Alternatively, we could have used `nixpkgs.lib`, as
`fileContents` doesn't need a system to use (anymore?).

Signed-off-by: Cole Helbling <cole.helbling@determinate.systems>
2023-10-27 10:33:50 -07:00
Maisem Ali
9107b5eadf cmd/tailscale/cli: use status before doing interactive feature query
We were inconsistent whether we checked if the feature was already
enabled which we could do cheaply using the locally available status.
We would do the checks fine if we were turning on funnel, but not serve.

This moves the cap checks down into enableFeatureInteractive so that
are always run.

Updates #9984

Co-authored-by: Tyler Smalley <tyler@tailscale.com>
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-10-26 17:10:24 -07:00
License Updater
e94d345e26 licenses: update android licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-10-26 15:21:33 -07:00
License Updater
7c7f60be22 licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-10-26 15:20:25 -07:00
Tyler Smalley
baa1fd976e ipn/localapi: require local Windows admin to set serve path (#9969)
For a serve config with a path handler, ensure the caller is a local administrator on Windows.

updates #8489

Signed-off-by: Tyler Smalley <tyler@tailscale.com>
2023-10-26 14:40:44 -07:00
Will Norris
42abf13843 .github: run tests on all PRs, regardless of branch name
The branch name selector "*" doesn't match branches with a "/" in their
name. The vast majority of our PRs are against the main (or previously,
master) branch anyway, so this will have minimal impact. But in the rare
cases that we want to open a PR against a branch with a "/" in the name,
tests should still run.

```
gh pr list --limit 9999 --state all --json baseRefName | \
  jq -cs '.[] | group_by(.baseRefName) |
    map({ base: .[0].baseRefName, count: map(.baseRefName) | length}) |
    sort_by(-.count) | .[]'

{"base":"main","count":4593}
{"base":"master","count":226}
{"base":"release-branch/1.48","count":4}
{"base":"josh-and-adrian-io_uring","count":3}
{"base":"release-branch/1.30","count":3}
{"base":"release-branch/1.32","count":3}
{"base":"release-branch/1.20","count":2}
{"base":"release-branch/1.26","count":2}
{"base":"release-branch/1.34","count":2}
{"base":"release-branch/1.38","count":2}
{"base":"Aadi/speedtest-tailscaled","count":1}
{"base":"josh/io_uring","count":1}
{"base":"maisem/hi","count":1}
{"base":"rel-144","count":1}
{"base":"release-branch/1.18","count":1}
{"base":"release-branch/1.2","count":1}
{"base":"release-branch/1.22","count":1}
{"base":"release-branch/1.24","count":1}
{"base":"release-branch/1.4","count":1}
{"base":"release-branch/1.46","count":1}
{"base":"release-branch/1.8","count":1}
{"base":"web-client-main","count":1}
```

Updates #cleanup

Signed-off-by: Will Norris <will@tailscale.com>
2023-10-26 10:47:39 -07:00
Brad Fitzpatrick
b4be4f089f safesocket: make clear which net.Conns are winio types
Follow-up to earlier #9049.

Updates #9049

Change-Id: I121fbd2468770233a23ab5ee3df42698ca1dabc2
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-10-26 10:11:08 -07:00
Aaron Klotz
95671b71a6 ipn, safesocket: use Windows token in LocalAPI
On Windows, the idiomatic way to check access on a named pipe is for
the server to impersonate the client on its current OS thread, perform
access checks using the client's access token, and then revert the OS
thread's access token back to its true self.

The access token is a better representation of the client's rights than just
a username/userid check, as it represents the client's effective rights
at connection time, which might differ from their normal rights.

This patch updates safesocket to do the aforementioned impersonation,
extract the token handle, and then revert the impersonation. We retain
the token handle for the remaining duration of the connection (the token
continues to be valid even after we have reverted back to self).

Since the token is a property of the connection, I changed ipnauth to wrap
the concrete net.Conn to include the token. I then plumbed that change
through ipnlocal, ipnserver, and localapi as necessary.

I also added a PermitLocalAdmin flag to the localapi Handler which I intend
to use for controlling access to a few new localapi endpoints intended
for configuring auto-update.

Updates https://github.com/tailscale/tailscale/issues/755

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2023-10-26 09:43:19 -06:00
Andrew Dunham
ef596aed9b net/portmapper: avoid alloc in getUPnPErrorsMetric
Updates #cleanup

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: Iea558024c038face24cc46584421998d10f13a66
2023-10-26 03:02:27 +02:00
James Tucker
237b4b5a2a .github/workflows: add checklocks
Currently the checklocks step is not configured to fail, as we do not
yet have the appropriate annotations.

Updates tailscale/corp#14381

Signed-off-by: James Tucker <james@tailscale.com>
2023-10-25 16:39:31 -07:00
Tyler Smalley
131518eed1 cmd/tailscale/cli: improve error when bg serve config is present (#9961)
We prevent shodow configs when starting a foreground when a background serve config already exists for the serve type and port. This PR improves the messaging to let the user know how to remove the previous config.

Updates #8489
ENG-2314

Signed-off-by: Tyler Smalley <tyler@tailscale.com>
2023-10-25 14:27:46 -07:00
Tyler Smalley
1873bc471b cmd/tailscale/cli: remove http flag for funnel command (#9955)
The `--http` flag can not be used with Funnel, so we should remove it to remove confusion.

Updates #8489
ENG-2316

Signed-off-by: Tyler Smalley <tyler@tailscale.com>
2023-10-25 14:05:54 -07:00
Val
19e5f242e0 net/portmapper: convert UPnP metrics to new syncs.Map.LoadOrInit method
Simplify UPnP error metrics by using the new syncs.Map.LoadOrInit method.

Updates #cleanup

Signed-off-by: Val <valerie@tailscale.com>
2023-10-25 22:39:47 +02:00
Andrew Lytvynov
8326fdd60f clientupdate: disable auto-updates on Synology for now (#9965)
Updates #755

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-10-25 16:02:46 -04:00
Flakes Updater
143bda87a3 go.mod.sri: update SRI hash for go.mod changes
Signed-off-by: Flakes Updater <noreply+flakes-updater@tailscale.com>
2023-10-24 20:16:27 -07:00
Marwan Sulaiman
5f3cdaf283 cmd/tailscale/cli: chage port flags to uint for serve and funnel
This PR changes the -https, -http, -tcp, and -tls-terminated-tcp
flags from string to int and also updates the validation to ensure
they fit the uint16 size as the flag library does not have a Uint16Var
method.

Updates #8489

Signed-off-by: Marwan Sulaiman <marwan@tailscale.com>
2023-10-24 20:12:17 -04:00
Andrea Gottardo
741d7bcefe Revert "ipn/ipnlocal: add new DNS and subnet router policies" (#9962)
This reverts commit 32194cdc70.

Signed-off-by: Nick O'Neill <nick@tailscale.com>
2023-10-24 17:07:25 -07:00
Marwan Sulaiman
a7e4cebb90 cmd/tailscale/cli: refactor TestServeDevConfigMutations
The TestServeDevConfigMutations test has 63 steps that all run
under the same scope. This tests breaks them out into isolated
subtests that can be run independently.

Updates #8489

Signed-off-by: Marwan Sulaiman <marwan@tailscale.com>
2023-10-24 18:07:24 -04:00
Sonia Appasamy
d79e0fde9c client/web: split errTaggedSelf resp from getTailscaleBrowserSession
Previously returned errTaggedSource in the case that of any tagged
source. Now distinguishing whether the source was local or remote.
We'll be presenting the two cases with varying copy on the frontend.

Updates tailscale/corp#14335

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-10-24 16:12:07 -04:00
Sonia Appasamy
e0a4a02b35 client/web: pipe Server.timeNow() through session funcs
Updates tailscale/corp#14335

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-10-24 15:46:13 -04:00
Andrew Lytvynov
21b6d373b0 cmd/tailscale/cli: unhide auto-update flags and mark update as Beta (#9954)
Updates #755

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-10-24 11:34:24 -07:00
Adrian Dewhurst
32194cdc70 ipn/ipnlocal: add new DNS and subnet router policies
In addition to the new policy keys for the new options, some
already-in-use but missing policy keys are also being added to
util/syspolicy.

Updates ENG-2133

Change-Id: Iad08ca47f839ea6a65f81b76b4f9ef21183ebdc6
Signed-off-by: Adrian Dewhurst <adrian@tailscale.com>
2023-10-24 14:33:59 -04:00
Marwan Sulaiman
f5a7551382 cmd/tailscale: fix help message for serve funnel
We currently print out "run tailscale serve --help" when the subcmd
might be funnel. This PR ensures the right subcmd is passed.

Updates #8489

Signed-off-by: Marwan Sulaiman <marwan@tailscale.com>
2023-10-24 14:32:11 -04:00
Andrew Lytvynov
d3bc575f35 cmd/tailscale/cli: set Sparkle auto-update on macsys (#9952)
On `tailscale set --auto-update`, set the Sparkle plist option for it.
Also make macsys report not supporting auto-updates over c2n, since they
will be triggered by Sparkle locally.

Updates #755

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-10-24 12:17:55 -06:00
James Tucker
6f69fe8ad7 wgnengine: remove unused field in userspaceEngine
Updates #cleanup

Signed-off-by: James Tucker <james@tailscale.com>
2023-10-24 11:01:19 -07:00
Tyler Smalley
269a498c1e cmd/tailscale/cli: serve --set-path should not force background mode (#9905)
A few people have run into issues with understanding why `--set-path` started in background mode, and/or why they couldn't use a path in foreground mode. This change allows `--set-path` to be used in either case (foreground or background).

updates #8489

Signed-off-by: Tyler Smalley <tyler@tailscale.com>
2023-10-24 09:56:41 -07:00
Thomas Kosiewski
b2ae8fdf80 derp/derphttp: strip port numbers from URL hostname
When trying to set up multiple derper instances meshing with each
other, it turned out that while one can specify an alternative
listening port using the -a flag, the TLS hostname gets incorrectly
determined and includes the set alternative listening port as part of
the hostname. Thus, the TLS hostname validation always fails when the
-mesh-with values have ports.

Updates #9949

Signed-off-by: Thomas Kosiewski <thomas.kosiewski@loft.sh>
2023-10-24 07:27:29 -07:00
Brad Fitzpatrick
514539b611 wgengine/magicsock: close disco listeners on Conn.Close, fix Linux root TestNewConn
TestNewConn now passes as root on Linux. It wasn't closing the BPF
listeners and their goroutines.

The code is still a mess of two Close overlapping code paths, but that
can be refactored later. For now, make the two close paths more similar.

Updates #9945

Change-Id: I8a3cf5fb04d22ba29094243b8e645de293d9ed85
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-10-23 19:19:09 -07:00
Andrew Lytvynov
593c086866 clientupdate: distinguish when auto-updates are possible (#9896)
clientupdate.Updater will have a non-nil Update func in a few cases
where it doesn't actually perform an update:
* on Arch-like distros, where it prints instructions on how to update
* on macOS app store version, where it opens the app store page

Add a new clientupdate.Arguments field to cause NewUpdater to fail when
we hit one of these cases. This results in c2n updates being "not
supported" and `tailscale set --auto-update` returning an error.

Updates #755

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-10-23 18:21:54 -07:00
James Tucker
7df6f8736a wgengine/netstack: only add addresses to correct protocols
Prior to an earlier netstack bump this code used a string conversion
path to cover multiple cases of behavior seemingly checking for
unspecified addresses, adding unspecified addresses to v6. The behavior
is now crashy in netstack, as it is enforcing address length in various
areas of the API, one in particular being address removal.

As netstack is now protocol specific, we must not create invalid
protocol addresses - an address is v4 or v6, and the address value
contained inside must match. If a control path attempts to do something
otherwise it is now logged and skipped rather than incorrect addressing
being added.

Fixes tailscale/corp#15377

Signed-off-by: James Tucker <james@tailscale.com>
2023-10-23 17:29:36 -07:00
Tyler Smalley
35d7b3aa27 cmd/tailscale/cli: updates help and background messaging (#9929)
* Fixes issue with template string not being provided in help text
* Updates background information to provide full URL, including path, to make it clear the source and destination
* Restores some tests
* Removes AllowFunnel in ServeConfig if no proxy exists for that port.

updates #8489

Signed-off-by: Tyler Smalley <tyler@tailscale.com>
2023-10-23 13:24:21 -07:00
Marwan Sulaiman
c53ee37912 cmd/tailscale: add set-raw to the new serve funnel commands
This PR adds the same set-raw from the old flow into the new one
so that users can continue to use it when transitioning into the new
flow.

Updates #8489

Signed-off-by: Marwan Sulaiman <marwan@tailscale.com>
2023-10-23 15:55:13 -04:00
Marwan Sulaiman
f232d4554a cmd/tailscale: translate old serve commands to new ones
This PR fixes the isLegacyInvocation to better catch serve and
funnel legacy commands. In addition, it now also returns a string
that translates the old command into the new one so that users
can have an easier transition story.

Updates #8489

Signed-off-by: Marwan Sulaiman <marwan@tailscale.com>
2023-10-23 15:54:24 -04:00
Sonia Appasamy
62d08d26b6 client/web: set Server.cgiMode field
Updates tailscale/corp#15373

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
Co-authored-by: Will Norris <will@tailscale.com>
2023-10-23 15:27:22 -04:00
Maisem Ali
17b2072b72 ipn/ipnlocal: set the push device token correctly
It would end up resetting whatever hostinfo we had constructed
and leave the backend statemachine in a broken state.
This fixes that by storing the PushDeviceToken on the LocalBackend
and populating it on Hostinfo before passing it to controlclient.

Updates tailscale/corp#8940
Updates tailscale/corp#15367

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-10-23 11:43:25 -07:00
Maisem Ali
0e89245c0f ipn/ipnlocal: drop hostinfo param from doSetHostinfoFilterServices
The value being passed was the same as whats on b.hostinfo, so just
use that directly.

Updates #cleanup

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-10-23 11:43:25 -07:00
Joe Tsai
152390e80a ipn/localapi: avoid unkeyed literal (#9933)
Go has no way to explicitly identify Go struct as effectively a tuple,
so staticcheck assumes any external use of unkeyed literals is wrong.

Updates #cleanup

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2023-10-23 11:15:25 -07:00
Marwan Sulaiman
60e768fd14 cmd/tailscale: allow serve|funnel off to delete an entire port
This PR allows you to do "tailscale serve -bg -https:4545 off" and it
will delete all handlers under it. It will also prompt you for a y/n in case
you wanted to delete a single port.

Updates #8489

Signed-off-by: Marwan Sulaiman <marwan@tailscale.com>
2023-10-23 13:42:10 -04:00
Andrew Lytvynov
e561f1ce61 clientupdate: manually restart Windows GUI after update (#9906)
When updating via c2n, `tailscale.exe update` runs from `tailscaled.exe`
which runs as SYSTEM. The MSI installer does not start the GUI when
running as SYSTEM. This results in Tailscale just existing on
auto-update, which is ungood.

Instead, always ask the MSI installer to not launch the GUI (via
`TS_NOLAUNCH` argument) and launch it manually with a token from the
current logged in user. The token code was borrowed from
d9081d6ba2/net/dns/wsl_windows.go (L207-L232)

Also, make some logging changes so that these issues are easier to debug
in the future.

Updates #755

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-10-23 10:24:57 -07:00
Irbe Krumina
e9956419f6 cmd/k8s-operator: allow cleanup of cluster resources for deleted devices (#9917)
Users should delete proxies by deleting or modifying the k8s cluster resources
that they used to tell the operator to create they proxy. With this flow,
the tailscale operator will delete the associated device from the control.
However, in some cases users might have already deleted the device from the control manually.

Updates tailscale/tailscale#9773

Signed-off-by: Irbe Krumina <irbe@tailscale.com>
2023-10-23 16:22:55 +01:00
Brad Fitzpatrick
e87862bce3 go.toolchain.rev: bump Tailscale Go toolchain
Updates tailscale/go#77

Change-Id: I367465fb90cd4369cfbafd913c3964bfe5553dd0
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-10-22 16:20:41 -07:00
Maisem Ali
f398712c00 ipn/ipnlocal: prevent changing serve config if conf.Locked
This adds a check to prevent changes to ServeConfig if tailscaled
is run with a Locked config.

Missed in 1fc3573446.

Updates #1412

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-10-20 21:21:34 -07:00
Tyler Smalley
d9081d6ba2 cmd/tailscale/cli: update serve/funnel CLI help text (#9895)
updates #8489
ENG-2308

Signed-off-by: Tyler Smalley <tyler@tailscale.com>
2023-10-20 14:17:28 -07:00
Adrian Dewhurst
5347e6a292 control/controlclient: support certstore without cgo
We no longer build Windows releases with cgo enabled, which
automatically turned off certstore support. Rather than re-enabling cgo,
we updated our fork of the certstore package to no longer require cgo.
This updates the package, cleans up how the feature is configured, and
removes the cgo build tag requirement.

Fixes tailscale/corp#14797
Fixes tailscale/coral#118

Change-Id: Iaea34340761c0431d759370532c16a48c0913374
Signed-off-by: Adrian Dewhurst <adrian@tailscale.com>
2023-10-20 15:17:32 -04:00
Sonia Appasamy
68da15516f ipn/localapi,client/web: clean up auth error handling
This commit makes two changes to the web client auth flow error
handling:

1. Properly passes back the error code from the noise request from
   the localapi. Previously we were using io.Copy, which was always
   setting a 200 response status code.
2. Clean up web client browser sessions on any /wait endpoint error.
   This avoids the user getting in a stuck state if something goes
   wrong with their auth path.

Updates tailscale/corp#14335

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-10-20 14:55:22 -04:00
Andrew Lytvynov
70f9c8a6ed clientupdate: change Mac App Store support (#9891)
In the sandboxed app from the app store, we cannot check
`/Library/Preferences/com.apple.commerce.plist` or run `softwareupdate`.
We can at most print a helpful message and open the app store page.

Also, reenable macsys update function to mark it as supporting c2n
updates. macsys support in `tailscale update` was fixed.

Updates #755

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-10-20 08:58:41 -07:00
Irbe Krumina
eced054796 ipn/ipnlocal: close connections for removed proxy transports (#9884)
Ensure that when a userspace proxy config is reloaded,
connections for any removed proxies are safely closed

Updates tailscale/tailscale#9725

Signed-off-by: Irbe Krumina <irbe@tailscale.com>
2023-10-20 12:04:00 +01:00
Sonia Appasamy
1df2d14c8f client/web: use auth ID in browser sessions
Stores ID from tailcfg.WebClientAuthResponse in browser session
data, and uses ID to hit control server /wait endpoint.

No longer need the control url cached, so removed that from Server.
Also added optional timeNow field, initially to manage time from
tests.

Updates tailscale/corp#14335

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-10-19 16:32:43 -04:00
Joe Tsai
6ada33db77 taildrop: fix theoretical race condition in fileDeleter.Init (#9876)
It is possible that upon a cold-start, we enqueue a partial file
for deletion that is resumed shortly after startup.

If the file transfer happens to last longer than deleteDelay,
we will delete the partial file, which is unfortunate.
The client spent a long time uploading a file,
only for it to be accidentally deleted.
It's a very rare race, but also a frustrating one
if it happens to manifest.

Fix the code to only delete partial files that
do not have an active puts against it.

We also fix a minor bug in ResumeReader
where we read b[:blockSize] instead of b[:cs.Size].
The former is the fixed size of 64KiB,
while the latter is usually 64KiB,
but may be less for the last block.

Updates tailscale/corp#14772

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2023-10-19 13:26:55 -07:00
Andrew Lytvynov
25b6974219 ipn/ipnlocal: send ClientVersion to Apple frontends (#9887)
Apple frontends will now understand this Notify field and handle it.

Updates #755

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-10-19 12:50:21 -07:00
Sonia Appasamy
b4247fabec tailcfg: add ID field to WebClientAuthResponse
Updates tailscale/corp#14335

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-10-19 15:13:57 -04:00
Tom DNetto
7e933a8816 appctype: move to types/appctype
Having a types package at the top level was almost certainly unintentional.

Signed-off-by: Tom DNetto <tom@tailscale.com>
Updates: https://github.com/tailscale/corp/issues/15038
2023-10-19 12:00:54 -07:00
Tom DNetto
02908a2d8d appc: implement app connector Server type
This change refactors & moves the bulk of the app connector logic from
./cmd/sniproxy.

A future change will delete the delta in sniproxy and wire it to this type.

Signed-off-by: Tom DNetto <tom@tailscale.com>
Updates: https://github.com/tailscale/corp/issues/15038
2023-10-19 11:35:26 -07:00
Joe Tsai
469b7cabad cmd/tailscale: improve taildrop progress printer on Linux (#9878)
The progress printer was buggy where it would not print correctly
and some of the truncation logic was faulty.

The progress printer now prints something like:

	go1.21.3.linux-amd64.tar.gz               21.53MiB      13.83MiB/s     33.88%    ETA 00:00:03

where it shows
* the number of bytes transferred so far
* the rate of bytes transferred
  (using a 1-second half-life for an exponentially weighted average)
* the progress made as a percentage
* the estimated time
  (as calculated from the rate of bytes transferred)

Other changes:
* It now correctly prints the progress for very small files
* It prints at a faster rate (4Hz instead of 1Hz)
* It uses IEC units for byte quantities
  (to avoid ambiguities of "kb" being kilobits or kilobytes)

Updates tailscale/corp#14772

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2023-10-19 11:04:33 -07:00
Tyler Smalley
7a3ae39025 cmd/tailscale/cli: [serve/funnel] support omitting scheme for TCP (#9856)
The `serve` command for TCP  has always required the scheme of the target to be specified. However, when it's omitted the error message reported is misleading

```
error: failed to apply TCP serve: invalid TCP target "localhost:5900": missing port in address
```

Since we know the target is TCP, we shouldn't require it to be specified. This aligns with the changes for HTTP proxies in https://github.com/tailscale/tailscale/issues/8489

closes #9855

Signed-off-by: Tyler Smalley <tyler@tailscale.com>
2023-10-19 11:03:06 -07:00
Tyler Smalley
35376d52d4 cmd/tailscale/cli: [serve/funnel] provide correct command for disabling (#9859)
The `off` subcommand removes a serve/funnel for the corresponding type and port. Previously, we were not providing this which would result in an error if someone was using something than the default https=443.

closes #9858

Signed-off-by: Tyler Smalley <tyler@tailscale.com>
2023-10-19 10:46:44 -07:00
Irbe Krumina
f09cb45f9d ipn/ipnlocal: initiate proxy transport once (#9883)
Initiates http/h2c transport for userspace proxy
backend lazily and at most once.

Updates tailscale/tailscale#9725

Signed-off-by: Irbe Krumina <irbe@tailscale.com>
2023-10-19 18:38:37 +01:00
Sonia Appasamy
73bbf941f8 client/web: hook up auth flow
Connects serveTailscaleAuth to the localapi webclient endpoint
and pipes auth URLs and session cookies back to the browser to
redirect users from the frontend.

All behind debug flags for now.

Updates tailscale/corp#14335

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-10-19 13:26:22 -04:00
Irbe Krumina
09b5bb3e55 ipn/ipnlocal: proxy gRPC requests over h2c if needed. (#9847)
Updates userspace proxy to detect plaintext grpc requests
using the preconfigured host prefix and request's content
type header and ensure that these will be proxied over h2c.

Updates tailscale/tailscale#9725

Signed-off-by: Irbe Krumina <irbe@tailscale.com>
2023-10-19 07:12:31 +01:00
Jordan Whited
891d964bd4 wgengine/magicsock: simplify tryEnableUDPOffload() (#9872)
Don't assume Linux lacks UDP_GRO support if it lacks UDP_SEGMENT
support. This mirrors a similar change in wireguard/wireguard-go@177caa7
for consistency sake. We haven't found any issues here, just being
overly paranoid.

Updates #cleanup

Signed-off-by: Jordan Whited <jordan@tailscale.com>
2023-10-18 18:50:40 -07:00
Joe Tsai
d603d18956 taildrop: fix TestResume (#9874)
Previously, the test simply relied on:
	defer close()
to cleanup file handles.

This works fine on Unix-based systems,
but not on Windows, which dislikes deleting files
where an open file handle continues to exist.

Fix the test by explicitly closing the file handle
after we are done with the resource.

Updates tailscale/corp#14772

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2023-10-18 18:07:30 -07:00
Brad Fitzpatrick
cf27761265 cmd/tsconnect/wasm: add missing tstun.Wrapper.Start call
It's required as of the recent 5297bd2cff.

Updates #7894
Updates #9394 (sure would be nice)

Change-Id: Id6672408dd8a6c82dba71022c8763e589d789fcd
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-10-18 17:24:02 -07:00
Joe Tsai
cb00eac850 taildrop: disable TestResume (#9873)
This test is currently failing on Windows.

Updates tailscale/corp#14772

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2023-10-18 15:29:06 -07:00
Joe Tsai
674beabc73 syncs: add Map.LoadFunc (#9869)
The LoadFunc loads a value and calls a user-provided function.
The utility of this method is to ensure that the map lock is held
while executing user-provided logic.
This allows us to solve TOCTOU bugs that would be nearly imposible
to the solve without this API.

Updates tailscale/corp#14772

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2023-10-18 15:02:45 -07:00
James Tucker
afb72ecd73 .github/workflows: update golangci-lint
Updates #cleanup
Signed-off-by: James Tucker <james@tailscale.com>
2023-10-18 14:17:35 -07:00
Sonia Appasamy
851536044a client/web: add tests for authorizeRequest
Updates tailscale/corp#14335

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-10-18 16:44:25 -04:00
Maisem Ali
c3a8e63100 util/linuxfw: add additional nftable detection logic
We were previously using the netlink API to see if there are chains/rules that
already exist. This works fine in environments where there is either full
nftable support or no support at all. However, we have identified certain
environments which have partial nftable support and the only feasible way of
detecting such an environment is to try to create some of the chains that we
need.

This adds a check to create a dummy postrouting chain which is immediately
deleted. The goal of the check is to ensure we are able to use nftables and
that it won't error out later. This check is only done in the path where we
detected that the system has no preexisting nftable rules.

Updates #5621
Updates #8555
Updates #8762

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-10-18 13:39:55 -07:00
Maisem Ali
b47cf04624 util/linuxfw: fix broken tests
These tests were broken at HEAD. CI currently does not run these
as root, will figure out how to do that in a followup.

Updates #5621
Updates #8555
Updates #8762

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-10-18 13:39:55 -07:00
Joe Tsai
a8fbe284b2 taildrop: fix theoretical race condition (#9866)
WaitGroup.Wait should not be concurrently called WaitGroup.Add.
In other words, we should not start new goroutines after shutodwn is called.
Thus, add a conditional to check that shutdown has not been called
before starting off a new waitAndDelete goroutine.

Updates tailscale/corp#14772

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2023-10-18 10:21:36 -07:00
License Updater
756a4c43b6 licenses: update win/apple licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-10-18 09:43:23 -07:00
Joe Tsai
3f27087e9d taildrop: switch hashing to be streaming based (#9861)
While the previous logic was correct, it did not perform well.
Resuming is a dance between the client and server, where
1. the client requests hashes for a partial file,
2. the server then computes those hashes,
3. the client computes hashes locally and compares them.
4. goto 1 while the partial file still has data

While step 2 is running, the client is sitting idle.
While step 3 is running, the server is sitting idle.

By streaming over the block hash immediately after the server
computes it, the client can start checking the hash,
while the server works on the next hash (in a pipelined manner).
This performs dramatically better and also uses less memory
as we don't need to hold a list of hashes, but only need to
handle one hash at a time.

There are two detriments to this approach:
* The HTTP API relies on a JSON stream,
  which is not a standard REST-like pattern.
  However, since we implement both client and server,
  this is fine.
* While the stream is on-going, we hold an open file handle
  on the server side while the file is being hashed.
  On really slow streams, this could hold a file open forever.

Updates tailscale/corp#14772

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
Co-authored-by: Rhea Ghosh <rhea@tailscale.com>
2023-10-17 17:53:40 -07:00
Joe Tsai
7971333603 ipn: fix localapi and peerapi protocol for taildrop resume (#9860)
Minor fixes:
* The branch for listing or hashing partial files was inverted.
* The host for peerapi call needs to be real (rather than bogus).
* Handle remote peers that don't support resuming.
* Make resume failures non-fatal (since we can still continue).

This was tested locally, end-to-end system test is future work.

Updates tailscale/corp#14772

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
Co-authored-by: Rhea Ghosh <rhea@tailscale.com>
2023-10-17 16:14:47 -07:00
Andrew Lytvynov
77127a2494 clientupdate: fix background install for linux tarballs (#9852)
Two bug fixes:
1. when tailscale update is executed as root, `os.UserCacheDir` may
   return an error because `$XDG_CACHE_HOME` and `$HOME` are not set;
   fallback to `os.TempDir` in those cases
2. on some weird distros (like my EndeavourOS), `/usr/sbin` is just a
   symlink to `/usr/bin`; when we resolve `tailscale` binary path from
   `tailscaled`, allow `tailscaled` to be in either directory

Updates #755

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-10-17 14:24:06 -07:00
Sonia Appasamy
c27870e160 client/web: refactor authorizeRequest
Moves request authorization back into Server.serve to be run at
the start of any request. Fixes Synology unstable track bug where
client would get stuck unable to auth due to not rendering the
Synology redirect auth html on index.html load.

Updates tailscale/corp#14335

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-10-17 17:16:18 -04:00
Joe Tsai
c2a551469c taildrop: implement asynchronous file deletion (#9844)
File resumption requires keeping partial files around for some time,
but we must still eventually delete them if never resumed.
Thus, we implement asynchronous file deletion, which could
spawn a background goroutine to delete the files.

We also use the same mechanism for deleting files on Windows,
where a file can't be deleted if there is still an open file handle.
We can enqueue those with the asynchronous file deleter as well.

Updates tailscale/corp#14772

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2023-10-17 13:46:05 -07:00
Andrew Lytvynov
33bb2bbfe9 tailcfg,cmd/tailscale: add UrgentSecurityUpdate flag to ClientVersion (#9848)
This flag is used in clients to surface urgent updates more prominently.

Updates #755

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-10-17 11:04:44 -07:00
Irbe Krumina
cac290da87 cmd/k8s-operator: users can configure firewall mode for kube operator proxies (#9769)
* cmd/k8s-operator: users can configure operator to set firewall mode for proxies

Users can now pass PROXY_FIREWALL_MODE={nftables,auto,iptables} to operator to make it create ingress/egress proxies with that firewall mode

Also makes sure that if an invalid firewall mode gets configured, the operator will not start provisioning proxy resources, but will instead log an error and write an error event to the related Service.

Updates tailscale/tailscale#9310

Signed-off-by: Irbe Krumina <irbe@tailscale.com>
2023-10-17 18:05:02 +01:00
Tyler Smalley
ddb2a6eb8d cmd/tailscale: promote new serve/funnel CLI to be default (#9833)
The change is being kept to a minimum to make a revert easy if necessary. After the release, we will go back for a final cleanup.

updates #8489

Signed-off-by: Tyler Smalley <tyler@tailscale.com>
2023-10-17 09:32:17 -07:00
Maisem Ali
f53c3be07c cmd/k8s-operator: use our own container image instead of busybox
We already have sysctl in the `tailscale/tailscale` image, just use that.

Updates #cleanup

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-10-17 08:11:16 -07:00
Brad Fitzpatrick
1fc3573446 ipn/{conffile,ipnlocal}: start booting tailscaled from a config file w/ auth key
Updates #1412

Change-Id: Icd880035a31df59797b8379f4af19da5c4c453e2
Co-authored-by: Maisem Ali <maisem@tailscale.com>
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-10-17 07:12:49 -07:00
Brad Fitzpatrick
6ca8650c7b tstest/tstest: add t.Parallel that can be disabled by TS_SERIAL_TESTS=true
Updates #9841

Change-Id: I1b8f4d6e34ac8540e3b0455a7c79bd400e2721b7
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-10-16 21:05:59 -07:00
Brad Fitzpatrick
4dec0c6eb9 tstest, tstest/integration, github/workflows: shard integration tests
Over four jobs for now.

Updates #cleanup

Change-Id: Ic2b1a739a454916893945a3f9efc480d6fcbd70b
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-10-16 20:09:24 -07:00
Maisem Ali
e6ab7d3c14 cmd/testwrapper: parse args better
Previously we were just smushing together args and not trying
to parse the values at all. This resulted in the args to testwrapper
being limited and confusing.

This makes it so that testwrapper parses flags in the exact format as `go test`
command and passes them down in the provided order. It uses tesing.Init to
register flags that `go test` understands, however those are not the only
flags understood by `go test` (such as `-exec`) so we register these separately.

Updates tailscale/corp#14975

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-10-16 17:33:50 -07:00
Rhea Ghosh
9d3c6bf52e ipn/ipnlocal/peerapi: refactoring taildrop to just one endpoint (#9832)
Updates #14772

Signed-off-by: Rhea Ghosh <rhea@tailscale.com>
2023-10-16 14:35:11 -05:00
Maisem Ali
4899c2c1f4 cmd/containerboot: revert to using tailscale up
This partially reverts commits a61a9ab087
and 7538f38671 and fully reverts
4823a7e591.

The goal of that commit was to reapply known config whenever the
container restarts. However, that already happens when TS_AUTH_ONCE was
false (the default back then). So we only had to selectively reapply the
config if TS_AUTH_ONCE is true, this does exactly that.

This is a little sad that we have to revert to `tailscale up`, but it
fixes the backwards incompatibility problem.

Updates tailscale/tailscale#9539

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-10-16 12:00:44 -07:00
Andrew Lytvynov
b949e208bb ipn/ipnlocal: fix AllowsUpdate disable after enable (#9827)
The old code would always retain value `true` if it was set once, even
if you then change `prefs.AutoUpdate.Apply` to `false`.
Instead of using the previous value, use the default (envknob) value to
OR with.

Updates #755

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-10-16 10:54:56 -07:00
Brad Fitzpatrick
18bd98d35b cmd/tailscaled,*: add start of configuration file support
Updates #1412

Co-authored-by: Maisem Ali <maisem@tailscale.com>
Change-Id: I38d559c1784d09fc804f521986c9b4b548718f7d
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-10-16 10:40:27 -07:00
Rhea Ghosh
71271e41d6 ipn/{ipnlocal/peerapi, localapi} initial taildrop resume api plumbing (#9798)
This change:
* adds a partial files peerAPI endpoint to get a list of partial files
* adds a helper function to extract the basename of a file
* updates the peer put peerAPI endpoint
* updates the file put localapi endpoint to allow resume functionality

Updates #14772

Signed-off-by: Rhea Ghosh <rhea@tailscale.com>
2023-10-16 12:36:31 -05:00
Brad Fitzpatrick
95faefd1f6 net/dnsfallback: disable recursive resolver for now
It seems to be implicated in a CPU consumption bug that's not yet
understood. Disable it until we understand.

Updates tailscale/corp#15261

Change-Id: Ia6d0c310da6464dda79a70fc3c18be0782812d3f
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-10-16 09:47:08 -07:00
Andrew Lytvynov
8a5b02133d clientupdate: return ErrUnsupported for macSys clients (#9793)
The Sparkle-based update is not quite working yet. Make `NewUpdater`
return `ErrUnsupported` for it to avoid the proliferation of exceptions
up the stack.

Updates #755

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-10-16 09:14:14 -07:00
Flakes Updater
51078b6486 go.mod.sri: update SRI hash for go.mod changes
Signed-off-by: Flakes Updater <noreply+flakes-updater@tailscale.com>
2023-10-16 09:12:16 -07:00
Brad Fitzpatrick
7fd6cc3caa go.mod: bump alexbrainman/sspi
For https://github.com/alexbrainman/sspi/pull/13

Fixes #9131 (hopefully)

Change-Id: I27bb00bbf5e03850f65f18c45f15c4441cc54b23
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-10-16 09:10:27 -07:00
Sonia Appasamy
feabb34ea0 ipn/localapi: add debug-web-client endpoint
Debug endpoint for the web client's auth flow to talk back to the
control server. Restricted behind a feature flag on control.

We will either be removing this debug endpoint, or renaming it
before launching the web client updates.

Updates tailscale/corp#14335

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-10-16 10:52:23 -04:00
Kristoffer Dalby
e06f2f1873 ipn/ipnlocal: change serial number policy to be PreferenceOption
This commit changes the PostureChecking syspolicy key to be a
PreferenceOption(user-defined, always, never) instead of Bool.

This aligns better with the defaults implementation on macOS allowing
CLI arguments to be read when user-defined or no defaults is set.

Updates #tailscale/tailscale/5902

Signed-off-by: Kristoffer Dalby <kristoffer@tailscale.com>
2023-10-16 16:01:54 +02:00
Denton Gentry
97ee3891f1 net/dns: use direct when NetworkManager has no systemd-resolved
Endeavour OS, at least, uses NetworkManager 1.44.2 and does
not use systemd-resolved behind the scenes at all. If we
find ourselves in that situation, return "direct" not
"systemd-resolved"

Fixes https://github.com/tailscale/tailscale/issues/9687

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2023-10-15 17:12:49 -07:00
Brad Fitzpatrick
56ebcd1ed4 .github/workflows: break up race builder a bit more
Move the compilation of everything to its own job too, separate
from test execution.

Updates #7894

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-10-14 19:28:31 -07:00
Brad Fitzpatrick
e89927de2b tsnet: fix data race in TestFallbackTCPHandler
Fixes #9805

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-10-14 19:12:43 -07:00
Brad Fitzpatrick
18e2936d25 github/workflows: move race tests to their own job
They're slow. Make them their own job that can run in parallel.

Also, only run them in race mode. No need to run them on 386
or non-race amd64.

Updates #7894

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-10-14 14:08:58 -07:00
Brad Fitzpatrick
c363b9055d tstest/integration: add tests for tun mode (requiring root)
Updates #7894

Change-Id: Iff0b07b21ae28c712dd665b12918fa28d6f601d0
Co-authored-by: Maisem Ali <maisem@tailscale.com>
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-10-14 13:52:30 -07:00
Brad Fitzpatrick
a6270826a3 wgengine/magicsock: fix data race regression in disco ping callbacks
Regression from c15997511d. The callback could be run multiple times
from different endpoints.

Fixes #9801

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-10-14 13:52:30 -07:00
Maisem Ali
5297bd2cff cmd/tailscaled,net/tstun: fix data race on start-up in TUN mode
Fixes #7894

Change-Id: Ice3f8019405714dd69d02bc07694f3872bb598b8

Co-authored-by: Brad Fitzpatrick <bradfitz@tailscale.com>
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-10-14 08:54:30 -07:00
Brad Fitzpatrick
5c555cdcbb tstest/integration: set race flag when cross compiling, conditionally fail on race
Misc cleanups and things noticed while working on #7894 and pulled out
of a separate change. Submitting them on their own to not distract
from later changes.

Updates #7894

Change-Id: Ie9abc8b88f121c559aeeb7e74db2aa532eb84d3d
Co-authored-by: Maisem Ali <maisem@tailscale.com>
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-10-13 20:01:32 -07:00
Rhea Ghosh
8c7169105e ipn/{ipnlocal/peerapi, localapi}: cleaning up http statuses for consistency and readability (#9796)
Updates #cleanup

Signed-off-by: Rhea Ghosh <rhea@tailscale.com>
2023-10-13 17:40:10 -05:00
Joe Tsai
9cb6c5bb78 util/httphdr: add new package for parsing HTTP headers (#9797)
This adds support for parsing Range and Content-Range headers
according to RFC 7230. The package could be extended in the future
to handle other headers.

Updates tailscale/corp#14772

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2023-10-13 15:38:22 -07:00
Andrew Lytvynov
af5a586463 ipn/ipnlocal: include AutoUpdate prefs in HostInfo.AllowsUpdate (#9792)
Updates #9260

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-10-13 11:14:23 -07:00
Claire Wang
754fb9a8a8 tailcfg: add tailnet field to register request (#9675)
Updates tailscale/corp#10967

Signed-off-by: Claire Wang <claire@tailscale.com>
2023-10-13 14:13:41 -04:00
Joe Tsai
8f948638c5 taildrop: minor cleanups and fixes (#9786)
Perform the same m==nil check in Manager.{PartialFiles,HashPartialFile}
as we do in the other methods.

Fix HashPartialFile is properly handle a length of -1.

Updates tailscale/corp#14772

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2023-10-13 10:21:15 -05:00
Joe Tsai
b1867eb23f taildrop: add logic for resuming partial files (#9785)
We add the following API:
* type FileChecksums
* type Checksum
* func Manager.PartialFiles
* func Manager.HashPartialFile
* func ResumeReader

The Manager methods provide the ability to query for partial files
and retrieve a list of checksums for a given partial file.
The ResumeReader function is a helper that wraps an io.Reader
to discard content that is identical locally and remotely.
The FileChecksums type represents the checksums of a file
and is safe to JSON marshal and send over the wire.

Updates tailscale/corp#14772

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
Co-authored-by: Rhea Ghosh <rhea@tailscale.com>
2023-10-12 16:50:11 -07:00
Maisem Ali
24f322bc43 ipn/ipnlocal: do unexpired cert renewals in the background
We were eagerly doing a synchronous renewal of the cert while
trying to serve traffic. Instead of that, just do the cert
renewal in the background and continue serving traffic as long
as the cert is still valid.

This regressed in c1ecae13ab when
we introduced ARI support and were trying to make the experience
of `tailscale cert` better. However, that ended up regressing
the experience for tsnet as it would not always doing the renewal
synchronously.

Fixes #9783

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-10-12 16:02:45 -07:00
Joe Tsai
1a78f240b5 tstime: add DefaultClock (#9691)
In almost every single use of Clock, there is a default behavior
we want to use when the interface is nil,
which is to use the the standard time package.

The Clock interface exists only for testing,
and so tests that care about mocking time
can adequately plumb the the Clock down the stack
and through various data structures.

However, the problem with Clock is that there are many
situations where we really don't care about mocking time
(e.g., measuring execution time for a log message),
where making sure that Clock is non-nil is not worth the burden.
In fact, in a recent refactoring, the biggest pain point was
dealing with nil-interface panics when calling tstime.Clock methods
where mocking time wasn't even needed for the relevant tests.
This required wasted time carefully reviewing the code to
make sure that tstime.Clock was always populated,
and even then we're not statically guaranteed to avoid a nil panic.

Ideally, what we want are default methods on Go interfaces,
but such a language construct does not exist.
However, we can emulate that behavior by declaring
a concrete type that embeds the interface.
If the underlying interface value is nil,
it provides some default behavior (i.e., use StdClock).

This provides us a nice balance of two goals:
* We can plumb tstime.DefaultClock in all relevant places
  for use with mocking time in the tests that care.
* For all other logic that don't care about,
  we never need to worry about whether tstime.DefaultClock
  is nil or not. This is especially relevant in production code
  where we don't want to panic.

Longer-term, we may want to perform a large-scale change
where we rename Clock to ClockInterface
and rename DefaultClock to just Clock.

Updates #cleanup

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2023-10-12 16:01:17 -07:00
Naman Sood
7783a960e8 client/web: add metric for exit node advertising (#9781)
* client/web: add metric for exit node advertising

Updates tailscale/corp#15215

Signed-off-by: Naman Sood <mail@nsood.in>

* client/web: use http request's context for IncrementCounter

Updates #cleanup

Signed-off-by: Naman Sood <mail@nsood.in>

---------

Signed-off-by: Naman Sood <mail@nsood.in>
2023-10-12 17:02:20 -04:00
James Tucker
ce0830837d appctype: introduce a configuration schema for app connectors
Updates tailscale/corp#15043

Signed-off-by: James Tucker <james@tailscale.com>
2023-10-12 10:49:23 -07:00
Joe Tsai
37c646d9d3 taildrop: improve the functionality and reliability of put (#9762)
Changes made:
* Move all HTTP related functionality from taildrop to ipnlocal.
* Add two arguments to taildrop.Manager.PutFile to specify
  an opaque client ID and a resume offset (both unused for now).
* Cleanup the logic of taildrop.Manager.PutFile
  to be easier to follow.
* Implement file conflict handling where duplicate files are renamed
  (e.g., "IMG_1234.jpg" -> "IMG_1234 (2).jpg").
* Implement file de-duplication where "renaming" a partial file
  simply deletes it if it already exists with the same contents.
* Detect conflicting active puts where a second concurrent put
  results in an error.

Updates tailscale/corp#14772

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
Co-authored-by: Rhea Ghosh <rhea@tailscale.com>
2023-10-12 09:28:46 -07:00
Maisem Ali
1294b89792 cmd/k8s-operator: allow setting same host value for tls and ingress rules
We were too strict and required the user not specify the host field at all
in the ingress rules, but that degrades compatibility with existing helm charts.

Relax the constraint so that rule.Host can either be empty, or match the tls.Host[0]
value exactly.

Fixes #9548

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-10-12 06:40:52 -07:00
Maisem Ali
2d4f808a4c cmd/containerboot: fix time based serveConfig watcher
This broke in a last minute refactor and seems to have never worked.

Fixes #9686

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-10-12 06:36:40 -07:00
James Tucker
4abd470322 tailcfg: implement text encoding for ProtoPortRange
Updates tailscale/corp#15043
Signed-off-by: James Tucker <james@tailscale.com>
2023-10-11 23:59:42 -07:00
James Tucker
96f01a73b1 tailcfg: import ProtoPortRange for local use
Imported type and parsing, with minor modifications.

Updates tailscale/corp#15043

Signed-off-by: James Tucker <james@tailscale.com>
2023-10-11 23:46:39 -07:00
Charlotte Brandhorst-Satzkorn
d62af8e643 words: flappy birds, but real life
These birds have been visually identified as having tails. Science
prevails.

Updates tailscale/corp#9599

Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2023-10-11 22:39:30 -07:00
Maisem Ali
1cb9e33a95 cmd/k8s-operator: update env var in manifest to APISERVER_PROXY
Replace the deprecated var with the one in docs to avoid confusion.
Introduced in 335a5aaf9a.

Updates #8317
Fixes #9764

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-10-11 21:55:46 -07:00
James Tucker
c1ef55249a types/ipproto: import and test string parsing for ipproto
IPProto has been being converted to and from string formats in multiple
locations with variations in behavior. TextMarshaller and JSONMarshaller
implementations are now added, along with defined accepted and preferred
formats to centralize the logic into a single cross compatible
implementation.

Updates tailscale/corp#15043
Fixes tailscale/corp#15141

Signed-off-by: James Tucker <james@tailscale.com>
2023-10-11 18:56:33 -07:00
Maisem Ali
319607625f ipn/ipnlocal: fix log spam from now expected paths
These log paths were actually unexpected until the refactor in
fe95d81b43. This moves the logs
to the callsites where they are actually unexpected.

Fixes #9670

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-10-11 14:53:58 -07:00
Maisem Ali
9d96e05267 net/packet: split off checksum munging into different pkg
The current structure meant that we were embedding netstack in
the tailscale CLI and in the GUIs. This removes that by isolating
the checksum munging to a different pkg which is only called from
`net/tstun`.

Fixes #9756

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-10-11 14:25:58 -07:00
Brad Fitzpatrick
8b630c91bc wgengine/filter: use slices.Contains in another place
We keep finding these.

Updates #cleanup

Change-Id: Iabc049b0f8da07341011356f0ecd5315c33ff548
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-10-11 14:16:52 -07:00
James 'zofrex' Sanderson
0a412eba40 words: Na na na na na na na na na na na na na na na na (#9753)
So gnarly!

Updates tailscale/corp#14698

Signed-off-by: James Sanderson <jsanderson@tailscale.com>
2023-10-11 22:15:53 +01:00
James Tucker
11348fbe72 util/nocasemaps: import nocasemaps from corp
This is a dependency of other code being imported later.

Updates tailscale/corp#15043

Signed-off-by: James Tucker <james@tailscale.com>
2023-10-11 13:55:00 -07:00
Maisem Ali
fbfee6a8c0 cmd/containerboot: use linuxfw.NetfilterRunner
This migrates containerboot to reuse the NetfilterRunner used
by tailscaled instead of manipulating iptables rule itself.
This has the added advantage of now working with nftables and
we can potentially drop the `iptables` command from the container
image in the future.

Updates #9310

Co-authored-by: Irbe Krumina <irbe@tailscale.com>
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-10-11 12:23:52 -07:00
Sonia Appasamy
7a0de2997e client/web: remove unused context param from NewServer
Updates tailscale/corp#14335

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-10-11 15:06:26 -04:00
Maisem Ali
aad3584319 util/linuxfw: move fake runner into pkg
This allows using the fake runner in different packages
that need to manage filter rules.

Updates #cleanup

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-10-11 11:48:43 -07:00
Tom DNetto
fffafc65d6 tsnet: support registering fallback TCP flow handlers
For the app connector use-case, it doesnt make sense to use listeners, because then you would
need to register thousands of listeners (for each proto/service/port combo) to handle ranges.

Instead, we plumb through the TCPHandlerForFlow abstraction, to avoid using the listeners
abstraction that would end up being a bit messy.

Signed-off-by: Tom DNetto <tom@tailscale.com>
Updates: https://github.com/tailscale/corp/issues/15038
2023-10-11 11:29:29 -07:00
David Anderson
9f05018419 clientupdate/distsign: add new prod root signing key to keychain
Updates tailscale/corp#15179

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-10-11 09:20:17 -07:00
Galen Guyer
04a8b8bb8e net/dns: properly detect newer debian resolvconf
Tailscale attempts to determine if resolvconf or openresolv
is in use by running `resolvconf --version`, under the assumption
this command will error when run with Debian's resolvconf. This
assumption is no longer true and leads to the wrong commands being
run on newer versions of Debian with resolvconf >= 1.90. We can
now check if the returned version string starts with "Debian resolvconf"
if the command is successful.

Fixes #9218

Signed-off-by: Galen Guyer <galen@galenguyer.com>
2023-10-11 08:38:25 -07:00
Paul Scott
4e083e4548 util/cmpver: only consider ascii numerals (#9741)
Fixes #9740

Signed-off-by: Paul Scott <paul@tailscale.com>
2023-10-11 13:42:32 +01:00
Maisem Ali
78a083e144 types/ipproto: drop IPProto from IPProtoVersion
Based on https://github.com/golang/go/wiki/CodeReviewComments#package-names.

Updates #cleanup

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-10-10 23:44:48 -07:00
Maisem Ali
05a1f5bf71 util/linuxfw: move detection logic
Just a refactor to consolidate the firewall detection logic in a single
package so that it can be reused in a later commit by containerboot.

Updates #9310

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-10-10 20:29:24 -07:00
Maisem Ali
56c0a75ea9 tool/gocross: handle VERSION file not found
Fixes #9734

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-10-10 17:55:33 -07:00
James Tucker
ba6ec42f6d util/linuxfw: add missing input rule to the tailscale tun
Add an explicit accept rule for input to the tun interface, as a mirror
to the explicit rule to accept output from the tun interface.

The rule matches any packet in to our tun interface and accepts it, and
the rule is positioned and prioritized such that it should be evaluated
prior to conventional ufw/iptables/nft rules.

Updates #391
Fixes #7332
Updates #9084

Signed-off-by: James Tucker <james@tailscale.com>
2023-10-10 17:22:47 -07:00
Andrew Lytvynov
677d486830 clientupdate: abort if current version is newer than latest (#9733)
This is only relevant for unstable releases and local builds. When local
version is newer than upstream, abort release.

Also, re-add missing newlines in output that were missed in
https://github.com/tailscale/tailscale/pull/9694.

Updates #cleanup

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-10-10 17:01:44 -07:00
Will Norris
7f08bddfe1 tailcfg: add type for web client auth response
This will be returned from the upcoming control endpoints for doing web
client session authentication.

Updates tailscale/corp#14335

Signed-off-by: Will Norris <will@tailscale.com>
2023-10-10 15:13:50 -07:00
Flakes Updater
00977f6de9 go.mod.sri: update SRI hash for go.mod changes
Signed-off-by: Flakes Updater <noreply+flakes-updater@tailscale.com>
2023-10-10 14:43:58 -07:00
License Updater
0ccfcb515c licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-10-10 14:43:50 -07:00
Brad Fitzpatrick
3749a3bbbb go.toolchain.rev: bump for CVE-2023-39325
Updates tailscale/corp#15165

Change-Id: Ib001cfb44eb3e6d735dfece9bd3ae9eea13048c9
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-10-10 11:46:38 -07:00
Brad Fitzpatrick
6b1ed732df go.mod: bump x/net to 0.17 for CVE-2023-39325
https://go.googlesource.com/net/+/b225e7ca6dde1ef5a5ae5ce922861bda011cfabd

Updates tailscale/corp#15165

Change-Id: Ia8b5e16b1acfe1b2400d321034b41370396f70e2
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-10-10 11:25:24 -07:00
Brad Fitzpatrick
70de16bda7 ipn/localapi: make whois take IP or IP:port as documented, fix capmap netstack lookup
The whois handler was documented as taking IP (e.g. 100.101.102.103)
or IP:port (e.g. usermode 127.0.0.1:1234) but that got broken at some point
and we started requiring a port always. Fix that.

Also, found in the process of adding tests: fix the CapMap lookup in
userspace mode (it was always returning the caps of 127.0.0.1 in
userspace mode). Fix and test that too.

Updates #9714

Change-Id: Ie9a59744286522fa91c4b70ebe89a1e94dbded26
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-10-10 11:05:04 -07:00
Kristoffer Dalby
7f540042d5 ipn/ipnlocal: use syspolicy to determine collection of posture data
Updates #5902

Signed-off-by: Kristoffer Dalby <kristoffer@tailscale.com>
2023-10-10 12:04:34 +02:00
Kristoffer Dalby
d0b8bdf8f7 posture: add get serial support for macOS
Updates #5902

Signed-off-by: Kristoffer Dalby <kristoffer@tailscale.com>
2023-10-09 14:46:59 +02:00
Kristoffer Dalby
9eedf86563 posture: add get serial support for Windows/Linux
This commit adds support for getting serial numbers from SMBIOS
on Windows/Linux (and BSD) using go-smbios.

Updates #5902

Signed-off-by: Kristoffer Dalby <kristoffer@tailscale.com>
2023-10-09 13:50:34 +02:00
Val
249edaa349 wgengine/magicsock: add probed MTU metrics
Record the number of MTU probes sent, the total bytes sent, the number of times
we got a successful return from an MTU probe of a particular size, and the max
MTU recorded.

Updates #311

Signed-off-by: Val <valerie@tailscale.com>
2023-10-09 01:57:12 -07:00
Val
893bdd729c disco,net/tstun,wgengine/magicsock: probe peer MTU
Automatically probe the path MTU to a peer when peer MTU is enabled, but do not
use the MTU information for anything yet.

Updates #311

Signed-off-by: Val <valerie@tailscale.com>
2023-10-09 01:57:12 -07:00
Kristoffer Dalby
b4e587c3bd tailcfg,ipn: add c2n endpoint for posture identity
Updates #5902

Signed-off-by: Kristoffer Dalby <kristoffer@tailscale.com>
2023-10-09 08:15:38 +02:00
Kristoffer Dalby
9593cd3871 posture: add get serial stub for all platforms
Updates #5902

Signed-off-by: Kristoffer Dalby <kristoffer@tailscale.com>
2023-10-09 08:15:38 +02:00
Kristoffer Dalby
623926a25d cmd/tailscale: add --posture-checking flag to set
Updates #5902

Signed-off-by: Kristoffer Dalby <kristoffer@tailscale.com>
2023-10-09 08:15:38 +02:00
Kristoffer Dalby
886917c42b ipn: add PostureChecks to Prefs
Updates #5902

Signed-off-by: Kristoffer Dalby <kristoffer@tailscale.com>
2023-10-09 08:15:38 +02:00
Simon Leonhardt
553f657248 sniproxy allows configuration of hostname
Signed-off-by: Simon Leonhardt <simon@controlzee.com>
2023-10-08 15:53:52 -07:00
Brad Fitzpatrick
6f36f8842c cmd/tailscale, magicsock: add debug command to flip DERP homes
For testing netmap patchification server-side.

Updates #1909

Change-Id: Ib1d784bd97b8d4a31e48374b4567404aae5280cc
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-10-06 20:48:13 -07:00
James Tucker
13767e5108 docs/sysv: add a sysv style init script
The script depends on a sufficiently recent start-stop-daemon as to
provide the `-m` and `--remove-pidfile` flags.

Updates #9502

Signed-off-by: James Tucker <james@tailscale.com>
2023-10-06 19:35:58 -07:00
Brad Fitzpatrick
f991c8a61f tstest: make ResourceCheck panic on parallel tests
To find potential flakes earlier.

Updates #deflake-effort

Change-Id: I52add6111d660821c3a23d4b1dd032821344bc48
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-10-06 19:12:34 -07:00
James Tucker
498f7ec663 syncs: add Map.LoadOrInit for lazily initialized values
I was reviewing some code that was performing this by hand, and wanted
to suggest using syncs.Map, however as the code in question was
allocating a non-trivial structure this would be necessary to meet the
target.

Updates #cleanup

Signed-off-by: James Tucker <james@tailscale.com>
2023-10-06 17:06:11 -07:00
Joe Tsai
e4cb83b18b taildrop: document and cleanup the package (#9699)
Changes made:
* Unexport declarations specific to internal taildrop functionality.
* Document all exported functionality.
* Move TestRedactErr to the taildrop package.
* Rename and invert Handler.DirectFileDoFinalRename as AvoidFinalRename.

Updates tailscale/corp#14772

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2023-10-06 15:41:14 -07:00
Andrew Lytvynov
e6aa7b815d clientupdate,cmd/tailscale/cli: use cli.Stdout/Stderr (#9694)
In case cli.Stdout/Stderr get overriden, all CLI output should use them
instead of os.Stdout/Stderr. Update the `update` command to follow this
pattern.

Updates #cleanup

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-10-06 12:00:15 -07:00
Brad Fitzpatrick
b7988b3825 api.md: remove clientConnectivity.derp field
We don't actually send this. It's always been empty.

Updates tailscale/corp#13400

Change-Id: I99b3d7a355fca17d2159bf81ede5be4ddd4b9dc9
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-10-06 09:29:42 -07:00
Rhea Ghosh
557ddced6c {ipn/ipnlocal, taildrop}: move put logic to taildrop (#9680)
Cleaning up taildrop logic for sending files.

Updates tailscale/corp#14772

Signed-off-by: Rhea Ghosh <rhea@tailscale.com>
Co-authored-by: Joe Tsai <joetsai@digital-static.net>
2023-10-06 09:47:03 -05:00
David Anderson
c761d102ea tool/gocross: don't absorb --tags flags passed to subcommand
Fixes tailscale/corp#15117

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-10-05 17:11:03 -07:00
Andrew Lytvynov
559f560d2d go.toolchain.rev: bump go to 1.21.2 (#9677)
Updates https://github.com/tailscale/go/pull/75

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-10-05 17:04:07 -07:00
Joe Tsai
c42398b5b7 ipn/ipnlocal: cleanup incomingFile (#9678)
This is being moved to taildrop, so clean it up to stop depending
on so much unreleated functionality by removing a dependency
on peerAPIHandler.

Updates tailscale/corp#14772

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
Co-authored-by: Rhea Ghosh <rhea@tailscale.com>
2023-10-05 16:26:06 -07:00
Andrew Lytvynov
3ee756757b cmd/tailscale/cli: add update notification to "up" (#9644)
Add available update message in "tailscale up" output. Also update the
message in "tailscale status" to match and mention auto-update.

Updates https://github.com/tailscale/tailscale/issues/755

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-10-05 16:21:06 -07:00
Rhea Ghosh
dc1c7cbe3e taildrop: initial commit of taildrop functionality refactoring (#9676)
Over time all taildrop functionality will be contained in the
taildrop package. This will include end to end unit tests. This is
simply the first smallest piece to move over.

There is no functionality change in this commit.

Updates tailscale/corp#14772

Signed-off-by: Rhea Ghosh <rhea@tailscale.com>
Co-authored-by: Joseph Tsai <joetsai@tailscale.com>
2023-10-05 16:05:45 -07:00
Sonia Appasamy
3befc0ef02 client/web: restrict full management client behind browser sessions
Adds `getTailscaleBrowserSession` to pull the user's session out of
api requests, and `serveTailscaleAuth` to provide the "/api/auth"
endpoint for browser to request auth status and new sessions.

Updates tailscale/corp#14335

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-10-05 17:21:39 -04:00
Brad Fitzpatrick
7868393200 net/dns/resolver, ipnlocal: fix ExitDNS on Android and iOS
Advertise it on Android (it looks like it already works once advertised).

And both advertise & likely fix it on iOS. Yet untested.

Updates #9672

Change-Id: If3b7e97f011dea61e7e75aff23dcc178b6cf9123
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-10-05 12:55:07 -07:00
Brad Fitzpatrick
b4816e19b6 hostinfo, ipnlocal: flesh out Wake-on-LAN support, send MACs, add c2n sender
This optionally uploads MAC address(es) to control, then adds a
c2n handler so control can ask a node to send a WoL packet.

Updates #306

RELNOTE=now supports waking up peer nodes on your LAN via Wake-on-LAN packets

Change-Id: Ibea1275fcd2048dc61d7059039abfbaf1ad4f465
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-10-05 11:51:29 -07:00
Tom DNetto
da1b917575 net/tstun: finish wiring IPv6 NAT support
Updates https://github.com/tailscale/corp/issues/11202
Updates ENG-991
Signed-off-by: Tom DNetto <tom@tailscale.com>
2023-10-04 16:07:05 -07:00
Brad Fitzpatrick
52e4f24c58 portlist: populate Pid field on Linux
The Port.Pid was always more of an implementation detail on some
platforms and isn't necessary on Linux so it was never populated.
(Nothing outside the portlist package ever used it)

But might as well populate it for consistency since we have it in
memory and its absence confused people.

Updates #cleanup

Change-Id: I869768a75c9fedeff242a5452206e2b2947a17cb
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-10-04 13:28:08 -07:00
Sonia Appasamy
b29047bcf0 client/web: add browser session cache to web.Server
Adds browser session cache, to be used to store sessions for the
full management web client.

Updates tailscale/corp#14335

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-10-04 13:44:41 -04:00
Brad Fitzpatrick
e499a6bae8 release/dist/unixpkgs: revert iptables move to Recommends, make it Depends
Partially reverts 1bd3edbb46 (but keeps part of it)

iptables is almost always required but not strictly needed.  Even if
you can technically run Tailscale without it (by manually configuring
nftables or userspace mode), we still now mark this as "Depends"
because our previous experiment in
https://github.com/tailscale/tailscale/issues/9236 of making it only
Recommends caused too many problems. Until our nftables table is more
mature, we'd rather err on the side of wasting a little disk by
including iptables for people who might not need it rather than
handle reports of it being missing.

Updates #9236

Change-Id: I86cc8aa3f78dafa0b4b729f55fb82eef6066be1c
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-10-04 08:56:42 -07:00
Brad Fitzpatrick
93c6e1d53b tstest/deptest: add check that x/exp/{maps,slices} imported as xfoo
Updates #cleanup

Change-Id: I4cbb5e477c739deddf7a46b66f286c9fdb106279
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-10-03 19:40:57 -07:00
Andrew Dunham
91b9899402 net/dns/resolver: fix flaky test
Updates #cleanup

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I2d073220bb6ac78ba88d8be35085cc23b727d69f
2023-10-03 22:23:05 -04:00
Brad Fitzpatrick
730cdfc1f7 Revert "tool/gocross: disable Linux static linking if GOCROSS_STATIC=0"
This reverts commit 2c0f0ee759.

Fixed by efac2cb8d6

Updates tailscale/corp#15058
Updates tailscale/corp#13113
2023-10-03 19:13:58 -07:00
Maisem Ali
3655fb3ba0 control/controlclient: fix deadlock in shutdown
Fixes a deadlock observed in a different repo.
Regressed in 5b3f5eabb5.

Updates tailscale/corp#14950
Updates tailscale/corp#14515
Updates tailscale/corp#14139
Updates tailscale/corp#13175

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-10-03 18:02:55 -07:00
Andrew Dunham
5902d51ba4 util/race: add test to confirm we don't leak goroutines
Updates #cleanup

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: Iff147268db50251d498fff5213adb8d4b8c999d4
2023-10-03 18:44:22 -04:00
Andrew Dunham
286c6ce27c net/dns/resolver: race UDP and TCP queries (#9544)
Instead of just falling back to making a TCP query to an upstream DNS
server when the UDP query returns a truncated query, also start a TCP
query in parallel with the UDP query after a given race timeout. This
ensures that if the upstream DNS server does not reply over UDP (or if
the response packet is blocked, or there's an error), we can still make
queries if the server replies to TCP queries.

This also adds a new package, util/race, to contain the logic required for
racing two different functions and returning the first non-error answer.

Updates tailscale/corp#14809

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I4311702016c1093b1beaa31b135da1def6d86316
2023-10-03 16:26:38 -04:00
Jordan Whited
eb22c0dfc7 wgengine/magicsock: use binary.NativeEndian for UDP GSO control data (#9640)
Updates #cleanup

Signed-off-by: Jordan Whited <jordan@tailscale.com>
2023-10-03 13:26:03 -07:00
Brad Fitzpatrick
efac2cb8d6 tool/gocross: merge user's build tags and implicitly added build tags together
Fixes tailscale/corp#15058

Change-Id: I7e539b3324153077597f30385a2cb540846e8bdc
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-10-03 13:08:34 -07:00
Brad Fitzpatrick
b775a3799e util/httpm, all: add a test to make sure httpm is used consistently
Updates #cleanup

Change-Id: I7dbf8a02de22fc6b317ab5e29cc97792dd75352c
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-10-03 09:26:13 -07:00
Val
73e53dcd1c cmd/tailscale,ipn/ipnlocal: print debug component names
Make the 'tailscale debug component-logs' command print the component names for
which extra logging can be turned on, for easier discoverability of debug
functions.

Updates #cleanup

Co-authored-by: Paul Scott <paul@tailscale.com>
Signed-off-by: Val <valerie@tailscale.com>
2023-10-03 06:07:34 -07:00
License Updater
5efd5e093e licenses: update win/apple licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-10-02 12:24:04 -07:00
License Updater
6cbd002eda licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-10-02 12:23:21 -07:00
Tom DNetto
656a77ab4e net/packet: implement methods for rewriting v6 addresses
Implements the ability for the address-rewriting code to support rewriting IPv6 addresses.

Specifically, UpdateSrcAddr & UpdateDstAddr.

Signed-off-by: Tom DNetto <tom@tailscale.com>
Updates https://github.com/tailscale/corp/issues/11202
2023-10-02 11:13:27 -07:00
Val
c26d91d6bd net/tstun: remove unused function DefaultMTU()
Now that corp is updated, remove the shim code to bridge the rename from
DefaultMTU() to DefaultTUNMTU.

Updates #311

Signed-off-by: Val <valerie@tailscale.com>
2023-10-02 10:12:45 -07:00
Val
4130851f12 wgengine/magicsock: probe but don't use path MTU from CLI ping
When sending a CLI ping with a specific size, continue to probe all possible UDP
paths to the peer until we find one with a large enough MTU to accommodate the
ping. Record any peer path MTU information we discover (but don't use it for
anything other than CLI pings).

Updates #311

Signed-off-by: Val <valerie@tailscale.com>
2023-10-02 03:52:02 -07:00
Val
67926ede39 wgengine/magicsock: add MTU to addrLatency and rename to addrQuality
Add a field to record the wire MTU of the path to this address to the
addrLatency struct and rename it addrQuality.

Updates #311

Signed-off-by: Val <valerie@tailscale.com>
2023-10-02 03:52:02 -07:00
Brad Fitzpatrick
425cf9aa9d tailcfg, all: use []netip.AddrPort instead of []string for Endpoints
It's JSON wire compatible.

Updates #cleanup

Change-Id: Ifa5c17768fec35b305b06d75eb5f0611c8a135a6
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-10-01 18:23:02 -07:00
Brad Fitzpatrick
5f5c9142cc util/slicesx: add EqualSameNil, like slices.Equal but same nilness
Then use it in tailcfg which had it duplicated a couple times.

I think we have it a few other places too.

And use slices.Equal in wgengine/router too. (found while looking for callers)

Updates #cleanup

Change-Id: If5350eee9b3ef071882a3db29a305081e4cd9d23
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-30 18:56:15 -07:00
Flakes Updater
72e53749c1 go.mod.sri: update SRI hash for go.mod changes
Signed-off-by: Flakes Updater <noreply+flakes-updater@tailscale.com>
2023-09-30 11:05:42 -07:00
Brad Fitzpatrick
d2ea9bb1eb cmd/cloner: fix typo in test type's name
s/SliceContianer/SliceContainer/g

Updates #9604

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-30 10:18:18 -07:00
James Tucker
ab810f1f6d cmd/cloner: add regression test for slice nil/empty semantics
We had a misstep with the semantics when applying an optimization that
showed up in the roll into corp. This test ensures that case and related
cases must be retained.

Updates #9410
Updates #9601
Signed-off-by: James Tucker <james@tailscale.com>
2023-09-29 19:00:40 -07:00
James Tucker
e03f0d5f5c net/dnsfallback: remove net/dnsfallback go:generate line
We should be able to freely run `./tool/go generate ./...`, but we're
continually dodging this particular generator. Instead of constantly
dodging it, let's just remove it.

Updates #cleanup
Signed-off-by: James Tucker <james@tailscale.com>
2023-09-29 18:36:12 -07:00
Claire Wang
a56e58c244 util/syspolicy: add read boolean setting (#9592) 2023-09-29 21:27:04 -04:00
James Tucker
324f0d5f80 cmd/cloner,*: revert: optimize nillable slice cloner
This reverts commit ee90cd02fd.

The outcome is not identical for empty slices. Cloner really needs
tests!

Updates #9601

Signed-off-by: James Tucker <james@tailscale.com>
2023-09-29 18:18:18 -07:00
James Tucker
ee90cd02fd cmd/cloner,*: optimize nillable slice cloner
A wild @josharian appears with a good suggestion for a refactor, thanks
Josh!

Updates #9410
Signed-off-by: James Tucker <james@tailscale.com>
2023-09-29 17:59:59 -07:00
Charlotte Brandhorst-Satzkorn
e91e96dfa5 words: i can't help but rave about these additions
It's no conspiracy that I love learning about new words.

Updates tailscale/corp#14698

Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2023-09-29 16:13:23 -07:00
James Tucker
41b05e6910 go.mod: bump wireguard-go
Updates #9555
Signed-off-by: James Tucker <james@tailscale.com>
2023-09-29 16:04:47 -07:00
Charlotte Brandhorst-Satzkorn
db9c0d0a63 words: gonna take some time to add the words we never had
(ooh, ooh)

Updates #tailscale/corp#14698

Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2023-09-29 15:39:10 -07:00
Jordan Whited
16fa3c24ea wgengine/magicsock: use x/sys/unix constants for UDP GSO (#9597)
Updates #cleanup

Signed-off-by: Jordan Whited <jordan@tailscale.com>
2023-09-29 14:59:46 -07:00
License Updater
a74970305b licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-09-29 14:55:33 -07:00
Chris Palmer
8833dc51f1 util/set: add some useful utility functions for Set (#9535)
Also give each type of set its own file.

Updates #cleanup

Signed-off-by: Chris Palmer <cpalmer@tailscale.com>
2023-09-29 14:31:02 -07:00
James Tucker
0c8c374a41 go.mod: bump all dependencies except go-billy
go-billy is held back at v5.4.1 in order to avoid a newly introduced
subdependency that is not compatible with plan9.

Updates #8043
Signed-off-by: James Tucker <james@tailscale.com>
2023-09-29 14:28:45 -07:00
James Tucker
84acf83019 go.mod,net/dnsfallback: bump go4.org/netipx
Updates #8043
Signed-off-by: James Tucker <james@tailscale.com>
2023-09-29 14:28:45 -07:00
James Tucker
87bc831730 go.mod,cmd/tsconnect: bump esbuild
Updates #8043
Signed-off-by: James Tucker <james@tailscale.com>
2023-09-29 14:28:45 -07:00
James Tucker
71f2c67c6b go.mod: bump wingoes for cross-platform HRESULT definition
Updates #9579
Signed-off-by: James Tucker <james@tailscale.com>
2023-09-29 13:15:14 -07:00
Brad Fitzpatrick
aae1a28a2b go.mod: add test that replace directives aren't added in oss
Prevent future problems like we earlier with go.mod replace directives
(e.g. removing our certstore replace in 6d6cf88d82 or wireguard-go
in ea5ee6f87c, both of which were reactions to problems caused by
go.mod replace in non-root modules, often because people are using tsnet
as a library from another module)

Updates #cleanup

Change-Id: I766715cfa7ce7021460ba4933bd2fa977c3081d2
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-29 12:31:52 -07:00
Claire Wang
32c0156311 util: add syspolicy package (#9550)
Add a more generalized package for getting policies.
Updates tailcale/corp#10967

Signed-off-by: Claire Wang <claire@tailscale.com>
Co-authored-by: Adrian Dewhurst <adrian@tailscale.com>
2023-09-29 13:40:35 -04:00
Maisem Ali
d71184d674 cmd/containerboot: only wipeout serve config when TS_SERVE_CONFIG is set
Fixes #9558

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-09-29 09:28:48 -07:00
Brad Fitzpatrick
246e0ccdca tsnet: add a test for restarting a tsnet server, fix Windows
Thanks to @qur and @eric for debugging!

Fixes #6973

Change-Id: Ib2cf8f030cf595cc73dd061c72e78ac19f5fae5d
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-29 09:05:45 -07:00
Denton Gentry
4823a7e591 cmd/containerboot: set TS_AUTH_ONCE default to true.
1.50.0 switched containerboot from using `tailscale up`
to `tailscale login`. A side-effect is that a re-usable
authkey is now re-applied on every boot by `tailscale login`,
where `tailscale up` would ignore an authkey if already
authenticated.

Though this looks like it is changing the default, in reality
it is setting the default to match what 1.48 and all
prior releases actually implemented.

Fixes https://github.com/tailscale/tailscale/issues/9539
Fixes https://github.com/tailscale/corp/issues/14953

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2023-09-29 07:28:29 -07:00
Brad Fitzpatrick
856d32b4a9 cmd/testwrapper: include flake URL in JSON metadata
Updates tailscale/corp#14975

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-28 18:37:22 -07:00
Flakes Updater
2a7b3ada58 go.mod.sri: update SRI hash for go.mod changes
Signed-off-by: Flakes Updater <noreply+flakes-updater@tailscale.com>
2023-09-28 18:20:42 -07:00
Andrea Barisani
f50b2a87ec wgengine/netstack: refactor address construction and conversion
Updates #9252
Updates #9253

Signed-off-by: Andrea Barisani <andrea@inversepath.com>
Signed-off-by: James Tucker <james@tailscale.com>
2023-09-28 16:17:16 -07:00
Andrea Barisani
b5b4298325 go.mod,*: bump gvisor
Updates #9253

Signed-off-by: Andrea Barisani <andrea@inversepath.com>
Signed-off-by: James Tucker <james@tailscale.com>
2023-09-28 16:17:16 -07:00
Brad Fitzpatrick
2c92f94e2a cmd/testwrapper: output machine-readable JSON on test flakes
For parsing by other tools.

Updates tailscale/corp#14975

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-28 15:08:47 -07:00
Sonia Appasamy
5429ee2566 client/web: add debug mode for web client ui updates
UI updates staged behind debug mode flags. Initial new views added
in app.tsx, rendered based on the current debug setting.

Updates tailscale/corp#14335

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-09-28 15:45:33 -04:00
Brad Fitzpatrick
5b3f5eabb5 control/controlclient: fix leaked http2 goroutines on shutdown
If a noise dial was happening concurrently with shutdown, the
http2 goroutines could leak.

Updates tailscale/corp#14950
Updates tailscale/corp#14515
Updates tailscale/corp#14139
Updates tailscale/corp#13175

Signed-off-by: Brad Fitzpatrick <brad@danga.com>
2023-09-28 11:16:46 -07:00
Brad Fitzpatrick
2c0f0ee759 tool/gocross: disable Linux static linking if GOCROSS_STATIC=0
So we can experiment with disabling static linking for tests in CI to
make GitHub Actions output less spammy.

Updates tailscale/corp#13113

Signed-off-by: Brad Fitzpatrick <brad@danga.com>
2023-09-28 09:51:21 -07:00
Sonia Appasamy
5d62b17cc5 client/web: add login client mode to web.Server
Adds new LoginOnly server option and swaps out API handler depending
on whether running in login mode or full web client mode.

Also includes some minor refactoring to the synology/qnap authorization
logic to allow for easier sharing between serveLoginAPI and serveAPI.

Updates tailscale/corp#14335

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-09-28 12:35:07 -04:00
Maisem Ali
354455e8be ipn: use NodeCapMap in CheckFunnel
These were missed when adding NodeCapMap and resulted
in tsnet binaries not being able to turn on funnel.

Fixes #9566

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-09-28 09:16:25 -07:00
James Tucker
5c2b2fa1f8 ipn/ipnlocal: plumb ExitNodeDNSResolvers for IsWireGuardOnly exit nodes
Control sends ExitNodeDNSResolvers when configured for IsWireGuardOnly
nodes that are to be used as the default resolver with a lower
precedence than split DNS, and a lower precedence than "Override local
DNS", but otherwise before local DNS is used when the exit node is in
use.

Neither of the below changes were problematic, but appeared so alongside
a number of other client and external changes. See tailscale/corp#14809.

Reland ea9dd8fabc.
Reland d52ab181c3.

Updates #9377
Updates tailscale/corp#14809

Signed-off-by: James Tucker <james@tailscale.com>
2023-09-27 19:47:38 -07:00
James Tucker
ca4396107e types/key: update some doc strings for public key serialization
Updates #cleanup
Signed-off-by: James Tucker <james@tailscale.com>
2023-09-27 14:04:33 -07:00
James Tucker
80206b5323 wgengine/magicsock: add nodeid to panic condition on public key reuse
If the condition arises, it should be easy to track down.

Updates #9547
Signed-off-by: James Tucker <james@tailscale.com>
2023-09-27 13:56:39 -07:00
James Tucker
2066f9fbb2 util/linuxfw: fix crash in DelSNATRule when no rules are found
Appears to be a missing nil handling case. I looked back over other
usage of findRule and the others all have nil guards. findRule returns
nil when no rules are found matching the arguments.

Fixes #9553
Signed-off-by: James Tucker <james@tailscale.com>
2023-09-27 12:51:27 -07:00
Sonia Appasamy
697f92f4a7 client/web: refactor serveGetNodeData
Remove the "JSON" ending, we no longer have a non-JSON version,
it was removed in d74c771 when we switched from the legacy web
client to React.

Also combine getNodeData into serveGetNodeData now that serveGetNodeData
is the single caller of getNodeData.

A #cleanup

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-09-27 13:53:51 -04:00
Andrew Dunham
d31460f793 net/portmapper: fix invalid UPnP metric name
Fixes #9551

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I06f3a15a668be621675be6cbc7e5bdcc006e8570
2023-09-27 12:28:14 -04:00
Brad Fitzpatrick
3e298e9380 go.toolchain.rev: bump go
Updates tailscale/go#74

Change-Id: I3858d785acadae6822e2387e5e62f234c4625927
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-26 12:07:30 -07:00
Rhea Ghosh
0275afa0c6 ipn/ipnlocal: prevent putting file if file already exists (#9515)
Also adding tests to ensure this works.

Updates tailscale/corp#14772

Signed-off-by: Rhea Ghosh <rhea@tailscale.com>
2023-09-26 12:22:13 -05:00
Claire Wang
e3d6236606 winutil: refactor methods to get values from registry to also return (#9536)
errors
Updates tailscale/corp#14879

Signed-off-by: Claire Wang <claire@tailscale.com>
2023-09-26 13:15:11 -04:00
Val
c608660d12 wgengine,net,ipn,disco: split up and define different types of MTU
Prepare for path MTU discovery by splitting up the concept of
DefaultMTU() into the concepts of the Tailscale TUN MTU, MTUs of
underlying network interfaces, minimum "safe" TUN MTU, user configured
TUN MTU, probed path MTU to a peer, and maximum probed MTU. Add a set
of likely MTUs to probe.

Updates #311

Signed-off-by: Val <valerie@tailscale.com>
2023-09-26 02:25:50 -07:00
Val
578b357849 wgengine/netstack: use buffer pools for UDP packet forwarding
Use buffer pools for UDP packet forwarding to prepare for increasing the
forwarded UDP packet size for peer path MTU discovery.

Updates #311

Co-authored-by: Brad Fitzpatrick <bradfitz@tailscale.com>
Signed-off-by: Val <valerie@tailscale.com>
2023-09-26 02:25:50 -07:00
Irbe Krumina
bdd9eeca90 cmd/k8s-operator: fix reconcile filters (#9533)
Ensure that when there is an event on a Tailscale managed Ingress or Service child resource, the right parent type gets reconciled

Updates tailscale/tailscale#502

Signed-off-by: Irbe Krumina <irbe@tailscale.com>
2023-09-26 06:09:35 +01:00
Marwan Sulaiman
651620623b ipn/ipnlocal: close foreground sessions on SetServeConfig
This PR ensures zombie foregrounds are shutdown if a new
ServeConfig is created that wipes the ongoing foreground ones.
For example, "tailscale serve|funnel reset|off" should close
all open sessions.

Updates #8489

Signed-off-by: Marwan Sulaiman <marwan@tailscale.com>
2023-09-26 00:29:50 +02:00
Andrew Dunham
530aaa52f1 net/dns: retry forwarder requests over TCP
We weren't correctly retrying truncated requests to an upstream DNS
server with TCP. Instead, we'd return a truncated request to the user,
even if the user was querying us over TCP and thus able to handle a
large response.

Also, add an envknob and controlknob to allow users/us to disable this
behaviour if it turns out to be buggy ( DNS ).

Updates #9264

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: Ifb04b563839a9614c0ba03e9c564e8924c1a2bfd
2023-09-25 16:42:07 -04:00
Aaron Klotz
098d110746 VERSION.txt: this is v1.51.0
Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2023-09-25 10:44:02 -06:00
License Updater
7aed9712d8 licenses: update win/apple licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-09-25 09:08:57 -07:00
Brad Fitzpatrick
04fabcd359 ipn/{ipnlocal,localapi}, cli: add debug force-netmap-update
For loading testing & profiling the cost of full netmap updates.

Updates #1909

Change-Id: I0afdf5de9967f8d95c7f81d5b531ed1c92c3208f
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-24 14:44:18 -07:00
Anton Tolchanov
75dbd71f49 api.md: document the invalid field in Get Key API response
Updates tailscale/terraform-provider-tailscale#144

Signed-off-by: Anton Tolchanov <anton@tailscale.com>
2023-09-24 09:47:40 -05:00
Brad Fitzpatrick
241c983920 net/tstun: use untyped consts, simplify DefaultMTU func
Updates #cleanup

Change-Id: Ic9ad1d6134818699f777c66a31024e846dfdc5d4
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-23 12:20:19 -07:00
Brad Fitzpatrick
3b32d6c679 wgengine/magicsock, controlclient, net/dns: reduce some logspam
Updates #cleanup

Change-Id: I78b0697a01e94baa33f3de474b591e616fa5e6af
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-23 11:52:47 -07:00
Val
08302c0731 Revert "wgengine/netstack: use buffer pools for UDP packet forwarding"
This reverts commit fb2f3e4741.

Signed-off-by: Val <valerie@tailscale.com>
2023-09-22 10:56:43 -07:00
Val
6cc5b272d8 Revert "wgengine,net,ipn,disco: split up and define different types of MTU"
This reverts commit 059051c58a.

Signed-off-by: Val <valerie@tailscale.com>
2023-09-22 10:56:43 -07:00
Val
059051c58a wgengine,net,ipn,disco: split up and define different types of MTU
Prepare for path MTU discovery by splitting up the concept of
DefaultMTU() into the concepts of the Tailscale TUN MTU, MTUs of
underlying network interfaces, minimum "safe" TUN MTU, user configured
TUN MTU, probed path MTU to a peer, and maximum probed MTU. Add a set
of likely MTUs to probe.

Updates #311

Signed-off-by: Val <valerie@tailscale.com>
2023-09-22 10:15:05 -07:00
Val
fb2f3e4741 wgengine/netstack: use buffer pools for UDP packet forwarding
Use buffer pools for UDP packet forwarding to prepare for increasing the
forwarded UDP packet size for peer path MTU discovery.

Updates #311

Co-authored-by: Brad Fitzpatrick <bradfitz@tailscale.com>
Signed-off-by: Val <valerie@tailscale.com>
2023-09-22 10:15:05 -07:00
License Updater
81e8335e23 licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-09-21 14:50:43 -07:00
Flakes Updater
b83804cc82 go.mod.sri: update SRI hash for go.mod changes
Signed-off-by: Flakes Updater <noreply+flakes-updater@tailscale.com>
2023-09-21 14:32:21 -07:00
Joe Tsai
36242904f1 go.mod: update github.com/go-json-experiment/json (#9508)
Update github.com/go-json-experiment/json to the latest version
and fix the build in light of some breaking API changes.

Updates #cleanup

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2023-09-21 14:19:27 -07:00
James Tucker
a82a74f2cf cmd/containerboot: avoid leaking bash scripts after test runs
The test was sending SIGKILL to containerboot, which results in no
signal propagation down to the bash script that is running as a child
process, thus it leaks.

Minor changes to the test daemon script, so that it cleans up the socket
that it creates on exit, and spawns fewer processes.

Fixes tailscale/corp#14833
Signed-off-by: James Tucker <james@tailscale.com>
2023-09-21 13:17:48 -07:00
License Updater
c5006f143f licenses: update win/apple licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-09-21 12:24:46 -07:00
Aaron Klotz
ea6ca78963 release/dist, tool/gocross: add fake "windowsdll" GOOS to gocross
We're going to need to build a DLL containing custom actions for the installer.
This patch adds the foundations of that capability to dist and gocross.

Updates https://github.com/tailscale/corp/issues/13998

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2023-09-21 13:09:36 -06:00
Joe Tsai
5473d11caa ipn/ipnlocal: perform additional sanity check in diskPath (#9500)
Use filepath.IsLocal to further validate the baseName.

Updates tailscale/corp#14772

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2023-09-21 10:01:27 -07:00
Val
65dc711c76 control,tailcfg,wgengine/magicsock: add nodeAttr to enable/disable peer MTU
Add a nodeAttr to enable/disable peer path MTU discovery.

Updates #311

Signed-off-by: Val <valerie@tailscale.com>
2023-09-21 04:17:12 -07:00
Val
95635857dc wgengine/magicsock: replace CanPMTUD() with ShouldPMTUD()
Replace CanPMTUD() with ShouldPMTUD() to check if peer path MTU discovery should
be enabled, in preparation for adding support for enabling/disabling peer MTU
dynamically.

Updated #311

Signed-off-by: Val <valerie@tailscale.com>
2023-09-21 04:17:12 -07:00
Val
a5ae21a832 wgengine/magicsock: improve don't fragment bit set/get support
Add an enable/disable argument to setDontFragment() in preparation for dynamic
enable/disable of peer path MTU discovery. Add getDontFragment() to get the
status of the don't fragment bit from a socket.

Updates #311

Co-authored-by: James Tucker <james@tailscale.com>
Signed-off-by: Val <valerie@tailscale.com>
2023-09-21 04:17:12 -07:00
Val
4c793014af wgengine/magicsock: fix don't fragment setsockopt arg for IPv6 on linux
Use IPV6_MTU_DISCOVER for setting don't fragment on IPv6 sockets on Linux (was
using IP_MTU_DISCOVER, the IPv4 arg).

Updates #311

Signed-off-by: Val <valerie@tailscale.com>
2023-09-21 04:17:12 -07:00
Val
055f3fd843 wgengine/magicsock: rename debugPMTUD() to debugEnablePMTUD()
Make the debugknob variable name for enabling peer path MTU discovery match the
env variable name.

Updates #311

Signed-off-by: Val <valerie@tailscale.com>
2023-09-21 04:17:12 -07:00
Val
bb3d338334 wgengine/magicsock: rename files for peer MTU
Rename dontfrag* to peermtu* to prepare for more peer MTU related code going
into these files.

Updates #311

Signed-off-by: Val <valerie@tailscale.com>
2023-09-21 04:17:12 -07:00
James Tucker
1c88a77f68 net/dns/publicdns: update Quad9 addresses and references
One Quad9 IPv6 address was incorrect, and an additional group needed
adding. Additionally I checked Cloudflare and included source reference
URLs for both.

Updates #cleanup
Signed-off-by: James Tucker <james@tailscale.com>
2023-09-20 16:55:58 -07:00
Denton Gentry
6e6a510001 go.toolchain.rev: update to Go 1.21.1+
Updates https://github.com/tailscale/tailscale/issues/8419

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2023-09-20 15:34:32 -07:00
Maisem Ali
4669e7f7d5 cmd/containerboot: add iptables based MSS clamping for ingress/egress proxies
In typical k8s setups, the MTU configured on the eth0 interfaces is typically 1500 which
results in packets being dropped when they make it to proxy pods as the tailscale0 interface
has a 1280 MTU.

As the primary use of this functionality is TCP, add iptables based MSS clamping to allow
connectivity.

Updates #502

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-09-20 13:58:30 -07:00
Brad Fitzpatrick
546506a54d ipn/ipnlocal: add a test for recent WhoIs regression
This would've prevented #9470.

This used to pass, fails as of 9538e9f970, and passes again
once #9472 is in.

Updates #9470

Change-Id: Iab97666f7a318432fb3b6372a177ab50c55d4697
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-20 13:56:52 -07:00
Joe Tsai
ae89482f25 ipn/ipnlocal: fix LocalBackend.WhoIs for self (#9472)
9538e9f970 broke LocalBackend.WhoIs
where you can no longer lookup yourself in WhoIs.
This occurs because the LocalBackend.peers map only contains peers.
If we fail to lookup a peer, double-check whether it is ourself.

Fixes #9470

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
Co-authored-by: Rhea Ghosh <rhea@tailscale.com>
2023-09-20 13:46:19 -07:00
Irbe Krumina
c5b2a365de cmd/k8s-operator: fix egress service name (#9494)
Updates https://github.com/tailscale/tailscale/issues/502

Signed-off-by: Irbe Krumina <irbe@tailscale.com>
2023-09-20 20:58:28 +01:00
Maisem Ali
5f4d76c18c cmd/k8s-operator: rename egress annotation
It was tailscale.com/ts-tailnet-target-ip, which was pretty
redundant. Change it to tailscale.com/tailnet-ip.

Updates #502

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-09-20 09:47:30 -07:00
Maisem Ali
ea9dd8fabc Revert "ipn/ipnlocal: plumb ExitNodeDNSResolvers for IsWireGuardOnly exit nodes"
This reverts commit f6845b10f6.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-09-19 20:47:33 -07:00
James Tucker
d52ab181c3 Revert "ipn/ipnlocal: allow Split-DNS and default resolvers with WireGuard nodes"
This reverts commit c7ce4e07e5.

Signed-off-by: James Tucker <james@tailscale.com>
2023-09-19 20:32:04 -07:00
James Tucker
c7ce4e07e5 ipn/ipnlocal: allow Split-DNS and default resolvers with WireGuard nodes
The initial implementation directly mirrored the behavior of Tailscale
exit nodes, where the WireGuard exit node DNS took precedence over other
configuration.

This adjusted implementation treats the WireGuard DNS
resolvers as a lower precedence default resolver than the tailnet
default resolver, and allows split DNS configuration as well.

This also adds test coverage to the existing DNS selection behavior with
respect to default resolvers and split DNS routes for Tailscale exit
nodes above cap 25. There may be some refinement to do in the logic in
those cases, as split DNS may not be working as we intend, though that
would be a pre-existing and separate issue.

Updates #9377
Signed-off-by: James Tucker <james@tailscale.com>
2023-09-19 16:29:57 -07:00
Maisem Ali
3056a98bbd net/tstun: add better logging of natV4Config
It might as well have been spewing out gibberish. This adds
a nicer output format for us to be able to read and identify
whats going on.

Sample output
```
natV4Config{nativeAddr: 100.83.114.95, listenAddrs: [10.32.80.33], dstMasqAddrs: [10.32.80.33: 407 peers]}
```

Fixes tailscale/corp#14650

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-09-19 16:20:15 -07:00
David Anderson
ed50f360db util/lru: update c.head when deleting the most recently used entry
Fixes tailscale/corp#14747

Signed-off-by: David Anderson <danderson@tailscale.com>
Co-authored-by: Brad Fitzpatrick <bradfitz@tailscale.com>
Signed-off-by: David Anderson <danderson@tailscale.com>
2023-09-19 12:17:50 -07:00
Flakes Updater
4232826cce go.mod.sri: update SRI hash for go.mod changes
Signed-off-by: Flakes Updater <noreply+flakes-updater@tailscale.com>
2023-09-19 10:14:02 -07:00
Will Norris
652f77d236 client/web: switch to using prebuilt web client assets
Updates tailscale/corp#13775

Co-authored-by: Sonia Appasamy <sonia@tailscale.com>
Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
Signed-off-by: Will Norris <will@tailscale.com>
2023-09-19 10:09:54 -07:00
Irbe Krumina
35ad2aafe3 Makefile: make it possibe to pass a custom tag when building dev images (#9461)
Updates #cleanup

Signed-off-by: Irbe Krumina <irbe@tailscale.com>
2023-09-19 17:51:22 +01:00
License Updater
1166765559 licenses: update win/apple licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-09-19 01:30:21 -07:00
Tom DNetto
c08cf2a9c6 all: declare & plumb IPv6 masquerade address for peer
This PR plumbs through awareness of an IPv6 SNAT/masquerade address from the wire protocol
through to the low-level (tstun / wgengine). This PR is the first in two PRs for implementing
IPv6 NAT support to/from peers.

A subsequent PR will implement the data-plane changes to implement IPv6 NAT - this is just plumbing.

Signed-off-by: Tom DNetto <tom@tailscale.com>
Updates ENG-991
2023-09-18 21:27:36 -07:00
Andrew Dunham
d9ae7d670e net/portmapper: add clientmetric for UPnP error codes
This should allow us to gather a bit more information about errors that
we encounter when creating UPnP mappings. Since we don't have a
"LabelMap" construction for clientmetrics, do what sockstats does and
lazily register a new metric when we see a new code.

Updates #9343

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: Ibb5aadd6138beb58721f98123debcc7273b611ba
2023-09-18 18:47:24 -04:00
Maisem Ali
19a9d9037f tailcfg: add NodeCapMap
Like PeerCapMap, add a field to `tailcfg.Node` which provides
a map of Capability to raw JSON messages which are deferred to be
parsed later by the application code which cares about the specific
capabilities. This effectively allows us to prototype new behavior
without having to commit to a schema in tailcfg, and it also opens up
the possibilities to develop custom behavior in tsnet applications w/o
having to plumb through application specific data in the MapResponse.

Updates #4217

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-09-18 12:00:34 -07:00
Maisem Ali
4da0689c2c tailcfg: add Node.HasCap helpers
This makes a follow up change less noisy.

Updates #cleanup

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-09-18 12:00:34 -07:00
Maisem Ali
d06b48dd0a tailcfg: add RawMessage
This adds a new RawMessage type backed by string instead of the
json.RawMessage which is backed by []byte. The byte slice makes
the generated views be a lot more defensive than the need to be
which we can get around by using a string instead.

Updates #cleanup

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-09-18 12:00:34 -07:00
Sonia Appasamy
258f16f84b ipn/ipnlocal: add tailnet MagicDNS name to ipn.LoginProfile
Start backfilling MagicDNS suffixes on LoginProfiles.

Updates #9286

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-09-18 13:58:32 -04:00
Brad Fitzpatrick
0d991249e1 types/netmap: remove NetworkMap.{Addresses,MachineStatus}
And convert all callers over to the methods that check SelfNode.

Now we don't have multiple ways to express things in tests (setting
fields on SelfNode vs NetworkMap, sometimes inconsistently) and don't
have multiple ways to check those two fields (often only checking one
or the other).

Updates #9443

Change-Id: I2d7ba1cf6556142d219fae2be6f484f528756e3c
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-18 17:08:11 +01:00
Marwan Sulaiman
d25217c9db cmd/tailscale/cli: error when serving foreground if bg already exists
This PR fixes a bug to make sure that we don't allow two configs
exist with duplicate ports

Updates #8489

Signed-off-by: Marwan Sulaiman <marwan@tailscale.com>
2023-09-18 11:16:01 -04:00
Brad Fitzpatrick
98b5da47e8 types/views: add SliceContainsFunc like slices.ContainsFunc
Needed for a future change.

Updates #cleanup

Change-Id: I6d89ee8a048b3bb1eb9cfb2e5a53c93aed30b021
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-18 16:09:59 +01:00
Maisem Ali
a61caea911 tailcfg: define a type for NodeCapability
Instead of untyped string, add a type to identify these.

Updates #cleanup

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-09-17 13:16:29 -07:00
Brad Fitzpatrick
3d37328af6 wgengine, proxymap: split out port mapping from Engine to new type
(Continuing quest to remove rando stuff from the "Engine")

Updates #cleanup

Change-Id: I77f39902c2194410c10c054b545d70c9744250b0
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-17 20:06:43 +01:00
Brad Fitzpatrick
db2f37d7c6 ipn/ipnlocal: add some test accessors
Updates tailscale/corp#12990

Change-Id: I82801ac4c003d2c7e1352c514adb908dbf01be87
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-17 19:35:17 +01:00
Brad Fitzpatrick
9538e9f970 ipn/ipnlocal: keep internal map updated of latest Nodes post mutations
We have some flaky integration tests elsewhere that have no one place
to ask about the state of the world. This makes LocalBackend be that
place (as it's basically there anyway) but doesn't yet add the ForTest
accessor method.

This adds a LocalBackend.peers map[NodeID]NodeView that is
incrementally updated as mutations arrive. And then we start moving
away from using NetMap.Peers at runtime (UpdateStatus no longer uses
it now). And remove another copy of NodeView in the LocalBackend
nodeByAddr map. Change that to point into b.peers instead.

Future changes will then start streaming whole-node-granularity peer
change updates to WatchIPNBus clients, tracking statefully per client
what each has seen. This will get the GUI clients from receiving less
of a JSON storm of updates all the time.

Updates #1909

Change-Id: I14a976ca9f493bdf02ba7e6e05217363dcf422e5
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-17 19:35:17 +01:00
Brad Fitzpatrick
926c990a09 types/netmap: start phasing out Addresses, add GetAddresses method
NetworkMap.Addresses is redundant with the SelfNode.Addresses. This
works towards a TODO to delete NetworkMap.Addresses and replace it
with a method.

This is similar to #9389.

Updates #cleanup

Change-Id: Id000509ca5d16bb636401763d41bdb5f38513ba0
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-17 19:16:43 +01:00
Brad Fitzpatrick
fb5ceb03e3 types/netmap: deprecate NetworkMap.MachineStatus, add accessor method
Step 1 of deleting it, per TODO.

Updates #cleanup

Change-Id: I1d3d0165ae5d8b20610227d60640997b73568733
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-17 19:09:11 +01:00
Brad Fitzpatrick
0f3c279b86 ipn/ipnlocal: delete some unused code
Updates #cleanup

Change-Id: I90b46c476f135124d97288e776c2b428b351b8b8
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-17 16:32:57 +01:00
Brad Fitzpatrick
760b945bc0 ipn/{ipnlocal,ipnstate}: start simplifying UpdateStatus/StatusBuilder
* Remove unnecessary mutexes (there's no concurrency)
* Simplify LocalBackend.UpdateStatus using the StatusBuilder.WantPeers
  field that was added in 0f604923d3, removing passing around some
  method values into func args. And then merge two methods.

More remains, but this is a start.

Updates #9433

Change-Id: Iaf2d7ec6e4e590799f00bae185465a4fd089b822
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-17 15:38:54 +01:00
James Tucker
8ab46952d4 net/ping: fix ICMP echo code field to 0
The code was trying to pass the ICMP protocol number here (1), which is
not a valid code. Many servers will not respond to echo messages with
codes other than 0.

https://www.iana.org/assignments/icmp-parameters/icmp-parameters.xhtml#icmp-parameters-codes-8

Updates #9299
Signed-off-by: James Tucker <james@tailscale.com>
2023-09-15 17:08:39 -07:00
James Tucker
f6845b10f6 ipn/ipnlocal: plumb ExitNodeDNSResolvers for IsWireGuardOnly exit nodes
This enables installing default resolvers specified by
tailcfg.Node.ExitNodeDNSResolvers when the exit node is selected.

Updates #9377

Signed-off-by: James Tucker <james@tailscale.com>
2023-09-15 13:58:38 -07:00
James Tucker
e7727db553 tailcfg: add DNS address list for IsWireGuardOnly nodes
Tailscale exit nodes provide DNS service over the peer API, however
IsWireGuardOnly nodes do not have a peer API, and instead need client
DNS parameters passed in their node description.

For Mullvad nodes this will contain the in network 10.64.0.1 address.

Updates #9377

Signed-off-by: James Tucker <james@tailscale.com>
2023-09-15 13:15:18 -07:00
Maisem Ali
335a5aaf9a cmd/k8s-operator: add APISERVER_PROXY env
The kube-apiserver proxy in the operator would only run in
auth proxy mode but thats not always desirable. There are
situations where the proxy should just be a transparent
proxy and not inject auth headers, so do that using a new
env var APISERVER_PROXY and deprecate the AUTH_PROXY env.

THe new env var has three options `false`, `true` and `noauth`.

Updates #8317

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-09-15 09:18:18 -05:00
James Tucker
4c693d2ee8 net/dns/publicdns: update Mullvad DoH server list
The following IPs are not used anymore: 193.19.108.2 and 193.19.108.3.
All of the servers are now named consistently under dns.mullvad.net.
Several new servers were added.

https://mullvad.net/en/help/dns-over-https-and-dns-over-tls/

Updates #5416
Updates #9345

Signed-off-by: James Tucker <james@tailscale.com>
2023-09-14 17:48:01 -07:00
Charlotte Brandhorst-Satzkorn
8428a64b56 words: holy mole we need some more mammals
Particularly of the polydactyl kind.

Updates #14698

Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2023-09-14 14:25:33 -07:00
James Tucker
1858ad65c8 cmd/cloner: do not allocate slices when the source is nil
tailcfg.Node zero-value clone equality checks failed when I added a
[]*foo to the structure, as the zero value and it's clone contained a
different slice header.

Updates #9377
Updates #9408
Signed-off-by: James Tucker <james@tailscale.com>
2023-09-14 11:36:34 -07:00
James Tucker
85155ddaf3 tailcfg: remove completed TODO from IsWireGuardOnly
Updates #7826
Signed-off-by: James Tucker <james@tailscale.com>
2023-09-14 10:16:18 -07:00
Tyler Smalley
dfefaa5e35 Use parent serve config
Signed-off-by: Tyler Smalley <tyler@tailscale.com>
2023-09-14 10:22:38 -05:00
Marwan Sulaiman
f3a5bfb1b9 cmd/tailscale/cli: add set serve validations
This PR adds validations for the new new funnel/serve
commands under the following rules:
1. There is always a single config for one port (bg or fg).
2. Foreground configs under the same port cannot co-exists (for now).
3. Background configs can change as long as the serve type is the same.

Updates #8489

Signed-off-by: Marwan Sulaiman <marwan@tailscale.com>
2023-09-14 10:22:38 -05:00
Andrew Lytvynov
7ce1c6f981 .github/workflows: fix slack-action format in govulncheck.yml (#9390)
Currently slack messages for errors fail:
https://github.com/tailscale/tailscale/actions/runs/6159104272/job/16713248204

```
Error: Unexpected token
 in JSON at position 151
```

This is likely due to the line break in the text. Restructure the
message to use separate title/text and fix the slack webhook body.

Updates #cleanup

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-09-13 14:36:40 -07:00
Marwan Sulaiman
3421784e37 cmd/tailscale/cli: use optimistic concurrency control on SetServeConfig
This PR uses the etag/if-match pattern to ensure multiple calls
to SetServeConfig are synchronized. It currently errors out and
asks the user to retry but we can add occ retries as a follow up.

Updates #8489

Signed-off-by: Marwan Sulaiman <marwan@tailscale.com>
2023-09-13 15:08:41 -05:00
Brad Fitzpatrick
6e66e5beeb cmd/tsconnect/wasm: pass a netmon to ipnserver.New
It became required as of 6e967446e4

Updates #8052

Change-Id: I08d100534254865293c1beca5beff8e529e4e9ac
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-13 12:52:55 -07:00
Brad Fitzpatrick
99bb355791 wgengine: remove DiscoKey method from Engine interface
It has one user (LocalBackend) which can ask magicsock itself.

Updates #cleanup

Change-Id: I8c03cbb1e5ba57b0b442621b5fa467030c14a2e2
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-13 10:01:44 -07:00
Will Norris
9843e922b8 README: update docs for building web client
Move into the main "building" section and add the missing `yarn install`
step.

Updates #9312

Signed-off-by: Will Norris <will@tailscale.com>
2023-09-13 09:38:40 -07:00
Tyler Smalley
82c1dd8732 cmd/tailscale: funnel wip cleanup and additional test coverage (#9316)
General cleanup and additional test coverage of WIP code.

* use enum for serveType
* combine instances of ServeConfig access within unset
* cleanMountPoint rewritten into cleanURLPath as it only handles URL paths
* refactor and test expandProxyTargetDev

> **Note**
> Behind the `TAILSCALE_USE_WIP_CODE` flag

updates #8489

Signed-off-by: Tyler Smalley <tyler@tailscale.com>
2023-09-13 10:41:30 -05:00
Brad Fitzpatrick
3c276d7de2 wgengine: remove SetDERPMap method from Engine interface
(continuing the mission of removing rando methods from the Engine
 interface that we don't need anymore)

Updates #cleanup

Change-Id: Id5190917596bf04d7185c3b331a852724a3f5a16
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-12 21:16:56 -07:00
Brad Fitzpatrick
67396d716b ipn/ipnlocal: remove defensiveness around not having a magicsock.Conn
We always have one. Stop pretending we might not.

Instead, add one early panic in NewLocalBackend if we actually don't.

Updates #cleanup

Change-Id: Iba4b78ed22cb6248e59c2b01a79355ca7a200ec8
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-12 20:52:08 -07:00
Brad Fitzpatrick
b8a4c96c53 wgengine: remove LinkChange method from Engine interface
It was only used by Android, until
https://github.com/tailscale/tailscale-android/pull/131
which does the call to the netMon directly instead.

Updates #cleanup

Change-Id: Iab8a1d8f1e63250705835c75f40e2cd8c1c4d5b8
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-12 17:25:17 -07:00
Brad Fitzpatrick
727b1432a8 wgengine: remove SetNetInfoCallback method from Engine
LocalBackend can talk to magicsock on its own to do this without
the "Engine" being involved.

(Continuing a little side quest of cleaning up the Engine
interface...)

Updates #cleanup

Change-Id: I8654acdca2b883b1bd557fdc0cfb90cd3a418a62
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-12 15:14:14 -07:00
Andrew Dunham
ad4c11aca1 net/netmon: log when the gateway/self IP changes
This logs that the gateway/self IP address has changed if one of the new
values differs.

Updates #8992

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I0919424b68ad97fbe1204dd36317ed6f5915411f
2023-09-12 17:48:29 -04:00
License Updater
45eafe1b06 licenses: update win/apple licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-09-12 14:11:00 -07:00
Brad Fitzpatrick
eb9f1db269 cmd/tsconnect/wasm: register netstack.Impl with tsd.System
I missed this in 343c0f1031 and I guess we don't have integration
tests for wasm. But it compiled! :)

Updates #fixup to a #cleanup

Change-Id: If147b90bab254d144ec851a392e8db10ab97f98e
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-12 14:10:06 -07:00
Brad Fitzpatrick
343c0f1031 wgengine{,/netstack}: remove AddNetworkMapCallback from Engine interface
It had exactly one user: netstack. Just have LocalBackend notify
netstack when here's a new netmap instead, simplifying the bloated
Engine interface that has grown a bunch of non-Engine-y things.
(plenty of rando stuff remains after this, but it's a start)

Updates #cleanup

Change-Id: I45e10ab48119e962fc4967a95167656e35b141d8
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-12 13:55:57 -07:00
David Crawshaw
47ffbffa97 clientupdate: add root key (#9364)
Signed-off-by: David Crawshaw <crawshaw@tailscale.com>
2023-09-12 15:24:01 -05:00
Brad Fitzpatrick
39ade4d0d4 tstest/integration: add start of integration tests for incremental map updates
This adds a new integration test with two nodes where the first gets a
incremental MapResponse (with only PeersRemoved set) saying that the
second node disappeared.

This extends the testcontrol package to support sending raw
MapResponses to nodes.

Updates #1909

Change-Id: Iea0c25c19cf0d72b52dba5a46d01b5cc87b9b39d
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-12 12:47:38 -07:00
Brad Fitzpatrick
9203916a4a control/controlknobs: move more controlknobs code from controlclient
Updates #cleanup

Change-Id: I2b8b6ac97589270f307bfb20e33674894ce873b5
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-12 12:44:35 -07:00
Brad Fitzpatrick
3af051ea27 control/controlclient, types/netmap: start plumbing delta netmap updates
Currently only the top four most popular changes: endpoints, DERP
home, online, and LastSeen.

Updates #1909

Change-Id: I03152da176b2b95232b56acabfb55dcdfaa16b79
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-12 12:23:24 -07:00
Andrew Lytvynov
c0ade132e6 clientupdate: restart tailscale after install on DSM6 (#9363)
DSM6 does not automatically restart packages on install, we have to do
it explicitly.

Also, DSM6 has a filter for publishers in Package Center. Make the error
message more helpful when update fails because of this filter not
allowing our package.

Fixes #9361

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-09-12 13:08:00 -05:00
Brad Fitzpatrick
668a0dd5ab cmd/tailscale/cli: fix panic in netcheck print when no DERP home
Fixes #8016

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-12 08:47:45 -07:00
Andrew Dunham
9ee173c256 net/portmapper: fall back to permanent UPnP leases if necessary
Some routers don't support lease times for UPnP portmapping; let's fall
back to adding a permanent lease in these cases. Additionally, add a
proper end-to-end test case for the UPnP portmapping behaviour.

Updates #9343

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I17dec600b0595a5bfc9b4d530aff6ee3109a8b12
2023-09-12 11:16:45 -04:00
Brad Fitzpatrick
7c1ed38ab3 ipn/ipnlocal: fix missing controlknobs.Knobs plumbing
I missed connecting some controlknobs.Knobs pieces in 4e91cf20a8
resulting in that breaking control knobs entirely.

Whoops.

The fix in ipn/ipnlocal (where it makes a new controlclient) but to
atone, I also added integration tests. Those integration tests use
a new "tailscale debug control-knobs" which by itself might be useful
for future debugging.

Updates #9351

Change-Id: Id9c89c8637746d879d5da67b9ac4e0d2367a3f0d
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-12 06:17:14 -07:00
Marwan Sulaiman
12d4685328 ipn/localapi, ipn/ipnlocal: add etag support for SetServeConfig
This PR adds optimistic concurrency control in the local client and
api in order to ensure multiple writes of the ServeConfig do not
conflict with each other.

Updates #9273

Signed-off-by: Marwan Sulaiman <marwan@tailscale.com>
2023-09-12 04:41:10 -04:00
Brad Fitzpatrick
ff6fadddb6 wgengine/magicsock: stop retaining *netmap.NetworkMap
We're trying to start using that monster type less and eventually get
rid of it.

Updates #1909

Change-Id: I8e1e725bce5324fb820a9be6c7952767863e6542
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-11 20:07:30 -07:00
Brad Fitzpatrick
f06e64c562 wgengine: use set.HandleSet in another place
I guess we missed this one earlier when we unified the various
copies into set.HandleSet.

Updates #cleanup

Change-Id: I7e6de9ce16e8fc4846abf384dfcc8eaec4d99e60
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-11 20:07:05 -07:00
Brad Fitzpatrick
42072683d6 control/controlknobs: move ForceBackgroundSTUN to controlknobs.Knobs
This is both more efficient (because the knobs' bool is only updated
whenever Node is changed, rarely) and also gets us one step closer to
removing a case of storing a netmap.NetworkMap in
magicsock. (eventually we want to phase out much of the use of that
type internally)

Updates #1909

Change-Id: I37e81789f94133175064fdc09984e4f3a431f1a1
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-11 18:11:09 -07:00
Brad Fitzpatrick
4e91cf20a8 control/controlknobs, all: add plumbed Knobs type, not global variables
Previously two tsnet nodes in the same process couldn't have disjoint
sets of controlknob settings from control as both would overwrite each
other's global variables.

This plumbs a new controlknobs.Knobs type around everywhere and hangs
the knobs sent by control on that instead.

Updates #9351

Change-Id: I75338646d36813ed971b4ffad6f9a8b41ec91560
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-11 12:44:03 -07:00
Brad Fitzpatrick
d050700a3b wgengine/magicsock: make peerMap also keyed by NodeID
In prep for incremental netmap update plumbing (#1909), make peerMap
also keyed by NodeID, as all the netmap node mutations passed around
later will be keyed by NodeID.

In the process, also:

* add envknob.InDevMode, as a signal that we can panic more aggressively
  in unexpected cases.
* pull two moderately large blocks of code in Conn.SetNetworkMap out
  into their own methods
* convert a few more sets from maps to set.Set

Updates #1909

Change-Id: I7acdd64452ba58e9d554140ee7a8760f9043f961
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-11 12:43:47 -07:00
Paul Scott
683ba62f3e cmd/testwrapper: fix exit deflake (#9342)
Sometimes `go test` would exit and close its stdout before we started reading
it, and we would return that "file closed" error then forget to os.Exit(1).
Fixed to prefer the go test subprocess error and exit regardless of the type of
error.

Fixes #9334

Signed-off-by: Paul Scott <paul@tailscale.com>
2023-09-11 19:06:11 +01:00
Brad Fitzpatrick
0396366aae cmd/testwrapper/flakytest: don't spam stderr in Mark when not under wrapper
If the user's running "go test" by hand, no need to spam stderr with
the sentinel marker. It already calls t.Logf (which only gets output
on actual failure, or verbose mode) which is enough to tell users it's
known flaky. Stderr OTOH always prints out and is distracting to
manual "go test" users.

Updates #cleanup

Change-Id: Ie5e6881bae291787c30f75924fa132f4a28abbb2
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-11 11:04:18 -07:00
Brad Fitzpatrick
70ea073478 tailcfg: flesh out some docs on MapResponse, clarify slices w/ omitempty
Updates #cleanup

Change-Id: If4caf9d00529edc09ae7af9cc70f6ba0ade38378
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-10 09:22:41 -07:00
Brad Fitzpatrick
a5ffd5e7c3 tailcfg: remove unused MapRequest.IncludeIPv6 field
It's been implicitly enabled (based on capver) for years.

Updates #cleanup

Change-Id: I8ff1ab844f9ed75c97e866e778dfc0b56cfa98a2
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-10 09:21:07 -07:00
Brad Fitzpatrick
9a86aa5732 all: depend on zstd unconditionally, remove plumbing to make it optional
All platforms use it at this point, including iOS which was the
original hold out for memory reasons. No more reason to make it
optional.

Updates #9332

Change-Id: I743fbc2f370921a852fbcebf4eb9821e2bdd3086
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-10 08:36:05 -07:00
Marwan Sulaiman
f12c71e71c cmd/tailscale: reduce duplicate calls to LocalBackend
This PR ensures calls to the LocalBackend are not happening
multiples times and ensures the set/unset methods are
only manipulating the serve config

Updates #8489

Signed-off-by: Marwan Sulaiman <marwan@tailscale.com>
2023-09-10 11:31:57 -04:00
Brad Fitzpatrick
dc7aa98b76 all: use set.Set consistently instead of map[T]struct{}
I didn't clean up the more idiomatic map[T]bool with true values, at
least yet.  I just converted the relatively awkward struct{}-valued
maps.

Updates #cleanup

Change-Id: I758abebd2bb1f64bc7a9d0f25c32298f4679c14f
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-09 10:59:19 -07:00
Brad Fitzpatrick
d506a55c8a ipn/ipnstate: address TODO about garbage during peer sorting
Updates #cleanup

Change-Id: I34938bca70a95571cc62ce1f76eaab5db8c2c3ef
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-09 09:12:23 -07:00
Brad Fitzpatrick
60e9bd6047 ipn/ipnstate: add some missing docs
Updates #cleanup

Change-Id: I689f8124a5986a98b8eb3891727d39c96408f0a7
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-09 08:55:43 -07:00
Brad Fitzpatrick
db307d35e1 types/netmap: delete a copy of views.SliceEqual
Updates #cleanup

Change-Id: Ibdfa6c5dc9211f5c97c763ba323802a1c1d80c9e
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-08 20:49:10 -07:00
David Anderson
95082a8dde util/lru, util/limiter: add debug helper to dump state as HTML
For use in tsweb debug handlers, so that we can easily inspect cache
and limiter state when troubleshooting.

Updates tailscale/corp#3601

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-09-08 14:47:03 -07:00
Andrew Lytvynov
d23b8ffb13 cmd/tailscale/cli,ipn: mention available update in "tailscale status" (#9205)
Cache the last `ClientVersion` value that was received from coordination
server and pass it in the localapi `/status` response.
When running `tailscale status`, print a message if `RunningAsLatest` is
`false`.

Updates #6907

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-09-08 14:27:49 -07:00
Andrew Lytvynov
1073b56e18 ipn/ipnlocal: add logging and locking to c2n /update (#9290)
Log some progress info to make updates more debuggable. Also, track
whether an active update is already started and return an error if
a concurrent update is attempted.

Some planned future PRs:
* add JSON output to `tailscale update`
* use JSON output from `tailscale update` to provide a more detailed
  status of in-progress update (stage, download progress, etc)

Updates #6907

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-09-08 14:26:55 -07:00
Sonia Appasamy
1eadb2b608 client/web: clean up assets handling
A #cleanup that moves all frontend asset handling into assets.go
(formerly dev.go), and stores a single assetsHandler field back
to web.Server that manages when to serve the dev vite proxy versus
static files itself.

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-09-08 16:05:11 -04:00
License Updater
4a38d8d372 licenses: update win/apple licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-09-08 08:44:43 -07:00
License Updater
0dc65b2e47 licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-09-08 08:42:58 -07:00
License Updater
1383fc57ad licenses: update android licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-09-08 08:41:56 -07:00
Joe Tsai
0a0adb68ad ssh/tailssh: log when recording starts and finishes (#9294)
Updates tailscale/corp#14579

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2023-09-07 18:47:04 -07:00
Marwan Sulaiman
a1d4144b18 cmd/tailscale: combine foreground and background serve logic
Previously, foreground mode only worked in the simple case of `tailscale funnel <port>`.
This PR ensures that whatever you can do in the background can also be
done in the foreground such as setting mount paths or tcp forwarding.

Updates #8489

Signed-off-by: Marwan Sulaiman <marwan@tailscale.com>
2023-09-07 20:48:58 -04:00
Craig Rodrigues
8452d273e3 util/linuxfw: Fix comment which lists supported linux arches
Only arm64 and amd64 are supported

Signed-off-by: Craig Rodrigues <rodrigc@crodrigues.org>
2023-09-07 16:49:50 -07:00
David Anderson
0909e90890 util/lru: replace container/list with a custom ring implementation
pre-generics container/list is quite unpleasant to use, and the pointer
manipulation operations for an LRU are simple enough to implement directly
now that we have generic types.

With this change, the LRU uses a ring (aka circularly linked list) rather
than a simple doubly-linked list as its internals, because the ring makes
list manipulation edge cases more regular: the only remaining edge case is
the transition between 0 and 1 elements, rather than also having to deal
specially with manipulating the first and last members of the list.

While the primary purpose was improved readability of the code, as it
turns out removing the indirection through an interface box also speeds
up the LRU:

       │ before.txt  │              after.txt              │
       │   sec/op    │   sec/op     vs base                │
LRU-32   67.05n ± 2%   59.73n ± 2%  -10.90% (p=0.000 n=20)

       │ before.txt │             after.txt              │
       │    B/op    │    B/op     vs base                │
LRU-32   21.00 ± 0%   10.00 ± 0%  -52.38% (p=0.000 n=20)

       │ before.txt │           after.txt            │
       │ allocs/op  │ allocs/op   vs base            │
LRU-32   0.000 ± 0%   0.000 ± 0%  ~ (p=1.000 n=20) ¹

Updates #cleanup

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-09-07 16:04:39 -07:00
David Anderson
472eb6f6f5 util/lru: add a microbenchmark
The benchmark simulates an LRU being queries with uniformly random
inputs, in a set that's too large for the LRU, which should stress
the eviction codepath.

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-09-07 16:04:39 -07:00
Maisem Ali
18b2638b07 metrics: add missing comma in histogram JSON export
Updates tailscale/corp#8641

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-09-07 15:28:12 -07:00
Tyler Smalley
70a9854b39 cmd/tailscale: add background mode to serve/funnel wip (#9202)
> **Note**
> Behind the `TAILSCALE_FUNNEL_DEV` flag

* Expose additional listeners through flags
* Add a --bg flag to run in the background
* --set-path to set a path for a specific target (assumes running in background)

See the parent issue for more context.

Updates #8489

Signed-off-by: Tyler Smalley <tyler@tailscale.com>
2023-09-07 15:07:53 -07:00
Maisem Ali
5ee349e075 tsweb/varz: fix exporting histograms
Updates tailscale/corp#8641

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-09-07 14:52:59 -07:00
Brad Fitzpatrick
1bd3edbb46 release/dist/unixpkgs: demote deb iptables+iproute2 packages to recommended
Fixes #9236

Change-Id: Idbad2edb0262ef842afd6b40ae47f46e685b112d
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-07 14:19:39 -07:00
Marwan Sulaiman
50990f8931 ipn, ipn/ipnlocal: add Foreground field for ServeConfig
This PR adds a new field to the serve config that can be used to identify which serves are in "foreground mode" and then can also be used to ensure they do not get persisted to disk so that if Tailscaled gets ungracefully shutdown, the reloaded ServeConfig will not have those ports opened.

Updates #8489

Signed-off-by: Marwan Sulaiman <marwan@tailscale.com>
2023-09-07 13:13:05 -04:00
Paul Scott
96094cc07e cmd/testwrapper: exit code 1 when go build fails (#9276)
Fixes #9275
Fixes #8586
Fixes tailscale/corp#13115

Signed-off-by: Paul Scott <paul@tailscale.com>
2023-09-07 17:18:26 +01:00
Skip Tavakkolian
6fd1961cd7 safesocket, paths: add Plan 9 support
Updates #5794

Change-Id: I69150ec18d101f55baabb38613512cde858447cb
Co-authored-by: Brad Fitzpatrick <bradfitz@tailscale.com>
Signed-off-by: Skip Tavakkolian <skip.tavakkolian@gmail.com>
2023-09-07 08:48:21 -07:00
Marwan Sulaiman
51d3220153 ipn, ipn/ipnlocal: remove log streaming for StreamServe
This PR removes the per request logging to the CLI as the CLI
will not be displaying those logs initially.

Updates #8489

Signed-off-by: Marwan Sulaiman <marwan@tailscale.com>
2023-09-06 21:15:05 -04:00
David Anderson
96c2cd2ada util/limiter: add a keyed token bucket rate limiter
Updates tailscale/corp#3601

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-09-06 17:48:17 -07:00
Maisem Ali
c2241248c8 tstest: relax ResourceCheck to 3s
It was only waiting for 0.5s (5ms * 100), but our CI
is too slow so make it wait up to 3s (10ms * 300).

Updates tailscale/corp#14515

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-09-06 15:42:08 -07:00
Chris Palmer
ac7b4d62fd cmd/tailscale/cli: make update visible in list (#8662)
This also makes "HIDDEN: " work (requires the custom UsageFunc).

Updates #6995

Signed-off-by: Chris Palmer <cpalmer@tailscale.com>
2023-09-06 10:28:04 -07:00
Andrew Dunham
d413dd7ee5 net/dns/publicdns: add support for Wikimedia DNS
RELNOTE=Adds support for Wikimedia DNS

Updates #9255

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I4213c29e0f91ea5aa0304a5a026c32b6690fead9
2023-09-06 11:38:15 -04:00
Andrea Barisani
d61494db68 adjust build tags for tamago
Signed-off-by: Andrea Barisani <andrea@inversepath.com>
2023-09-06 05:50:18 -07:00
Paul Scott
9a56184bef cmd/tailscale: Check App Store tailscaled dialable before selecting. (#9234)
PR #9217 attempted to fix the same issue, but suffered from not letting the
user connect to non-oss tailscaled if something was listening on the socket, as
the --socket flag doesn't let you select the mac apps.

Rather than leave the user unable to choose, we keep the mac/socket preference
order the same and check a bit harder whether the macsys version really is
running. Now, we prefer the App Store Tailscale (even if it's Stopped) and you
can use --socket to sswitch. But if you quit the App Store Tailscale, we'll try
the socket without needing the flag.

Fixes #5761
Signed-off-by: Paul Scott <408401+icio@users.noreply.github.com>
2023-09-06 12:43:10 +01:00
Anton Tolchanov
86b0fc5295 util/cmpver: add a few tests covering different OS versions
Updates tailscale/corp#14491

Signed-off-by: Anton Tolchanov <anton@tailscale.com>
2023-09-06 09:43:40 +01:00
Aaron Klotz
7686ff6c46 Update clientupdate/distsign/distsign_test.go
Co-authored-by: Andrew Lytvynov <awly@tailscale.com>
Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2023-09-05 15:43:36 -06:00
Aaron Klotz
7d60c19d7d clientupdate/distsign: add ability to validate a binary that is already located on disk
Our build system caches files locally and only updates them when something
changes. Since I need to integrate some distsign stuff into the build system
to validate our Windows 7 MSIs, I want to be able to check the cached copy
of a package before downloading a fresh copy from pkgs.

If the signature changes, then obviously the local copy is outdated and we
return an error, at which point we call Download to refresh the package.

Updates https://github.com/tailscale/corp/issues/14334

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2023-09-05 15:43:36 -06:00
Maisem Ali
f6a203fe23 control/controlclient: check c.closed in waitUnpause
We would only check if the client was paused, but not
if the client was closed. This meant that a call to
Shutdown may block forever/leak goroutines

Updates #cleanup

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-09-05 12:31:25 -07:00
Marwan Sulaiman
45eeef244e ipn, ipn/ipnlocal: add Foreground field to ServeConfig
This PR adds a new field to the ServeConfig which maps
WatchIPNBus session ids to foreground serve configs.

The PR also adds a DeleteForegroundSession method to ensure the config
gets cleaned up on sessions ending.

Note this field is not currently used but will be in follow up work.

Updates #8489

Signed-off-by: Marwan Sulaiman <marwan@tailscale.com>
2023-09-05 15:10:11 -04:00
Maisem Ali
cb3b281e98 ipn/ipnlocal: fix race in enterState
It would acquire the lock, calculate `nextState`, relase
the lock, then call `enterState` which would acquire the lock
again. There were obvious races there which could lead to
nil panics as seen in a test in a different repo.

```
panic: runtime error: invalid memory address or nil pointer dereference
[signal SIGSEGV: segmentation violation code=0x2 addr=0x70 pc=0x1050f2c7c]

goroutine 42240 [running]:
tailscale.com/ipn/ipnlocal.(*LocalBackend).enterStateLockedOnEntry(0x14002154e00, 0x6)
        tailscale.com/ipn/ipnlocal/local.go:3715 +0x30c
tailscale.com/ipn/ipnlocal.(*LocalBackend).enterState(0x14002154e00?, 0x14002e3a140?)
        tailscale.com/ipn/ipnlocal/local.go:3663 +0x8c
tailscale.com/ipn/ipnlocal.(*LocalBackend).stateMachine(0x14001f5e280?)
        tailscale.com/ipn/ipnlocal/local.go:3836 +0x2c
tailscale.com/ipn/ipnlocal.(*LocalBackend).setWgengineStatus(0x14002154e00, 0x14002e3a190, {0x0?, 0x0?})
        tailscale.com/ipn/ipnlocal/local.go:1193 +0x4d0
tailscale.com/wgengine.(*userspaceEngine).RequestStatus(0x14005d90300)
        tailscale.com/wgengine/userspace.go:1051 +0x80
tailscale.com/wgengine.NewUserspaceEngine.func2({0x14002e3a0a0, 0x2, 0x140025cce40?})
        tailscale.com/wgengine/userspace.go:318 +0x1a0
tailscale.com/wgengine/magicsock.(*Conn).updateEndpoints(0x14002154700, {0x105c13eaf, 0xf})
        tailscale.com/wgengine/magicsock/magicsock.go:531 +0x424
created by tailscale.com/wgengine/magicsock.(*Conn).ReSTUN in goroutine 42077
        tailscale.com/wgengine/magicsock/magicsock.go:2142 +0x3a4
```

Updates tailscale/corp#14480

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-09-05 10:45:11 -07:00
Marwan Sulaiman
a4aa6507fa ipn, ipn/ipnlocal: add session identifier for WatchIPNBus
This PR adds a SessionID field to the ipn.Notify struct so that
ipn buses can identify a session and register deferred clean up
code in the future. The first use case this is for is to be able to
tie foreground serve configs to a specific watch session and ensure
its clean up when a connection is closed.

Updates #8489

Signed-off-by: Marwan Sulaiman <marwan@tailscale.com>
2023-09-05 13:30:04 -04:00
Brad Fitzpatrick
7175f06e62 util/rands: add package with HexString func
We use it a number of places in different repos. Might as well make
one. Another use is coming.

Updates #cleanup

Change-Id: Ib7ce38de0db35af998171edee81ca875102349a4
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-05 09:17:21 -07:00
Sonia Appasamy
f824274093 cli/serve: shorten help text on error
Our BETA serve help text is long and often hides the actual error
in the user's usage. Instead of printing the full text, prompt
users to use `serve --help` if they want the help info.

Fixes #14274

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-09-05 11:30:18 -04:00
Maisem Ali
3280c81c95 .github,cmd/gitops-pusher: update to checkout@v4
checkout@v3 is broken:
actions/checkout#1448

Updates #cleanup

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-09-04 15:12:57 -07:00
Maisem Ali
0f397baf77 cmd/testwrapper: emit logs of failed tests on timeout
It would just fail the entire pkg, but would not print any
logs. It was already tracking all the logs, so have it emit
them when the pkg fails/times out.

Updates #9231

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-09-04 15:12:28 -07:00
Maisem Ali
52a19b5970 ipn/ipnlocal: prevent cc leaks on multiple Start calls
If Start was called multiple times concurrently, it would
create a new client and shutdown the previous one. However
there was a race possible between shutting down the old one
and assigning a new one where the concurent goroutine may
have assigned another one already and it would leak.

Updates tailscale/corp#14471

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-09-04 14:06:57 -07:00
Maisem Ali
6bc15f3a73 ipn/ipnlocal: fix startIsNoopLocked
It got broken back when FUS was introduced, but we
never caught it.

Updates tailscale/corp#14471

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-09-04 14:06:57 -07:00
Brad Fitzpatrick
1262df0578 net/netmon, net/tsdial: add some link change metrics
Updates #9040

Change-Id: I2c87572d79d2118bcf1f0122eccfe712c1bea9d5
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-02 14:38:34 -07:00
Craig Rodrigues
8683ce78c2 client/web, clientupdate, util/linuxfw, wgengine/magicsock: Use %v verb for errors
Replace %w verb with %v verb when logging errors.
Use %w only for wrapping errors with fmt.Errorf()

Fixes: #9213

Signed-off-by: Craig Rodrigues <rodrigc@crodrigues.org>
2023-09-02 14:06:48 -07:00
Maisem Ali
d06a75dcd0 ipn/ipnlocal: fix deadlock in resetControlClientLocked
resetControlClientLocked is called while b.mu was held and
would call cc.Shutdown which would wait for the observer queue
to drain.
However, there may be active callbacks from cc already waiting for
b.mu resulting in a deadlock.

This makes it so that resetControlClientLocked does not call
Shutdown, and instead just returns the value.
It also makes it so that any status received from previous cc
are ignored.

Updates tailscale/corp#12827

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-09-02 13:47:32 -07:00
Joe Tsai
c6fadd6d71 all: implement AppendText alongside MarshalText (#9207)
This eventually allows encoding packages that may respect
the proposed encoding.TextAppender interface.
The performance gains from this is between 10-30%.

Updates tailscale/corp#14379

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2023-09-01 18:15:19 -07:00
Will Norris
9a3bc9049c client/web,cmd/tailscale: add prefix flag for web command
We already had a path on the web client server struct, but hadn't
plumbed it through to the CLI. Add that now and use it for Synology and
QNAP instead of hard-coding the path. (Adding flag for QNAP is
tailscale/tailscale-qpkg#112) This will allow supporting other
environments (like unraid) without additional changes to the client/web
package.

Also fix a small bug in unraid handling to only include the csrf token
on POST requests.

Updates tailscale/corp#13775

Signed-off-by: Will Norris <will@tailscale.com>
2023-09-01 14:29:36 -07:00
Andrew Lytvynov
34e3450734 cmd/tailscale,ipn: add auto-update flags and prefs (#8861)
The flags are hidden for now. Adding propagation to tailscaled and
persistence only. The prefs field is wrapped in a struct to allow for
future expansion (like update schedule).

Updates #6907

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-09-01 13:45:12 -07:00
Brad Fitzpatrick
055fdb235f cmd/tailscaled, tstest/integration: make tailscaled die when parent dies
I noticed that failed tests were leaving aroudn stray tailscaled processes
on macOS at least.

To repro, add this to tstest/integration:

    func TestFailInFewSeconds(t *testing.T) {
        t.Parallel()
        time.Sleep(3 * time.Second)
        os.Exit(1)
        t.Fatal("boom")
    }

Those three seconds let the other parallel tests (with all their
tailscaled child processes) start up and start running their tests,
but then we violently os.Exit(1) the test driver and all the children
were kept alive (and were spinning away, using all available CPU in
gvisor scheduler code, which is a separate scary issue)

Updates #cleanup

Change-Id: I9c891ed1a1ec639fb2afec2808c04dbb8a460e0e
Co-authored-by: Maisem Ali <maisem@tailscale.com>
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-01 12:32:47 -07:00
Tyler Smalley
e1fbb5457b cmd/tailscale: combine serve and funnel for debug wip funnel stream model (#9169)
> **Note**
> Behind the `TAILSCALE_USE_WIP_CODE` flag

In preparing for incoming CLI changes, this PR merges the code path for the `serve` and `funnel` subcommands.

See the parent issue for more context.

The following commands will run in foreground mode when using the environment flag.
```
tailscale serve localhost:3000
tailscae funnel localhost:3000
```

Replaces #9134
Updates #8489

Signed-off-by: Tyler Smalley <tyler@tailscale.com>
Signed-off-by: Marwan Sulaiman <marwan@tailscale.com>
Co-authored-by: Marwan Sulaiman <marwan@tailscale.com>
2023-09-01 12:28:29 -07:00
Brad Fitzpatrick
003e4aff71 control/controlclient: clean up various things in prep for state overhaul
We want the overall state (used only for tests) to be computed from
the individual states of each component, rather than moving the state
around by hand in dozens of places.

In working towards that, we found a lot of things to clean up.

Updates #cleanup

Change-Id: Ieaaae5355dfae789a8ec7a56ce212f1d7e3a92db
Co-authored-by: Maisem Ali <maisem@tailscale.com>
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-01 12:23:34 -07:00
Brad Fitzpatrick
0c1e3ff625 ipn/ipnlocal: avoid calling Start from resetForProfileChangeLockedOnEntry
During Shutdown of an ephemeral node, we called Logout (to best effort
delete the node earlier), which then called back into
resetForProfileChangeLockedOnEntry, which then tried to Start
again. That's all a waste of work during shutdown and complicates
other cleanups coming later.

Updates #cleanup

Change-Id: I0b8648cac492fc70fa97c4ebef919bbe352c5d7b
Co-authored-by: Maisem Ali <maisem@tailscale.com>
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-01 11:18:26 -07:00
Brad Fitzpatrick
9cbec4519b control/controlclient: serialize Observer calls
Don't just start goroutines and hope for them to be ordered.

Fixes potential regression from earlier 7074a40c0.

Updates #cleanup

Change-Id: I501a6f3e4e8e6306b958bccdc1e47869991c31f7
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-01 10:25:37 -07:00
Brad Fitzpatrick
8b3ea13af0 net/tsdial: be smarter about when to close SystemDial conns
It was too aggressive before, as it only had the ill-defined "Major"
bool to work with. Now it can check more precisely.

Updates #9040

Change-Id: I20967283b64af6a9cad3f8e90cff406de91653b8
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-09-01 09:33:55 -07:00
Brad Fitzpatrick
f7b7ccf835 control/controlclient, ipn/ipnlocal: unplumb a bool true literal opt
Updates #cleanup

Change-Id: I664f280a2e06b9875942458afcaf6be42a5e462a
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-31 22:34:21 -07:00
Brad Fitzpatrick
346445acdd .github/workflows: only run bench all on packages with benchmarks
Drops time by several minutes.

Also, on top of that: skip building variant CLIs on the race builder
(29s), and getting qemu (15s).

Updates #9182

Change-Id: I979e02ab8c0daeebf5200459c9e4458a1f62f728
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-31 21:52:18 -07:00
Maisem Ali
96277b63ff ipn/ipnlocal: rename LogoutSync to Logout
Updates #cleanup

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-08-31 21:29:12 -07:00
Maisem Ali
f52273767f ipn/ipnlocal: fix missing mutex usage for profileManager
It required holding b.mu but was documented incorrectly, fix.

Updates #cleanup

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-08-31 21:29:12 -07:00
Maisem Ali
959362a1f4 ipn/ipnlocal,control/controlclient: make Logout more sync
We already removed the async API, make it more sync and remove
the FinishLogout state too.

This also makes the callback be synchronous again as the previous
attempt was trying to work around the logout callback resulting
in a client shutdown getting blocked forever.

Updates #3833

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-08-31 21:29:12 -07:00
Maisem Ali
1f12b3aedc .github: do not use testwrapper for benchmarks
Updates #9182

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-08-31 15:23:41 -07:00
Maisem Ali
7074a40c06 control/controlclient: run SetControlClientStatus in goroutine
We have cases where the SetControlClientStatus would result in
a Shutdown call back into the auto client that would block
forever. The right thing to do here is to fix the LocalBackend
state machine but thats a different dumpster fire that we
are slowly making progress towards.

This makes it so that the SetControlClientStatus happens in a
different goroutine so that calls back into the auto client
do not block.

Also add a few missing mu.Unlocks in LocalBackend.Start.

Updates #9181

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-08-31 14:54:02 -07:00
Brad Fitzpatrick
86dc0af5ae control/controlclient: rename Auto cancel methods, add missing Lock variant
Then use the Locked variants in Shutdown while we already hold the lock.

Updates #cleanup

Change-Id: I367d53e6be6f37f783c8f43fc9c4d498d0adf501
Co-authored-by: Maisem Ali <maisem@tailscale.com>
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-31 14:53:48 -07:00
Brad Fitzpatrick
61ae16cb6f ipn/ipnlocal: add missing mutex unlock in error path
Found while debugging something else.

Updates #cleanup

Change-Id: I73fe55da14bcc3b1ffc39e2dbc0d077bc7f70cf1
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-31 14:34:03 -07:00
Brad Fitzpatrick
47cf836720 tsnet: remove redundant ephemeral logout on close
LocalBackend.Shutdown already does it.

Updates #cleanup

Change-Id: Ie5dd7d8e5d9e69644f211ee1de6c790f57f5ae25
Co-authored-by: Maisem Ali <maisem@tailscale.com>
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-31 09:45:30 -07:00
Brad Fitzpatrick
21247f766f ipn/ipnlocal: deflake some tests
* don't try to re-Start (and thus create a new client) during Shutdown
* in tests, wait for controlclient to fully shut down when replacing it
* log a bit more

Updates tailscale/corp#14139
Updates tailscale/corp#13175 etc
Updates #9178 and its flakes.

Change-Id: I3ed2440644dc157aa6e616fe36fbd29a6056846c
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-31 09:34:39 -07:00
Brad Fitzpatrick
04e1ce0034 control/controlclient: remove unused StartLogout
Updates #cleanup

Co-authored-by: Maisem Ali <maisem@tailscale.com>
Change-Id: I9d052fdbee787f1e8c872124e4bee61c7f04d142
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-30 20:23:03 -07:00
Brad Fitzpatrick
ecc1d6907b types/logger: add TestLogger
We have this in another repo and I wanted it here too.

Updates #cleanup

Change-Id: If93dc73f11eaaada5024acf2a885a153b88db5a0
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-30 20:23:03 -07:00
Flakes Updater
77060c4d89 go.mod.sri: update SRI hash for go.mod changes
Signed-off-by: Flakes Updater <noreply+flakes-updater@tailscale.com>
2023-08-30 16:26:57 -07:00
Andrew Lytvynov
4e72992900 clientupdate: add linux tarball updates (#9144)
As a fallback to package managers, allow updating tailscale that was
self-installed in some way. There are some tricky bits around updating
the systemd unit (should we stick to local binary paths or to the ones
in tailscaled.service?), so leaving that out for now.

Updates #6995

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-08-30 17:25:06 -06:00
Chris Palmer
ce1e02096a ipn/ipnlocal: support most Linuxes in handleC2NUpdate (#9114)
* ipn/ipnlocal: support most Linuxes in handleC2NUpdate

Updates #6995

Signed-off-by: Chris Palmer <cpalmer@tailscale.com>
2023-08-30 14:50:03 -07:00
Brad Fitzpatrick
c621141746 control/controlclient: cancel map poll when logging out
Don't depend on the server to do it.

Updates #cleanup

Change-Id: I8ff40b02aa877155a71fd4db58cbecb872241ac8
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-30 13:46:54 -07:00
Brad Fitzpatrick
313a129fe5 control/controlclient: use slices package more
Updates #cleanup

Change-Id: Ic17384266dc59bc4e710efdda311d6e0719529da
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-30 13:45:20 -07:00
Will Norris
37eab31f68 client/web: simply csrf key caching in cgi mode
Instead of trying to use the user config dir, and then fail back to the
OS temp dir, just always use the temp dir. Also use a filename that is
less likely to cause collisions.

This addresses an issue on a test synology instance that was
mysteriously failing because there was a file at /tmp/tailscale. We
could still technically run into this issue if a
/tmp/tailscale-web-csrf.key file exists, but that seems far less likely.

Updates tailscale/corp#13775

Signed-off-by: Will Norris <will@tailscale.com>
2023-08-30 11:49:09 -07:00
Brad Fitzpatrick
f5bfdefa00 control/controlclient: de-pointer Status.PersistView, document more
Updates #cleanup
Updates #1909

Change-Id: I31d91e120e3b299508de2136021eab3b34131a44
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-30 11:48:58 -07:00
Brad Fitzpatrick
7053e19562 control/controlclient: delete Status.Log{in,out}Finished
They were entirely redundant and 1:1 with the status field
so this turns them into methods instead.

Updates #cleanup
Updates #1909

Change-Id: I7d939750749edf7dae4c97566bbeb99f2f75adbc
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-30 11:21:06 -07:00
Maisem Ali
794650fe50 cmd/k8s-operator: emit event if HTTPS is disabled on Tailnet
Instead of confusing users, emit an event that explicitly tells the
user that HTTPS is disabled on the tailnet and that ingress may not
work until they enable it.

Updates #9141

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-08-30 10:53:40 -07:00
Denton Gentry
be9914f714 cmd/sniproxy: move default debug-port away from 8080.
Port 8080 is routinely used for HTTP services, make it easier to
use --forwards=tcp/8080/... by moving the metrics port out of the
way.

Updates #1748

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2023-08-30 10:52:22 -07:00
Brad Fitzpatrick
9ce1f5c7d2 control/controlclient: unexport Status.state, add test-only accessor
Updates #cleanup
Updates #1909

Change-Id: I38dcde6fa0de0f58ede4529992cee2e36de33dd6
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-30 10:40:05 -07:00
Maisem Ali
306b85b9a3 cmd/k8s-operator: add metrics to track usage
Updates #502

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-08-30 10:33:54 -07:00
Andrea Barisani
0a74d46568 adjust build tags for tamago
Signed-off-by: Andrea Barisani <andrea@inversepath.com>
2023-08-30 09:14:54 -07:00
Brad Fitzpatrick
14320290c3 control/controlclient: merge, simplify two health check calls
I'm trying to remove some stuff from the netmap update path.

Updates #1909

Change-Id: Iad2c728dda160cd52f33ef9cf0b75b4940e0ce64
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-30 09:14:01 -07:00
Irbe Krumina
17438a98c0 cm/k8s-operator,cmd/containerboot: fix STS config, more tests (#9155)
Ensures that Statefulset reconciler config has only one of Cluster target IP or tailnet target IP.
Adds a test case for containerboot egress proxy mode.

Updates tailscale/tailscale#8184

Signed-off-by: irbekrm <irbekrm@gmail.com>
2023-08-30 14:22:06 +01:00
Denton Gentry
29a35d4a5d cmd/sniproxy: switch to peterbourgon/ff for flags
Add support for TS_APPC_* variables to supply arguments by
switching to https://github.com/peterbourgon/ff for CLI
flag parsing. For example:
TS_APPC_FORWARDS=tcp/22/github.com ./sniproxy

Updates https://github.com/tailscale/tailscale/issues/1748

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2023-08-30 06:05:40 -07:00
Irbe Krumina
fe709c81e5 cmd/k8s-operator,cmd/containerboot: add kube egress proxy (#9031)
First part of work for the functionality that allows users to create an egress
proxy to access Tailnet services from within Kubernetes cluster workloads.
This PR allows creating an egress proxy that can access Tailscale services over HTTP only.

Updates tailscale/tailscale#8184

Signed-off-by: irbekrm <irbekrm@gmail.com>
Co-authored-by: Maisem Ali <maisem@tailscale.com>
Co-authored-by: Rhea Ghosh <rhea@tailscale.com>
2023-08-30 08:31:37 +01:00
Maisem Ali
ae747a2e48 cmd/testwrapper: handle timeouts as test failures
While investigating the fix in 7538f38671,
I was curious why the testwrapper didn't fail. Turns out if the test
times out and there was no explicit failure, the only message we get
is that the overall pkg failed and no failure information about the
individual test. This resulted in a 0 exit code.

This fixes that by failing the explicit case of the pkg failing when
there is nothing to retry for that pkg.

Updates #8493

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-08-29 19:11:41 -07:00
Maisem Ali
b90b9b4653 client/web: fix data race
Fixes #9150

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-08-29 19:00:20 -07:00
Maisem Ali
7538f38671 cmd/containerboot: fix broken tests
The tests were broken in a61a9ab087, maybe
even earlier.

Updates #502

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-08-29 17:41:12 -07:00
Andrew Lytvynov
abfe5d3879 clientupdate: detect when tailscale is installed without package manager (#9137)
On linux users can install Tailscale via package managers or direct
tarball downloads. Detect when Tailscale is not installed via a package
manager so we can pick the correct update mechanism. Leave the tarball
update function unimplemented for now (coming in next PR!).

Updates #6995
Updates #8760

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-08-29 17:36:05 -07:00
David Anderson
8b492b4121 net/wsconn: accept a remote addr string and plumb it through
This makes wsconn.Conns somewhat present reasonably when they are
the client of an http.Request, rather than just put a placeholder
in that field.

Updates tailscale/corp#13777

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-08-29 16:57:16 -07:00
Sonia Appasamy
e952564b59 client/web: pipe unraid csrf token through apiFetch
Ensures that we're sending back the csrf token for all requests
made back to unraid clients.

Updates tailscale/corp#13775

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-08-29 18:55:52 -04:00
Sonia Appasamy
1cd03bc0a1 client/web: remove self node on server
This is unused. Can be added back if needed in the future.

Updates tailscale/corp#13775

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-08-29 17:55:09 -04:00
Sonia Appasamy
da6eb076aa client/web: add localapi proxy
Adds proxy to the localapi from /api/local/ web client endpoint.
The localapi proxy is restricted to an allowlist of those actually
used by the web client frontend.

Updates tailscale/corp#13775

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-08-29 17:54:59 -04:00
Maisem Ali
c919ff540f cmd/k8s-operator,ipn/store/kubestore: patch secrets instead of updating
We would call Update on the secret, but that was racey and would occasionaly
fail. Instead use patch whenever we can.

Fixes errors like
```
boot: 2023/08/29 01:03:53 failed to set serve config: sending serve config: updating config: writing ServeConfig to StateStore: Operation cannot be fulfilled on secrets "ts-webdav-kfrzv-0": the object has been modified; please apply your changes to the latest version and try again

{"level":"error","ts":"2023-08-29T01:03:48Z","msg":"Reconciler error","controller":"ingress","controllerGroup":"networking.k8s.io","controllerKind":"Ingress","Ingress":{"name":"webdav","namespace":"default"},"namespace":"default","name":"webdav","reconcileID":"96f5cfed-7782-4834-9b75-b0950fd563ed","error":"failed to provision: failed to create or get API key secret: Operation cannot be fulfilled on secrets \"ts-webdav-kfrzv-0\": the object has been modified; please apply your changes to the latest version and try again","stacktrace":"sigs.k8s.io/controller-runtime/pkg/internal/controller.(*Controller).reconcileHandler\n\tsigs.k8s.io/controller-runtime@v0.15.0/pkg/internal/controller/controller.go:324\nsigs.k8s.io/controller-runtime/pkg/internal/controller.(*Controller).processNextWorkItem\n\tsigs.k8s.io/controller-runtime@v0.15.0/pkg/internal/controller/controller.go:265\nsigs.k8s.io/controller-runtime/pkg/internal/controller.(*Controller).Start.func2.2\n\tsigs.k8s.io/controller-runtime@v0.15.0/pkg/internal/controller/controller.go:226"}
```

Updates #502
Updates #7895

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-08-29 13:24:05 -07:00
Joe Tsai
930e6f68f2 types/opt: use switch in Bool.UnmarshalJSON (#9140)
The compiler does indeed perform this optimization.

Updates #cleanup

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2023-08-29 13:12:49 -07:00
Brad Fitzpatrick
11ece02f52 net/{interfaces,netmon}: remove "interesting", EqualFiltered API
This removes a lot of API from net/interfaces (including all the
filter types, EqualFiltered, active Tailscale interface func, etc) and
moves the "major" change detection to net/netmon which knows more
about the world and the previous/new states.

Updates #9040

Change-Id: I7fe66a23039c6347ae5458745b709e7ebdcce245
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-29 11:57:30 -07:00
Brad Fitzpatrick
6dfa403e6b cmd/tailscaled: default to userspace-networking on plan9
No tun support yet.

Updates #5794

Change-Id: Ibd8db67594d4c65b47e352ae2af2ab3d2712dfad
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-29 11:46:33 -07:00
Sonia Appasamy
7aea219a0f client/web: pull SynoToken logic into apiFetch
Updates tailscale/corp#13775
2023-08-29 14:27:38 -04:00
Brad Fitzpatrick
6b882a1511 control/controlclient: clean up a few little things
De-pointer a *time.Time type, move it after the mutex which guard is,
rename two test-only methods with our conventional "ForTest" suffix.

Updates #cleanup

Change-Id: I4f4d1acd9c2de33d9c3cb6465d7349ed051aa9f9
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-29 08:17:23 -07:00
Brad Fitzpatrick
3bce9632d9 derp/derphttp: fix data race and crash in proxy dial error path
Named result meant error paths assigned that variable to nil.
But a goroutine was concurrently using that variable.

Don't use a named result for that first parameter. Then then return
paths don't overwrite it.

Fixes #9129

Change-Id: Ie57f99d40ca8110085097780686d9bd620aaf160
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-29 07:56:54 -07:00
Val
8ba07aac85 ipn/iplocale: remove unused argument to shouldUseOneCGNATRoute
Remove an unused argument to shouldUseOneCGNATRoute.

Updates #cleanup

Signed-off-by: Val <valerie@tailscale.com>
2023-08-29 04:48:28 -07:00
Brad Fitzpatrick
55bb7314f2 control/controlclient: replace a status func with Observer interface
For now the method has only one interface (the same as the func it's
replacing) but it will grow, eventually with the goal to remove the
controlclient.Status type for most purposes.

Updates #1909

Change-Id: I715c8bf95e3f5943055a94e76af98d988558a2f2
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-28 21:07:04 -07:00
Brad Fitzpatrick
a64593d7ef types/logger: fix test failure I missed earlier
I didn't see the race builder fail on CI earlier in 590c693b9.
This fixes the test.

Updates #greenci

Change-Id: I9f271bfadfc29b010226b55bf6647f35f03730b1
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-28 21:06:03 -07:00
Brad Fitzpatrick
590c693b96 types/logger: add AsJSON
Printing out JSON representation things in log output is pretty common.

Updates #cleanup

Change-Id: Ife2d2e321a18e6e1185efa8b699a23061ac5e5a4
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-28 15:14:24 -07:00
Brad Fitzpatrick
a79b1d23b8 control/controlclient: convert PeersChanged nodes to patches internally
So even if the server doesn't support sending patches (neither the
Tailscale control server nor Headscale yet do), this makes the client
convert a changed node to its diff so the diffs can be processed
individually in a follow-up change.

This lets us make progress on #1909 without adding a dependency on
finishing the server-side part, and also means other control servers
will get the same upcoming optimizations.

And add some clientmetrics while here.

Updates #1909

Change-Id: I9533bcb8bba5227e17389f0b10dff71f33ee54ec
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-28 15:03:12 -07:00
Andrew Lytvynov
67e48d9285 clientupdate: use SPKsVersion instead of Version (#9118)
Top-level Version in pkgs response is not always in sync with SPK
versions, especially on unstable track. It's very confusing when the
confirmation prompt asks you "update to 1.49.x?" and you end up updating
to 1.49.y.
Instead, grab the SPK-specific version field.

Updates #cleanup.

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-08-28 14:26:19 -07:00
Andrew Lytvynov
8d2eaa1956 clientupdate: download SPK and MSI packages with distsign (#9115)
Reimplement `downloadURLToFile` using `distsign.Download` and move all
of the progress reporting logic over there.

Updates #6995
Updates #755

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-08-28 13:48:33 -07:00
Maisem Ali
0c6fe94cf4 cmd/k8s-operator: add matching family addresses to status
This was added in 3451b89e5f, but
resulted in the v6 Tailscale address being added to status when
when the forwarding only happened on the v4 address.

Updates #502

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-08-28 13:41:17 -07:00
Maisem Ali
f92e6a1be8 cmd/k8s-operator: update RBAC to allow creating events
The new ingress reconcile raises events on failure, but I forgot to
add the updated permission.

Updates #502

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-08-28 13:15:04 -07:00
Joe Tsai
fcbb2bf348 net/memnet: export the network name (#9111)
This makes it more maintainable for other code to statically depend
on the exact value of this string. It also makes it easier to
identify what code might depend on this string by looking up
references to this constant.

Updates tailscale/corp#13777

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2023-08-28 11:43:51 -07:00
Chris Palmer
346dc5f37e ipn/ipnlocal: move C2NUpdateResponse to c2ntypes.go (#9112)
Updates #cleanup

Signed-off-by: Chris Palmer <cpalmer@tailscale.com>
2023-08-28 11:30:55 -07:00
Will Norris
d74c771fda client/web: always use new web client; remove old client
This uses the new react-based web client for all builds, not just with
the --dev flag.

If the web client assets have not been built, the client will serve a
message that Tailscale was built without the web client, and link to
build instructions. Because we will include the web client in all of our
builds, this should only be seen by developers or users building from
source. (And eventually this will be replaced by attempting to download
needed assets as runtime.)

We do now checkin the build/index.html file, which serves the error
message when assets are unavailable.  This will also eventually be used
to trigger in CI when new assets should be built and uploaded to a
well-known location.

Updates tailscale/corp#13775

Signed-off-by: Will Norris <will@tailscale.com>
2023-08-28 11:11:16 -07:00
Will Norris
be5bd1e619 client/web: skip authorization checks for static assets
Updates tailscale/corp#13775

Signed-off-by: Will Norris <will@tailscale.com>
2023-08-28 11:11:16 -07:00
Andrew Lytvynov
18d9c92342 release/dist/cli: add verify-package-signature command (#9110)
Helper command to verify package signatures, mainly for debugging.
Also fix a copy-paste mistake in error message in distsign.

Updates #8760

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-08-28 10:52:05 -07:00
Andrew Dunham
c86a610eb3 cmd/tailscale, net/portmapper: add --log-http option to "debug portmap"
This option allows logging the raw HTTP requests and responses that the
portmapper Client makes when using UPnP. This can be extremely helpful
when debugging strange UPnP issues with users' devices, and might allow
us to avoid having to instruct users to perform a packet capture.

Updates #8992

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I2c3cf6930b09717028deaff31738484cc9b008e4
2023-08-28 13:06:17 -04:00
Mike Beaumont
3451b89e5f cmd/k8s-operator: put Tailscale IPs in Service ingress status
Updates #502

Signed-off-by: Mike Beaumont <mjboamail@gmail.com>
2023-08-28 09:07:18 -07:00
Mike Beaumont
ce4bf41dcf cmd/k8s-operator: support being the default loadbalancer controller
Updates #502

Signed-off-by: Mike Beaumont <mjboamail@gmail.com>
2023-08-28 08:43:46 -07:00
Brad Fitzpatrick
4af22f3785 util/deephash: add IncludeFields, ExcludeFields HasherForType Options
Updates tailscale/corp#6198

Change-Id: Iafc18c5b947522cf07a42a56f35c0319cc7b1c94
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-27 21:01:12 -07:00
Brad Fitzpatrick
e7d1538a2d types/views: add SliceEqual, like std slices.Equal
Updates tailscale/corp#6198

Change-Id: I38614a4552c9fa933036aa493c7cdb57c7ffe2d2
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-27 18:54:03 -07:00
David Anderson
b407fdef70 flake.nix: use Go 1.21 to build tailscale, for real this time
The previous change just switched the Go version used in the dev
environment (for use with e.g. direnv), not the version used for
the distribution build. Oops.

Updates #cleanup

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-08-26 21:10:43 -07:00
David Anderson
fe91160775 flake.nix: use Go 1.21 to build tailscale flake
Updates #cleanup

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-08-26 21:05:25 -07:00
Flakes Updater
e80ba4ce79 go.mod.sri: update SRI hash for go.mod changes
Signed-off-by: Flakes Updater <noreply+flakes-updater@tailscale.com>
2023-08-26 20:50:03 -07:00
Maisem Ali
9430481926 cmd/containerboot: account for k8s secret reflection in fsnotify
On k8s the serve-config secret mount is symlinked so checking against
the Name makes us miss the events.

Updates #7895

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-08-25 18:19:12 -04:00
Andrew Lytvynov
ce5909dafc release/dist: remove extra Close on a signed file (#9094)
We pass the file as an io.Reader to http.Post under the hood as request
body. Post, helpfully, detects that the body is an io.Closer and closes
it. So when we try to explicitly close it again, we get "file already
closed" error.

The Close there is not load-bearing, we have a defer for it anyway.
Remove the explicit close and error check.

Updates #cleanup

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-08-25 11:36:39 -07:00
Sonia Appasamy
4828e4c2db client/web: move api handler into web.go
Also uses `http.HandlerFunc` to pass the handler into `csrfProtect`
so we can get rid of the extraneous `api` struct.

Updates tailscale/corp#13775

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-08-25 14:27:25 -04:00
Dave Anderson
7b18ed293b tsweb: check for key-based debug access before XFF check (#9093)
Fly apps all set X-Forwarded-For, which breaks debug access even
with a preshared key otherwise.

Updates tailscale/corp#3601

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-08-25 11:12:11 -07:00
Aaron Klotz
6b6a8cf843 util/osdiag: add query for Windows page file configuration and status
It's very common for OOM crashes on Windows to be caused by lack of page
file space (the NT kernel does not overcommit). Since Windows automatically
manages page file space by default, unless the machine is out of disk space,
this is typically caused by manual page file configurations that are too
small.

This patch obtains the current page file size, the amount of free page file
space, and also determines whether the page file is automatically or manually
managed.

Fixes #9090

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2023-08-25 10:31:36 -06:00
Denton Gentry
535db01b3f scripts/installer: add Kaisen, Garuda, Fedora-Asahi.
Fixes https://github.com/tailscale/tailscale/issues/8648
Fixes https://github.com/tailscale/tailscale/issues/8737
Fixes https://github.com/tailscale/tailscale/issues/9087

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2023-08-25 08:40:14 -07:00
Maisem Ali
c8dea67cbf cmd/k8s-operator: add support for Ingress resources
Previously, the operator would only monitor Services and create
a Tailscale StatefulSet which acted as a L3 proxy which proxied
traffic inbound to the Tailscale IP onto the services ClusterIP.

This extends that functionality to also monitor Ingress resources
where the `ingressClassName=tailscale` and similarly creates a
Tailscale StatefulSet, acting as a L7 proxy instead.

Users can override the desired hostname by setting:

```
- tls
  hosts:
  - "foo"
```

Hostnames specified under `rules` are ignored as we only create a single
host. This is emitted as an event for users to see.

Fixes #7895

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-08-25 00:28:11 -04:00
Maisem Ali
320f77bd24 cmd/containerboot: add support for setting ServeConfig
This watches the provided path for a JSON encoded ipn.ServeConfig.
Everytime the file changes, or the nodes FQDN changes it reapplies
the ServeConfig.

At boot time, it nils out any previous ServeConfig just like tsnet does.

As the ServeConfig requires pre-existing knowledge of the nodes FQDN to do
SNI matching, it introduces a special `${TS_CERT_DOMAIN}` value in the JSON
file which is replaced with the known CertDomain before it is applied.

Updates #502
Updates #7895

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-08-24 18:58:40 -04:00
Maisem Ali
12ac672542 cmd/k8s-operator: handle changes to services w/o teardown
Previously users would have to unexpose/expose the service in order to
change Hostname/TargetIP. This now applies those changes by causing a
StatefulSet rollout now that a61a9ab087 is in.

Updates #502

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-08-24 18:57:50 -04:00
Denton Gentry
24d41e4ae7 cmd/sniproxy: add port forwarding and prometheus metrics
1. Add TCP port forwarding.
   For example: ./sniproxy -forwards=tcp/22/github.com
   will forward SSH to github.

   % ssh -i ~/.ssh/id_ecdsa.pem -T git@github.com
   Hi GitHubUser! You've successfully authenticated, but GitHub does not
   provide shell access.

   % ssh -i ~/.ssh/id_ecdsa.pem -T git@100.65.x.y
   Hi GitHubUser! You've successfully authenticated, but GitHub does not
   provide shell access.

2. Additionally export clientmetrics as prometheus metrics for local
   scraping over the tailnet: http://sniproxy-hostname:8080/debug/varz

Updates https://github.com/tailscale/tailscale/issues/1748

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2023-08-24 15:52:17 -07:00
Brad Fitzpatrick
98a5116434 all: adjust some build tags for plan9
I'm not saying it works, but it compiles.

Updates #5794

Change-Id: I2f3c99732e67fe57a05edb25b758d083417f083e
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-24 15:42:35 -07:00
Andrew Lytvynov
de9ba1c621 clientupdate/distsign/roots: add temporary dev root key (#9080)
Adding a root key that signs the current signing key on
pkgs.tailscale.com. This key is here purely for development and should
be replaced before 1.50 release.

Updates #8760

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-08-24 15:24:26 -07:00
Sonia Appasamy
f3077c6ab5 client/web: add self node cache
Adds a cached self node to the web client Server struct, which will
be used from the web client api to verify that request came from the
node's own machine (i.e. came from the web client frontend). We'll
be using when we switch the web client api over to acting as a proxy
to the localapi, to protect against DNS rebinding attacks.

Updates tailscale/corp#13775

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-08-24 18:23:37 -04:00
Andrew Lytvynov
3b7ebeba2e clientupdate: remove Arch support (#9081)
An Arch Linux maintainer asked us to not implement "tailscale update" on
Arch-based distros:
https://github.com/tailscale/tailscale/issues/6995#issuecomment-1687080106

Return an error to the user if they try to run "tailscale update".

Updates #6995

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-08-24 15:23:13 -07:00
Andrew Lytvynov
b42c4e2da1 cmd/dist,release/dist: add distsign signing hooks (#9070)
Add `dist.Signer` hook which can arbitrarily sign linux/synology
artifacts. Plumb it through in `cmd/dist` and remove existing tarball
signing key. Distsign signing will happen on a remote machine, not using
a local key.

Updates #755
Updates #8760

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-08-24 14:36:47 -07:00
Will Norris
dc8287ab3b client/web: enforce full path for CGI platforms
Synology and QNAP both run the web client as a CGI script. The old web
client didn't care too much about requests paths, since there was only a
single GET and POST handler. The new client serves assets on different
paths, so now we need to care.

First, enforce that the CGI script is always accessed from its full
path, including a trailing slash (e.g. /cgi-bin/tailscale/index.cgi/).
Then, strip that prefix off before passing the request along to the main
serve handler. This allows for properly serving both static files and
the API handler in a CGI environment. Also add a CGIPath option to allow
other CGI environments to specify a custom path.

Finally, update vite and one "api/data" call to no longer assume that we
are always serving at the root path of "/".

Updates tailscale/corp#13775

Signed-off-by: Will Norris <will@tailscale.com>
2023-08-24 14:17:41 -07:00
Will Norris
0c3d343ea3 client/web: invert auth logic for synology and qnap
Add separate server methods for synology and qnap, and enforce
authentication and authorization checks before calling into the actual
serving handlers. This allows us to remove all of the auth logic from
those handlers, since all requests will already be authenticated by that
point.

Also simplify the Synology token redirect handler by using fetch.

Remove the SynologyUser from nodeData, since it was never used in the
frontend anyway.

Updates tailscale/corp#13775

Signed-off-by: Will Norris <will@tailscale.com>
2023-08-24 14:17:41 -07:00
Will Norris
05486f0f8e client/web: move synology and qnap logic into separate files
This commit doesn't change any of the logic, but just organizes the code
a little to prepare for future changes.

Updates tailscale/corp#13775

Signed-off-by: Will Norris <will@tailscale.com>
2023-08-24 14:17:41 -07:00
Maisem Ali
ff7f4b4224 cmd/testwrapper: fix off-by-one error in maxAttempts check
It was checking if `>= maxAttempts` which meant that the third
attempt would never run.

Updates #8493

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-08-24 16:59:37 -04:00
Maisem Ali
a61a9ab087 cmd/containerboot: reapply known args on restart
Previously we would not reapply changes to TS_HOSTNAME etc when
then the container restarted and TS_AUTH_ONCE was enabled.

This splits those into two steps login and set, allowing us to
only rerun the set step on restarts.

Updates #502

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-08-24 16:05:21 -04:00
Andrew Lytvynov
d45af7c66f release/dist/cli: add sign-key and verify-key-signature commands (#9041)
Now we have all the commands to generate the key hierarchy and verify
that signing keys were signed correctly:
```
$ ./tool/go run ./cmd/dist gen-key --priv-path root-priv.pem --pub-path root-pub.pem --root
wrote private key to root-priv.pem
wrote public key to root-pub.pem

$ ./tool/go run ./cmd/dist gen-key --priv-path signing-priv.pem --pub-path signing-pub.pem --signing
wrote private key to signing-priv.pem
wrote public key to signing-pub.pem

$ ./tool/go run ./cmd/dist sign-key --root-priv-path root-priv.pem --sign-pub-path signing-pub.pem
wrote signature to signature.bin

$ ./tool/go run ./cmd/dist verify-key-signature --root-pub-path root-pub.pem --sign-pub-path signing-pub.pem --sig-path signature.bin
signature ok
```

Updates #8760

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-08-24 10:54:42 -07:00
Aaron Klotz
5fb1695bcb util/osdiag, util/osdiag/internal/wsc: add code to probe the Windows Security Center for installed software
The Windows Security Center is a component that manages the registration of
security products on a Windows system. Only products that have obtained a
special cert from Microsoft may register themselves using the WSC API.
Practically speaking, most vendors do in fact sign up for the program as it
enhances their legitimacy.

From our perspective, this is useful because it gives us a high-signal
source of information to query for the security products installed on the
system. I've tied this query into the osdiag package and is run during
bugreports.

It uses COM bindings that were automatically generated by my prototype
metadata processor, however that program still has a few bugs, so I had
to make a few manual tweaks. I dropped those binding into an internal
package because (for the moment, at least) they are effectively
purpose-built for the osdiag use case.

We also update the wingoes dependency to pick up BSTR.

Fixes #10646

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2023-08-24 11:51:18 -06:00
Sonia Appasamy
349c05d38d client/web: refresh on tab focus
Refresh node data when user switches to the web client browser tab.
This helps clean up the auth flow where they're sent to another tab
to authenticate then return to the original tab, where the data
should be refreshed to pick up the login updates.

Updates tailscale/corp#13775

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-08-24 12:22:47 -04:00
Will Norris
824cd02d6d client/web: cache csrf key when running in CGI mode
Indicate to the web client when it is running in CGI mode, and if it is
then cache the csrf key between requests.

Updates tailscale/corp#13775

Signed-off-by: Will Norris <will@tailscale.com>
2023-08-24 09:17:04 -07:00
shayne
46b0c9168f .github: update flakehub workflow to support existing tags (#9067)
This adds a workflow_dispatch input to the update-flakehub workflow that
allows the user to specify an existing tag to publish to FlakeHub. This
is useful for publishing a version of a package that has already been
tagged in the repository.

Updates #9008

Signed-off-by: Shayne Sweeney <shayne@tailscale.com>
2023-08-24 11:09:16 -04:00
shayne
7825074444 .github: fix flakehub-publish-tagged.yml glob (#9066)
The previous regex was too advanced for GitHub Actions. They only
support a simpler glob syntax.

https://docs.github.com/en/actions/using-workflows/workflow-syntax-for-github-actions#filter-pattern-cheat-sheet

Updates #9008

Signed-off-by: Shayne Sweeney <shayne@tailscale.com>
2023-08-24 10:50:25 -04:00
Brad Fitzpatrick
5b6a90fb33 types/logger, cmd/tailscale/cli: flesh out, simplify some non-unix build tags
Can write "wasm" instead of js || wasi1p, since there's only two:

    $ go tool dist list | grep wasm
    js/wasm
    wasip1/wasm

Plus, if GOOS=wasip2 is added later, we're already set.

Updates #5794

Change-Id: Ifcfb187c3775c17c9141bc721512dc4577ac4434
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-24 03:41:13 -07:00
Brad Fitzpatrick
a5dcc4c87b paths: remove wasm file, no-op stubs, make OS-specific funcs consistent
Some OS-specific funcs were defined in init. Another used build tags
and required all other OSes to stub it out. Another one could just be in
the portable file.

Simplify it a bit, removing a file and some stubs in the process.

Updates #5794

Change-Id: I51df8772cc60a9335ac4c1dc0ab59b8a0d236961
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-24 03:40:52 -07:00
Brad Fitzpatrick
d58ba59fd5 cmd/tailscale/cli: make netcheck run even if machine lacks TLS certs
We have a fancy package for doing TLS cert validation even if the machine
doesn't have TLS certs (for LetsEncrypt only) but the CLI's netcheck command
wasn't using it.

Also, update the tlsdial's outdated package docs while here.

Updates #cleanup

Change-Id: I74b3cb645d07af4d8ae230fb39a60c809ec129ad
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-23 21:11:04 -07:00
Brad Fitzpatrick
e881c1caec net/netmon: factor out debounce loop, simplify polling impl
This simplifies some netmon code in prep for other changes.

It breaks up Monitor.debounce into a helper method so locking is
easier to read and things unindent, and then it simplifies the polling
netmon implementation to remove the redundant stuff that the caller
(the Monitor.debounce loop) was already basically doing.

Updates #9040

Change-Id: Idcfb45201d00ae64017042a7bdee6ef86ad37a9f
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-23 19:42:09 -07:00
Will Norris
9ea3942b1a client/web: don't require secure cookies for csrf
Under normal circumstances, you would typically want to keep the default
behavior of requiring secure cookies.  In the case of the Tailscale web
client, we are regularly serving on localhost (where secure cookies
don't really matter), and/or we are behind a reverse proxy running on a
network appliance like a NAS or Home Assistant. In those cases, those
devices are regularly accessed over local IP addresses without https
configured, so would not work with secure cookies.

Updates tailscale/corp#13775

Signed-off-by: Will Norris <will@tailscale.com>
2023-08-23 16:44:44 -07:00
Andrew Lytvynov
f61dd12f05 clientupdate/distsign: use distinct PEM types for root/signing keys (#9045)
To make key management less error-prone, use different PEM block types
for root and signing keys. As a result, separate out most of the Go code
between root/signing keys too.

Updates #8760

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-08-23 16:13:03 -07:00
Marwan Sulaiman
9c07f4f512 all: replace deprecated ioutil references
This PR removes calls to ioutil library and replaces them
with their new locations in the io and os packages.

Fixes #9034
Updates #5210

Signed-off-by: Marwan Sulaiman <marwan@tailscale.com>
2023-08-23 23:53:19 +01:00
Denton Gentry
1b8a538953 scripts/installer.sh: add CloudLinux and Alibaba Linux
Fixes https://github.com/tailscale/tailscale/issues/9010

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2023-08-23 15:29:17 -07:00
Sonia Appasamy
776f9b5875 client/web: open auth URLs in new browser tab
Open control server auth URLs in new browser tabs on web clients
so users don't loose original client URL when redirected for login.

Updates tailscale/corp#13775

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-08-23 17:38:50 -04:00
Brad Fitzpatrick
ad9b711a1b tailcfg: bump capver to 72 to restore UPnP
Actually fixed in 77ff705545 but that was cherry-picked to a branch
and we don't bump capver in branches.

This tells the control plane that UPnP should be re-enabled going
forward.

Updates #8992

Change-Id: I5c4743eb52fdee94175668c368c0f712536dc26b
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-23 13:55:39 -07:00
Brad Fitzpatrick
ea4425d8a9 ipn/ipnlocal, wgengine/magicsock: move UpdateStatus stuff around
Upcoming work on incremental netmap change handling will require some
replumbing of which subsystems get notified about what. Done naively,
it could break "tailscale status --json" visibility later. To make sure
I understood the flow of all the updates I was rereading the status code
and realized parts of ipnstate.Status were being populated by the wrong
subsystems.

The engine (wireguard) and magicsock (data plane, NAT traveral) should
only populate the stuff that they uniquely know. The WireGuard bits
were fine but magicsock was populating stuff stuff that LocalBackend
could've better handled, so move it there.

Updates #1909

Change-Id: I6d1b95d19a2d1b70fbb3c875fac8ea1e169e8cb0
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-23 13:35:47 -07:00
Maisem Ali
74388a771f cmd/k8s-operator: fix regression from earlier refactor
I forgot to move the defer out of the func, so the tsnet.Server
immediately closed after starting.

Updates #502

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-08-23 15:14:29 -04:00
Brad Fitzpatrick
9089efea06 net/netmon: make ChangeFunc's signature take new ChangeDelta, not bool
Updates #9040

Change-Id: Ia43752064a1a6ecefc8802b58d6eaa0b71cf1f84
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-23 10:42:14 -07:00
Sonia Appasamy
78f087aa02 cli/web: pass existing localClient to web client
Updates tailscale/corp#13775

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-08-23 13:25:11 -04:00
David Anderson
5cfa85e604 tsweb: clean up pprof handler registration, document why it's there
Updates #cleanup

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-08-23 10:16:14 -07:00
Will Norris
09068f6c16 release: add empty embed.FS for release files
This ensures that `go mod vendor` includes these files, which are needed
for client builds run in corp.

Updates tailscale/corp#13775

Signed-off-by: Will Norris <will@tailscale.com>
2023-08-23 09:54:10 -07:00
Maisem Ali
836f932ead cmd/k8s-operator: split operator.go into svc.go/sts.go
Updates #502

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-08-23 12:07:07 -04:00
Maisem Ali
7f6bc52b78 cmd/k8s-operator: refactor operator code
It was jumbled doing a lot of things, this breaks it up into
the svc reconciliation and the tailscale sts reconciliation.

Prep for future commit.

Updates #502

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-08-23 12:07:07 -04:00
Will Norris
cf45d6a275 client/web: remove old /redirect handler
I thought this had something to do with Synology or QNAP support, since
they both have specific authentication logic.  But it turns out this was
part of the original web client added in #1621, and then refactored as
part of #2093.  But with how we handle logging in now, it's never
called.

Updates tailscale/corp#13775

Signed-off-by: Will Norris <will@tailscale.com>
2023-08-22 16:39:30 -07:00
Andrew Lytvynov
05523bdcdd release/dist/cli: add gen-key command (#9023)
Add a new subcommand to generate a Ed25519 key pair for release signing.
The same command can be used to generate both root and signing keys.

Updates #8760

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-08-22 16:29:56 -07:00
James Tucker
e1c7e9b736 wgengine/magicsock: improve endpoint selection for WireGuard peers with rx time
If we don't have the ICMP hint available, such as on Android, we can use
the signal of rx traffic to bias toward a particular endpoint.

We don't want to stick to a particular endpoint for a very long time
without any signals, so the sticky time is reduced to 1 second, which is
large enough to avoid excessive packet reordering in the common case,
but should be small enough that either rx provides a strong signal, or
we rotate in a user-interactive schedule to another endpoint, improving
the feel of failover to other endpoints.

Updates #8999

Co-authored-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>

Signed-off-by: James Tucker <james@tailscale.com>
Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2023-08-22 15:39:08 -07:00
James Tucker
5edb39d032 wgengine/magicsock: clear out endpoint statistics when it becomes bad
There are cases where we do not detect the non-viability of a route, but
we will instead observe a failure to send. In a Disco path this would
normally be handled as a side effect of Disco, which is not available to
non-Disco WireGuard nodes. In both cases, recognizing the failure as
such will result in faster convergence.

Updates #8999
Signed-off-by: James Tucker <james@tailscale.com>
2023-08-22 15:22:50 -07:00
Charlotte Brandhorst-Satzkorn
7c9c68feed wgengine/magicsock: update lastfullping comment to include wg only
LastFullPing is now used for disco or wireguard only endpoints. This
change updates the comment to make that clear.

Updates #7826

Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2023-08-22 14:31:19 -07:00
Aaron Klotz
ea693eacb6 util/winutil: add RegisterForRestart, allowing programs to indicate their preferences to the Windows restart manager
In order for the installer to restart the GUI correctly post-upgrade, we
need the GUI to be able to register its restart preferences.

This PR adds API support for doing so. I'm adding it to OSS so that it
is available should we need to do any such registrations on OSS binaries
in the future.

Updates https://github.com/tailscale/corp/issues/13998

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2023-08-22 15:06:48 -06:00
James Tucker
3a652d7761 wgengine/magicsock: clear endpoint state in noteConnectivityChange
There are latency values stored in bestAddr and endpointState that are
no longer applicable after a connectivity change and should be cleared
out, following the documented behavior of the function.

Updates #8999

Signed-off-by: James Tucker <james@tailscale.com>
2023-08-22 13:38:20 -07:00
Andrew Lytvynov
7364c6beec clientupdate/distsign: add new library for package signing/verification (#8943)
This library is intended for use during release to sign packages which
are then served from pkgs.tailscale.com.
The library is also then used by clients downloading packages for
`tailscale update` where OS package managers / app stores aren't used.

Updates https://github.com/tailscale/tailscale/issues/8760
Updates https://github.com/tailscale/tailscale/issues/6995

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-08-22 13:35:30 -07:00
Maisem Ali
4b13e6e087 go.mod: bump golang.org/x/net
Theory is that our long lived http2 connection to control would
get tainted by _something_ (unclear what) and would get closed.

This picks up the fix for golang/go#60818.

Updates tailscale/corp#5761

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-08-22 16:25:19 -04:00
Will Norris
5ebff95a4c client/web: fix globbing for file embedding
src/**/* was only grabbing files in subdirectories, but not in the src
directory itself.

Updates tailscale/corp#13775

Signed-off-by: Will Norris <will@tailscale.com>
2023-08-22 12:42:34 -07:00
Marwan Sulaiman
000c0a70f6 ipn, ipn/ipnlocal: clean up documentation and use clock instead of time
This PR addresses a number of the follow ups from PR #8491 that were written
after getting merged.

Updates #8489

Signed-off-by: Marwan Sulaiman <marwan@tailscale.com>
2023-08-22 19:17:29 +01:00
Will Norris
0df5507c81 client/web: combine embeds into a single embed.FS
instead of embedding each file individually, embed them all into a
single embed filesystem.  This is basically a noop for the current
frontend, but sets things up a little cleaner for the new frontend.

Also added an embed.FS for the source files needed to build the new
frontend. These files are not actually embedded into the binary (since
it is a blank identifier), but causes `go mod vendor` to copy them into
the vendor directory.

Updates tailscale/corp#13775

Signed-off-by: Will Norris <will@tailscale.com>
2023-08-22 11:17:16 -07:00
Will Norris
3722b05465 release/dist: run yarn build before building CLI
This builds the assets for the new web client as part of our release
process. The path to the web client source is specified by the
-web-client-root flag.  This allows corp builds to first vendor the
tailscale.com module, and then build the web client assets in the vendor
directory.

The default value for the -web-client-root flag is empty, so no assets
are built by default.

This is an update of the previously reverted 0fb95ec

Updates tailscale/corp#13775

Signed-off-by: Will Norris <will@tailscale.com>
2023-08-22 11:12:47 -07:00
Sonia Appasamy
09e5e68297 client/web: track web client initializations
Updates tailscale/corp#13775

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-08-22 14:11:19 -04:00
Brad Fitzpatrick
947def7688 types/netmap: remove redundant Netmap.Hostinfo
It was in SelfNode.Hostinfo anyway. The redundant copy was just
costing us an allocation per netmap (a Hostinfo.Clone).

Updates #1909

Change-Id: Ifac568aa5f8054d9419828489442a0f4559bc099
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-22 09:54:02 -07:00
Sonia Appasamy
50b558de74 client/web: hook up remaining legacy POST requests
Hooks up remaining legacy POST request from the React side in --dev.

Updates tailscale/corp#13775

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-08-22 12:42:12 -04:00
Brad Fitzpatrick
db017d3b12 control/controlclient: remove quadratic allocs in mapSession
The mapSession code was previously quadratic: N clients in a netmap
send updates proportional to N and then for each, we do N units of
work. This removes most of that "N units of work" per update. There's
still a netmap-sized slice allocation per update (that's #8963), but
that's it.

Bit more efficient now, especially with larger netmaps:

                                 │     before     │                after                │
                                 │     sec/op     │   sec/op     vs base                │
    MapSessionDelta/size_10-8       47.935µ ±  3%   1.232µ ± 2%  -97.43% (p=0.000 n=10)
    MapSessionDelta/size_100-8      79.950µ ±  3%   1.642µ ± 2%  -97.95% (p=0.000 n=10)
    MapSessionDelta/size_1000-8    355.747µ ± 10%   4.400µ ± 1%  -98.76% (p=0.000 n=10)
    MapSessionDelta/size_10000-8   3079.71µ ±  3%   27.89µ ± 3%  -99.09% (p=0.000 n=10)
    geomean                          254.6µ         3.969µ       -98.44%

                                 │     before     │                after                 │
                                 │      B/op      │     B/op      vs base                │
    MapSessionDelta/size_10-8        9.651Ki ± 0%   2.395Ki ± 0%  -75.19% (p=0.000 n=10)
    MapSessionDelta/size_100-8      83.097Ki ± 0%   3.192Ki ± 0%  -96.16% (p=0.000 n=10)
    MapSessionDelta/size_1000-8     800.25Ki ± 0%   10.32Ki ± 0%  -98.71% (p=0.000 n=10)
    MapSessionDelta/size_10000-8   7896.04Ki ± 0%   82.32Ki ± 0%  -98.96% (p=0.000 n=10)
    geomean                          266.8Ki        8.977Ki       -96.64%

                                 │    before     │               after                │
                                 │   allocs/op   │ allocs/op   vs base                │
    MapSessionDelta/size_10-8         72.00 ± 0%   20.00 ± 0%  -72.22% (p=0.000 n=10)
    MapSessionDelta/size_100-8       523.00 ± 0%   20.00 ± 0%  -96.18% (p=0.000 n=10)
    MapSessionDelta/size_1000-8     5024.00 ± 0%   20.00 ± 0%  -99.60% (p=0.000 n=10)
    MapSessionDelta/size_10000-8   50024.00 ± 0%   20.00 ± 0%  -99.96% (p=0.000 n=10)
    geomean                          1.754k        20.00       -98.86%

Updates #1909

Change-Id: I41ee29358a5521ed762216a76d4cc5b0d16e46ac
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-22 08:59:57 -07:00
shayne
a3b0654ed8 .github: add flakehub-publish-tagged.yml (#9009)
This workflow will publish a flake to flakehub when a tag is pushed to
the repository. It will only publish tags that match the pattern
`v*.*.*`.

Fixes #9008

Signed-off-by: Shayne Sweeney <shayne@tailscale.com>
2023-08-22 11:18:29 -04:00
Marwan Sulaiman
35ff5bf5a6 cmd/tailscale/cli, ipn/ipnlocal: [funnel] add stream mode
Adds ability to start Funnel in the foreground and stream incoming
connections. When foreground process is stopped, Funnel is turned
back off for the port.

Exampe usage:
```
TAILSCALE_FUNNEL_V2=on tailscale funnel 8080
```

Updates #8489

Signed-off-by: Marwan Sulaiman <marwan@tailscale.com>
2023-08-22 10:07:34 -04:00
Brad Fitzpatrick
cb4a61f951 control/controlclient: don't clone self node on each NetworkMap
Drop in the bucket, but have to start somewhere.

Real wins will come once this is done for peers.

                                 │     before     │                after                │
                                 │      B/op      │     B/op       vs base              │
    MapSessionDelta/size_10-8      10.213Ki ± ∞ ¹   9.650Ki ± ∞ ¹  -5.51% (p=0.008 n=5)
    MapSessionDelta/size_100-8      83.64Ki ± ∞ ¹   83.08Ki ± ∞ ¹  -0.67% (p=0.008 n=5)
    MapSessionDelta/size_1000-8     800.8Ki ± ∞ ¹   800.3Ki ± ∞ ¹  -0.07% (p=0.008 n=5)
    MapSessionDelta/size_10000-8    7.712Mi ± ∞ ¹   7.711Mi ± ∞ ¹  -0.01% (p=0.008 n=5)
    geomean                         271.1Ki         266.8Ki        -1.59%

                                 │    before    │               after                │
                                 │  allocs/op   │  allocs/op    vs base              │
    MapSessionDelta/size_10-8       73.00 ± ∞ ¹    72.00 ± ∞ ¹  -1.37% (p=0.008 n=5)
    MapSessionDelta/size_100-8      524.0 ± ∞ ¹    523.0 ± ∞ ¹  -0.19% (p=0.008 n=5)
    MapSessionDelta/size_1000-8    5.025k ± ∞ ¹   5.024k ± ∞ ¹  -0.02% (p=0.008 n=5)
    MapSessionDelta/size_10000-8   50.02k ± ∞ ¹   50.02k ± ∞ ¹  -0.00% (p=0.040 n=5)
    geomean                        1.761k         1.754k        -0.40%

Updates #1909

Change-Id: Ie19dea3371de251d64d4373dd00422f53c2675ea
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-21 15:42:33 -07:00
Will Norris
a461d230db Revert "release/dist: run yarn build before building CLI"
This caused breakages on the build server:

synology/dsm7/x86_64: chdir /home/ubuntu/builds/2023-08-21T21-47-38Z-unstable-main-tagged-devices/0/client/web: no such file or directory
synology/dsm7/i686: chdir /home/ubuntu/builds/2023-08-21T21-47-38Z-unstable-main-tagged-devices/0/client/web: no such file or directory
synology/dsm7/armv8: chdir /home/ubuntu/builds/2023-08-21T21-47-38Z-unstable-main-tagged-devices/0/client/web: no such file or directory
...

Reverting while I investigate.

This reverts commit 0fb95ec07d.

Signed-off-by: Will Norris <will@tailscale.com>
2023-08-21 14:56:05 -07:00
Will Norris
0fb95ec07d release/dist: run yarn build before building CLI
This builds the assets for the new web client as part of our release
process. These assets will soon be embedded into the cmd/tailscale
binary, but are not actually done so yet.

Updates tailscale/corp#13775

Signed-off-by: Will Norris <will@tailscale.com>
2023-08-21 14:30:59 -07:00
Brad Fitzpatrick
84b94b3146 types/netmap, all: make NetworkMap.SelfNode a tailcfg.NodeView
Updates #1909

Change-Id: I8c470cbc147129a652c1d58eac9b790691b87606
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-21 13:34:49 -07:00
License Updater
699f9699ca licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-08-21 12:36:37 -07:00
Flakes Updater
f6615931d7 go.mod.sri: update SRI hash for go.mod changes
Signed-off-by: Flakes Updater <noreply+flakes-updater@tailscale.com>
2023-08-21 12:04:38 -07:00
Sonia Appasamy
077bbb8403 client/web: add csrf protection to web client api
Adds csrf protection and hooks up an initial POST request from
the React web client.

Updates tailscale/corp#13775

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-08-21 15:02:02 -04:00
Andrew Dunham
77ff705545 net/portmapper: never select port 0 in UPnP
Port 0 is interpreted, per the spec (but inconsistently among router
software) as requesting to map every single available port on the UPnP
gateway to the internal IP address. We'd previously avoided picking
ports below 1024 for one of the two UPnP methods (in #7457), and this
change moves that logic so that we avoid it in all cases.

Updates #8992

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I20d652c0cd47a24aef27f75c81f78ae53cc3c71e
2023-08-21 14:33:26 -04:00
Brad Fitzpatrick
b5ff68a968 control/controlclient: flesh out mapSession to break up gigantic method
Now mapSession has a bunch more fields and methods, rather than being
just one massive func with a ton of local variables.

So far there are no major new optimizations, though. It should behave
the same as before.

This has been done with an eye towards testability (so tests can set
all the callback funcs as needed, or not, without a huge Direct client
or long-running HTTP requests), but this change doesn't add new tests
yet. That will follow in the changes which flesh out the NetmapUpdater
interface.

Updates #1909

Change-Id: Iad4e7442d5bbbe2614bd4b1dc4b02e27504898df
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-21 10:38:32 -07:00
Brad Fitzpatrick
1b223566dd util/linuxfw: fix typo in unexported doc comment
And flesh it out and use idiomatic doc style ("whether" for bools)
and end in a period while there anyway.

Updates #cleanup

Change-Id: Ieb82f13969656e2340c3510e7b102dc8e6932611
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-21 10:14:28 -07:00
Val
c85d7c301a tool: force HTTP/1.1 in curl to prevent hang behind load balancer
When running in our github CI environment, curl sometimes hangs while closing
the download from the nodejs.org server and fails with INTERNAL_ERROR. This is
likely caused by CI running behind some kind of load balancer or proxy that
handles HTTP/2 incorrectly in some minor way, so force curl to use HTTP 1.1.

Updates #8988

Signed-off-by: Val <valerie@tailscale.com>
2023-08-21 08:37:26 -07:00
Denton Gentry
f486041fd1 tsnet: add support for clientmetrics.
Updates https://github.com/tailscale/tailscale/issues/1748

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2023-08-21 06:26:40 -07:00
Val
c15997511d wgengine/magicsock: only accept pong sent by CLI ping
When sending a ping from the CLI, only accept a pong that is in reply
to the specific CLI ping we sent.

Updates #311

Signed-off-by: Val <valerie@tailscale.com>
2023-08-21 01:57:41 -07:00
Brad Fitzpatrick
165f0116f1 types/netmap: move some mutations earlier, remove, document some fields
And optimize the Persist setting a bit, allocating later and only mutating
fields when there's been a Node change.

Updates #1909

Change-Id: Iaddfd9e88ef76e1d18e8d0a41926eb44d0955312
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-20 16:26:11 -07:00
Brad Fitzpatrick
21170fb175 control/controlclient: scope a variable tighter, de-pointer a *time.Time
Just misc cleanups.

Updates #1909

Change-Id: I9d64cb6c46d634eb5fdf725c13a6c5e514e02e9a
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-20 15:06:24 -07:00
Maisem Ali
2548496cef types/views,cmd/viewer: add ByteSlice[T] to replace mem.RO
Add a new views.ByteSlice[T ~[]byte] to provide a better API to use
with views.

Updates #cleanup

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-08-20 15:30:35 -04:00
Maisem Ali
8a5ec72c85 cmd/cloner: use maps.Clone and ptr.To
Updates #cleanup

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-08-20 13:47:26 -04:00
Brad Fitzpatrick
4511e7d64e ipn/ipnstate: add PeerStatus.AltSharerUserID, stop mangling Node.User
In b987b2ab18 (2021-01-12) when we introduced sharing we mapped
the sharer to the userid at a low layer, mostly to fix the display of
"tailscale status" and the client UIs, but also some tests.

The commit earlier today, 7dec09d169, removed the 2.5yo option
to let clients disable that automatic mapping, as clearly we were never
getting around to it.

This plumbs the Sharer UserID all the way to ipnstatus so the CLI
itself can choose to print out the Sharer's identity over the node's
original owner.

Then we stop mangling Node.User and let clients decide how they want
to render things.

To ease the migration for the Windows GUI (which currently operates on
tailcfg.Node via the NetMap from WatchIPNBus, instead of PeerStatus),
a new method Node.SharerOrUser is added to do the mapping of
Sharer-else-User.

Updates #1909
Updates tailscale/corp#1183

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-20 08:18:52 -07:00
Maisem Ali
d483ed7774 tailcfg: generate RegisterResponse.Clone, remove manually written
It had a custom Clone func with a TODO to replace with cloner, resolve
that todo. Had to pull out the embedded Auth struct into a named struct.

Updates #cleanup

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-08-19 23:35:57 -04:00
Brad Fitzpatrick
282dad1b62 tailcfg: update docs on NetInfo.FirewallMode
Updates #391

Change-Id: Ifef196b31dd145f424fb0c0d0bb04565cc22c717
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-19 20:19:33 -07:00
Brad Fitzpatrick
d8191a9813 ipn/ipnlocal: fix regression in printf arg type
I screwed this up in 58a4fd43d as I expected. I even looked out for
cases like this (because this always happens) and I still missed
it. Vet doesn't flag these because they're not the standard printf
funcs it knows about. TODO: make our vet recognize all our
"logger.Logf" types.

Updates #8948

Change-Id: Iae267d5f81da49d0876b91c0e6dc451bf7dcd721
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-19 20:03:11 -07:00
Brad Fitzpatrick
f35ff84ee2 util/deephash: relax an annoyingly needy test
I'd added a test case of deephash against a tailcfg.Node to make sure
it worked at all more than anything. We don't care what the exact
bytes are in this test, just that it doesn't fail. So adjust for that.

Then when we make changes to tailcfg.Node and types under it, we don't
need to keep adjusting this test.

Updates #cleanup

Change-Id: Ibf4fa42820aeab8f5292fe65f9f92ffdb0b4407b
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-19 19:57:03 -07:00
Brad Fitzpatrick
93a806ba31 types/tkatype: add test for MarshaledSignature's JSON format
Lock in its wire format before a potential change to its Go type.

Updates #1909

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-19 19:34:18 -07:00
Brad Fitzpatrick
7dec09d169 control/controlclient: remove Opts.KeepSharerAndUserSplit
It was added 2.5 years ago in c1dabd9436 but was never used.
Clearly that migration didn't matter.

We can attempt this again later if/when this matters.

Meanwhile this simplifies the code and thus makes working on other
current efforts in these parts of the code easier.

Updates #1909

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-19 15:06:05 -07:00
Maisem Ali
02b47d123f tailcfg: remove unused Domain field from Login/User
Updates #cleanup

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-08-18 20:07:17 -07:00
Brad Fitzpatrick
58a4fd43d8 types/netmap, all: use read-only tailcfg.NodeView in NetworkMap
Updates #8948

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-18 20:04:35 -07:00
KevinLiang10
b040094b90 util/linuxfw: reorganize nftables rules to allow it to work with ufw
This commit tries to mimic the way iptables-nft work with the filewall rules. We
follow the convention of using tables like filter, nat and the conventional
chains, to make our nftables implementation work with ufw.

Updates: #391

Signed-off-by: KevinLiang10 <kevinliang@tailscale.com>
2023-08-18 18:24:05 -07:00
Will Norris
d4586ca75f tsnet/example/web-client: listen on localhost
Serving the web client on the tailscale interface, while useful for
remote management, is also inherently risky if ACLs are not configured
appropriately. Switch the example to listen only on localhost, which is
a much safer default. This is still a valuable example, since it still
demonstrates how to have a web client connected to a tsnet instance.

Updates #13775

Signed-off-by: Will Norris <will@tailscale.com>
2023-08-18 14:57:08 -07:00
KevinLiang10
93cab56277 wgengine/router: fall back and set iptables as default again
Due to the conflict between our nftables implementation and ufw, which is a common utility used
on linux. We now want to take a step back to prevent regression. This will give us more chance to
let users to test our nftables support and heuristic.

Updates: #391
Signed-off-by: KevinLiang10 <kevinliang@tailscale.com>
2023-08-18 16:33:06 -04:00
Brad Fitzpatrick
6e57dee7eb cmd/viewer, types/views, all: un-special case slice of netip.Prefix
Make it just a views.Slice[netip.Prefix] instead of its own named type.

Having the special case led to circular dependencies in another WIP PR
of mine.

Updates #8948

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-18 12:27:44 -07:00
Brad Fitzpatrick
261cc498d3 types/views: add LenIter method to slice view types
This is basically https://github.com/bradfitz/iter which was
a joke but now that Go's adding range over int soonish, might
as well. It simplies our code elsewher that uses slice views.

Updates #8948

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-18 08:21:52 -07:00
Brad Fitzpatrick
af2e4909b6 all: remove some Debug fields, NetworkMap.Debug, Reconfig Debug arg
Updates #8923

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-17 19:04:30 -07:00
Andrew Lytvynov
86ad1ea60e clientupdate: parse /etc/synoinfo.conf to get CPU arch (#8940)
The hardware version in `/proc/sys/kernel/syno_hw_version` does not map
exactly to versions in
https://github.com/SynoCommunity/spksrc/wiki/Synology-and-SynoCommunity-Package-Architectures.
It contains some slightly different version formats.

Instead, `/etc/synoinfo.conf` exists and contains a `unique` line with
the CPU architecture encoded. Parse that out and filter through the list
of architectures that we have SPKs for.

Tested on DS218 and DS413j.

Updates #8927

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-08-17 16:45:50 -07:00
Marwan Sulaiman
72d2122cad cmd/tailscale: change serve and funnel calls to StatusWithoutPeers
The tailscale serve|funnel commands frequently call the LocalBackend's Status
but they never need the peers to be included. This PR changes the call to be
StatusWithoutPeers which should gain a noticeable speed improvement

Updates #8489

Signed-off-by: Marwan Sulaiman <marwan@tailscale.com>
2023-08-17 17:01:43 -04:00
Brad Fitzpatrick
121d1d002c tailcfg: add nodeAttrs for forcing OneCGNAT on/off [capver 71]
Updates #8923

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-17 13:32:12 -07:00
Brad Fitzpatrick
25663b1307 tailcfg: remove most Debug fields, move bulk to nodeAttrs [capver 70]
Now a nodeAttr: ForceBackgroundSTUN, DERPRoute, TrimWGConfig,
DisableSubnetsIfPAC, DisableUPnP.

Kept support for, but also now a NodeAttr: RandomizeClientPort.

Removed: SetForceBackgroundSTUN, SetRandomizeClientPort (both never
used, sadly... never got around to them. But nodeAttrs are better
anyway), EnableSilentDisco (will be a nodeAttr later when that effort
resumes).

Updates #8923

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-17 10:52:47 -07:00
David Anderson
e92adfe5e4 net/art: allow non-pointers as values
Values are still turned into pointers internally to maintain the
invariants of strideTable, but from the user's perspective it's
now possible to tbl.Insert(pfx, true) rather than
tbl.Insert(pfx, ptr.To(true)).

Updates #7781

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-08-17 10:43:18 -07:00
Brad Fitzpatrick
bc0eb6b914 all: import x/exp/maps as xmaps to distinguish from Go 1.21 "maps"
Updates #8419

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-17 09:54:18 -07:00
Brad Fitzpatrick
e8551d6b40 all: use Go 1.21 slices, maps instead of x/exp/{slices,maps}
Updates #8419

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-17 08:42:35 -07:00
Denton Gentry
e8d140654a cmd/derper: count bootstrap dns unique lookups.
Updates https://github.com/tailscale/corp/issues/13979

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2023-08-17 08:02:56 -07:00
Denton Gentry
7e15c78a5a syncs: add map.Clear() method
Updates https://github.com/tailscale/corp/issues/13979

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2023-08-17 08:02:56 -07:00
Brad Fitzpatrick
239ad57446 tailcfg: move LogHeapPprof from Debug to c2n [capver 69]
And delete Debug.GoroutineDumpURL, which was already in c2n.

Updates #8923

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-16 20:35:04 -07:00
Maisem Ali
24509f8b22 cmd/k8s-operator: add support for control plane assigned groups
Previously we would use the Impersonate-Group header to pass through
tags to the k8s api server. However, we would do nothing for non-tagged
nodes. Now that we have a way to specify these via peerCaps respect those
and send down groups for non-tagged nodes as well.

For tagged nodes, it defaults to sending down the tags as groups to retain
legacy behavior if there are no caps set. Otherwise, the tags are omitted.

Updates #5055

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-08-16 19:40:47 -04:00
Brad Fitzpatrick
0913ec023b CODEOWNERS: add the start of an owners file
Updates tailscale/corp#13972

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-16 15:57:29 -07:00
Brad Fitzpatrick
b090d61c0f tailcfg: rename prototype field to reflect its status
(Added earlier today in #8916, 57da1f150)

Updates tailscale/corp#13969

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-16 15:34:51 -07:00
Richard Castro
57da1f1501 client: update DNSConfig type (#8916)
This PR adds DNSFilterURL to the DNSConfig type to be used by
control changes to add DNS filtering logic

Fixes #cleanup

Signed-off-by: Richard Castro <richard@tailscale.com>
2023-08-16 14:54:17 -07:00
Chris Palmer
37c0b9be63 clientupdate: return NOTREACHED for macsys (#8898)
* clientupdate: return NOTREACHED for macsys

The work is done in Swift; this is now a documentation placeholder.

Updates #6995

Signed-off-by: Chris Palmer <cpalmer@tailscale.com>
2023-08-16 14:01:10 -07:00
Sonia Appasamy
18280ebf7d client/web: hook up data fetching to fill --dev React UI
Updates tailscale/corp#13775

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-08-16 16:14:26 -04:00
David Anderson
623d72c83b net/art: move child table pointers out of strideEntry
In preparation for a different refactor, but incidentally also saves
10-25% memory on overall table size in benchmarks.

Updates #7781

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-08-16 12:17:25 -07:00
Charlotte Brandhorst-Satzkorn
f101a75dce cmd/tailscale/cli: fix comment accuracy
All exit nodes are shown under this subcommand.

Updates tailscale/corp#13025

Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2023-08-16 11:10:50 -07:00
Adrian Dewhurst
f75a36f9bc tsweb: add request ID for errors
If an optional request ID generating func is supplied to StdHandler,
then requests that return an error will be logged with a request ID that
is also shown as part of the response.

Updates tailscale/corp#2549

Change-Id: Ic7499706df42f95b6878d44d4aab253e2fc6a69b
Signed-off-by: Adrian Dewhurst <adrian@tailscale.com>
2023-08-16 12:55:31 -04:00
Andrew Lytvynov
cf31b58ed1 VERSION.txt: this is v1.49.0 (#8907)
Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-08-16 09:37:36 -07:00
Brad Fitzpatrick
6c791f7d60 derp: include src IPs in mesh watch messages
Updates tailscale/corp#13945

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-16 08:46:52 -07:00
KevinLiang10
7ed3681cbe tailcfg: Add FirewallMode to NetInfo to record wether host using iptables or nftables
To record wether user is using iptables or nftables after we add support to nftables on linux, we
are adding a field FirewallMode to NetInfo in HostInfo to reflect what firewall mode the host is
running, and form metrics. The information is gained from a global constant in hostinfo.go. We
set it when selection heuristic made the decision, and magicsock reports this to control.

Updates: tailscale/corp#13943
Signed-off-by: KevinLiang10 <kevinliang@tailscale.com>
2023-08-15 18:52:51 -04:00
Andrew Dunham
95d776bd8c wgengine/magicsock: only cache N most recent endpoints per-Addr
If a node is flapping or otherwise generating lots of STUN endpoints, we
can end up caching a ton of useless values and sending them to peers.
Instead, let's apply a fixed per-Addr limit of endpoints that we cache,
so that we're only sending peers up to the N most recent.

Updates tailscale/corp#13890

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I8079a05b44220c46da55016c0e5fc96dd2135ef8
2023-08-15 14:06:42 -07:00
Will Norris
9c4364e0b7 client/web: copy existing UI to basic react components
This copies the existing go template frontend into very crude react
components that will be driven by a simple JSON api for fetching and
updating data.  For now, this returns a static set of test data.

This just implements the simple existing UI, so I've put these all in a
"legacy" component, with the expectation that we will rebuild this with
more properly defined components, some pulled from corp.

Updates tailscale/corp#13775

Signed-off-by: Will Norris <will@tailscale.com>
2023-08-15 12:01:36 -07:00
Will Norris
ddba4824c4 client/web: add prettier and format scripts
Updates tailscale/corp#13775

Signed-off-by: Will Norris <will@tailscale.com>
2023-08-15 12:01:36 -07:00
Brad Fitzpatrick
bd02d00608 ssh/tailssh: fix gokrazy SSH crash
Stupid mistake in earlier refactor.

Updates gokrazy/gokrazy#209

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-15 10:56:25 -07:00
Brad Fitzpatrick
25a8daf405 wgengine/router: always use nftables mode on gokrazy
Updates gokrazy/gokrazy#209

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-15 10:55:56 -07:00
Brad Fitzpatrick
17ce75347c wgengine: adjust debug logging for WireGuard-only peers
Updates #cleanup

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-15 10:05:29 -07:00
Sonia Appasamy
1a64166073 cli/serve: add interactive flow for enabling HTTPS certs
When trying to use serve with https, send users through https cert
provisioning enablement before editing the ServeConfig.

Updates tailscale/corp#10577

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-08-15 12:32:58 -04:00
Sonia Appasamy
0052830c64 cli/serve: funnel interactive enablement flow tweaks
1. Add metrics to funnel flow.
2. Stop blocking users from turning off funnels when no longer in
   their node capabilities.
3. Rename LocalClient.IncrementMetric to IncrementCounter to better
   callout its usage is only for counter clientmetrics.

Updates tailscale/corp#10577

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-08-15 00:46:18 -04:00
Sonia Appasamy
8e63d75018 client/tailscale: add LocalClient.IncrementMetric func
A #cleanup to add a func to utilize the already-present
"/localapi/v0/upload-client-metrics" localapi endpoint.

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-08-14 18:56:30 -04:00
Aaron Klotz
c17a817769 util/osdiag: add logging for winsock layered service providers to Windows bugreports
The Layered Service Provider (LSP) is a deprecated (but still supported)
mechanism for inserting user-mode DLLs into a filter chain between the
Winsock API surface (ie, ws2_32.dll) and the internal user-mode interface
to the networking stack.

While their use is becoming more rare due to the aforementioned deprecation,
it is still possible for third-party software to install their DLLs into
this filter chain and interfere with Winsock API calls. Knowing whether
this is happening is useful for troubleshooting.

Fixes https://github.com/tailscale/tailscale/issues/8142

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2023-08-14 15:03:54 -06:00
KevinLiang10
411e3364a9 wgengine/router: use iptablesRunner when no firewall tool is available:
The current router errors out when neither iptables nor nftables support is present. We
should fall back to the previous behaviour which we creates a dummy iptablesRunner.

Fixes: #8878
Signed-off-by: KevinLiang10 <kevinliang@tailscale.com>
2023-08-14 16:21:23 -04:00
Sonia Appasamy
12238dab48 client/web: add tailwind styling to react app
Updates tailscale/corp#13775

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-08-14 15:29:12 -04:00
Aaron Klotz
b07347640c util/winutil/authenticode: add missing docs for CertSubjectError
A #cleanup PR.

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2023-08-14 11:07:12 -06:00
Brad Fitzpatrick
1fcae42055 control/controlclient: move lastUpdateGenInformed to tighter scope
No need to have it on Auto or be behind a mutex; it's only read/written
from a single goroutine. Move it there.

Updates tailscale/corp#5761

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-13 10:39:17 -07:00
Brad Fitzpatrick
2398993804 control/controlclient: refactor in prep for optimized delta handling
See issue. This is a baby step towards passing through deltas
end-to-end from node to control back to node and down to the various
engine subsystems, not computing diffs from two full netmaps at
various levels. This will then let us support larger netmaps without
burning CPU.

But this change itself changes no behavior. It just changes a func
type to an interface with one method. That paves the way for future
changes to then add new NetmapUpdater methods that do more
fine-grained work than updating the whole world.

Updates #1909

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-12 16:09:58 -07:00
Denton Gentry
4940a718a1 scripts/installer.sh: set Deepin to a debian version
Deepin Linux 20.x reports its version as "apricot"
Set it to bullseye, the Debian version it corresponds to.

Also fix the installer CI: OpenSUSE Leap appears to have removed
curl from the base image recently, we have to install it now.

Fixes https://github.com/tailscale/tailscale/issues/8850
Updates https://github.com/tailscale/tailscale/issues/7862
Updates https://github.com/tailscale/corp/issues/8952

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2023-08-12 07:51:11 -07:00
M. J. Fromberger
9e24a6508a control/controlclient: avert a data race when logging (#8863)
The read of the synced field for logging takes place outside the lock, and
races with other (locked) writes of this field, including for example the one
at current line 556 in mapRoutine.

Updates tailscale/corp#13856

Change-Id: I056b36d7a93025aafdf73528dd7645f10b791af6
Signed-off-by: M. J. Fromberger <fromberger@tailscale.com>
2023-08-11 18:49:40 -07:00
Andrew Lytvynov
c40d095c35 clientupdate: implement updates for Synology (#8858)
Implement naive update for Synology packages, using latest versions from
pkgs.tailscale.com. This is naive because we completely trust
pkgs.tailscale.com to give us a safe package. We should switch this to
some better signing mechanism later.

I've only tested this on one DS218 box, so all the CPU architecture
munging is purely based on docs.

Updates #6995

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-08-11 14:55:07 -07:00
Brad Fitzpatrick
a1b8d703d6 tstime/mono: remove unsafe
This removes the unsafe/linkname and only uses the standard library.

It's a bit slower, for now, but https://go.dev/cl/518336 should get us
back.

On darwin/arm64, without https://go.dev/cl/518336

    pkg: tailscale.com/tstime/mono
              │   before    │                after                │
              │   sec/op    │   sec/op     vs base                │
    MonoNow-8   16.20n ± 0%   19.75n ± 0%  +21.92% (p=0.000 n=10)
    TimeNow-8   39.46n ± 0%   39.40n ± 0%   -0.16% (p=0.002 n=10)
    geomean     25.28n        27.89n       +10.33%

And with it,

    MonoNow-8   16.34n ±  1%   16.93n ± 0%  +3.67% (p=0.001 n=10)
    TimeNow-8   39.55n ± 15%   38.46n ± 1%  -2.76% (p=0.000 n=10)
    geomean     25.42n         25.52n       +0.41%

Updates #8839
Updates tailscale/go#70

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-11 13:23:16 -07:00
shayne
cc3caa4b2a hostinfo: add Home Assistant Add-On detection (#8857)
Fixes #8856

Signed-off-by: Shayne Sweeney <shayne@tailscale.com>
2023-08-11 15:55:01 -04:00
James Tucker
de8e55fda6 net/netcheck,wgengine/magicsock: reduce coupling between netcheck and magicsock
Netcheck no longer performs I/O itself, instead it makes requests via
SendPacket and expects users to route reply traffic to
ReceiveSTUNPacket.

Netcheck gains a Standalone function that stands up sockets and
goroutines to implement I/O when used in a standalone fashion.

Magicsock now unconditionally routes STUN traffic to the netcheck.Client
that it hosts, and plumbs the send packet sink.

The CLI is updated to make use of the Standalone mode.

Fixes #8723

Signed-off-by: James Tucker <james@tailscale.com>
2023-08-11 10:08:21 -07:00
Sonia Appasamy
d5ac18d2c4 client/web: add tsconfig.json
Also allows us to use absolute import paths (see change in index.tsx).

Updates tailscale/corp#13775

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-08-11 11:55:29 -04:00
Maisem Ali
21e32b23f7 .github: use testwrapper on windows
Updates #cleanup

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-08-11 08:40:59 -07:00
Sonia Appasamy
3f12b9c8b2 client/web: pipe through to React in dev mode
Updates tailscale/corp#13775

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-08-11 11:33:27 -04:00
Maisem Ali
98ec8924c2 ipn/ipnlocal,net/tsdial: update docs/rename funcs
Updates #cleanup

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-08-11 07:00:08 -07:00
Brad Fitzpatrick
92fc9a01fa cmd/tailscale: add debug commands to break connections
For testing reconnects.

Updates tailscale/corp#5761

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-11 06:37:26 -07:00
salman aljammaz
99e06d3544 magicsock: set the don't fragment sockopt (#8715)
This sets the Don't Fragment flag, for now behind the
TS_DEBUG_ENABLE_PMTUD envknob.

Updates #311.

Signed-off-by: Val <valerie@tailscale.com>
Signed-off-by: salman <salman@tailscale.com>
2023-08-11 09:34:51 +01:00
Sonia Appasamy
16bc9350e3 client/web: add barebones vite dev setup
Currently just serving a "Hello world" page when running the web
cli in --dev mode.

Updates tailscale/corp#13775

Co-authored-by: Will Norris <will@tailscale.com>
Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-08-10 21:54:43 -04:00
Andrew Lytvynov
215480a022 cmd/tailscale/cli,clientupdate: extract new clientupdate package (#8827)
Extract the self-update logic from cmd/tailscale/cli into a standalone
package that could be used from tailscaled later.

Updates #6995

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-08-10 17:01:22 -07:00
Sonia Appasamy
53c722924b tool/{node,yarn}: update node and yarn tools
Syncing these up with what we've got in corp.

Updates tailscale/corp#13775

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-08-10 17:29:29 -04:00
Maisem Ali
d16946854f control/controlclient: add Auto.updateRoutine
Instead of having updates replace the map polls, create
a third goroutine which is solely responsible for making
sure that control is aware of the latest client state.

This also makes it so that the streaming map polls are only
broken when there are auth changes, or the client is paused.

Updates tailscale/corp#5761

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-08-10 12:23:08 -07:00
Brad Fitzpatrick
7a5263e6d0 util/linuxfw: rename ErrorFWModeNotSupported
Go style is for error variables to start with "err" (or "Err")
and for error types to end in "Error".

Updates #cleanup

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-10 09:27:05 -07:00
Will Norris
3d56cafd7d tsnet: add new example serving the Tailscale web client
Updates tailscale/corp#13775

Co-authored-by: Sonia Appasamy <sonia@tailscale.com>
Signed-off-by: Will Norris <will@tailscale.com>
Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-08-10 08:34:33 -07:00
Will Norris
6ee85ba412 client/web: fix rendering of node owner profile
Fixes #8837

Signed-off-by: Will Norris <will@tailscale.com>
2023-08-09 20:19:34 -07:00
Sonia Appasamy
2bc98abbd9 client/web: add web client Server struct
Updates tailscale/corp#13775

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-08-09 19:09:09 -04:00
Sonia Appasamy
7815fbe17a tailscale/cli: add interactive flow for enabling Funnel
Updates tailscale/corp#10577

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-08-09 18:55:43 -04:00
Andrew Lytvynov
90081a25ca control/controlhttp: remove tstest.Clock from tests (#8830)
These specific tests rely on some timers in the controlhttp code.
Without time moving forward and timers triggering, the tests fail.

Updates #8587

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-08-09 15:03:22 -07:00
Aaron Klotz
3d2e35c053 util/winutil/authenticode: fix an inaccurate doc comment
A #cleanup PR

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2023-08-09 15:33:49 -06:00
Will Norris
f9066ac1f4 client/web: extract web client from cli package
move the tailscale web client out of the cmd/tailscale/cli package, into
a new client/web package.  The remaining cli/web.go file is still
responsible for parsing CLI flags and such, and then calls into
client/web. This will allow the web client to be hooked into from other
contexts (for example, from a tsnet server), and provide a dedicated
space to add more functionality to this client.

Updates tailscale/corp#13775

Signed-off-by: Will Norris <will@tailscale.com>
2023-08-09 09:53:37 -07:00
Will Norris
69f1324c9e cmd/tailscale: refactor shared utility methods
Refactor two shared functions used by the tailscale cli,
calcAdvertiseRoutes and licensesURL. These are used by the web client as
well as other tailscale subcommands. The web client is being moved out
of the cli package, so move these two functions to new locations.

Updates tailscale/corp#13775

Signed-off-by: Will Norris <will@tailscale.com>
2023-08-09 08:59:10 -07:00
Brad Fitzpatrick
b3618c23bf go.toolchain.rev: merge Go 1.21.0 final (non-rc)
Diff:
d149af2823..593313088f

Updates #8419

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-08 22:01:14 -07:00
Brad Fitzpatrick
be4eb6a39e derp, net/dns/recursive: use Go 1.21 min
Updates #8419

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-08 21:34:47 -07:00
Brad Fitzpatrick
66f27c4beb all: require Go 1.21
Updates #8419

Change-Id: I809b6a4d59d92a2ab6ec587ccbb9053376bf02c2
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-08 21:15:08 -07:00
Maisem Ali
682fd72f7b util/testenv: add new package to hold InTest
Removes duplicated code.

Updates #cleanup

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-08-08 19:51:44 -06:00
Maisem Ali
3e255d76e1 ipn/ipnlocal: fix profile duplication
We would only look for duplicate profiles when a new login
occurred but when using `--force-reauth` we could switch
users which would end up with duplicate profiles.

Updates #7726

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-08-08 13:43:37 -06:00
Maisem Ali
500b9579d5 ipn/ipnlocal: add test to find issues with profile duplication
There are a few situations where we end up with duplicate profiles.
Add tests to identify those situations, fix in followup.

Updates #7726

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-08-08 13:43:37 -06:00
Maisem Ali
734928d3cb control/controlclient: make Direct own all changes to Persist
It was being modified in two places in Direct for the auth routine
and then in LocalBackend when a new NetMap was received. This was
confusing, so make Direct also own changes to Persist when a new
NetMap is received.

Updates #7726

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-08-08 13:43:37 -06:00
Maisem Ali
6aaf1d48df types/persist: drop duplicated Persist.LoginName
It was duplicated from Persist.UserProfile.LoginName, drop it.

Updates #7726

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-08-08 13:43:37 -06:00
KevinLiang10
ae63c51ff1 wgengine/router: add auto selection heuristic for iptables/nftables
This commit replaces the TS_DEBUG_USE_NETLINK_NFTABLES envknob with
a TS_DEBUG_FIREWALL_MODE that should be set to either 'iptables' or
'nftables' to select firewall mode manually, other wise tailscaled
will automatically choose between iptables and nftables depending on
environment and system availability.

updates: #319
Signed-off-by: KevinLiang10 <kevinliang@tailscale.com>
2023-08-08 14:59:06 -04:00
Maisem Ali
17ed2da94d control/controlclient: use ptr.To
Updates #cleanup

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-08-08 10:47:24 -06:00
Maisem Ali
82454b57dd ipn/ipnlocal: make tests pass when offline
Updates #cleanup

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-08-08 10:28:55 -06:00
salman aljammaz
25a7204bb4 wgengine,ipn,cmd/tailscale: add size option to ping (#8739)
This adds the capability to pad disco ping message payloads to reach a
specified size. It also plumbs it through to the tailscale ping -size
flag.

Disco pings used for actual endpoint discovery do not use this yet.

Updates #311.

Signed-off-by: salman <salman@tailscale.com>
Co-authored-by: Val <valerie@tailscale.com>
2023-08-08 13:11:28 +01:00
Sonia Appasamy
49896cbdfa ipn/ipnlocal: add profile pic header to serve HTTP proxy
Fixes #8807

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-08-07 13:55:12 -04:00
Brad Fitzpatrick
c56e94af2d ipn: avoid useless no-op WriteState calls
Rather than make each ipn.StateStore implementation guard against
useless writes (a write of the same value that's already in the
store), do writes via a new wrapper that has a fast path for the
unchanged case.

This then fixes profileManager's flood of useless writes to AWS SSM,
etc.

Updates #8785

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-07 08:44:24 -07:00
License Updater
a3f11e7710 licenses: update android licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-08-06 18:51:21 -07:00
Flakes Updater
10acc06389 go.mod.sri: update SRI hash for go.mod changes
Signed-off-by: Flakes Updater <noreply+flakes-updater@tailscale.com>
2023-08-05 10:02:40 -07:00
Claire Wang
a17c45fd6e control: use tstime instead of time (#8595)
Updates #8587
Signed-off-by: Claire Wang <claire@tailscale.com>
2023-08-04 19:29:44 -04:00
License Updater
a8e32f1a4b licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-08-04 09:43:49 -07:00
Andrew Lytvynov
371e1ebf07 cmd/dist,release/dist: expose RPM signing hook (#8789)
Plumb a signing callback function to `unixpkgs.rpmTarget` to allow
signing RPMs. This callback is optional and RPMs will build unsigned if
not set, just as before.

Updates https://github.com/tailscale/tailscale/issues/1882

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-08-03 15:27:06 -07:00
Andrew Lytvynov
eb6883bb5a go.mod: upgrade nfpm to v2 (#8786)
Upgrade the nfpm package to the latest version to pick up
24a43c5ad7.
The upgrade is from v0 to v2, so there was some breakage to fix.
Generated packages should have the same contents as before.

Updates https://github.com/tailscale/tailscale/issues/1882

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-08-03 13:00:45 -07:00
Aaron Klotz
37925b3e7a go.mod, cmd/tailscaled, ipn/localapi, util/osdiag, util/winutil, util/winutil/authenticode: add Windows module list to OS-specific logs that are written upon bugreport
* We update wingoes to pick up new version information functionality
  (See pe/version.go in the https://github.com/dblohm7/wingoes repo);
* We move the existing LogSupportInfo code (including necessary syscall
  stubs) out of util/winutil into a new package, util/osdiag, and implement
  the public LogSupportInfo function may be implemented for other platforms
  as needed;
* We add a new reason argument to LogSupportInfo and wire that into
  localapi's bugreport implementation;
* We add module information to the Windows implementation of LogSupportInfo
  when reason indicates a bugreport. We enumerate all loaded modules in our
  process, and for each one we gather debug, authenticode signature, and
  version information.

Fixes #7802

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2023-08-03 11:33:14 -06:00
Sonia Appasamy
301e59f398 tailcfg,ipn/localapi,client/tailscale: add QueryFeature endpoint
Updates tailscale/corp#10577

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-08-02 16:56:49 -04:00
Brad Fitzpatrick
ab7749aed7 go.toolchain.rev: go1.21rc4 (now that VERSION file is updated upstream)
Updates #8419

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-02 09:44:27 -07:00
Andrew Lytvynov
f57cc19ba2 cmd/tailscale/cli: add latest version output to "tailscale version" (#8700)
Add optional `--upstream` flag to `tailscale version` to fetch the
latest upstream release version from `pkgs.tailscale.com`. This is
useful to diagnose `tailscale update` behavior or write other tooling.

Example output:
$ tailscale version --upstream --json
{
	"majorMinorPatch": "1.47.35",
	"short": "1.47.35",
	"long": "1.47.35-t6afffece8",
	"unstableBranch": true,
	"gitCommit": "6afffece8a32509aa7a4dc2972415ec58d8316de",
	"cap": 66,
	"upstream": "1.45.61"
}

Fixes #8669

RELNOTE=adds "tailscale version --upstream"

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-08-02 08:24:18 -07:00
License Updater
b4c1f039b6 licenses: update android licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-08-01 21:31:58 -07:00
Brad Fitzpatrick
c3b979a176 go.toolchain.rev: bump to ~go1.21rc4
Updates tailscale/go#69

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-01 21:19:24 -07:00
Sonia Appasamy
34bfd7b419 tailcfg: add CapabilityHTTPS const
A #cleanup

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-08-01 21:59:28 -04:00
Brad Fitzpatrick
66e46bf501 ipnlocal, net/*: deprecate interfaces.GetState, use netmon more for it
Updates #cleanup

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-08-01 16:14:46 -07:00
License Updater
6d65c04987 licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-08-01 14:06:13 -07:00
Tom DNetto
767e839db5 all: implement lock revoke-keys command
The revoke-keys command allows nodes with tailnet lock keys
to collaborate to erase the use of a compromised key, and remove trust
in it.

Signed-off-by: Tom DNetto <tom@tailscale.com>
Updates ENG-1848
2023-08-01 15:37:55 -05:00
Aaron Klotz
7adf15f90e cmd/tailscale/cli, util/winutil/authenticode: flesh out authenticode support
Previously, tailscale upgrade was doing the bare minimum for checking
authenticode signatures via `WinVerifyTrustEx`. This is fine, but we can do
better:

* WinVerifyTrustEx verifies that the binary's signature is valid, but it doesn't
  determine *whose* signature is valid; tailscale upgrade should also ensure that
  the binary is actually signed *by us*.
* I added the ability to check the signatures of MSI files.
* In future PRs I will be adding diagnostic logging that lists details about
  every module (ie, DLL) loaded into our process. As part of that metadata, I
  want to be able to extract information about who signed the binaries.

This code is modelled on some C++ I wrote for Firefox back in the day. See
https://searchfox.org/mozilla-central/rev/27e4816536c891d85d63695025f2549fd7976392/toolkit/xre/dllservices/mozglue/Authenticode.cpp
for reference.

Fixes #8284

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2023-08-01 14:27:30 -06:00
Denton Gentry
ec9213a627 cmd/sniproxy: add client metrics
Count number of sessions, number of DNS queries answered
successfully and in error, and number of http->https redirects.

Updates #1748

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2023-08-01 12:14:01 -07:00
Andrew Lytvynov
eef15b4ffc cmd/dist,release/dist: sign release tarballs with an ECDSA key (#8759)
Pass an optional PEM-encoded ECDSA key to `cmd/dist` to sign all built
tarballs. The signature is stored next to the tarball with a `.sig`
extension.

Tested this with an `openssl`-generated key pair and verified the
resulting signature.

Updates #8760

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-07-31 15:47:00 -07:00
David Anderson
ed46442cb1 client/tailscale/apitype: document never-nil property of WhoIsResponse
Every time I use WhoIsResponse I end up writing mildly irritating nil-checking
for both Node and UserProfile, but it turns out our code guarantees that both
are non-nil in successful whois responses.

Updates #cleanup

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-07-31 10:15:44 -07:00
Brad Fitzpatrick
5ebb271322 derp/derphttp: add optional Client.BaseContext hook
Like net/http.Server.BaseContext, this lets callers specify a base
context for dials.

Updates tailscale/corp#12702

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-07-30 20:06:19 -07:00
Maisem Ali
058d427fa6 tailcfg: add helper to unmarshal PeerCap values
Updates #4217

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-07-29 19:31:44 -07:00
salman aljammaz
68f8e5678e wgengine/magicsock: remove dead code (#8745)
The nonce value is not read by anything, and di.sharedKey.Seal()
a few lines below generates its own. #cleanup

Signed-off-by: salman <salman@tailscale.com>
2023-07-29 18:53:33 +01:00
License Updater
0554deb48c licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-07-28 17:42:52 -04:00
David Anderson
6114247d0a types/logid: add a Compare method
Updates #cleanup

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-07-28 13:54:07 -07:00
David Anderson
52212f4323 all: update exp/slices and fix call sites
slices.SortFunc suffered a late-in-cycle API breakage.

Updates #cleanup

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-07-28 13:11:53 -07:00
Claire Wang
90a7d3066c derp: use tstime (#8634)
Updates #8587

Signed-off-by: Claire Wang <claire@tailscale.com>
2023-07-27 15:56:33 -04:00
Claire Wang
2315bf246a ipn: use tstime (#8597)
Updates #8587
Signed-off-by: Claire Wang <claire@tailscale.com>
2023-07-27 15:41:31 -04:00
Andrew Lytvynov
c1ecae13ab ipn/{ipnlocal,localapi}: actually renew certs before expiry (#8731)
While our `shouldStartDomainRenewal` check is correct, `getCertPEM`
would always bail if the existing cert is not expired. Add the same
`shouldStartDomainRenewal` check to `getCertPEM` to make it proceed with
renewal when existing certs are still valid but should be renewed.

The extra check is expensive (ARI request towards LetsEncrypt), so cache
the last check result for 1hr to not degrade `tailscale serve`
performance.

Also, asynchronous renewal is great for `tailscale serve` but confusing
for `tailscale cert`. Add an explicit flag to `GetCertPEM` to force a
synchronous renewal for `tailscale cert`.

Fixes #8725

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-07-27 12:29:40 -07:00
tinku-tailscale
aa37be70cf api.md: update device authorize API docs to allow for deauth (#8728)
Signed-off-by: tinku-tailscale <139132124+tinku-tailscale@users.noreply.github.com>
2023-07-27 15:30:14 +01:00
Charlotte Brandhorst-Satzkorn
35bdbeda9f cli: introduce exit-node subcommand to list and filter exit nodes
This change introduces a new subcommand, `exit-node`, along with a
subsubcommand of `list` and a `--filter` flag.

Exit nodes without location data will continue to be displayed when
`status` is used. Exit nodes with location data will only be displayed
behind `exit-node list`, and in status if they are the active exit node.

The `filter` flag can be used to filter exit nodes with location data by
country.

Exit nodes with Location.Priority data will have only the highest
priority option for each country and city listed. For countries with
multiple cities, a <Country> <Any> option will be displayed, indicating
the highest priority node within that country.

Updates tailscale/corp#13025

Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2023-07-26 16:41:52 -07:00
David Anderson
9d89e85db7 wgengine/magicsock: document mysterious-looking assignment
Updates #cleanup

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-07-26 14:57:01 -07:00
David Anderson
84777354a0 wgengine/magicsock: factor out more separable parts
Updates #8720

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-07-26 14:39:43 -07:00
David Anderson
9a76deb4b0 disco: move disco pcap helper to disco package
Updates tailscale/corp#13464

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-07-26 13:39:57 -07:00
David Anderson
cde37f5307 wgengine/magicsock: factor out peerMap into separate file
Updates tailscale/corp#13464

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-07-26 13:39:57 -07:00
David Anderson
f7016d8c00 wgengine/magicsock: factor out endpoint into its own file
Updates tailscale/corp#13464

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-07-26 12:05:32 -07:00
David Anderson
c2831f6614 wgengine/magicsock: delete unused stuff
Updates tailscale/corp#13464

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-07-26 11:44:41 -07:00
Andrew Lytvynov
9edb848505 cmd/tailscale/cli: implement update on FreeBSD (#8710)
Implement `tailscale update` on FreeBSD. This is much simpler than other
platforms because `pkg rquery` lets us get the version in their repos
without any extra parsing.

Updates #6995

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-07-25 17:38:25 -07:00
Maisem Ali
1ecc16da5f tailcfg,ipn/ipnlocal,wgengine: add values to PeerCapabilities
Define PeerCapabilty and PeerCapMap as the new way of sending down
inter-peer capability information.

Previously, this was unstructured and you could only send down strings
which got too limiting for certain usecases. Instead add the ability
to send down raw JSON messages that are opaque to Tailscale but provide
the applications to define them however they wish.

Also update accessors to use the new values.

Updates #4217

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-07-25 14:32:51 -07:00
Andrew Lytvynov
306deea03a cmd/tailscale/cli,version/distro: update support for Alpine (#8701)
Similar to Arch support, use the latest version info from the official
`apk` repo and don't offer explicit track or version switching.
Add detection for Alpine Linux in version/distro along the way.

Updates #6995

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-07-24 16:53:15 -07:00
David Anderson
6afffece8a net/art: use more intelligible, go-ish state tracking in table.Get
Updates #7781

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-07-24 13:33:48 -07:00
David Anderson
4f14ed2ad6 net/art: use encoding/binary for address bit twiddling
Updates #7781

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-07-24 13:33:48 -07:00
David Anderson
f1cd67488d net/art: move slice closer to its use
Updates #7781

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-07-24 13:33:48 -07:00
David Anderson
44ad7b3746 net/art: factor out picking the right strideTable for addr family
Updates #7781

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-07-24 13:33:48 -07:00
David Anderson
125b982ba5 net/art: make Table.Get alloc-free
Updates #7781

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-07-24 13:33:48 -07:00
David Anderson
b76d8a88ae net/art: document return value of strideTable.delete
Updates #7781

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-07-24 13:33:48 -07:00
David Anderson
b242e2c2cb net/art: reword confusing function docstring
Updates #7781

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-07-24 13:33:48 -07:00
David Anderson
8478358d77 net/art: use "index", not "idx" in function names
Updates #7781

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-07-24 13:33:48 -07:00
David Anderson
de5c6ed4be net/art: document valid values of strideTable.prefix
Updates #7781

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-07-24 13:33:48 -07:00
David Anderson
736a44264f net/art: fix comment typo
Updates #7781

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-07-24 13:33:48 -07:00
David Anderson
1e6f0bb608 net/art: fix slowPrefixTable bugs found by fuzzing
One is a straight "I forgot how to Go" bug, the others are semantic
mismatches with the main implementation around masking the prefixes
passed to insert/delete.

Updates #7781

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-07-24 13:33:48 -07:00
David Anderson
aaca911904 net/art: add another consistency test for insert/delete
Updates #7781

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-07-24 13:33:48 -07:00
David Anderson
b145a22f55 net/art: add more exhaustive table testing
Updates #7781

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-07-24 13:33:48 -07:00
David Anderson
9cc3f7a3d6 net/art: fix format of debug output
Updates #7781

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-07-24 13:33:48 -07:00
David Anderson
ac657caaf1 net/art: add debug hooks to strideTable
Updates #7781

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-07-24 13:33:48 -07:00
David Anderson
fcf4d044fa net/art: implement path compression optimization
Updates #7781

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-07-24 13:33:48 -07:00
David Anderson
486195edf0 net/art: make each strideTable track the IP prefix it represents
This is a prerequisite for path compression, so that insert/delete
can determine when compression occurred.

Updates #7781

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-07-24 13:33:48 -07:00
David Anderson
45b5d0983c net/art: fix running tests outside of CI
Updates #7866

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-07-24 13:33:48 -07:00
License Updater
4c05d43008 licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-07-24 10:42:00 -07:00
Andrew Lytvynov
894b237a70 cmd/tailscale/cli: implement update for dnf/yum-based distros (#8678)
This is the Fedora family of distros, including CentOS, RHEL and others.
Tested in `fedora:latest` and `centos:7` containers.

Updates #6995

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-07-24 10:20:17 -07:00
Brad Fitzpatrick
f1cc8ab3f9 tailcfg: add UserProfile.Groups
Updates tailscale/corp#13375

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-07-23 15:23:59 -07:00
Michael Stapelberg
2a6c237d4c net/dns: overwrite /tmp/resolv.conf on gokrazy
Appliances built using https://gokrazy.org/ have a read-only root file system,
including /etc/resolv.conf, which is a symlink to /tmp/resolv.conf.

The system’s dhcp client overwrites /tmp/resolv.conf instead,
so we need to use this path in Tailscale, too.

related to https://github.com/gokrazy/gokrazy/issues/209

fixes https://github.com/tailscale/tailscale/issues/8689

Signed-off-by: Michael Stapelberg <michael@stapelberg.de>
2023-07-23 09:53:32 -07:00
Brad Fitzpatrick
453620dca1 go.toolchain.rev: bump Go version
For a96a9eddc0

Updates tailscale/corp#12702

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-07-22 22:14:59 -07:00
Brad Fitzpatrick
41db1d7bba tailcfg: deprecate Debug, flesh out Node.DERP docs
Updates #docs

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-07-22 09:33:45 -07:00
Jenny Zhang
907c56c200 api.md: add documentation to API endpoint about SCIM group warnings
Updates #8645
Signed-off-by: Jenny Zhang <jz@tailscale.com>
2023-07-21 15:35:08 -04:00
Claire Wang
e1bcecc393 logtail: use tstime (#8607)
Updates #8587
Signed-off-by: Claire Wang <claire@tailscale.com>
2023-07-21 13:10:39 -04:00
Joe Tsai
bb4b35e923 ssh: ignore io.EOF from sftp.Server.Serve
If the connection provided to sftp.NewServer is closed,
Serve returns the io.EOF error verbatim from io.Reader.Read.
This is an odd error since this is an expected situation,
so we manually ignore io.EOF.
This is somewhat buggy since the sftp package itself
incorrectly reports io.EOF in cases where it should actually
be reporting io.ErrUnexpectedEOF.
See https://github.com/pkg/sftp/pull/554 which patches Serve to
return nil on clean closes and fixes buggy uses of io.ReadFull.

Fixes #8592

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2023-07-21 07:41:36 -07:00
Brad Fitzpatrick
88cc0ad9f7 util/linuxfw: remove yet-unused code to fix linux/arm64 crash
The util/linuxfw/iptables.go had a bunch of code that wasn't yet used
(in prep for future work) but because of its imports, ended up
initializing code deep within gvisor that panicked on init on arm64
systems not using 4KB pages.

This deletes the unused code to delete the imports and remove the
panic. We can then cherry-pick this back to the branch and restore it
later in a different way.

A new test makes sure we don't regress in the future by depending on
the panicking package in question.

Fixes #8658

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-07-20 23:18:40 -07:00
Brad Fitzpatrick
7560435eb5 tstest/deptest: add test-only package to unify negative dep tests
Updates #8658

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-07-20 23:18:40 -07:00
Chris Palmer
32d486e2bf cmd/tailscale/cli: ensure custom UsageFunc is always set (#8665)
Updates #6995

Signed-off-by: Chris Palmer <cpalmer@tailscale.com>
2023-07-20 17:43:39 -07:00
Chris Palmer
3c53bedbbf cmd/tailscale/cli: limit Darwin-only option to Darwin (#8657) 2023-07-20 11:19:09 -07:00
Anton Tolchanov
388b124513 net/dns: detect when libnss_resolve is used
Having `127.0.0.53` is not the only way to use `systemd-resolved`. An
alternative way is to enable `libnss_resolve` module, which seems to now
be used by default on Debian 12 bookworm.

Fixes #8549

Signed-off-by: Anton Tolchanov <anton@tailscale.com>
2023-07-20 18:26:23 +02:00
Andrew Lytvynov
efd6d90dd7 cmd/tailscale/cli: implement update for arch-based distros (#8655)
Arch version of tailscale is not maintained by us, but is generally
up-to-date with our releases. Therefore "tailscale update" is just a
thin wrapper around "pacman -Sy tailscale" with different flags.

Updates #6995

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-07-19 17:53:56 -07:00
Chris Palmer
3f6b0d8c84 cmd/tailscale/cli: make tailscale update query softwareupdate (#8641)
* cmd/tailscale/cli: make `tailscale update` query `softwareupdate`

Even on macOS when Tailscale was installed via the App Store, we can check for
and even install new versions if people ask explicitly. Also, warn if App Store
AutoUpdate is not turned on.

Updates #6995
2023-07-19 17:06:16 -07:00
Tom DNetto
bec9815f02 tka: guard against key-length panics when verifying signatures
In late 2022 a subtle but crucial part of documentation was added to ed25519.Verify: It
will panic if len(publicKey) is not [PublicKeySize].

02ed0e5e67

This change catches that error so it won't lead to a panic.

Signed-off-by: Tom DNetto <tom@tailscale.com>
Updates https://github.com/tailscale/corp/issues/8568
2023-07-19 15:33:01 -05:00
Andrea Gottardo
486ab427b4 VERSION.txt: this is v1.47.0 (#8654)
Signed-off-by: Andrea Gottardo <andrea@tailscale.com>
2023-07-19 13:02:01 -07:00
Andrew Lytvynov
7c04846eac tsweb: relax CSP for debug handlers (#8649)
Allow inline CSS for debug handlers to make prototyping easier. These
are generally not accessible to the public and the small risk of CSS
injection via user content seems acceptable.

Also allow form submissions on the same domain, instead of banning all
forms. An example of such form is
http://webhooks.corp.ts.net:6359/debug/private-nodes/

Updates #3576

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-07-19 11:58:29 -07:00
Jenny Zhang
9ab70212f4 cmd/gitops-pusher: re-use existing types from acl package
This changes the ACLTestError type to reuse the existing/identical
types from the ACL implementation, to avoid issues in the future if
the two types fall out of sync.

Updates #8645

Signed-off-by: Jenny Zhang <jz@tailscale.com>
2023-07-19 14:44:45 -04:00
Jenny Zhang
6b56e92acc client/tailscale: add warnings slice to ACLTestFailureSummary
Updates #8645

Signed-off-by: Jenny Zhang <jz@tailscale.com>
2023-07-19 14:44:45 -04:00
KevinLiang10
a3c7b21cd1 util/linuxfw: add nftables support
This commit adds nftable rule injection for tailscaled. If tailscaled is
started with envknob TS_DEBUG_USE_NETLINK_NFTABLES = true, the router
will use nftables to manage firewall rules.

Updates: #391

Signed-off-by: KevinLiang10 <kevinliang@tailscale.com>
2023-07-19 14:33:23 -04:00
Tom DNetto
abcb7ec1ce cmd/tailscale: warn if node is locked out on bringup
Updates https://github.com/tailscale/corp/issues/12718
Signed-off-by: Tom DNetto <tom@tailscale.com>
2023-07-19 12:31:21 -05:00
Tom DNetto
2c782d742c tka: allow checkpoint AUMs to change TKA state
Updates https://github.com/tailscale/corp/issues/8568
Signed-off-by: Tom DNetto <tom@tailscale.com>
2023-07-19 12:06:20 -05:00
Xe Iaso
24f0e91169 tsnet: add examples (#8289)
Closes #8288

Follows the examples from the KB[1].

[1]: https://tailscale.com/kb/1244/tsnet/

Signed-off-by: Xe Iaso <xe@tailscale.com>
2023-07-19 12:36:49 -04:00
Val
1138f4eb5f wgengine/router,ipn/ipnlocal: add MTU field to router config
The MacOS client can't set the MTU when creating the tun due to lack
of permissions, so add it to the router config and have MacOS set it
in the callback using a method that it does have permissions for.

Updates #8219

Signed-off-by: Val <valerie@tailscale.com>
2023-07-19 04:22:12 -07:00
Andrew Dunham
9b5e29761c net/netcheck: ignore PreferredDERP changes that are small
If the absolute value of the difference between the current
PreferredDERP's latency and the best latency is <= 10ms, don't change
it and instead prefer the previous value.

This is in addition to the existing hysteresis that tries to remain
on the previous DERP region if the relative improvement is small, but
handles nodes that have low latency to >1 DERP region better.

Updates #8603

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I1e34c94178f8c9a68a69921c5bc0227337514c70
2023-07-18 16:50:24 -04:00
dependabot[bot]
8bdc03913c go.mod: bump github.com/docker/distribution (#8121)
Bumps [github.com/docker/distribution](https://github.com/docker/distribution) from 2.8.1+incompatible to 2.8.2+incompatible.
- [Release notes](https://github.com/docker/distribution/releases)
- [Commits](https://github.com/docker/distribution/compare/v2.8.1...v2.8.2)

---
updated-dependencies:
- dependency-name: github.com/docker/distribution
  dependency-type: indirect
...

Signed-off-by: dependabot[bot] <support@github.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
2023-07-18 11:05:26 -07:00
Maisem Ali
3304819739 metrics: add histogram support
Add initial histogram support.

Updates tailscale/corp#8641

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-07-18 09:18:55 -07:00
License Updater
9101fabdf8 licenses: update win/apple licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-07-18 05:14:01 -07:00
Brad Fitzpatrick
94a51bdd62 go.toolchain.rev: bump Go to Go1.21rc3
Updates #8632

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-07-18 04:00:50 -07:00
Will Norris
f8b0caa8c2 serve: fix hostname for custom http ports
When using a custom http port like 8080, this was resulting in a
constructed hostname of `host.tailnet.ts.net:8080.tailnet.ts.net` when
looking up the serve handler. Instead, strip off the port before adding
the MagicDNS suffix.

Also use the actual hostname in `serve status` rather than the literal
string "host".

Fixes #8635

Signed-off-by: Will Norris <will@tailscale.com>
2023-07-17 17:10:14 -07:00
Andrew Lytvynov
c19b5bfbc3 .github/workflows: add govulncheck workflow (#8623) 2023-07-14 14:56:21 -07:00
Claire Wang
0573f6e953 tstime: add Since method (#8622)
Updates #8463

Signed-off-by: Claire Wang <claire@tailscale.com>
2023-07-14 16:50:17 -04:00
Maisem Ali
60e5761d60 control/controlclient: reset backoff in mapRoutine on netmap recv
We were never resetting the backoff in streaming mapResponses.
The call to `PollNetMap` always returns with an error. Changing that contract
is harder, so manually reset backoff when a netmap is received.

Updates tailscale/corp#12894

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-07-13 21:08:28 -07:00
Andrew Dunham
7aba0b0d78 net/netcheck, tailcfg: add DERPHomeParams and use it
This allows providing additional information to the client about how to
select a home DERP region, such as preferring a given DERP region over
all others.

Updates #8603

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I7c4a270f31d8585112fab5408799ffba5b75266f
2023-07-13 22:41:21 -04:00
Andrew Lytvynov
7a82fd8dbe ipn/ipnlocal: add optional support for ACME Renewal Info (ARI) (#8599) 2023-07-13 14:29:59 -07:00
Andrew Lytvynov
354885a08d wgengine/netlog: fix nil pointer dereference in logtail (#8598) 2023-07-13 08:54:29 -07:00
Denton Gentry
4f95b6966b cmd/tailscale: remove TS_EXPERIMENT_OAUTH_AUTHKEY guardrail
We've had support for OAuth client keys in `--authkey=...`
for several releases, and we're using it in
https://github.com/tailscale/github-action

Remove the TS_EXPERIMENT_* guardrail, it is fully supported now.

Fixes https://github.com/tailscale/tailscale/issues/8403

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2023-07-13 07:20:38 -07:00
License Updater
c95de4c7a8 licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-07-12 12:26:40 -07:00
License Updater
3d70fecde4 licenses: update win/apple licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-07-12 12:25:19 -07:00
Andrew Lytvynov
96d7af3469 cmd/derper,tsweb: consistently add HTTP security headers (#8579)
Add a few helper functions in tsweb to add common security headers to handlers. Use those functions for all non-tailscaled-facing endpoints in derper.

Signed-off-by: Andrew Lytvynov <awly@tailscale.com>
2023-07-11 11:53:46 -07:00
Maisem Ali
8cda647a0f cmd/testwrapper: handle build failures
`go test -json` outputs invalid JSON when a build fails.
Handle that case by reseting the json.Decode and continuing to read.

Updates #8493

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-07-11 11:44:30 -07:00
Joe Tsai
49015b00fe logtail: fix race condition with sockstats label (#8578)
Updates tailscale/corp#8427

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2023-07-11 10:51:51 -07:00
Tom DNetto
2bbedd2001 ipn: rename CapTailnetLockAlpha -> CapTailnetLock
Updates tailscale/corp#8568
Signed-off-by: Tom DNetto <tom@tailscale.com>
2023-07-11 12:47:02 -05:00
Andrew Dunham
60ab8089ff logpolicy, various: allow overriding log function
This allows sending logs from the "logpolicy" package (and associated
callees) to something other than the log package. The behaviour for
tailscaled remains the same, passing in log.Printf

Updates #8249

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: Ie1d43b75fa7281933d9225bffd388462c08a5f31
2023-07-10 18:08:50 -04:00
Flakes Updater
cd313e410b go.mod.sri: update SRI hash for go.mod changes
Signed-off-by: Flakes Updater <noreply+flakes-updater@tailscale.com>
2023-07-10 13:25:20 -07:00
Adrian Dewhurst
8c0572e088 go.mod: bump wireguard-go
This pulls in IP checksum optimization on amd64, see
tailscale/wireguard-go@bb2c8f2.

Updates tailscale/corp#9755

Change-Id: I60e932fc4031703b56eb86a676465c5d02d99236
Signed-off-by: Adrian Dewhurst <adrian@tailscale.com>
2023-07-10 16:20:47 -04:00
Andrew Dunham
a7648a6723 net/dnsfallback: run recursive resolver and compare results
When performing a fallback DNS query, run the recursive resolver in a
separate goroutine and compare the results returned by the recursive
resolver with the results we get from "regular" bootstrap DNS. This will
allow us to gather data about whether the recursive DNS resolver works
better, worse, or about the same as "regular" bootstrap DNS.

Updates #5853

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: Ifa0b0cc9eeb0dccd6f7a3d91675fe44b3b34bd48
2023-07-10 16:12:48 -04:00
Brad Fitzpatrick
ffaa6be8a4 tailcfg: add json omitempty to DNSConfig.ExitNodeFilteredSet
We were storing a lot of "ExitNodeFilteredSet":null in the database.

Updates tailscale/corp#1818 (found in the process)

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-07-08 19:58:23 -07:00
Brad Fitzpatrick
7b1c3dfd28 tailcfg,etc: remove unused tailcfg.Node.KeepAlive field
The server hasn't sent it in ages.

Updates #cleanup

Change-Id: I9695ab0f074ec6fb006e11faf3cdfc5ca049fbf8
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-07-08 06:57:10 -07:00
Charlotte Brandhorst-Satzkorn
f05a9f3e7f tsnet: mark TestLoopbackLocalAPI as flakey
Test flaked in CI.

Updates  #8557

Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2023-07-07 21:23:48 -07:00
Charlotte Brandhorst-Satzkorn
339397ab74 wgengine/magicsock: remove noV4/noV6 check in addrForSendWireGuardLocked
This change removes the noV4/noV6 check from addrForSendWireGuardLocked.

On Android, the client panics when reaching	`rand.Intn()`, likely due to
the candidates list being containing no candidates. The suspicion is
that the `noV4` and the `noV6` are both being triggered causing the
loop to continue.

Updates tailscale/corp#12938
Updates #7826

Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2023-07-07 18:59:19 -07:00
Maisem Ali
9d1a3a995c control/controlclient: use ctx passed down to NoiseClient.getConn
Without this, the client would just get stuck dialing even if the
context was canceled.

Updates tailscale/corp#12590

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-07-07 15:11:44 -07:00
Adrian Dewhurst
92fb80d55f tstest, tstime: mockable timers and tickers
This change introduces tstime.Clock which is the start of a mockable
interface for use with testing other upcoming code changes.

Fixes #8463

Change-Id: I59eabc797828809194575736615535d918242ec4
Signed-off-by: Adrian Dewhurst <adrian@tailscale.com>
2023-07-07 11:13:03 -04:00
Andrea Gottardo
28ee355c56 version: fix tvOS network extension bundle identifier (#8545)
Fixes #8544 and updates #8282.

Signed-off-by: Andrea Gottardo <andrea@tailscale.com>
2023-07-06 16:19:15 -07:00
Adrian Dewhurst
cd4c71c122 tstest: prepare for Clock API changes
This change introduces tstime.NewClock and tstime.ClockOpts as a new way
to construct tstime.Clock. This is a subset of #8464 as a stepping stone
so that we can update our internal code to use the new API before making
the second round of changes.

Updates #8463

Change-Id: Ib26edb60e5355802aeca83ed60e4fdf806c90e27
Signed-off-by: Adrian Dewhurst <adrian@tailscale.com>
2023-07-06 17:03:19 -04:00
Aaron Klotz
fd8c8a3700 client/tailscale: add API for verifying network lock signing deeplink
Fixes #8539

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2023-07-06 09:59:24 -07:00
Claire Wang
3f1f906b63 words: ack Miles Prower (#8479)
Signed-off-by: Claire Wang <claire@tailscale.com>
2023-07-06 11:29:09 -04:00
Brad Fitzpatrick
cb53846717 tempfork/heap: add copy of Go's container/heap but using generics
From Go commit 0a48e5cbfabd679e, then with some generics sprinkled
about.

Updates tailscale/corp#7354

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-07-05 19:33:56 -07:00
David Wolever
0c427f23bd docs/k8s: don't call kubectl directly from Makefile
Instead of calling kubectl directly in k8s Makefile, write the yaml to
stdout so it can be reviewed/edited/etc before manually applying with
kubectl.

Fixes: #8511

Signed-off-by: David Wolever <david@wolever.net>
2023-07-01 11:44:09 -07:00
Brad Fitzpatrick
4d94d72fba metrics: add LabelMap.GetIncrFunc
Updates tailscale/corp#7354

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-07-01 07:14:55 -07:00
David Anderson
0a86705d59 release/dist: add helper to build Go binaries with custom tags
Updates tailscale/corp#12861

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-06-30 19:03:03 -07:00
KevinLiang10
a795b4a641 tsnet: add TestLoopbackSOCKS5 as flaky test
Signed-off-by: KevinLiang10 <kevinliang@tailscale.com>
2023-06-30 18:22:15 -04:00
KevinLiang10
6ebd87c669 util/linuxfw: add new arch build constraints
Exclide GOARCHs including: mips, mips64, mips64le, mipsle, riscv64.
These archs are not supported by gvisor.dev/gvisor/pkg/hostarch.

Fixes: #391
Signed-off-by: KevinLiang10 <kevinliang@tailscale.com>
2023-06-30 18:22:15 -04:00
Maisem Ali
1ca5dcce15 cmd/testwrapper: stream output results
Previously it would wait for all tests to run before printing anything,
instead stream the results over a channel so that they can be emitted
immediately.

Updates #8493

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-06-30 12:37:32 -07:00
Maisem Ali
2e4e7d6b9d cmd/testwrapper: output packages tested
Previously it would only print the failures without providing
more information on which package the failures from.

This commit makes it so that it prints out the package information
as well as the attempt numbers.

```
➜  tailscale.com git:(main) ✗ go run ./cmd/testwrapper ./cmd/...
ok       tailscale.com/cmd/derper
ok       tailscale.com/cmd/k8s-operator
ok       tailscale.com/cmd/tailscale/cli
ok       tailscale.com/cmd/tailscaled
=== RUN   TestFlakeRun
    flakytest.go:38: flakytest: issue tracking this flaky test: https://github.com/tailscale/tailscale/issues/0
    flakytest_test.go:41: First run in testwrapper, failing so that test is retried. This is expected.
--- FAIL: TestFlakeRun (0.00s)
FAIL     tailscale.com/cmd/testwrapper/flakytest

Attempt #2: Retrying flaky tests:

ok       tailscale.com/cmd/testwrapper/flakytest
```

Updates #8493

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-06-30 11:17:09 -07:00
Brad Fitzpatrick
79ee6d6e1e tsweb/varz: use default metrics.LabelMap.Label on serialization
To not break Prometheus if the label is unset.

Updates tailscale/corp#12830

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-06-30 09:08:43 -07:00
Maisem Ali
2e19790f61 types/views: add JSON marshal/unmarshal and AsMap to Map
This allows cloning a Map as well as marshaling the Map
as JSON.

Updates tailscale/corp#12754

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-06-29 10:12:26 -07:00
Joe Tsai
e42be5a060 tstime/mono: fix Time.Unmarshal (#8480)
Calling both mono.Now() and time.Now() is slow and
leads to unnecessary precision errors.
Instead, directly compute mono.Time relative to baseMono and baseWall.
This is the opposite calculation as mono.Time.WallTime.

Updates tailscale/corp#8427

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2023-06-28 15:16:52 -07:00
Maisem Ali
075abd8ec1 tstest: do not panic when a panic logs
The panicLogWriter is too strict, and any panics that occur
get wrapped up in quotes. This makes it so that it will allow
panics to continue writing to Stderr without going through
logger.Logf.

Updates #cleanup

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-06-28 13:27:26 -07:00
Maisem Ali
12a2221db2 cmd/testwrapper/flakytest: clearly describe why TestFlakeRun fails
Fixes #8474

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-06-28 12:19:25 -07:00
Tom DNetto
97ee0bc685 cmd/tailscale: improve error message when signing without a tailnet lock key
Updates #8568
Signed-off-by: Tom DNetto <tom@tailscale.com>
2023-06-28 14:19:05 -05:00
Brad Fitzpatrick
b0a984dc26 util/lru: add a package for a typed LRU cache
Updates tailscale/corp#7355

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-06-28 10:16:15 -07:00
License Updater
626f650033 licenses: update android licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-06-28 10:05:31 -07:00
License Updater
d4413f723d licenses: update win/apple licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-06-28 10:05:10 -07:00
Brad Fitzpatrick
cafd9a2bec syncs: add ShardedMap.Mutate
To let callers do atomic/CAS-like operations.

Updates tailscale/corp#7355

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-06-28 08:43:15 -07:00
Andrew Dunham
ab310a7f60 derp: use new net/tcpinfo package
Updates #8413

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I8bf8046517195a6d42cabb32d6ec7f1f79cef860
2023-06-27 21:59:43 -04:00
Andrew Dunham
d9eca20ee2 net/tcpinfo: add package to allow fetching TCP information
This package contains platform-independent abstractions for fetching
information about an open TCP connection.

Updates #8413

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I236657b1060d7e6a45efc7a2f6aacf474547a2fe
2023-06-27 21:59:43 -04:00
KevinLiang10
243ce6ccc1 util/linuxfw: decoupling IPTables logic from linux router
This change is introducing new netfilterRunner interface and moving iptables manipulation to a lower leveled iptables runner.

For #391

Signed-off-by: KevinLiang10 <kevinliang@tailscale.com>
2023-06-27 19:54:27 -04:00
Charlotte Brandhorst-Satzkorn
9c64e015e5 tailcfg: update location docs
This change updates the documentation for the fields on the location
struct.

Updates tailscale/corp#12146

Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2023-06-27 12:29:29 -07:00
Ross Zurowski
832f1028c7 net/netutil: parse IP forwarding val as int, not bool (#8455)
This commit updates our IP forwarding parsing logic to allow the less
common but still valid value of `2` to be parsed as `true`, which fixes
an error some users encountered.

Fixes #8375

Signed-off-by: Ross Zurowski <ross@rosszurowski.com>
2023-06-27 15:00:42 -04:00
Brad Fitzpatrick
a874f1afd8 all: adjust case of "IPv4" and "IPv6"
Updates #docs

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-06-27 10:09:30 -07:00
valscale
e26376194d ipn/ipnlocal: validate ping type (#8458)
Correct a minor cut-n-paste error that resulted in an invalid or
missing ping type being accepted as a disco ping.

Fixes #8457

Signed-off-by: Val <valerie@tailscale.com>
2023-06-27 09:33:29 -07:00
Brad Fitzpatrick
77f56794c9 types/key: add test for NodePublic.Shard
Updates #cleanup

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-06-27 08:49:44 -07:00
Tom DNetto
1377618dbc tsnet: expose field to configure Wireguard port
Signed-off-by: Tom DNetto <tom@tailscale.com>
Updates #1748
2023-06-26 18:11:36 -05:00
Maisem Ali
8e840489ed cmd/testwrapper: only retry flaky failed tests
Redo the testwrapper to track and only retry flaky tests instead
of retrying the entire pkg. It also fails early if a non-flaky test fails.

This also makes it so that the go test caches are used.

Fixes #7975

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-06-26 08:54:20 -07:00
Anton Tolchanov
2cf6e12790 hostinfo: make lxcfs container check more specific
Instead of treating any lxcfs mount as an indicator that we're running
in a container, check for one of the mounts actually used by LXC
containers.

For reference, here's a list of mounts I am seeing in an LXC container:

```
$ grep lxcfs /proc/mounts
lxcfs /proc/cpuinfo fuse.lxcfs rw,nosuid,nodev,relatime,user_id=0,group_id=0,allow_other 0 0
lxcfs /proc/diskstats fuse.lxcfs rw,nosuid,nodev,relatime,user_id=0,group_id=0,allow_other 0 0
lxcfs /proc/loadavg fuse.lxcfs rw,nosuid,nodev,relatime,user_id=0,group_id=0,allow_other 0 0
lxcfs /proc/meminfo fuse.lxcfs rw,nosuid,nodev,relatime,user_id=0,group_id=0,allow_other 0 0
lxcfs /proc/stat fuse.lxcfs rw,nosuid,nodev,relatime,user_id=0,group_id=0,allow_other 0 0
lxcfs /proc/swaps fuse.lxcfs rw,nosuid,nodev,relatime,user_id=0,group_id=0,allow_other 0 0
lxcfs /proc/uptime fuse.lxcfs rw,nosuid,nodev,relatime,user_id=0,group_id=0,allow_other 0 0
lxcfs /sys/devices/system/cpu/online fuse.lxcfs rw,nosuid,nodev,relatime,user_id=0,group_id=0,allow_other 0 0
```

Fixes #8444

Signed-off-by: Anton Tolchanov <anton@tailscale.com>
2023-06-26 15:34:54 +01:00
Maisem Ali
c11af12a49 .github: actually run tests in CI
Updates #cleanup

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-06-25 15:57:28 -07:00
Brad Fitzpatrick
ba41d14320 syncs: add ShardedMap type
Updates tailscale/corp#7354

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-06-25 12:51:19 -07:00
Brad Fitzpatrick
1f57088cbd words: ovuliferous was a bit too much, but...
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-06-24 13:30:49 -07:00
Charlotte Brandhorst-Satzkorn
3417ddc00c tailcfg: add location field to hostinfo
This change adds Location field to HostInfo.
Location contains the option for a Country, CountryCode, City, CityCode
and a Priority. Neither of these fields are populated by default.

The Priority field is used to determine the priority an exit
node should be given for use, if the field is set. The higher the value
set, the higher priority the node should be given for use.

Updates tailscale/corp#12146

Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2023-06-23 15:34:31 -07:00
phirework
2a9817da39 api.md: add info for key description (#8429)
Updates tailscale/corp#7773

Signed-off-by: Jenny Zhang <jz@tailscale.com>
2023-06-23 17:38:20 -04:00
David Anderson
bfe5623a86 tool/gocross: make gocross behave with pre-release Go toolchains
Also switch the wrapper script to use bash not posix shell. We now
depend on bash elsewhere for saner behavior in esoteric areas, so
might as well use it everywhere for consistency.

Fixes #8425

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-06-23 13:57:05 -07:00
David Anderson
4a58b1c293 release/dist/synology: remove 'version' field from ui/config
As far as I can tell from the DSM documentation and known undocumented
fields, there is no 'version' field in this config file that DSM cares
about.

Updates #8232

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-06-23 13:43:15 -07:00
Brad Fitzpatrick
7c1068b7ac util/goroutines: let ScrubbedGoroutineDump get only current stack
ScrubbedGoroutineDump previously only returned the stacks of all
goroutines. I also want to be able to use this for only the current
goroutine's stack. Add a bool param to support both ways.

Updates tailscale/corp#5149

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-06-23 12:50:45 -07:00
phirework
fbacc0bd39 go.toolchain: switch to tailscale.go1.21 (#8415)
Updates #8419

Signed-off-by: Jenny Zhang <jz@tailscale.com>
2023-06-23 09:12:19 -04:00
Brad Fitzpatrick
8b80d63b42 wgengine/magicsock: clarify a log message is a warning, not an error
Updates #cleanup

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-06-22 08:16:41 -07:00
Joe Tsai
61886e031e ssh/tailssh: fix double race condition with non-pty command (#8405)
There are two race conditions in output handling.

The first race condition is due to a misuse of exec.Cmd.StdoutPipe.
The documentation explicitly forbids concurrent use of StdoutPipe
with exec.Cmd.Wait (see golang/go#60908) because Wait will
close both sides of the pipe once the process ends without
any guarantees that all data has been read from the pipe.
To fix this, we allocate the os.Pipes ourselves and
manage cleanup ourselves when the process has ended.

The second race condition is because sshSession.run waits
upon exec.Cmd to finish and then immediately proceeds to call ss.Exit,
which will close all output streams going to the SSH client.
This may interrupt any asynchronous io.Copy still copying data.
To fix this, we close the write-side of the os.Pipes after
the process has finished (and before calling ss.Exit) and
synchronously wait for the io.Copy routines to finish.

Fixes #7601

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
Co-authored-by: Maisem Ali <maisem@tailscale.com>
2023-06-21 19:57:45 -07:00
dependabot[bot]
d4de60c3ae .github: Bump actions/checkout from 1 to 3
Bumps [actions/checkout](https://github.com/actions/checkout) from 1 to 3.
- [Release notes](https://github.com/actions/checkout/releases)
- [Changelog](https://github.com/actions/checkout/blob/main/CHANGELOG.md)
- [Commits](https://github.com/actions/checkout/compare/v1...v3)

---
updated-dependencies:
- dependency-name: actions/checkout
  dependency-type: direct:production
  update-type: version-update:semver-major
...

Signed-off-by: dependabot[bot] <support@github.com>
2023-06-21 12:01:59 -07:00
Charlotte Brandhorst-Satzkorn
30d9201a11 VERSION.txt: this is v1.45.0
Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2023-06-21 10:54:17 -07:00
Brad Fitzpatrick
32b8f25ed1 Revert "ssh/tailssh: change to user directory when running login/command"
This reverts commit dc5bc32d8f.

It broke tests. (sadly, ones which we have disabled on CI, but go test
./ssh/tailssh broke)
2023-06-21 10:49:18 -07:00
Aaron Bieber
6829caf6de tsnet: remove extra wording from Store comment 2023-06-21 10:28:11 -07:00
Brad Fitzpatrick
e48c0bf0e7 ipn/ipnlocal: quiet some spammy network lock logging
Updates #cleanup

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-06-21 10:24:53 -07:00
valscale
f314fa4a4a prober: fix data race when altering derpmap (#8397)
Move the clearing of STUNOnly flag to the updateMap() function.

Fixes #8395

Signed-off-by: Val <valerie@tailscale.com>
2023-06-21 10:16:31 -07:00
Derek Burdick
dc5bc32d8f ssh/tailssh: change to user directory when running login/command
On redhat 9 and similarly locked down systems, root user does not have
access to a users directory. This fix does not set a directory for the
incubator process and instead sets the directory when the actual process
requested by remote user is executed.

Fixes #8118

Signed-off-by: Derek Burdick <derek-burdick@users.noreply.github.com>
2023-06-21 10:14:19 -07:00
shayne
6697690b55 {cmd/tailscale/cli,ipn}: add http support to tailscale serve (#8358)
Updates #8357

Signed-off-by: Shayne Sweeney <shayne@tailscale.com>
2023-06-21 12:32:20 -04:00
Brad Fitzpatrick
a2153afeeb types/views: add Slice methods on Slice views
Updates #cleanup for change elsewhere.

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-06-20 20:19:39 -07:00
Sonia Appasamy
0f5090c526 ipn/ipnlocal: add docs header to serve HTTP proxy
Adds a `Tailscale-Headers-Info` header whenever the `Tailscale-User-`
headers are filled from the HTTP proxy handler.

Planning on hooking this shorturl up to KB docs about the header
values (i.e. what's a login name vs. display name) and security
considerations to keep in mind while using these headers - notibly
that they can also be filled from external requests that do not hit
tailscaled.

Updates https://github.com/tailscale/tailscale/issues/6954

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-06-20 16:46:10 -04:00
valscale
88097b836a prober: allow monitoring of nodes marked as STUN only in default derpmap (#8391)
prober uses NewRegionClient() to connect to a derper using a faked up
single-node region, but NewRegionClient() fails to connect if there is
no non-STUN only client in the region. Set the STUN only flag to false
before we call NewRegionClient() so we can monitor nodes marked as
STUN only in the default derpmap.

Updates #11492

Signed-off-by: Val <valerie@tailscale.com>
2023-06-20 12:04:55 -07:00
Maisem Ali
2ae670eb71 ssh/tailssh: work around lack of scontext in SELinux
Trying to SSH when SELinux is enforced results in errors like:

```
➜  ~ ssh ec2-user@<ip>
Last login: Thu Jun  1 22:51:44 from <ip2>
ec2-user: no shell: Permission denied
Connection to <ip> closed.
```

while the `/var/log/audit/audit.log` has
```
type=AVC msg=audit(1685661291.067:465): avc:  denied  { transition } for  pid=5296 comm="login" path="/usr/bin/bash" dev="nvme0n1p1" ino=2564 scontext=system_u:system_r:unconfined_service_t:s0 tcontext=unconfined_u:unconfined_r:unconfined_t:s0 tclass=process permissive=0
```

The right fix here would be to somehow install the appropriate context when
tailscale is installed on host, but until we figure out a way to do that
stop using the `login` cmd in these situations.

Updates #4908

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-06-20 10:44:22 -07:00
Ross Zurowski
0ed088b47b tka: add function for generating signing deeplinks (#8385)
This commit continues the work from #8303, providing a method for a
tka.Authority to generate valid deeplinks for signing devices. We'll
use this to provide the necessary deeplinks for users to sign from
their mobile devices.

Updates #8302

Signed-off-by: Ross Zurowski <ross@rosszurowski.com>
2023-06-20 09:36:37 -07:00
Flakes Updater
909e9eabe4 go.mod.sri: update SRI hash for go.mod changes
Signed-off-by: Flakes Updater <noreply+flakes-updater@tailscale.com>
2023-06-19 10:42:31 -04:00
Andrew Dunham
b6d20e6f8f go.mod, net/dns/recursive: update github.com/miekg/dns
Updates #cleanup

Change-Id: If4de6a84448a17dd81cc2a8af788bd18c3d0bbe3
Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
2023-06-19 10:32:48 -04:00
Maisem Ali
1302295299 Dockerfile.base: install iputils
Fixes #8361

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-06-18 07:54:05 -07:00
License Updater
c6794dec11 licenses: update android licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-06-17 17:58:29 -07:00
Nick O'Neill
c783f28228 tool/gocross: properly set simulator deployment target (#8355)
Fixes tailscale/corp#11876

Signed-off-by: Nick O'Neill <nick@tailscale.com>
2023-06-15 12:42:30 -07:00
License Updater
c1cbd41fdc licenses: update win/apple licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-06-15 09:22:09 -07:00
Sonia Appasamy
e1cdcf7708 ipn/ipnlocal: add identity headers to HTTP serve proxy
Adds two new headers to HTTP serve proxy:
- `Tailscale-User-Login`: Filled with requester's login name.
- `Tailscale-User-Name`: Filled with requester's display name.

These headers only get filled when the SrcAddr is associated with
a non-tagged (i.e. user-owned) node within the client's Tailnet.

The headers are passed through empty when the request originated
from another tailnet, or the public internet (via funnel).

Updates https://github.com/tailscale/tailscale/issues/6954

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-06-14 14:20:28 -04:00
Claire Wang
80692edcb8 .github/workflows: Add docker build check (#8345)
Fixes #8344

Signed-off-by: Claire Wang <claire@tailscale.com>
2023-06-14 13:49:18 -04:00
Claire Wang
27a0f0a55b Remove unused dependency from dockerfile (#8343)
Closes #8342

Signed-off-by: Claire Wang <claire@tailscale.com>
2023-06-14 13:21:30 -04:00
Andrea Gottardo
99f17a7135 tka: provide verify-deeplink local API endpoint (#8303)
* tka: provide verify-deeplink local API endpoint

Fixes https://github.com/tailscale/tailscale/issues/8302

Signed-off-by: Andrea Gottardo <andrea@tailscale.com>

Address code review comments

Signed-off-by: Andrea Gottardo <andrea@tailscale.com>

Address code review comments by Ross

Signed-off-by: Andrea Gottardo <andrea@tailscale.com>

* Improve error encoding, fix logic error

Signed-off-by: Andrea Gottardo <andrea@tailscale.com>

---------

Signed-off-by: Andrea Gottardo <andrea@tailscale.com>
2023-06-13 11:39:23 -07:00
Graham Christensen
4dda949760 tailscale ping: note that -c can take 0 for infinity
Signed-off-by: Graham Christensen <graham@grahamc.com>
2023-06-12 20:57:25 -07:00
Brad Fitzpatrick
a076213f58 net/memnet: add optional Listener.NewConn config knob
Updates tailscale/corp#11620

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-06-12 14:06:11 -07:00
License Updater
4451a7c364 licenses: update win/apple licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-06-12 13:40:57 -07:00
Maisem Ali
fe95d81b43 ipn/ipnlocal,wgengine/netstack: move LocalBackend specifc serving logic to LocalBackend
The netstack code had a bunch of logic to figure out if the LocalBackend should handle an
incoming connection and then would call the function directly on LocalBackend. Move that
logic to LocalBackend and refactor the methods to return conn handlers.

Updates #cleanup

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-06-12 12:56:07 -07:00
Denton Gentry
5b110685fb wgengine/netstack: increase maxInFlightConnectionAttempts
Address reports of subnet router instability when running in
`--tun=userspace-networking` mode.

Fixes https://github.com/tailscale/corp/issues/12184

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2023-06-12 12:00:38 -07:00
License Updater
0b3b81b37a licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-06-12 09:28:27 -07:00
dependabot[bot]
6172f9590b .github: Bump golangci/golangci-lint-action from 3.4.0 to 3.6.0
Bumps [golangci/golangci-lint-action](https://github.com/golangci/golangci-lint-action) from 3.4.0 to 3.6.0.
- [Release notes](https://github.com/golangci/golangci-lint-action/releases)
- [Commits](08e2f20817...639cd343e1)

---
updated-dependencies:
- dependency-name: golangci/golangci-lint-action
  dependency-type: direct:production
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <support@github.com>
2023-06-12 06:23:35 -07:00
Brad Fitzpatrick
1543e233e6 net/tstun, tsnet: make happier on WASI
Also fix a js/wasm issue with tsnet in the process. (same issue as WASI)

Updates #8320
Fixes #8315

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-06-11 18:03:42 -07:00
Flakes Updater
167e154bcc go.mod.sri: update SRI hash for go.mod changes
Signed-off-by: Flakes Updater <noreply+flakes-updater@tailscale.com>
2023-06-11 09:55:48 -07:00
Brad Fitzpatrick
67e912824a all: adjust some build tags for wasi
A start.

Updates #8320

Change-Id: I64057f977be51ba63ce635c56d67de7ecec415d1
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-06-11 09:45:46 -07:00
Charlotte Brandhorst-Satzkorn
63b1a4e35d words: here comes trouble
If you start hearing everything in auto-tune for the rest of the day,
I take no responsibility for it.

Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2023-06-11 08:02:40 -07:00
Andrew Dunham
f077b672e4 net/dns/recursive: add initial implementation of recursive DNS resolver
We've talked in the past about reworking how bootstrap DNS works to
instead do recursive DNS resolution from the root; this would better
support on-prem customers and Headscale users where the DERP servers
don't currently resolve their DNS server. This package is an initial
implementation of recursive resolution for A and AAAA records.

Updates #5853

Change-Id: Ibe974d78709b4b03674b47c4ef61f9a00addf8b4
Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
2023-06-09 14:11:40 -04:00
Maisem Ali
2e0aa151c9 ssh/tailssh: add support for remote/reverse port forwarding
This basically allows running services on the SSH client and reaching
them from the SSH server during the session.

Updates #6575

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-06-09 08:47:32 -07:00
Andrew Dunham
62130e6b68 util/slicesx: add Partition function
Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: If97995ca9ee9fad40f327420dcb1857dd7ea2315
2023-06-08 13:08:51 -04:00
Andrew Dunham
2a9d46c38f wgengine/magicsock: prefer private endpoints to public ones
Switch our best address selection to use a scoring-based approach, where
we boost each address based on whether it's a private IP or IPv6.

For users in cloud environments, this biases endpoint selection towards
using an endpoint that is less likely to cost the user money, and should
be less surprising to users.

This also involves updating the tests to not use private IPv4 addresses;
other than that change, the behaviour should be identical for existing
endpoints.

Updates #8097

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I069e3b399daea28be66b81f7e44fc27b2943d8af
2023-06-08 12:23:28 -04:00
Brad Fitzpatrick
eefee6f149 all: use cmpx.Or where it made sense
I left a few out where writing it explicitly was better
for various reasons.

Updates #8296

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-06-07 22:06:24 -07:00
phirework
699996ad6c go.toolchain.rev: upgrade to Go 1.20.5 (#8304)
Change-Id: I317b6e61d62212efca0e905ea9c626cc24a6912b

Signed-off-by: Jenny Zhang <jz@tailscale.com>
2023-06-07 22:12:18 -04:00
Brad Fitzpatrick
12f8c98823 util/cmpx: add package with cmp-like things from future Go releases
Updates #8296

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-06-07 12:41:31 -07:00
Andrea Gottardo
1c4a047ad0 version: detect tvOS by checking XPC_SERVICE_NAME (#8295)
Another change needed working towards #8282.

Updates https://github.com/tailscale/tailscale/issues/8282

Signed-off-by: Andrea Gottardo <andrea@tailscale.com>
2023-06-07 12:19:31 -07:00
Marwan Sulaiman
f8f0b981ac portlist: remove async functionality
This PR removes all async functionality from the portlist package
which may be a breaking change for non-tailscale importers. The only
importer within this codebase (LocalBackend) is already using the synchronous
API so no further action needed.

Fixes #8171

Signed-off-by: Marwan Sulaiman <marwan@tailscale.com>
2023-06-07 10:22:09 -04:00
Andrea Gottardo
a353ae079b tool/gocross: handle TVOS_DEPLOYMENT_TARGET (#8292)
This is needed in order to build our network extension on tvOS. First step for #8282

Signed-off-by: Andrea Gottardo <andrea@tailscale.com>
Co-authored-by: Andrea Gottardo <andrea@tailscale.com>
2023-06-06 18:06:17 -07:00
Xe Iaso
43e230d4cd tsnet: document how to use Dir with multiple servers per process (#8286)
Followup from a conversation on the Gophers slack, also matches the
examples in the tsnet kb.

Closes #8287

Signed-off-by: Xe Iaso <xe@tailscale.com>
2023-06-06 15:20:00 -04:00
Marwan Sulaiman
5dd0b02133 portlist: add a synchronous Poll method
This is a follow up on PR #8172 that adds a synchronous Poll method
which allows for the Poller to be used as a zero value without needing
the constructor. The local backend is also changed to use the new API.
A follow up PR will remove the async functionality from the portlist package.

Updates #8171

Signed-off-by: Marwan Sulaiman <marwan@tailscale.com>
2023-06-05 23:10:42 -04:00
Derek Burdick
d3c8c3dd00 ssh/tailssh: Max Username Length 256 for linux
Max username length is increased to 256 on linux to match /usr/include/bits/local_lim.h

Fixes #8277

Signed-off-by: Derek Burdick <derek-burdick@users.noreply.github.com>
2023-06-05 18:04:30 -07:00
Denton Gentry
64f16f7f38 net/dnscache: use PreferGo on Windows.
Updates https://github.com/tailscale/tailscale/issues/5161

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2023-06-05 15:58:49 -07:00
Denton Gentry
6554a0cbec build_dist.sh: use $go consistently.
The invocation at the end unconditionally used
./tool/go, but the structuring on lines 14-17
sets up to use a different toolchain if the
platform requires it.

Fixes https://github.com/tailscale/tailscale/issues/8156

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2023-06-05 10:21:03 -07:00
License Updater
d17312265e licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-06-05 09:54:12 -07:00
Denton Gentry
4321d1d6e9 scripts/installer.sh: add sle-micro-rancher.
Fixes https://github.com/tailscale/tailscale/issues/5633

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2023-06-04 17:05:51 -07:00
DJRHails
2492ca2900 words: remove misspelling of trex
Signed-off-by: DJRHails <hello@hails.info>
2023-06-04 14:18:36 -07:00
Dominic Black
570cb018da ipn/localapi: require only read permission for WatchIPNBus (#7798)
Allow calls to `WatchIPNBus` to be permformed by clients with
Readonly permissions. This brings it in line with the permissions
required for `Status`, which also exposes the similar information.

This allows clients to get realtime updates about the tailnet
in their own applications, without needing to actively poll the
`Status` endpoint.

Fixes https://github.com/tailscale/tailscale/issues/7797

Signed-off-by: Dominic Black <dom@encore.dev>
2023-06-04 09:05:21 -07:00
Heiko Rothe
dc1d8826a2 ipn/ipnlocal: [serve/funnel] add forwarded host and proto header (#8224)
This replicates the headers also sent by the golang reverse proxy by
default.

Fixes https://github.com/tailscale/tailscale/issues/7061

Signed-off-by: Heiko Rothe <me@heikorothe.com>
2023-06-04 09:04:33 -07:00
Denton Gentry
67882ad35d scripts/installer.sh: add BlendOS support.
Fixes https://github.com/tailscale/tailscale/issues/8100

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2023-06-04 08:31:58 -07:00
Andrew Dunham
07eacdfe92 ipn/ipnlocal: renew certificates based on lifetime
Instead of renewing certificates based on whether or not they're expired
at a fixed 14-day period in the future, renew based on whether or not
we're more than 2/3 of the way through the certificate's lifetime. This
properly handles shorter-lived certificates without issue.

Updates #8204

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I5e82a9cadc427c010d04ce58c7f932e80dd571ea
2023-06-02 12:36:32 -04:00
License Updater
d06fac0ede licenses: update win/apple licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-06-01 19:02:47 -07:00
Andrew Dunham
9d09c821f7 ipn/ipnlocal: add more logging during profile migration
Updates tailscale/corp#11883

Change-Id: I3a3ca8f25bfefca139115b25ec4161c069da7e4a
Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
2023-06-01 21:00:55 -04:00
Aaron Klotz
2aa8299c37 cmd/tailscaled, util/winutil: log our registry keys during tailscaled startup
In order to improve our ability to understand the state of policies and
registry settings when troubleshooting, we enumerate all values in all subkeys.
x/sys/windows does not already offer this, so we need to call RegEnumValue
directly.

For now we're just logging this during startup, however in a future PR I plan to
also trigger this code during a bugreport. I also want to log more than just
registry.

Fixes #8141

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2023-06-01 13:39:17 -06:00
Flakes Updater
88ee857bc8 go.mod.sri: update SRI hash for go.mod changes
Signed-off-by: Flakes Updater <noreply+flakes-updater@tailscale.com>
2023-06-01 09:11:17 -07:00
Vince Prignano
1a691ec5b2 cmd/k8s-operator: update controller-runtime to v0.15
Fixes #8170

Signed-off-by: Vince Prignano <vince@prigna.com>
2023-06-01 05:51:25 -07:00
Anton Tolchanov
6a156f6243 client/tailscale: support deauthorizing a device
This adds a new `SetAuthorized` method that allows setting device
authorization to true or false. I chose the method name to be consistent
with SetTags.

Updates https://github.com/tailscale/corp/issues/10160

Signed-off-by: Anton Tolchanov <anton@tailscale.com>
2023-06-01 12:46:28 +01:00
dependabot[bot]
525b9c806f .github: bump peter-evans/create-pull-request from 5.0.0 to 5.0.1
Bumps [peter-evans/create-pull-request](https://github.com/peter-evans/create-pull-request) from 5.0.0 to 5.0.1.
- [Release notes](https://github.com/peter-evans/create-pull-request/releases)
- [Commits](5b4a9f6a9e...284f54f989)

---
updated-dependencies:
- dependency-name: peter-evans/create-pull-request
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>
2023-05-30 09:56:55 -07:00
David Anderson
fc5b137d25 release/dist/synology: build hi3535 as armv5, not armv7
This platform is technically an armv7, but has no hardware floating
point unit. armv5 is the only target Go understands to lack floating
point, so use that.

Updates #6860

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-05-29 21:01:40 -07:00
David Anderson
32e0ba5e68 release/dist/synology: build synology packages with cmd/dist
Updates #8217

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-05-29 14:18:37 -07:00
Denton Gentry
399a80785e wgengine/netstack: use ping6 on BSD platforms
Various BSD-derived operating systems including macOS and FreeBSD
require that ping6 be used for IPv6 destinations. The "ping" command
does not understand an IPv6 destination.

FreeBSD 13.x and later do handle IPv6 in the regular ping command,
but also retain a ping6 command. We use ping6 on all versions of
FreeBSD.

Fixes https://github.com/tailscale/tailscale/issues/8225

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2023-05-28 09:50:21 -07:00
David Anderson
c0b4a54146 release/dist/cli: correctly handle absolute build outputs in manifest
Some builders return absolute paths to build products already. When that
happens, the manifest writing logic shouldn't tack on another absolute
prefix.

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-05-25 19:52:40 -07:00
Brad Fitzpatrick
c4fe9c536d go.toolchain.rev: bump, again
For https://go-review.googlesource.com/c/go/+/498398

Updates tailscale/go#63
Updates tailscale/go#64

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-05-25 15:50:24 -07:00
valscale
370b2c37e0 tka: fix go vet complaint on copy of lock value in tailchonk_test.go (#8208)
go vet complains when we copy a lock value. Create clone function that
copies everything but the lock value.

Fixes #8207

Signed-off-by: Val <valerie@tailscale.com>
2023-05-25 13:34:13 -07:00
Brad Fitzpatrick
cb94ddb7b8 go.toolchain.rev: bump
Updates tailscale/go#63
Updates tailscale/go#64

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-05-25 12:21:39 -07:00
Andrea Gottardo
66f97f4bea tka: provide authority StateID in NetworkLockStatus response (#8200)
Fixes #8201.

Signed-off-by: Andrea Gottardo <andrea@tailscale.com>
Co-authored-by: Andrea Gottardo <andrea@tailscale.com>
2023-05-24 13:36:25 -07:00
Marwan Sulaiman
e32e5c0d0c portlist: add Poller.IncludeLocalhost option
This PR parameterizes receiving loopback updates from the portlist package.
Callers can now include services bound to localhost if they want.
Note that this option is off by default still.

Fixes #8171

Signed-off-by: Marwan Sulaiman <marwan@tailscale.com>
2023-05-24 13:26:16 -04:00
Will Norris
3d180a16c3 VERSION.txt: this is v1.43.0
Signed-off-by: Will Norris <will@tailscale.com>
2023-05-24 09:03:59 -07:00
Charlotte Brandhorst-Satzkorn
4e86857313 ssh/tailssh: add ssh session recording failed event type
This change introduces a SSHSessionRecordingFailed event type
that is used when a session recording fails to start or fails during a
session, and the on failure indicates that it should fail open.

Updates tailscale/corp#9967

Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2023-05-22 17:39:01 -07:00
salman aljammaz
745ee97973 api.md: update device authorized API docs to allow for deauth (#8162)
The authorize device API (/api/v2/device/{deviceID}/authorized)
will soon allow device deauthorisation.

Fixes corp#10160.

Signed-off-by: salman <salman@tailscale.com>
2023-05-22 12:52:40 +01:00
Brad Fitzpatrick
a4fd4fd845 ssh/tailssh: fix regression after LDAP support
58ab66ec51 added LDAP support
for #4945 by shelling out to getdent.

It was supposed to fall back to the old method when getdent wasn't
found, but some variable name confusion (uid vs username) meant the
old path wasn't calling the right lookup function (user.LookupId
instead of user.Lookup).

Which meant that changed probably also broke FreeBSD and macOS SSH
support in addition to the reported OpenWRT regression.

The gokrazy support didn't look right either.

Fixes #8180

Change-Id: I273bbe96fe98b2517fbf0335fd476b483c051554
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-05-21 07:53:25 -07:00
James Tucker
e3cb982139 words: shell-ebrating crustacean chaos
Hey team! I've been diving deep into the code ocean for the past few
hours, tackling those sneaky race conditions that were threatening our
database. It was quite the crabby situation, but fear not! It's friday
and I've emerged and I'm ready to shell-ebrate with some punny word
additions. 🎉

This commit introduces a shell-shocking array of crustaceans to our word
list. From the lively lobsters to the clever prawns.

Signed-off-by: James Tucker <james@tailscale.com>
2023-05-19 14:15:26 -07:00
valscale
5ae786988c derp: remove default logging of disconnecting clients (#8163)
~97% of the log messages derper outputs are related to the normal
non-error state of a client disconnecting in some manner. Add a
verbose logging feature that only logs these messages when enabled.

Fixes #8024

Signed-off-by: Val <valerie@tailscale.com>
2023-05-18 15:35:16 -07:00
Maisem Ali
0ca8bf1e26 ssh/tailssh: close tty on session close
We were only closing on side of the pty/tty pair.
Close the other side too.

Thanks to @fritterhoff for reporting and debugging the issue!

Fixes #8119

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-05-18 09:35:42 -07:00
Gabriel Martinez
03e848e3b5 cmd/k8s-operator: add support for priorityClassName
Updates #8155

Signed-off-by: Gabriel Martinez <gabrielmartinez@sisti.pt>
2023-05-17 15:28:06 -07:00
Derek Kaser
7c88eeba86 cmd/tailscale: allow Tailscale to work with Unraid web interface (#8062)
Updates tailscale/tailscale#8026

Signed-off-by: Derek Kaser <derek.kaser@gmail.com>
2023-05-17 13:26:39 -07:00
Sonia Appasamy
f0ee03dfaf cmd/tailscale/cli: [serve] add reset flag
Usage: `tailscale serve reset`

Fixes #8139

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-05-16 16:19:08 -04:00
Brad Fitzpatrick
4664318be2 client/tailscale: revert CreateKey API change, add Client.CreateKeyWithExpiry
The client/tailscale is a stable-ish API we try not to break. Revert
the Client.CreateKey method as it was and add a new
CreateKeyWithExpiry method to do the new thing. And document the
expiry field and enforce that the time.Duration can't be between in
range greater than 0 and less than a second.

Updates #7143
Updates #8124 (reverts it, effectively)

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-05-12 21:05:12 -07:00
shayne
678bb92bb8 cmd/tailscale/cli: [up] fix CreateKey missing argument (#8124)
Signed-off-by: Shayne Sweeney <shayne@tailscale.com>
2023-05-12 02:03:17 -04:00
Matt Brown
9b6e48658f client: allow the expiry time to be specified for new keys
Adds a parameter for create key that allows a number of seconds
(less than 90) to be specified for new keys.

Fixes https://github.com/tailscale/tailscale/issues/7965

Signed-off-by: Matthew Brown <matthew@bargrove.com>
2023-05-11 22:05:18 -07:00
Maisem Ali
85215ed58a cmd/k8s-operator: handle NotFound secrets
getSingleObject can return `nil, nil`, getDeviceInfo was not handling
that case which resulted in panics.

Fixes #7303

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-05-11 18:26:11 -07:00
Brad Fitzpatrick
b69059334b util/set: add a basic map-based Set type
We have two other types of Sets here. Add the basic obvious one too.

Needed for a change elsewhere.

Updates #cleanup

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-05-11 15:17:34 -07:00
Joe Tsai
84c99fe0d9 logtail: be less aggressive about re-uploads (#8117)
The retry logic was pathological in the following ways:

* If we restarted the logging service, any pending uploads
would be placed in a retry-loop where it depended on backoff.Backoff,
which was too aggresive. It would retry failures within milliseconds,
taking at least 10 retries to hit a delay of 1 second.

* In the event where a logstream was rate limited,
the aggressive retry logic would severely exacerbate the problem
since each retry would also log an error message.
It is by chance that the rate of log error spam
does not happen to exceed the rate limit itself.

We modify the retry logic in the following ways:

* We now respect the "Retry-After" header sent by the logging service.

* Lacking a "Retry-After" header, we retry after a hard-coded period of
30 to 60 seconds. This avoids the thundering-herd effect when all nodes
try reconnecting to the logging service at the same time after a restart.

* We do not treat a status 400 as having been uploaded.
This is simply not the behavior of the logging service.

Updates #tailscale/corp#11213

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2023-05-11 12:52:35 -07:00
James Tucker
da90fab899 net/netcheck: reenable TestBasic on Windows
This test was either fixed by intermediate changes or was mis-flagged as
failing during #7876 triage.

Updates #7876

Signed-off-by: James Tucker <jftucker@gmail.com>
2023-05-10 20:16:35 -07:00
James Tucker
ca49b29582 tsnet: reenable TestLoopbackSOCKS5 on Windows
This test was either fixed in the intermediate time or mis-flagged
during the #7876 triage, but is now passing.

Updates #7876

Signed-off-by: James Tucker <jftucker@gmail.com>
2023-05-10 20:15:41 -07:00
Brad Fitzpatrick
cb2fd5be92 cmd/tsconnect: fix forgotten API change for wasm
Fix regression from 6e967446e4

Updates #8036

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-05-09 21:23:29 -07:00
David Anderson
d27a6e1c53 tool/gocross: fix incorrect relpath usage in bootstrap script
The subshell in which gocross gets built cd's to the corp checkout dir
near the top, so all future references to corp repository files should
be simple relative paths, and not reference $repo_root. When $repo_root
is an absolute path, it doesn't matter and everything works out, but on
some OSes and shells and invocations, $repo_root is a completely relative
path that is invalidated by the "cd".

Fixes tailscale/corp#11183

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-05-09 16:19:46 -07:00
Brad Fitzpatrick
4f454f4122 util/codegen: support embedded fields
I noticed cmd/{cloner,viewer} didn't support structs with embedded
fields while working on a change in another repo. This adds support.

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-05-09 15:40:17 -07:00
Will Norris
ea84fc9ad2 net/sockstats: wait before reporting battery usage
Wait 2 minutes before we start reporting battery usage. There is always
radio activity on initial startup, which gets reported as 100% high
power usage.  Let that settle before we report usage data.

Updates tailscale/corp#9230

Signed-off-by: Will Norris <will@tailscale.com>
2023-05-09 10:18:16 -07:00
salman
1ce08256c0 release/dist: add deb/rpm arch mappings for mipses
According to https://wiki.debian.org/SupportedArchitectures Debian does
not support big-endian mips64, so that one remains disabled.

According to https://fedoraproject.org/wiki/Architectures Fedora only
supports little-endian mips, so leaving both big-endian ones out too.

Updates #8005.

Signed-off-by: salman <salman@tailscale.com>
2023-05-09 17:31:13 +01:00
Craig Rodrigues
827abbeeaa cmd/k8s-operator: print version in startup logs
Fixes: #7813

Signed-off-by: Craig Rodrigues <rodrigc@crodrigues.org>
2023-05-08 18:56:21 -07:00
License Updater
d1ecb1f43b licenses: update win/apple licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-05-08 16:48:36 -07:00
Brad Fitzpatrick
a743b66f9d ssh/tailssh: move some user-related code into new user.go
The previous commit 58ab66e added ssh/tailssh/user.go as part of
working on #4945. So move some more user-related code over to it.

Updates #cleanup

Change-Id: I24de66df25ffb8f867e1a0a540d410f9ef16d7b0
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-05-08 13:47:59 -07:00
Brad Fitzpatrick
58ab66ec51 ssh/tailssh: support LDAP users for Tailscale SSH
Fixes #4945

Change-Id: Ie013cb47684cb87928a44f92c66352310bfe53f1
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-05-08 11:29:14 -07:00
Chenyang Gao
e8b06b2232 version: properly handle vcs.modified when it's "false"
Current code will set the "dirty" field of VersionInfo always "true"
if vcs.modified flag is there. No matter whether the flag is "true" or
"false".  It will make sense to set this field due to vcs.modified
value, not only the existence of the key.

Signed-off-by: Chenyang Gao <gps949@outlook.com>
2023-05-07 09:15:38 -07:00
License Updater
df8b1b2179 licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-05-06 23:48:30 -07:00
License Updater
4d730e154c licenses: update android licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2023-05-06 16:33:37 -07:00
Chenyang Gao
b9fb8ac702 fix sys.Set(router) issue will crash the daemon in some OSs
Signed-off-by: Chenyang Gao <gps949@outlook.com>

in commit 6e96744, the tsd system type has been added.
Which will cause the daemon will crash on some  OSs (Windows, darwin and so on).
The root cause is that on those OSs, handleSubnetsInNetstack() will return true and set the conf.Router with a wrapper. 
Later in NewUserspaceEngine() it will do subsystem set and found that early set router mismatch to current value, then panic.
2023-05-06 14:11:43 -07:00
James Tucker
5c38f0979e tsweb/promvarz: fix repeated expvar definition in test
expvar can only be defined once, so running tests with a repeat counter
will fail if the variables are defined inside of the test function.

Observed failure:

```
--- FAIL: TestHandler (0.00s)
panic: Reuse of exported var name: gauge_promvarz_test_expvar
 [recovered]
        panic: Reuse of exported var name: gauge_promvarz_test_expvar

goroutine 9 [running]:
testing.tRunner.func1.2({0x100f267e0, 0x1400026e770})
        /usr/local/go/src/testing/testing.go:1526 +0x1c8
testing.tRunner.func1()
        /usr/local/go/src/testing/testing.go:1529 +0x364
panic({0x100f267e0, 0x1400026e770})
        /usr/local/go/src/runtime/panic.go:884 +0x1f4
log.Panicln({0x140000b8e20?, 0x1a?, 0x1400026e750?})
        /usr/local/go/src/log/log.go:398 +0x60
expvar.Publish({0x100e2b21d, 0x1a}, {0x100fd7a08?, 0x140000232c0})
        /usr/local/go/src/expvar/expvar.go:284 +0xc0
expvar.NewInt(...)
        /usr/local/go/src/expvar/expvar.go:304
tailscale.com/tsweb/promvarz.TestHandler(0x14000082b60)
        /Users/charlotte/ts-src/tailscale/tsweb/promvarz/promvarz_test.go:18 +0x5c
testing.tRunner(0x14000082b60, 0x100fd5858)
        /usr/local/go/src/testing/testing.go:1576 +0x104
created by testing.(*T).Run
        /usr/local/go/src/testing/testing.go:1629 +0x370
FAIL    tailscale.com/tsweb/promvarz    0.149s
```

Fixes #8065
Signed-off-by: James Tucker <james@tailscale.com>
2023-05-06 09:53:09 -07:00
Charlotte Brandhorst-Satzkorn
024d48d9c1 tailcfg: bump capability version
This change bumps the capability version to 62, after support for
sending SSHEventNotificationRequests to control via noise for failure
events was introduced.

Updates tailscale/corp#9967

Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2023-05-05 14:22:59 -07:00
Charlotte Brandhorst-Satzkorn
29ded8f9f9 ssh/tailssh,tailcfg: add connID to ssheventnotifyrequest and castheader
This change adds a ConnectionID field to both SSHEventNotifyRequest and
CastHeader that identifies the ID of a connection to the SSH server.

Updates tailscale/corp#9967

Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2023-05-05 14:22:59 -07:00
Charlotte Brandhorst-Satzkorn
68307c1411 ssh/tailssh: send ssh event notifications on recording failures
This change sends an SSHEventNotificationRequest over noise when a
SSH session is set to fail closed and the session is unable to start
because a recorder is not available or a session is terminated because
connection to the recorder is ended. Each of these scenarios have their
own event type.

Updates tailscale/corp#9967

Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2023-05-05 14:22:59 -07:00
Charlotte Brandhorst-Satzkorn
2804327074 tailcfg: update rename SSHFailureNotifyRequest and add EventType
This change renames SSHFailureNotifyRequest to SSHEventNotifyRequest
to better reflect the additional events we could add in the future.
This change also adds an EventType used to catagories the events.

Updates tailscale/corp#9967

Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2023-05-05 14:22:59 -07:00
Charlotte Brandhorst-Satzkorn
8d3d48e000 ipn/ipnlocal: add NodeKey func to return the public node NodeKey
This change introduces a NodeKey func on localbackend that returns the
public node key.

Updates tailscale/corp#9967

Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2023-05-05 14:22:59 -07:00
Brad Fitzpatrick
8864112a0c ipn/ipnlocal: bound how long cert fetchher checks for existing DNS records
It was supposed to be best effort but in some cases (macsys at least,
per @marwan-at-work) it hangs and exhausts the whole context.Context
deadline so we fail to make the SetDNS call to the server.

Updates #8067
Updates #3273 etc

Change-Id: Ie1f04abe9689951484748aecdeae312afbafdb0f
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-05-05 12:31:45 -07:00
James Tucker
9ed3a061c3 net/netns: fix segv when no tailscale interface is found
`interfaces.Tailscale()` returns all zero values when it finds no
Tailscale interface and encounters no errors. The netns package was
treating no error as a signal that it would receive a non-zero pointer
value leading to nil pointer dereference.

Observed in:

```
--- FAIL: TestGetInterfaceIndex (0.00s)
    --- FAIL: TestGetInterfaceIndex/IP_and_port (0.00s)
panic: runtime error: invalid memory address or nil pointer dereference [recovered]
        panic: runtime error: invalid memory address or nil pointer dereference
[signal SIGSEGV: segmentation violation code=0x2 addr=0x0 pc=0x1029eb7d8]

goroutine 7 [running]:
testing.tRunner.func1.2({0x102a691e0, 0x102bc05c0})
        /Users/raggi/.cache/tailscale-go/src/testing/testing.go:1526 +0x1c8
testing.tRunner.func1()
        /Users/raggi/.cache/tailscale-go/src/testing/testing.go:1529 +0x384
panic({0x102a691e0, 0x102bc05c0})
        /Users/raggi/.cache/tailscale-go/src/runtime/panic.go:884 +0x204
tailscale.com/net/netns.getInterfaceIndex(0x14000073f28, 0x1028d0284?, {0x1029ef3b7, 0xa})
        /Users/raggi/src/github.com/tailscale/tailscale/net/netns/netns_darwin.go:114 +0x228
tailscale.com/net/netns.TestGetInterfaceIndex.func2(0x14000138000)
        /Users/raggi/src/github.com/tailscale/tailscale/net/netns/netns_darwin_test.go:37 +0x54
testing.tRunner(0x14000138000, 0x140000551b0)
        /Users/raggi/.cache/tailscale-go/src/testing/testing.go:1576 +0x10c
created by testing.(*T).Run
        /Users/raggi/.cache/tailscale-go/src/testing/testing.go:1629 +0x368
FAIL    tailscale.com/net/netns 0.824s
```

Fixes #8064

Signed-off-by: James Tucker <jftucker@gmail.com>
2023-05-05 11:31:43 -07:00
Brad Fitzpatrick
6e967446e4 tsd: add package with System type to unify subsystem init, discovery
This is part of an effort to clean up tailscaled initialization between
tailscaled, tailscaled Windows service, tsnet, and the mac GUI.

Updates #8036

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-05-04 14:21:59 -07:00
Derek Kaser
0d7303b798 various: add detection and Taildrop for Unraid
Updates tailscale/tailscale#8025

Signed-off-by: Derek Kaser <derek.kaser@gmail.com>
2023-05-04 13:40:13 -07:00
Flakes Updater
d1ce7a9b5e go.mod.sri: update SRI hash for go.mod changes
Signed-off-by: Flakes Updater <noreply+flakes-updater@tailscale.com>
2023-05-04 12:55:01 -07:00
James Tucker
5def4f4a1c go.mod: bump goreleaser deps
Periodic update for start of cycle. goreleaser is not updated to v2 yet,
but indirects updated.

Updates #8043

Signed-off-by: James Tucker <james@tailscale.com>
2023-05-04 12:32:24 -07:00
Flakes Updater
1c6ff310ae go.mod.sri: update SRI hash for go.mod changes
Signed-off-by: Flakes Updater <noreply+flakes-updater@tailscale.com>
2023-05-04 12:31:31 -07:00
James Tucker
48605226dd go.mod: bump gvisor
Periodic update for start of cycle.

Updates #8043

Signed-off-by: James Tucker <james@tailscale.com>
2023-05-04 12:30:27 -07:00
Maisem Ali
f46c1aede0 go.mod: bump k8s libs
The key is to update sigs.k8s.io/controller-runtime and let it update others.

Updates #8043

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-05-04 12:00:03 -07:00
Brad Fitzpatrick
73d128238e envknob: support tailscaled-env.txt on macOS too
Updates #3707

Co-authored-by: Marwan Sulaiman <marwan@tailscale.com>
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-05-04 10:27:59 -07:00
Anton Tolchanov
787fc41fa4 scripts/installer.sh: check connectivity with pkgs.tailscale.com
Installer script relies on pkgs.tailscale.com being reachable, both for
checking what Linux distros are supported, but also for actually
downloading repo configuration files, gpg keys and packages themselves.

This change adds a simple reachability check which will print an error
message when pkgs.tailscale.com is not reachable.

Fixes https://github.com/tailscale/corp/issues/8952

Signed-off-by: Anton Tolchanov <anton@tailscale.com>
2023-05-04 16:49:56 +02:00
Flakes Updater
5783adcc6f go.mod.sri: update SRI hash for go.mod changes
Signed-off-by: Flakes Updater <noreply+flakes-updater@tailscale.com>
2023-05-03 19:56:23 -07:00
License Updater
503b6dd8be licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-05-03 19:56:00 -07:00
Brad Fitzpatrick
9e9ea6e974 go.mod: bump all deps possible that don't break the build
This holds back gvisor, kubernetes, goreleaser, and esbuild, which all
had breaking API changes.

Updates #8043
Updates #7381
Updates #8042 (updates u-root which adds deps)

Change-Id: I889759bea057cd3963037d41f608c99eb7466a5b
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-05-03 19:52:54 -07:00
M. J. Fromberger
459744c9ea .github: mark bots for exemption by issuebot (#8041)
#cleanup

Change-Id: I13757ee20240166af72606d166e840ae3ee797d7
Signed-off-by: M. J. Fromberger <fromberger@tailscale.com>
2023-05-03 18:36:19 -07:00
License Updater
7675d323fa licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2023-05-03 15:48:09 -07:00
dependabot[bot]
270942094f build(deps): bump github.com/docker/docker
Bumps [github.com/docker/docker](https://github.com/docker/docker) from 20.10.16+incompatible to 20.10.24+incompatible.
- [Release notes](https://github.com/docker/docker/releases)
- [Commits](https://github.com/docker/docker/compare/v20.10.16...v20.10.24)

---
updated-dependencies:
- dependency-name: github.com/docker/docker
  dependency-type: indirect
...

Signed-off-by: dependabot[bot] <support@github.com>
2023-05-03 15:40:46 -07:00
Maisem Ali
be190e990f ssh/tailssh: restore support for recording locally
We removed it earlier in 916aa782af, but we still want to support it for some time longer.

Updates tailscale/corp#9967

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-05-03 15:00:01 -07:00
Brad Fitzpatrick
4d7927047c wgengine/magicsock: annotate, skip flaky TestIsWireGuardOnlyPickEndpointByPing
Updates #8037
Updates #7826

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-05-03 14:58:28 -07:00
Charlotte Brandhorst-Satzkorn
ddb4040aa0 wgengine/magicsock: add address selection for wireguard only endpoints (#7979)
This change introduces address selection for wireguard only endpoints.
If a endpoint has not been used before, an address is randomly selected
to be used based on information we know about, such as if they are able
to use IPv4 or IPv6. When an address is initially selected, we also
initiate a new ICMP ping to the endpoints addresses to determine which
endpoint offers the best latency. This information is then used to
update which endpoint we should be using based on the best possible
route. If the latency is the same for a IPv4 and an IPv6 address, IPv6
will be used.

Updates #7826

Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2023-05-02 17:49:56 -07:00
Brad Fitzpatrick
c1e6888fc7 derp: add a README.md with some docs
Updates #docs

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-05-02 13:42:25 -07:00
Maisem Ali
3ae7140690 net/tstun: handle exit nodes in NAT configs
In the case where the exit node requires SNAT, we would SNAT all traffic not just the
traffic meant to go through the exit node. This was a result of the default route being
added to the routing table which would match basically everything.

In this case, we need to account for all peers in the routing table not just the ones
that require NAT.

Fix and add a test.

Updates tailscale/corp#8020

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-05-02 13:03:30 -07:00
Andrew Dunham
bcf7b63d7e wgengine/magicsock: add hysteresis to endpoint selection
Avoid selecting an endpoint as "better" than the current endpoint if the
total latency improvement is less than 1%. This adds some hysteresis to
avoid flapping between endpoints for a minimal improvement in latency.

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: If8312e1768ea65c4b4d4e13d8de284b3825d7a73
2023-05-02 08:56:16 -07:00
Tom DNetto
c5bf868940 ssh/tailssh: improve debug logging around revoked sessions
Updates https://github.com/tailscale/corp/issues/10943
Signed-off-by: Tom DNetto <tom@tailscale.com>
2023-05-01 14:10:16 -07:00
Andrew Dunham
42fd964090 control/controlclient: use dnscache.Resolver for Noise client
This passes the *dnscache.Resolver down from the Direct client into the
Noise client and from there into the controlhttp client. This retains
the Resolver so that it can share state across calls instead of creating
a new resolver.

Updates #4845
Updates #6110

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: Ia5d6af1870f3b5b5d7dd5685d775dcf300aec7af
2023-05-01 13:22:10 -07:00
License Updater
979d29b5f5 licenses: update win/apple licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-05-01 09:13:43 -07:00
Anton Tolchanov
1f4a34588b .github: test installer script in CI in docker
Every time we change `installer.sh`, run it in a few docker
containers based on different Linux distros, just as a simple test.

Also includes a few changes to the installer script itself to make
installation work in docker:
- install dnf config-manager command before running it
- run zypper in non-interactive mode
- update pacman indexes before installing packages

Updates https://github.com/tailscale/corp/issues/8952

Signed-off-by: Anton Tolchanov <anton@tailscale.com>
2023-04-29 08:48:19 +01:00
Denton Gentry
a82f275619 cmd/sniproxy: Set App name in tsnet hostinfo
Updates #1748
Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2023-04-28 21:50:30 -07:00
James Tucker
b3c3a9f174 syncs: add Map.Len to get the length of the Map
I need this for a corp change where I have a set as a queue, and make a
different decisison if the set is empty.

Updates tailscale/corp#10344

Signed-off-by: James Tucker <james@tailscale.com>
2023-04-27 19:10:28 -07:00
ayanamist
042f82ea32 build_dist.sh: make cross-compilation friendly for env CC specified
Signed-off-by: ayanamist <ayanamist@gmail.com>
2023-04-27 18:51:59 -07:00
dependabot[bot]
633d08bd7b .github: Bump actions/setup-go from 3 to 4
Bumps [actions/setup-go](https://github.com/actions/setup-go) from 3 to 4.
- [Release notes](https://github.com/actions/setup-go/releases)
- [Commits](https://github.com/actions/setup-go/compare/v3...v4)

---
updated-dependencies:
- dependency-name: actions/setup-go
  dependency-type: direct:production
  update-type: version-update:semver-major
...

Signed-off-by: dependabot[bot] <support@github.com>
2023-04-27 17:21:59 -07:00
James Tucker
d35ce1add9 syncs: add documentation to Map.Range
Updates #cleanup

Signed-off-by: James Tucker <james@tailscale.com>
2023-04-27 17:07:07 -07:00
Charlotte Brandhorst-Satzkorn
c3ab36cb9d words: charlotte 1 spell-checking-linter 0 (#7993)
Can't have a dupe when the dupe is wrong. Clearly we need to up
our spell checking game. Did anyone say AI?

Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2023-04-27 08:58:52 -07:00
James Tucker
8032b966a1 .github/workflows: add recency bias to action cache keys
The action cache restore process either matches the restore key pattern
exactly, or uses a matching prefix with the most recent date.

If the restore key is an exact match, then no updates are uploaded, but
if we've just computed tests executions for more recent code then we
will likely want to use those results in future runs.

Appending run_id to the cache key will give us an always new key, and
then we will be restore a recently uploaded cache that is more likely
has a higher overlap with the code being tested.

Updates #7975

Signed-off-by: James Tucker <james@tailscale.com>
2023-04-26 21:36:53 -07:00
Kyle Carberry
d78b334964 cmd/derper: disable http2
DERP doesn't support HTTP/2. If an HTTP/2 proxy was placed in front of
a DERP server requests would fail because the connection would
be initialized with HTTP/2, which the DERP client doesn't support.

Signed-off-by: Kyle Carberry <kyle@carberry.com>
2023-04-26 20:45:32 -07:00
Charlotte Brandhorst-Satzkorn
161d1d281a net/ping,netcheck: add v6 pinging capabilities to pinger (#7971)
This change adds a v6conn to the pinger to enable sending pings to v6
addrs.

Updates #7826

Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2023-04-26 15:59:37 -07:00
Denton Gentry
1145b9751d VERSION.txt: this is v1.41.0
Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2023-04-26 15:58:30 -07:00
Brad Fitzpatrick
1e876a3c1d ipn/ipnlocal: fix fmt format arg type mismatch in log line
It was printing like "v0xxxxxxxx" after version.Long became a func
in 8b2ae47c31.

Fixes #7976

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-04-26 14:28:09 -07:00
Maisem Ali
a8f10c23b2 cmd/tailscale/cli: [up] reuse --advertise-tags for OAuth key generation
We need to always specify tags when creating an AuthKey from an OAuth key.

Check for that, and reuse the `--advertise-tags` param.

Updates #7982

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-04-26 14:17:29 -07:00
Brad Fitzpatrick
b2b5379348 cmd/tailscale/cli: [up] change oauth authkey format
Updates #7982

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-04-26 13:36:17 -07:00
Brad Fitzpatrick
13de36303d cmd/tailscale/cli: [up] add experimental oauth2 authkey support
Updates #7982

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-04-26 12:25:42 -07:00
James Tucker
095d3edd33 ipn/ipnlocal: reenable profile tests on Windows
This fix does not seem ideal, but the test infrastructure using a local
goos doesn't seem to avoid all of the associated challenges, but is
somewhat deeply tied to the setup.

The core issue this addresses for now is that when run on Windows there
can be no code paths that attempt to use an invalid UID string, which on
Windows is described in [1].

For the goos="linux" tests, we now explicitly skip the affected
migration code if runtime.GOOS=="windows", and for the Windows test we
explicitly use the running users uid, rather than just the string
"user1". We also now make the case where a profile exists and has
already been migrated a non-error condition toward the outer API.

Updates #7876

[1] https://learn.microsoft.com/en-us/windows-server/identity/ad-ds/manage/understand-security-identifiers

Signed-off-by: James Tucker <jftucker@gmail.com>
2023-04-26 11:33:38 -07:00
James Tucker
43819309e1 .github/workflows: split tests and benchmarks for caching
Benchmark flags prevent test caching, so benchmarks are now executed
independently of tests.

Fixes #7975

Signed-off-by: James Tucker <james@tailscale.com>
2023-04-26 10:49:38 -07:00
Maisem Ali
1b8a0dfe5e ssh/tailssh: also handle recording upload failure during writes
Previously we would error out when the recording server disappeared after the in memory
buffer filled up for the io.Copy. This makes it so that we handle failing open correctly
in that path.

Updates tailscale/corp#9967

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-04-25 19:40:46 -07:00
shayne
018a382729 cmd/tailscale/cli: [serve] fix MinGW path conversion (#7964)
Fixes #7963

Signed-off-by: Shayne Sweeney <shayne@tailscale.com>
2023-04-25 13:07:17 -04:00
License Updater
2e07245384 licenses: update android licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2023-04-25 09:10:26 -07:00
License Updater
aa87e999dc licenses: update win/apple licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-04-25 09:10:05 -07:00
Maisem Ali
f58751eb2b net/packet: add NAT support for DCCP and GRE
Updates tailscale/corp#8020

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-04-24 15:30:50 -07:00
Marwan Sulaiman
ce11c82d51 ipn/store/awsstore: persist state with intelligent tiering
Fixes #6784

This PR makes it so that we can persist the tailscaled state with
intelligent tiering which increases the capacity from 4kb to 8kb

Signed-off-by: Marwan Sulaiman <marwan@tailscale.com>
2023-04-24 14:35:13 -04:00
Brad Fitzpatrick
90ba26cea1 net/netcheck: fix crash when IPv6 kinda but not really works
Looks like on some systems there's an IPv6 address, but then opening
a IPv6 UDP socket fails later. Probably some firewall. Tolerate it
better and don't crash.

To repro: check the "udp6" to something like "udp7" (something that'll
fail) and run "go run ./cmd/tailscale netcheck" on a machine with
active IPv6. It used to crash and now it doesn't.

Fixes #7949

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-04-22 17:53:39 -07:00
Maisem Ali
7778d708a6 ssh/tailssh: handle dialing multiple recorders and failing open
This adds support to try dialing out to multiple recorders each
with a 5s timeout and an overall 30s timeout. It also starts respecting
the actions `OnRecordingFailure` field if set, if it is not set
it fails open.

Updates tailscale/corp#9967

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-04-22 10:23:13 -07:00
Maisem Ali
f66ddb544c tailcfg: add SSHRecorderFailureAction and SSHRecordingFailureNotifyRequest
This allows control to specify how to handle situations where the recorder
isn't available.

Updates tailscale/corp#9967

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-04-22 10:23:13 -07:00
Flakes Updater
e3b2250e26 go.mod.sri: update SRI hash for go.mod changes
Signed-off-by: Flakes Updater <noreply@tailscale.com>
2023-04-21 21:36:21 -07:00
Andrew Dunham
6f521c138d tailcfg: add CanPort80 field to DERPNode
A follow-up PR will start using this field after we set it in our
production DERPMap.

Updates #7925

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: Idb41b79e6055dddb8944f79d91ad4a186ace98c7
2023-04-21 14:15:26 -04:00
Andrew Dunham
04a3118d45 net/tstun: add tests for captureHook
Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I630f852d9f16c951c721b34f2bc4128e68fe9475
2023-04-21 14:05:20 -04:00
Denton Gentry
c791e64881 scripts/installer: add Deepin, RisiOS.
Fixes https://github.com/tailscale/tailscale/issues/7862
Fixes https://github.com/tailscale/tailscale/issues/7899

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2023-04-20 18:51:50 -07:00
Mihai Parparita
7330aa593e all: avoid repeated default interface lookups
On some platforms (notably macOS and iOS) we look up the default
interface to bind outgoing connections to. This is both duplicated
work and results in logspam when the default interface is not available
(i.e. when a phone has no connectivity, we log an error and thus cause
more things that we will try to upload and fail).

Fixed by passing around a netmon.Monitor to more places, so that we can
use its cached interface state.

Fixes #7850
Updates #7621

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-04-20 15:46:01 -07:00
Will Norris
7f17e04a5a log/sockstatlog: bump logInterval to 10 seconds
We are seeing indications that some devices are still getting into an
upload loop.  Bump logInterval in case these devices are on slow
connections that are taking more than 3 seconds to uploads sockstats.

Updates #7719

Signed-off-by: Will Norris <will@tailscale.com>
2023-04-20 11:37:06 -07:00
Mihai Parparita
4722f7e322 all: move network monitoring from wgengine/monitor to net/netmon
We're using it in more and more places, and it's not really specific to
our use of Wireguard (and does more just link/interface monitoring).

Also removes the separate interface we had for it in sockstats -- it's
a small enough package (we already pull in all of its dependencies
via other paths) that it's not worth the extra complexity.

Updates #7621
Updates #7850

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-04-20 10:15:59 -07:00
Andrew Dunham
3ede3aafe4 ipn/localapi: also verify STUN queries work in 'debug derp'
Updates #6526

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I274b7ed53ee0be3fb94fdb00cafe06a1d676e1cf
2023-04-20 10:14:59 -04:00
James Tucker
f844791e15 safesocket: enable test to run on Windows unpriviliged
I manually tested that the code path that relaxes pipe permissions is
not executed when run with elevated priviliges, and the test also passes
in that case.

Updates #7876

Signed-off-by: James Tucker <jftucker@gmail.com>
2023-04-19 19:06:18 -07:00
James Tucker
cd35a79136 syncs: relax TestWatchMultipleValues timing on Windows
The test is re-enabled for Windows with a relaxed time assertion.

On Windows the runtime poller currently does not have sufficient
resolution to meet the normal requirements for this test.

See https://github.com/golang/go/issues/44343 for background.

Updates #7876

Signed-off-by: James Tucker <jftucker@gmail.com>
2023-04-19 19:00:34 -07:00
Andrew Dunham
f85dc6f97c ci: add more lints (#7909)
This is a follow-up to #7905 that adds two more linters and fixes the corresponding findings. As per the previous PR, this only flags things that are "obviously" wrong, and fixes the issues found.

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I8739bdb7bc4f75666a7385a7a26d56ec13741b7c
2023-04-19 21:54:19 -04:00
dependabot[bot]
5acc7c4b1e .github: Bump ruby/action-slack from 3.0.0 to 3.2.1
Bumps [ruby/action-slack](https://github.com/ruby/action-slack) from 3.0.0 to 3.2.1.
- [Release notes](https://github.com/ruby/action-slack/releases)
- [Commits](https://github.com/ruby/action-slack/compare/v3.0.0...v3.2.1)

---
updated-dependencies:
- dependency-name: ruby/action-slack
  dependency-type: direct:production
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <support@github.com>
2023-04-19 18:41:00 -07:00
dependabot[bot]
c328770184 .github: Bump peter-evans/create-pull-request from 4.2.4 to 5.0.0
Bumps [peter-evans/create-pull-request](https://github.com/peter-evans/create-pull-request) from 4.2.4 to 5.0.0.
- [Release notes](https://github.com/peter-evans/create-pull-request/releases)
- [Commits](38e0b6e68b...5b4a9f6a9e)

---
updated-dependencies:
- dependency-name: peter-evans/create-pull-request
  dependency-type: direct:production
  update-type: version-update:semver-major
...

Signed-off-by: dependabot[bot] <support@github.com>
2023-04-19 18:38:14 -07:00
License Updater
588a234fdc licenses: update win/apple licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-04-19 17:06:12 -07:00
Maisem Ali
c3ef6fb4ee ipn/ipnlocal: handle masquerade addresses in PeerAPI
Without this, the peer fails to do anything over the PeerAPI if it
has a masquerade address.

```
Apr 19 13:58:15 hydrogen tailscaled[6696]: peerapi: invalid request from <ip>:58334: 100.64.0.1/32 not found in self addresses
```

Updates #8020

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-04-19 15:51:44 -07:00
Maisem Ali
85de580455 net/tsdial: do not use proxies when dialing out to PeerAPI
Found this when adding a test that does a ping over PeerAPI.

Our integration tests set up a trafficTrap to ensure that tailscaled
does not call out to the internet, and it does so via a HTTP_PROXY.

When adding a test for pings over PeerAPI, it triggered the trap and investigation
lead to the realization that we were not removing the Proxy when trying to
dial out to the PeerAPI.

Updates tailscale/corp#8020

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-04-19 15:51:44 -07:00
Mihai Parparita
d0906cda97 net/sockstats: expose debug info
Exposes some internal state of the sockstats package via the C2N and
PeerAPI endpoints, so that it can be used for debugging. For now this
includes the estimated radio on percentage and a second-by-second view
of the times the radio was active.

Also fixes another off-by-one error in the radio on percentage that
was leading to >100% values (if n seconds have passed since we started
to monitor, there may be n + 1 possible seconds where the radio could
have been on).

Updates tailscale/corp#9230

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-04-19 14:33:12 -07:00
Will Norris
7c386ca6d2 net/sockstats: fix calculation of radio power usage
When splitting the radio monitor usage array, we were splitting at now %
3600 to get values into chronological order.  This caused the value for
the final second to be included at the beginning of the ordered slice
rather than the end.  If there was activity during that final second, an
extra five seconds of high power usage would get recorded in some cases.
This could result in a final calculation of greater than 100% usage.

This corrects that by splitting values at (now+1 % 3600).

This also simplifies the percentage calculation by always rounding
values down, which is sufficient for our usage.

Signed-off-by: Will Norris <will@tailscale.com>
2023-04-19 13:18:02 -07:00
License Updater
7f057d7489 licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2023-04-19 10:22:36 -07:00
Mihai Parparita
c7cea825ae net/netns: don't log errors when we can't get the default route on Darwin
It's somewhat common (e.g. when a phone has no reception), and leads to
lots of logspam.

Updates #7850

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-04-18 09:57:15 -07:00
Andrew Dunham
280255acae various: add golangci-lint, fix issues (#7905)
This adds an initial and intentionally minimal configuration for
golang-ci, fixes the issues reported, and adds a GitHub Action to check
new pull requests against this linter configuration.

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I8f38fbc315836a19a094d0d3e986758b9313f163
2023-04-17 18:38:24 -04:00
Joe Tsai
ff1b35ec6c net/connstats: exclude traffic with internal Tailscale service (#7904)
Exclude traffic with 100.100.100.100 (for IPv4) and
with fd7a:115c:a1e0::53 (for IPv6) since this traffic with the
Tailscale service running locally on the node.
This traffic never left the node.

It also happens to be a high volume amount of traffic since
DNS requests occur over UDP with each request coming from a
unique port, thus resulting in many discrete traffic flows.

Fixes tailscale/corp#10554

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2023-04-17 14:24:29 -07:00
Mihai Parparita
9a655a1d58 net/dnsfallback: more explicitly pass through logf function
Redoes the approach from #5550 and #7539 to explicitly pass in the logf
function, instead of having global state that can be overridden.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-04-17 12:06:23 -07:00
dependabot[bot]
28cb1221ba .github: Bump actions/setup-go from 3 to 4
Bumps [actions/setup-go](https://github.com/actions/setup-go) from 3 to 4.
- [Release notes](https://github.com/actions/setup-go/releases)
- [Commits](https://github.com/actions/setup-go/compare/v3...v4)

---
updated-dependencies:
- dependency-name: actions/setup-go
  dependency-type: direct:production
  update-type: version-update:semver-major
...

Signed-off-by: dependabot[bot] <support@github.com>
2023-04-17 11:51:30 -07:00
Brad Fitzpatrick
d5a870b4dc wgengine/monitor: add --monitor-duration flag to opt-in TestMonitorMode
TestMonitorMode skips by default, without the --monitor flag, and then
it previously ran forever. This adds an option --monitor-duration flag
that defaults to zero (run forever) but if non-zero bounds how long
the tests runs. This means you can then also use e.g. `go test
--cpuprofile` and capture a CPU/mem profile for a minute or two.

Updates #7621

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-04-17 11:14:40 -07:00
Brad Fitzpatrick
162488a775 net/interfaces: cache "home" router lookup on big Linux routers
This is a continuation of the earlier 2a67beaacf but more aggressive;
this now remembers that we failed to find the "home" router IP so we
don't try again later on the next call.

Updates #7621

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-04-17 10:51:21 -07:00
James Tucker
c5150eae67 net/netcheck: reenable TestNodeAddrResolve on Windows
Updates #7876

Co-authored-by: Andrew Dunham <andrew@du.nham.ca>
Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Signed-off-by: James Tucker <james@tailscale.com>
Change-Id: Idb2e6cc2edf6ca123b751d6c8f8729b0cba86023
2023-04-17 12:41:56 -04:00
Andrew Dunham
80b138f0df wgengine/magicsock: keep advertising endpoints after we stop discovering them
Previously, when updating endpoints we would immediately stop
advertising any endpoint that wasn't discovered during
determineEndpoints. This could result in, for example, a case where we
performed an incremental netcheck, didn't get any of our three STUN
packets back, and then dropped our STUN endpoint from the set of
advertised endpoints... which would result in clients falling back to a
DERP connection until the next call to determineEndpoints.

Instead, let's cache endpoints that we've discovered and continue
reporting them to clients until a timeout expires. In the above case
where we temporarily don't have a discovered STUN endpoint, we would
continue reporting the old value, then re-discover the STUN endpoint
again and continue reporting it as normal, so clients never see a
withdrawal.

Updates tailscale/coral#108

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I42de72e7418ab328a6c732bdefc74549708cf8b9
2023-04-17 11:26:02 -04:00
Brad Fitzpatrick
4b49ca4a12 wgengine/magicsock: update comments on what implements conn.Bind
The comment still said *magicsock.Conn implemented wireguard-go conn.Bind.
That wasn't accurate anymore.

A doc #cleanup.

Change-Id: I7fd003b939497889cc81147bfb937b93e4f6865c
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-04-16 09:07:13 -07:00
Brad Fitzpatrick
10f1c90f4d wgengine/magicsock, types/nettype, etc: finish ReadFromUDPAddrPort netip migration
So we're staying within the netip.Addr/AddrPort consistently and
avoiding allocs/conversions to the legacy net addr types.

Updates #5162

Change-Id: I59feba60d3de39f773e68292d759766bac98c917
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-04-15 13:40:15 -07:00
Brad Fitzpatrick
29f7df9d8f wgengine/magicsock, etc: remove mostly unused WriteTo methods
Updates #2331
Updates #5162

Change-Id: I8291884425481eeaedde38a54adfd8ed7292a497
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-04-15 08:32:11 -07:00
Brad Fitzpatrick
83c41f3697 net/netcheck: remove unused method from interface
Updates #2331
Updates #5162

Change-Id: I77ff956c2d59bde611d47523659a07afb4a6da2d
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-04-15 07:55:43 -07:00
James Tucker
20f17d6e7b wgengine/magicsock: reenable magicsock tests on Windows
These tests are passing locally and on CI. They had failed earlier in
the day when first fixing up CI, and it is not immediately clear why. I
have cycled IPv6 support locally, but this should not have a substantial
effect.

Updates #7876

Signed-off-by: James Tucker <jftucker@gmail.com>
2023-04-14 22:53:53 -07:00
James Tucker
bd0c32ca21 tsnet: disable TestLoopbackSOCKS5 on Windows
This test is not regularly passing on CI, but seems to pass reliably
locally. Needs deeper debugging.

Updates #7876

Signed-off-by: James Tucker <jftucker@gmail.com>
2023-04-14 22:28:04 -07:00
James Tucker
b7f51a1468 .github/workflows: add artifact caching and remove double build on race
Go artifact caching will help provided that the cache remains small
enough - we can reuse the strategy from the Windows build where we only
cache and pull the zips, but let go(1) do the many-file unpacking as it
does so faster.

The race matrix was building once without race, then running all the
tests with race, so change the matrix to incldue a `buildflags`
parameter and use that both in the build and test steps.

Updates #cleanup

Signed-off-by: James Tucker <james@tailscale.com>
2023-04-14 22:07:06 -07:00
Andrew Dunham
f352f8a0e6 util/set: move Slice type from corp to oss
This is an exact copy of the files misc/set/set{,_test}.go from
tailscale/corp@a5415daa9c, plus the
license headers.

For use in #7877

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I712d09c6d1a180c6633abe3acf8feb59b27e2866
2023-04-14 19:25:39 -04:00
James Tucker
8dec1a8724 .github/workflows: reenable Windows CI, disable broken tests
We accidentally switched to ./tool/go in
4022796484 which resulted in no longer
running Windows builds, as this is attempting to run a bash script.

I was unable to quickly fix the various tests that have regressed, so
instead I've added skips referencing #7876, which we need to back and
fix.

Updates #7262
Updates #7876

Signed-off-by: James Tucker <james@tailscale.com>
2023-04-14 14:13:53 -07:00
Will Norris
4ecc7fdf5f api.md: update example auth key value
example was missing the "-auth" type in the key prefix, which all new
keys now contain.  Also update key ID to match the full key, and fix
indenting of closing braces.

Signed-off-by: Will Norris <will@tailscale.com>
2023-04-14 11:35:33 -07:00
Brad Fitzpatrick
6866aaeab3 wgengine/magicsock: factor out receiveIPv4 & receiveIPv6 common code
Updates #2331

Change-Id: I801df38b217f5d17203e8dc3b8654f44747e0f4b
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-04-14 10:40:42 -07:00
Brad Fitzpatrick
c889254b42 net/art: skip tests on CI for now
To get the tree green again for other people.

Updates #7866

Change-Id: Ibdad2e1408e5f0c97e49a148bfd77aad17c2c5e5
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-04-14 10:24:38 -07:00
Andrew Dunham
228d0c6aea net/netcheck: use dnscache.Resolver when resolving DERP IPs
This also adds a bunch of tests for this function to ensure that we're
returning the proper IP(s) in all cases.

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I0d9d57170dbab5f2bf07abdf78ecd17e0e635399
2023-04-14 13:14:29 -04:00
Maisem Ali
64bbf1738e tailcfg: make SelfNodeV4MasqAddrForThisPeer a pointer
This makes `omitempty` actually work, and saves bytes in each map response.

Updates tailscale/corp#8020

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-04-13 11:28:33 -07:00
David Anderson
a5fd51ebdc net/art: disable the IPv6 100k routes benchmark.
At the current unoptimized memory utilization of the various data structures,
100k IPv6 routes consumes in the ballpark of 3-4GiB, which risks OOMing our
386 test machine.

Until we have the optimizations to (drastically) reduce that consumption,
skip the test that bloats too much for 32-bit machines.

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-04-13 09:04:17 -07:00
David Anderson
a7c910e361 net/art: implement the Table type, a multi-level art route table.
Updates #7781

                           │    sec/op     │
TableInsertion/ipv4/10       1.562µ ±   2%
TableInsertion/ipv4/100      2.398µ ±   5%
TableInsertion/ipv4/1000     2.097µ ±   3%
TableInsertion/ipv4/10000    2.756µ ±   4%
TableInsertion/ipv4/100000   2.473µ ±  13%
TableInsertion/ipv6/10       7.649µ ±   2%
TableInsertion/ipv6/100      12.09µ ±   3%
TableInsertion/ipv6/1000     14.84µ ±   5%
TableInsertion/ipv6/10000    14.72µ ±   8%
TableInsertion/ipv6/100000   13.23µ ±  41%
TableDelete/ipv4/10          378.4n ±   5%
TableDelete/ipv4/100         366.9n ±   3%
TableDelete/ipv4/1000        418.6n ±   3%
TableDelete/ipv4/10000       609.2n ±  11%
TableDelete/ipv4/100000      679.2n ±  28%
TableDelete/ipv6/10          504.2n ±   4%
TableDelete/ipv6/100         959.5n ±  12%
TableDelete/ipv6/1000        1.436µ ±   6%
TableDelete/ipv6/10000       1.772µ ±  15%
TableDelete/ipv6/100000      1.172µ ± 113%
TableGet/ipv4/10             32.14n ±  11%
TableGet/ipv4/100            38.58n ±   2%
TableGet/ipv4/1000           45.03n ±   2%
TableGet/ipv4/10000          52.90n ±   7%
TableGet/ipv4/100000         135.2n ±  11%
TableGet/ipv6/10             41.55n ±   1%
TableGet/ipv6/100            44.78n ±   2%
TableGet/ipv6/1000           49.03n ±   2%
TableGet/ipv6/10000          65.38n ±   5%
TableGet/ipv6/100000         525.0n ±  39%

                           │   avg-B/op   │
TableInsertion/ipv4/10       25.18Ki ± 0%
TableInsertion/ipv4/100      17.63Ki ± 0%
TableInsertion/ipv4/1000     14.14Ki ± 0%
TableInsertion/ipv4/10000    12.92Ki ± 0%
TableInsertion/ipv4/100000   11.13Ki ± 0%
TableInsertion/ipv6/10       76.87Ki ± 0%
TableInsertion/ipv6/100      98.33Ki ± 0%
TableInsertion/ipv6/1000     91.44Ki ± 0%
TableInsertion/ipv6/10000    90.39Ki ± 0%
TableInsertion/ipv6/100000   87.19Ki ± 0%
TableDelete/ipv4/10            3.230 ± 0%
TableDelete/ipv4/100           4.020 ± 0%
TableDelete/ipv4/1000          3.990 ± 0%
TableDelete/ipv4/10000         4.000 ± 0%
TableDelete/ipv4/100000        4.000 ± 0%
TableDelete/ipv6/10            16.00 ± 0%
TableDelete/ipv6/100           16.00 ± 0%
TableDelete/ipv6/1000          16.00 ± 0%
TableDelete/ipv6/10000         16.00 ± 0%
TableDelete/ipv6/100000        16.00 ± 0%

                           │ avg-allocs/op │
TableInsertion/ipv4/10          2.900 ± 0%
TableInsertion/ipv4/100         2.330 ± 0%
TableInsertion/ipv4/1000        2.070 ± 0%
TableInsertion/ipv4/10000       1.980 ± 0%
TableInsertion/ipv4/100000      1.840 ± 0%
TableInsertion/ipv6/10          6.800 ± 0%
TableInsertion/ipv6/100         8.420 ± 0%
TableInsertion/ipv6/1000        7.900 ± 0%
TableInsertion/ipv6/10000       7.820 ± 0%
TableInsertion/ipv6/100000      7.580 ± 0%
TableDelete/ipv4/10             1.000 ± 0%
TableDelete/ipv4/100            1.000 ± 0%
TableDelete/ipv4/1000           1.000 ± 0%
TableDelete/ipv4/10000          1.000 ± 0%
TableDelete/ipv4/100000         1.000 ± 0%
TableDelete/ipv6/10             1.000 ± 0%
TableDelete/ipv6/100            1.000 ± 0%
TableDelete/ipv6/1000           1.000 ± 0%
TableDelete/ipv6/10000          1.000 ± 0%
TableDelete/ipv6/100000         1.000 ± 0%

                           │   routes/s   │
TableInsertion/ipv4/10       640.3k ±  2%
TableInsertion/ipv4/100      417.1k ±  5%
TableInsertion/ipv4/1000     477.0k ±  3%
TableInsertion/ipv4/10000    362.8k ±  5%
TableInsertion/ipv4/100000   404.5k ± 15%
TableInsertion/ipv6/10       130.7k ±  1%
TableInsertion/ipv6/100      82.69k ±  3%
TableInsertion/ipv6/1000     67.37k ±  5%
TableInsertion/ipv6/10000    67.93k ±  9%
TableInsertion/ipv6/100000   75.63k ± 29%
TableDelete/ipv4/10          2.642M ±  6%
TableDelete/ipv4/100         2.726M ±  3%
TableDelete/ipv4/1000        2.389M ±  3%
TableDelete/ipv4/10000       1.641M ± 12%
TableDelete/ipv4/100000      1.472M ± 27%
TableDelete/ipv6/10          1.984M ±  4%
TableDelete/ipv6/100         1.042M ± 11%
TableDelete/ipv6/1000        696.5k ±  6%
TableDelete/ipv6/10000       564.4k ± 13%
TableDelete/ipv6/100000      853.6k ± 53%

                     │   addrs/s    │
TableGet/ipv4/10       31.11M ± 10%
TableGet/ipv4/100      25.92M ±  2%
TableGet/ipv4/1000     22.21M ±  2%
TableGet/ipv4/10000    18.91M ±  8%
TableGet/ipv4/100000   7.397M ± 12%
TableGet/ipv6/10       24.07M ±  1%
TableGet/ipv6/100      22.33M ±  2%
TableGet/ipv6/1000     20.40M ±  2%
TableGet/ipv6/10000    15.30M ±  5%
TableGet/ipv6/100000   1.905M ± 28%

                     │    B/op    │
TableGet/ipv4/10       4.000 ± 0%
TableGet/ipv4/100      4.000 ± 0%
TableGet/ipv4/1000     4.000 ± 0%
TableGet/ipv4/10000    4.000 ± 0%
TableGet/ipv4/100000   4.000 ± 0%
TableGet/ipv6/10       16.00 ± 0%
TableGet/ipv6/100      16.00 ± 0%
TableGet/ipv6/1000     16.00 ± 0%
TableGet/ipv6/10000    16.00 ± 0%
TableGet/ipv6/100000   16.00 ± 0%

                     │ allocs/op  │
TableGet/ipv4/10       1.000 ± 0%
TableGet/ipv4/100      1.000 ± 0%
TableGet/ipv4/1000     1.000 ± 0%
TableGet/ipv4/10000    1.000 ± 0%
TableGet/ipv4/100000   1.000 ± 0%
TableGet/ipv6/10       1.000 ± 0%
TableGet/ipv6/100      1.000 ± 0%
TableGet/ipv6/1000     1.000 ± 0%
TableGet/ipv6/10000    1.000 ± 0%
TableGet/ipv6/100000   1.000 ± 0%

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-04-13 09:04:17 -07:00
Mihai Parparita
edb02b63f8 net/sockstats: pass in logger to sockstats.WithSockStats
Using log.Printf may end up being printed out to the console, which
is not desirable. I noticed this when I was investigating some client
logs with `sockstats: trace "NetcheckClient" was overwritten by another`.
That turns to be harmless/expected (the netcheck client will fall back
to the DERP client in some cases, which does its own sockstats trace).

However, the log output could be visible to users if running the
`tailscale netcheck` CLI command, which would be needlessly confusing.

Updates tailscale/corp#9230

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-04-12 18:40:03 -07:00
Mihai Parparita
782ccb5655 .github/workflows: run one set of tests with the tailscale_go build tag
We use it to gate code that depends on custom Go toolchain, but it's
currently only passed in the corp runners. Add a set on OSS so that we
can catch regressions earlier.

To specifically test sockstats this required adding a build tag to
explicitly enable them -- they're normally on for iOS, macOS and Android
only, and we don't run tests on those platforms normally.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-04-12 16:34:26 -07:00
Will Norris
bb34589748 log/sockstatlog: limit sockstat logs to 5 MB
Updates tailscale/corp#9230

Signed-off-by: Will Norris <will@tailscale.com>
2023-04-12 15:32:01 -07:00
Brad Fitzpatrick
9e50da321b client/tailscale: dial LocalAPI at 127.0.0.1 on macOS
Updates #7851

Change-Id: Ib53cf53cdfee277ef42f7833352bc51ecb5db959
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-04-12 14:09:24 -07:00
Mihai Parparita
bdc7a61c24 tool/gocross: add ts_macext build tag for Xcode builds
It's used to control various opt-in functionality for the macOS and iOS
apps, and was lost in the migration to gocross.

Updates tailscale/tailscale#7769

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-04-11 11:27:26 -07:00
License Updater
33b006cacf licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2023-04-11 09:06:08 -07:00
License Updater
e5d272f445 licenses: update win/apple licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-04-11 09:05:56 -07:00
Flakes Updater
7c95734907 go.mod.sri: update SRI hash for go.mod changes
Signed-off-by: Flakes Updater <noreply@tailscale.com>
2023-04-11 08:54:53 -07:00
Anton Tolchanov
8546ff98fb tsweb: move varz handler(s) into separate modules
This splits Prometheus metric handlers exposed by tsweb into two
modules:
- `varz.Handler` exposes Prometheus metrics generated by our expvar
  converter;
- `promvarz.Handler` combines our expvar-converted metrics and native
  Prometheus metrics.

By default, tsweb will use the promvarz handler, however users can keep
using only the expvar converter. Specifically, `tailscaled` now uses
`varz.Handler` explicitly, which avoids a dependency on the
(heavyweight) Prometheus client.

Updates https://github.com/tailscale/corp/issues/10205

Signed-off-by: Anton Tolchanov <anton@tailscale.com>
2023-04-11 08:37:32 +01:00
Anton Tolchanov
c153e6ae2f prober: migrate to Prometheus metric library
This provides an example of using native Prometheus metrics with tsweb.

Prober library seems to be the only user of PrometheusVar, so I am
removing support for it in tsweb.

Updates https://github.com/tailscale/corp/issues/10205

Signed-off-by: Anton Tolchanov <anton@tailscale.com>
2023-04-11 08:37:32 +01:00
Anton Tolchanov
11e6247d2a tsweb: expose native Prometheus metrics in /debug/varz
The handler will expose built-in process and Go metrics by default,
which currently duplicate some of the expvar-proxied metrics
(`goroutines` vs `go_goroutines`, `memstats` vs `go_memstats`), but as
long as their names are different, Prometheus server will just scrape
both.

This will change /debug/varz behaviour for most tsweb binaries, but
notably not for control, which configures a `tsweb.VarzHandler`
[explicitly](a5b5d5167f/cmd/tailcontrol/tailcontrol.go (L779))

Updates https://github.com/tailscale/corp/issues/10205

Signed-off-by: Anton Tolchanov <anton@tailscale.com>
2023-04-11 08:37:32 +01:00
License Updater
690446c784 licenses: update android licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2023-04-10 21:29:19 -07:00
Mihai Parparita
cef0a474f8 ipn/ipnlocal: check that sockstatLogger is available in c2n endpoint
Otherwise there may be a panic if it's nil (and the control side of
the c2n call will just time out).

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-04-10 17:59:26 -07:00
Mihai Parparita
03b2c44a21 ipn/ipnlocal: more explicitly say if sockstats are not available
Makes it more apparent in the PeerAPI endpoint that the client was
not built with the appropriate toolchain or build tags.

Updates tailscale/corp#9230

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-04-10 14:59:11 -07:00
Flakes Updater
1bec2cbbd5 go.mod.sri: update SRI hash for go.mod changes
Signed-off-by: Flakes Updater <noreply@tailscale.com>
2023-04-10 10:34:42 -07:00
Jordan Whited
f571536598 go.mod: bump wireguard-go (#7836)
This pulls in a synchronization optimization, see
tailscale/wireguard-go@af17262.

Updates tailscale/corp#8734

Signed-off-by: Jordan Whited <jordan@tailscale.com>
2023-04-10 10:32:46 -07:00
James Tucker
e09c434e5d wgengine/magicsock: remove locking sync requirements on conn disco keys
The lazy initialization of the disco key is not necessary, and
contributes to unnecessary locking and state checking.

Updates #cleanup

Signed-off-by: James Tucker <james@tailscale.com>
2023-04-10 09:47:54 -07:00
James Tucker
e1b71c83ac wgengine/magicsock: remove unused fields on discoInfo
Updates #cleanup

Signed-off-by: James Tucker <james@tailscale.com>
2023-04-10 09:24:00 -07:00
James Tucker
a257b2f88b wgengine/magicsock: add immutability documentation to endpointDisco
Updates #7825

Signed-off-by: James Tucker <james@tailscale.com>
2023-04-10 09:13:44 -07:00
James Tucker
fb18af5564 wgengine/netstack: fix data-race on startup
Running tailscaled with the race detector enabled immediately fires on
this field, as it is updated after first read.

Updates #cleanup

Signed-off-by: James Tucker <james@tailscale.com>
2023-04-10 09:13:21 -07:00
Charlotte Brandhorst-Satzkorn
c573bef0aa tailcfg,wgengine: add initial support for WireGuard only peers
A peer can have IsWireGuardOnly, which means it will not support DERP or
Disco, and it must have Endpoints filled in order to be usable.

In the present implementation only the first Endpoint will be used as
the bestAddr.

Updates tailscale/corp#10351

Co-authored-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
Co-authored-by: James Tucker <james@tailscale.com>
Signed-off-by: James Tucker <james@tailscale.com>
2023-04-08 22:08:25 -07:00
James Tucker
6cfcb3cae4 wgengine/magicsock: fix synchronization of endpoint disco fields
Identified in review in #7821 endpoint.discoKey and endpoint.discoShort
are often accessed without first taking endpoint.mu. The arrangement
with endpoint.mu is inconvenient for a good number of those call-sites,
so it is instead replaced with an atomic pointer to carry both pieces of
disco info. This will also help with #7821 that wants to add explicit
checks/guards to disable disco behaviors when disco keys are missing
which is necessarily implicitly mostly covered by this change.

Updates #7821

Signed-off-by: James Tucker <james@tailscale.com>
2023-04-08 17:15:54 -07:00
Mihai Parparita
e978299bf0 net/sockstats: disable deltas for the cell radio power state metric
Updates tailscale/corp#9230

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-04-07 18:01:01 -07:00
Will Norris
22680a11ae net/sockstats: return early if no radio period length
Signed-off-by: Will Norris <will@tailscale.com>
2023-04-07 17:03:36 -07:00
Will Norris
75784e10e2 sockstats: add client metrics for radio power state
power state is very roughly approximated based on observed network
activity and AT&T's state transition timings for a typical 3G radio.

Updates tailscale/corp#9230
Updates #3363

Signed-off-by: Will Norris <will@tailscale.com>
2023-04-07 14:38:27 -07:00
Tom DNetto
6a627e5a33 net, wgengine/capture: encode NAT addresses in pcap stream
Signed-off-by: Tom DNetto <tom@tailscale.com>
2023-04-06 13:26:00 -07:00
License Updater
92459a9248 licenses: update win/apple licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-04-06 11:31:00 -07:00
License Updater
7012bf7981 licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2023-04-06 11:30:46 -07:00
License Updater
07b29f13dc licenses: update android licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2023-04-06 11:30:16 -07:00
Mihai Parparita
f49b9f75b8 util/clientmetric: allow client metric values to be provided by a function
Adds NewGaugeFunc and NewCounterFunc (inspired by expvar.Func) which
change the current value to be reported by a function. This allows
some client metric values to be computed on-demand during uploading (at
most every 15 seconds), instead of being continuously updated.

clientmetric uploading had a bunch of micro-optimizations for memory
access (#3331) which are not possible with this approach. However, any
performance hit from function-based metrics is contained to those metrics
only, and we expect to have very few.

Also adds a DisableDeltas() option for client metrics, so that absolute
values are always reported. This makes server-side processing of some
metrics easier to reason about.

Updates tailscale/corp#9230

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-04-05 17:21:16 -07:00
phirework
c0e0a5458f cmd/tailscale: show reauth etc. links even if no login name (#7803)
Signed-off-by: Jenny Zhang <jz@tailscale.com>
2023-04-05 17:00:18 -04:00
shayne
81fd00a6b7 cmd/tailscale/cli: [serve] add support for proxy paths (#7800) 2023-04-05 12:33:18 -04:00
Maisem Ali
d42d570066 ssh/tailssh: handle output matching better in tests (#7799) 2023-04-05 11:35:02 -04:00
Brad Fitzpatrick
2c0bda6e2e ssh/tailssh: make Tailscale SSH work on gokrazy
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-04-04 22:22:02 -07:00
Flakes Updater
3d29da105c go.mod.sri: update SRI hash for go.mod changes
Signed-off-by: Flakes Updater <noreply@tailscale.com>
2023-04-04 20:01:56 -07:00
Jordan Whited
765d3253f3 go.mod: bump wireguard-go (#7792)
Pull in TUN checksum optimizations and crypto channel changes.

Updates tailscale/corp#8734

Signed-off-by: Jordan Whited <jordan@tailscale.com>
2023-04-04 19:56:00 -07:00
shayne
ba4e58f429 cmd/tailscale/cli: do not allow turning Funnel on while shields-up (#7770) 2023-04-04 22:20:27 -04:00
valscale
7bfb7744b7 derp,magicsock: add debug envknobs for HTTP and derp server name (#7744)
Make developing derp easier by:

1. Creating an envknob telling clients to use HTTP to connect to derp
servers, so devs don't have to acquire a valid TLS cert.

2. Creating an envknob telling clients which derp server to connect
to, so devs don't have to edit the ACLs in the admin console to add a
custom DERP map.

3. Explaining how the -dev and -a command lines args to derper
interact.

To use this:

1. Run derper with -dev.

2. Run tailscaled with TS_DEBUG_USE_DERP_HTTP=1 and
TS_DEBUG_USE_DERP_ADDR=localhost

This will result in the client connecting to derp via HTTP on port
3340.

Fixes #7700

Signed-off-by: Val <valerie@tailscale.com>
2023-04-04 17:10:50 -07:00
Jordan Whited
f475e5550c net/neterror, wgengine/magicsock: use UDP GSO and GRO on Linux (#7791)
This commit implements UDP offloading for Linux. GSO size is passed to
and from the kernel via socket control messages. Support is probed at
runtime.

UDP GSO is dependent on checksum offload support on the egress netdev.
UDP GSO will be disabled in the event sendmmsg() returns EIO, which is
a strong signal that the egress netdev does not support checksum
offload.

Updates tailscale/corp#8734

Signed-off-by: Jordan Whited <jordan@tailscale.com>
2023-04-04 16:32:16 -07:00
David Anderson
45138fcfba go.toolchain.rev: update for go 1.20.3
Signed-off-by: David Anderson <danderson@tailscale.com>
2023-04-04 11:44:02 -07:00
James Tucker
b0ed863d55 atomicfile: use /tmp for socket path on macOS
macOS does not allow unix socket creation in private temp directories,
but global /tmp is ok, so swap out for global temp for now.

Updates #7658
Updates #7785

Signed-off-by: James Tucker <jftucker@gmail.com>
2023-04-04 09:14:37 -07:00
David Anderson
4d1b3bc26f net/art: implement the stride table building block of ART
A stride table is an 8-bit routing table implemented as an array binary
tree, with a special tree updating function (allot) that enables lightning
fast address lookups and reasonably fast insertion and deletion.

Insertion, deletion and lookup are all allocation-free.

Updates #7781

                                        │    sec/op    │
StrideTableInsertion/10/random_order       16.79n ± 2%
StrideTableInsertion/10/largest_first      16.83n ± 1%
StrideTableInsertion/10/smallest_first     16.83n ± 0%
StrideTableInsertion/50/random_order       17.84n ± 1%
StrideTableInsertion/50/largest_first      20.04n ± 1%
StrideTableInsertion/50/smallest_first     16.39n ± 0%
StrideTableInsertion/100/random_order      14.63n ± 0%
StrideTableInsertion/100/largest_first     17.45n ± 4%
StrideTableInsertion/100/smallest_first    12.98n ± 0%
StrideTableInsertion/200/random_order      12.51n ± 4%
StrideTableInsertion/200/largest_first     18.36n ± 3%
StrideTableInsertion/200/smallest_first    9.609n ± 3%
StrideTableDeletion/10/random_order        19.50n ± 1%
StrideTableDeletion/10/largest_first       19.34n ± 0%
StrideTableDeletion/10/smallest_first      19.43n ± 0%
StrideTableDeletion/50/random_order        14.58n ± 1%
StrideTableDeletion/50/largest_first       14.27n ± 2%
StrideTableDeletion/50/smallest_first      15.51n ± 0%
StrideTableDeletion/100/random_order       12.02n ± 3%
StrideTableDeletion/100/largest_first      10.64n ± 0%
StrideTableDeletion/100/smallest_first     13.21n ± 3%
StrideTableDeletion/200/random_order       14.05n ± 4%
StrideTableDeletion/200/largest_first      9.288n ± 5%
StrideTableDeletion/200/smallest_first     18.51n ± 1%
StrideTableGet                            0.5010n ± 0%

                                        │  routes/s   │
StrideTableInsertion/10/random_order      59.55M ± 2%
StrideTableInsertion/10/largest_first     59.42M ± 1%
StrideTableInsertion/10/smallest_first    59.43M ± 0%
StrideTableInsertion/50/random_order      56.04M ± 1%
StrideTableInsertion/50/largest_first     49.91M ± 1%
StrideTableInsertion/50/smallest_first    61.00M ± 0%
StrideTableInsertion/100/random_order     68.35M ± 0%
StrideTableInsertion/100/largest_first    57.32M ± 3%
StrideTableInsertion/100/smallest_first   77.06M ± 0%
StrideTableInsertion/200/random_order     79.93M ± 4%
StrideTableInsertion/200/largest_first    54.47M ± 3%
StrideTableInsertion/200/smallest_first   104.1M ± 3%
StrideTableDeletion/10/random_order       51.28M ± 1%
StrideTableDeletion/10/largest_first      51.70M ± 0%
StrideTableDeletion/10/smallest_first     51.48M ± 0%
StrideTableDeletion/50/random_order       68.60M ± 1%
StrideTableDeletion/50/largest_first      70.09M ± 2%
StrideTableDeletion/50/smallest_first     64.45M ± 0%
StrideTableDeletion/100/random_order      83.21M ± 3%
StrideTableDeletion/100/largest_first     94.03M ± 0%
StrideTableDeletion/100/smallest_first    75.69M ± 3%
StrideTableDeletion/200/random_order      71.20M ± 5%
StrideTableDeletion/200/largest_first     107.7M ± 5%
StrideTableDeletion/200/smallest_first    54.02M ± 1%
StrideTableGet                            1.996G ± 0%

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-04-04 09:00:24 -07:00
Will Norris
6d5c3c1637 ipn: prefer allow/denylist terminology
Signed-off-by: Will Norris <will@tailscale.com>
2023-04-04 08:02:50 -07:00
Will Norris
5a3da3cd7f ipn: add sockstat logger to stable builds
This makes the sockstat logger available on all builds, but only enables
it by default for unstable.  For stable builds, the logger must be
explicitly enabled via C2N component logger.

Updates tailscale/corp#9230
Updates #3363

Signed-off-by: Will Norris <will@tailscale.com>
2023-04-03 14:44:12 -07:00
Aaron Klotz
90fd04cbde ipn/ipnlocal, util/winutil/policy: modify Windows profile migration to load legacy prefs from within tailscaled
I realized that a lot of the problems that we're seeing around migration and
LocalBackend state can be avoided if we drive Windows pref migration entirely
from within tailscaled. By doing it this way, tailscaled can automatically
perform the migration as soon as the connection with the client frontend is
established.

Since tailscaled is already running as LocalSystem, it already has access to
the user's local AppData directory. The profile manager already knows which
user is connected, so we simply need to resolve the user's prefs file and read
it from there.

Of course, to properly migrate this information we need to also check system
policies. I moved a bunch of policy resolution code out of the GUI and into
a new package in util/winutil/policy.

Updates #7626

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2023-04-03 14:41:46 -07:00
Mihai Parparita
e3cb8cc88d ipn/ipnlocal: automatically upload sockstats logs when the period ends
Avoids needing a separate c2n call to get the logs uploaded.

Updates tailscale/corp#9230

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-04-03 14:31:15 -07:00
Andrew Dunham
8d3acc9235 util/sysresources, magicsock: scale DERP buffer based on system memory
This adds the util/sysresources package, which currently only contains a
function to return the total memory size of the current system.

Then, we modify magicsock to scale the number of buffered DERP messages
based on the system's available memory, ensuring that we never use a
value lower than the previous constant of 32.

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: Ib763c877de4d0d4ee88869078e7d512f6a3a148d
2023-04-03 17:14:14 -04:00
Tom DNetto
483109b8fc client/tailscale: Fix NPE caused by erroneous close in error case
Fixes https://github.com/tailscale/tailscale/issues/7572

When handling an error during `StreamDebugCapture`, the response body
is closed, even though the response struct is always nil. Thanks
to https://github.com/darkrain42 for debugging this!!

Signed-off-by: Tom DNetto <tom@tailscale.com>
2023-04-03 11:47:27 -07:00
shayne
59879e5770 cmd/tailscale/cli: make serve and funnel visible in list (#7737) 2023-04-03 10:09:04 -04:00
Flakes Updater
1bf65e4760 go.mod.sri: update SRI hash for go.mod changes
Signed-off-by: Flakes Updater <noreply@tailscale.com>
2023-04-02 21:41:41 -07:00
Mihai Parparita
38bbb30aaf .github/workflows: remove tsconnect-pkg-publish.yml
Moved to the corp repo with tailscale/corp#7990

Updates tailscale/corp#10165

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-03-31 14:43:59 -07:00
James Tucker
f4da995940 atomicfile: reject overwriting irregular files
The intent of atomicfile is to overwrite regular files. Most use cases
that would overwrite irregular files, unix sockets, named pipes,
devices, and so on are more than likely misuse, so disallow them.

Fixes #7658

Signed-off-by: James Tucker <james@tailscale.com>
2023-03-31 13:29:52 -07:00
Mihai Parparita
02582083d5 cmd/tsconnect: allow root directory to be passed in
#7339 changed the root directory logic to find the ancestor of the cwd
with a go.mod file. This works when running the the binary from this
repo directly, but breaks when we're a dependency in another repo.

Allow the directory to be passed in via a -rootdir flag (the repo that
depends on it can then use `go list -m -f '{{.Dir}}' tailscale.com`
or similar to pass in the value).

Updates tailscale/corp#10165

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-03-30 16:23:55 -07:00
James Tucker
40fa2a420c envknob,net/tstun,wgengine: use TS_DEBUG_MTU consistently
Noted on #5915 TS_DEBUG_MTU was not used consistently everywhere.
Extract the default into a function that can apply this centrally and
use it everywhere.

Added envknob.Lookup{Int,Uint}Sized to make it easier to keep CodeQL
happy when using converted values.

Updates #5915

Signed-off-by: James Tucker <james@tailscale.com>
2023-03-30 14:26:10 -07:00
Andrew Dunham
8ed4fd1dbc envknob/logknob: add package for configurable logging
A LogKnob allows enabling logs with an envknob, netmap capability, and
manually, and calling a logging function when logs are enabled.

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: Id66c608d4e488bfd4eaa5e867a8d9289686748be
2023-03-30 11:16:26 -04:00
Andrew Dunham
3b39ca9017 ipn/ipnlocal: update comment in SetComponentDebugLogging
Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I8c36a62079dce77fc81b9cdfb5fe723b007218ba
2023-03-30 10:13:21 -04:00
Maisem Ali
e0d291ab8a ipn/store: add support for stores to hook into a custom dialer
For stores like k8s secrets we need to dial out to the k8s API as though Tailscale
wasn't running. The issue currently only manifests when you try to use an exit node
while running inside a k8s cluster and are trying to use Kubernetes secrets as the
backing store.

This doesn't address cmd/containerboot, which I'll do in a follow up.

Updates #7695

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-29 16:35:46 -07:00
License Updater
2b00d6922f licenses: update win/apple licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-03-29 16:12:48 -07:00
License Updater
7b4e85aa78 licenses: update win/apple licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-03-29 15:16:11 -07:00
Will Norris
e99c7c3ee5 sockstats: add labels for netlog and sockstatlog packages
Signed-off-by: Will Norris <will@tailscale.com>
2023-03-29 14:53:07 -07:00
Andrew Dunham
38e4d303a2 net/tshttpproxy: don't proxy through ourselves
When running a SOCKS or HTTP proxy, configure the tshttpproxy package to
drop those addresses from any HTTP_PROXY or HTTPS_PROXY environment
variables.

Fixes #7407

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I6cd7cad7a609c639780484bad521c7514841764b
2023-03-29 17:09:45 -04:00
Will Norris
62a1e9a44f log/sockstatlog: add delay before writing logs to disk
Split apart polling of sockstats and logging them to disk.  Add a 3
second delay before writing logs to disk to prevent an infinite upload
loop when uploading stats to logcatcher.

Fixes #7719

Signed-off-by: Will Norris <will@tailscale.com>
2023-03-29 13:10:42 -07:00
Maisem Ali
985535aebc net/tstun,wgengine/*: add support for NAT to routes
This adds support to make exit nodes and subnet routers work
when in scenarios where NAT is required.

It also updates the NATConfig to be generated from a `wgcfg.Config` as
that handles merging prefs with the netmap, so it has the required information
about whether an exit node is already configured and whether routes are accepted.

Updates tailscale/corp#8020

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-29 12:30:18 -07:00
Maisem Ali
d1d5d52b2c net/tstun/table: add initial RoutingTable implementation
It is based on `*tempfork/device.AllowedIPs`.

Updates tailscale/corp#8020

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-29 12:30:18 -07:00
Maisem Ali
2522b0615f tempfork/device: add a temp fork of golang.zx2c4.com/wireguard/device
This will allow us to reuse the AllowedIPs for NAT decisions in a follow on commit.

The files `allowedips_*.go` are as-is, `peer.go` only keeps the `Peer` declaration with a
single element required for AllowedIPs.

Upstream commit https://git.zx2c4.com/wireguard-go/commit/?id=052af4a8072bbbd3bfe7edf46fe3c1b350f71f08

Updates tailscale/corp#8020

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-29 09:53:09 -07:00
Andrew Dunham
c98652c333 doctor/permissions: add new check to print process permissions
Since users can run tailscaled in a variety of ways (root, non-root,
non-root with process capabilities on Linux), this check will print the
current process permissions to the log to aid in debugging.

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: Ida93a206123f98271a0c664775d0baba98b330c7
2023-03-29 11:50:23 -04:00
License Updater
524f53de89 licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2023-03-28 20:34:14 -07:00
James Tucker
8c2b755b2e tool/gocross: use grep -E over egrep to avoid warning
Recent egrep builds produce a warning:

```
egrep: warning: egrep is obsolescent; using grep -E
```

Updates #cleanup

Signed-off-by: James Tucker <james@tailscale.com>
2023-03-28 20:07:11 -07:00
James Tucker
a31e43f760 go.mod: bump gvisor to 20230320 for dispatcher locking
Upstream improved code around an issue showing up in CI, where sometimes
shutdown will race on endpoint.dispatcher being nil'd, causing a panic
down stack of injectInbound. The upstream patch makes some usage more
safe, but it does not itself fix the local issue.

See panic in https://github.com/tailscale/tailscale/actions/runs/4548299564/jobs/8019187385#step:7:843

See fix in google/gvisor@13d7bf69d8

Updates #7715

Signed-off-by: James Tucker <james@tailscale.com>
2023-03-28 20:06:54 -07:00
James Tucker
c628132b34 wgengine/netstack: do not send packets to netstack after close
Use the local context on Impl to check for shut down state in order to
drop rather than inject packets after close has begun.

Netstack sets endpoint.dispatcher to nil during shutdown. After the
recent adjustment in 920ec69241 we now
wait for netstack to fully shutdown before we release tests. This means
that we may continue to accept packets and attempt to inject them, which
we must prevent in order to avoid nil pointer panic.

References google/gvisor#8765
Fixes #7715

Signed-off-by: James Tucker <james@tailscale.com>
2023-03-28 19:55:45 -07:00
Maisem Ali
e04acabfde ssh/tailssh: fix race in errors returned when starting recorder
There were two code paths that could fail depending on how fast
the recorder responses. This fixes that by returning the correct
error from both paths.

Fixes #7707

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-28 19:15:46 -07:00
Flakes Updater
cb960d6cdd go.mod.sri: update SRI hash for go.mod changes
Signed-off-by: Flakes Updater <noreply@tailscale.com>
2023-03-28 15:39:08 -07:00
Jordan Whited
27e37cf9b3 go.mod, net/tstun, wgengine/magicsock: update wireguard-go (#7712)
This commit updates the wireguard-go dependency to pull in fixes for
the tun package, specifically 052af4a and aad7fca.

Signed-off-by: Jordan Whited <jordan@tailscale.com>
2023-03-28 15:37:11 -07:00
License Updater
946451b43e licenses: update win/apple licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-03-28 09:06:37 -07:00
License Updater
840d69e1eb licenses: update win/apple licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-03-28 08:48:55 -07:00
Josh Bleecher Snyder
3ba9f8dd04 util/codegen: add -copyright to control presence of copyright headers
Fixes #7702

Signed-off-by: Josh Bleecher Snyder <josharian@gmail.com>
2023-03-27 16:33:34 -07:00
Will Norris
7c99210e68 log: allow toggling sockstat logs via c2n component logging
Signed-off-by: Will Norris <will@tailscale.com>
2023-03-27 15:44:47 -07:00
Maisem Ali
920ec69241 tsnet,wgenegine/netstack: add test and fix resource leaks
We were not closing the http.Server and were also not waiting for
netstack to fully close.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-27 12:13:12 -07:00
Anton Tolchanov
2a933c1903 cmd/tailscale: extend hostname validation (#7678)
In addition to checking the total hostname length, validate characters used in each DNS label and label length.

Updates https://github.com/tailscale/corp/issues/10012

Signed-off-by: Anton Tolchanov <anton@tailscale.com>
2023-03-27 18:21:58 +01:00
shayne
43f7ec48ca funnel: change references from alpha to beta (#7613)
Updates CLI and docs to reference Funnel as beta

Signed-off-by: Shayne Sweeney <shayne@tailscale.com>
2023-03-27 10:12:32 -04:00
shayne
3177ccabe5 ipn/ipnlocal: [serve/funnel] use actual SrcAddr as X-Forwarded-For (#7600)
The reverse proxy was sending the ingressd IPv6 down as the
X-Forwarded-For. This update uses the actual remote addr.

Updates tailscale/corp#9914

Signed-off-by: Shayne Sweeney <shayne@tailscale.com>
2023-03-27 10:12:04 -04:00
shayne
7908b6d616 ipn/ipnlocal: [serve] Trim mountPoint prefix from proxy path (#7334)
This change trims the mountPoint from the request URL path before
sending the request to the reverse proxy.

Today if you mount a proxy at `/foo` and request to
`/foo/bar/baz`, we leak the `mountPoint` `/foo` as part of the request
URL's path.

This fix makes removed the `mountPoint` prefix from the path so
proxied services receive requests as if they were running at the root
(`/`) path.

This could be an issue if the app generates URLs (in HTML or otherwise)
and assumes `/path`. In this case, those URLs will 404.

With that, I still think we should trim by default and not leak the
`mountPoint` (specific to Tailscale) into whatever app is hosted.
If it causes an issue with URL generation, I'd suggest looking at configuring
an app-specific path prefix or running Caddy as a more advanced
solution.

Fixes: #6571

Signed-off-by: Shayne Sweeney <shayne@tailscale.com>
2023-03-27 10:11:46 -04:00
Denton Gentry
ed10a1769b scripts/installer.sh: check Photon OS version with pkg server.
Photon OS support crossed streams with using pkgserve to check
for supported versions 6f9aed1656.
Make Photon OS also rely on pkgserve.

Updates https://github.com/tailscale/tailscale/issues/7651
Updates https://github.com/tailscale/corp/issues/8952

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2023-03-25 18:08:20 -07:00
Maisem Ali
5ba57e4661 ssh/tailssh: add tests for recording failure
Updates tailscale/corp#9967

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-25 11:15:42 -07:00
Denton Gentry
d5abdd915e scripts/installer: add VMWare PhotonOS.
Fixes https://github.com/tailscale/tailscale/issues/7651

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2023-03-25 04:53:40 -07:00
valscale
74eb99aed1 derp, derphttp, magicsock: send new unknown peer frame when destination is unknown (#7552)
* wgengine/magicsock: add envknob to send CallMeMaybe to non-existent peer

For testing older client version responses to the PeerGone packet format change.

Updates #4326

Signed-off-by: Val <valerie@tailscale.com>

* derp: remove dead sclient struct member replaceLimiter

Leftover from an previous solution to the duplicate client problem.

Updates #2751

Signed-off-by: Val <valerie@tailscale.com>

* derp, derp/derphttp, wgengine/magicsock: add new PeerGone message type Not Here

Extend the PeerGone message type by adding a reason byte. Send a
PeerGone "Not Here" message when an endpoint sends a disco message to
a peer that this server has no record of.

Fixes #4326

Signed-off-by: Val <valerie@tailscale.com>

---------

Signed-off-by: Val <valerie@tailscale.com>
2023-03-24 19:11:48 -07:00
Maisem Ali
09d0b632d4 ssh/tailssh: add session recording test for non-pty sessions
Updates tailscale/corp#9967

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-24 16:27:11 -07:00
Maisem Ali
d39a5e4417 tsnet: support TS_AUTH_KEY variant too
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-24 13:24:10 -07:00
Maisem Ali
d2fd101eb4 net/tstun: only log natConfig on changes
Updates tailscale/corp#8020

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-24 13:23:49 -07:00
Maisem Ali
8ac5976897 logpolicy: do not upload logs in tests
Fixes tailscale/corp#10030

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-24 13:13:36 -07:00
Maisem Ali
7300b908fb logpolicy: split out DialContext into a func
Updates tailscale/corp#10030

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-24 13:13:36 -07:00
Maisem Ali
ca19cf13e9 log/sockstatlog: add resource cleanup test
Updates tailscale/corp#10030

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-24 13:13:36 -07:00
Andrew Dunham
33b359642e net/dns: don't send on closed channel in resolvedManager
Fixes #7686

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: Ibffb05539ab876b12407d77dcf2201d467895981
2023-03-24 15:34:54 -04:00
Anton Tolchanov
6f9aed1656 scripts: use pkg server to determine supported deb/rpm distros
Fixes https://github.com/tailscale/corp/issues/8952

Signed-off-by: Anton Tolchanov <anton@tailscale.com>
2023-03-24 17:36:43 +00:00
Andrew Dunham
4cb1bfee44 net/netcheck: improve determinism in hairpinning test
If multiple Go channels have a value (or are closed), receiving from
them all in a select will nondeterministically return one of the two
arms. In this case, it's possible that the hairpin check timer will have
expired between when we start checking and before we check at all, but
the hairpin packet has already been received. In such cases, we'd
nondeterministically set report.HairPinning.

Instead, check if we have a value in our results channel first, then
select on the value and timeout channel after. Also, add a test that
catches this particular failure.

Fixes #1795

Change-Id: I842ab0bd38d66fabc6cabf2c2c1bb9bd32febf35
Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
2023-03-24 12:01:23 -04:00
Maisem Ali
4a89642f7f log/sockstatlog: make shutdown close idle connections
Updates tailscale/corp#10030

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-23 19:15:30 -07:00
Maisem Ali
9e81db50f6 ipn/ipnlocal: use atomicfile.WriteFile in certFileStore
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-23 17:35:44 -07:00
Maisem Ali
8a11f76a0d ipn/ipnlocal: fix cert storage in Kubernetes
We were checking against the wrong directory, instead if we
have a custom store configured just use that.

Fixes #7588
Fixes #7665

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-23 17:35:44 -07:00
Maisem Ali
ec90522a53 ipn/ipnlocal: also store ACME keys in the certStore
We were not storing the ACME keys in the state store, they would always
be stored on disk.

Updates #7588

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-23 17:35:44 -07:00
Maisem Ali
0e203e414f net/packet: add checksum update tests
Updates tailscale/corp#8020

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-23 16:54:12 -07:00
Maisem Ali
0bf8c8e710 net/tstun: use p.Buffer() in more places
Updates tailscale/corp#8020

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-23 16:54:12 -07:00
Maisem Ali
f6ea6863de tstest/integration: add ping test w/ masquerades
Updates tailscale/corp#8020

Co-authored-by: Melanie Warrick <warrick@tailscale.com>
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-23 16:54:12 -07:00
Maisem Ali
bb31fd7d1c net/tstun: add inital support for NAT v4
This adds support in tstun to utitilize the SelfNodeV4MasqAddrForThisPeer and
perform the necessary modifications to the packet as it passes through tstun.

Currently this only handles ICMP, UDP and TCP traffic.
Subnet routers and Exit Nodes are also unsupported.

Updates tailscale/corp#8020

Co-authored-by: Melanie Warrick <warrick@tailscale.com>
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-23 16:54:12 -07:00
Maisem Ali
535fad16f8 net/tstun: rename filterIn/filterOut methods to be more descriptive
Updates tailscale/corp#8020

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-23 16:54:12 -07:00
Maisem Ali
f61b306133 tailcfg: add Node.SelfNodeV4MasqAddrForThisPeer
This only adds the field, to be used in a future commit.

Updates tailscale/corp#8020

Co-authored-by: Melanie Warrick <warrick@tailscale.com>
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-23 16:54:12 -07:00
Maisem Ali
583e86b7df ssh/tailssh: handle session recording when running in userspace mode
Previously it would dial out using the http.DefaultClient, however that doesn't work
when tailscaled is running in userspace mode (e.g. when testing).

Updates tailscale/corp#9967

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-23 16:51:10 -07:00
Maisem Ali
df89b7de10 cmd/k8s-operator: disable HTTP/2 for the auth proxy
Kubernetes uses SPDY/3.1 which is incompatible with HTTP/2, disable it
in the transport and server.

Fixes #7645
Fixes #7646

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-23 16:46:41 -07:00
Maisem Ali
8a246487c2 ssh/tailssh: enable recording of non-pty sessions
Updates tailscale/corp#9967

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-23 13:25:43 -07:00
Maisem Ali
8765568373 ssh/tailssh: add docs to CastHeader fields
Updates tailscale/corp#9967

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-23 13:25:43 -07:00
Maisem Ali
9d8b7a7383 ipn/store/kubestore: handle "/" in ipn.StateKeys
Kubernetes doesn't allow slashes as keys in secrets, replace them with "__".

This shows up in the kubernetes-operator now that tsnet sets resets the ServeConfig
at startup.

Fixes #7662

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-23 12:33:47 -07:00
Will Norris
57a008a1e1 all: pass log IDs as the proper type rather than strings
This change focuses on the backend log ID, which is the mostly commonly
used in the client.  Tests which don't seem to make use of the log ID
just use the zero value.

Signed-off-by: Will Norris <will@tailscale.com>
2023-03-23 11:26:55 -07:00
Andrew Dunham
13377e6458 ssh/tailssh: always assert our final uid/gid
Move the assertions about our post-privilege-drop UID/GID out of the
conditional if statement and always run them; I haven't been able to
find a case where this would fail. Defensively add an envknob to disable
this feature, however, which we can remove after the 1.40 release.

Updates #7616

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: Iaec3dba9248131920204bd6c6d34bbc57a148185
2023-03-23 14:26:36 -04:00
Andrew Dunham
9de8287d47 ssh/tailssh: lock OS thread during incubator
This makes it less likely that we trip over bugs like golang/go#1435.

Updates #7616

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: Ic28c03c3ad8ed5274a795c766b767fa876029f0e
2023-03-23 14:09:57 -04:00
Maisem Ali
c350cd1f06 ssh/tailssh: use background context for uploading recordings
Otherwise we see errors like
```
ssh-session(sess-20230322T005655-5562985593): recording: error sending recording to <addr>:80: Post "http://<addr>:80/record": context canceled
```

The ss.ctx is closed when the session closes, but we don't want to break the upload at that time. Instead we want to wait for the session to
close the writer when it finishes, which it is already doing.

Updates tailscale/corp#9967

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-23 10:46:09 -07:00
Will Norris
f13b8bf0cf log: use logtail to log and upload sockstat logs
Switch to using logtail for logging sockstat logs. Always log locally
(on supported platforms), but disable automatic uploading.  Change
existing c2n sockstats request to trigger upload to log server and
return log ID.

Signed-off-by: Will Norris <will@tailscale.com>
2023-03-23 09:39:41 -07:00
Mihai Parparita
731688e5cc ipn/localapi: add endpoint for adding debug log entries
Allows the iOS and macOS apps to include their frontend logs when
generating bug reports (tailscale/corp#9982).

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-03-22 11:10:06 -07:00
Anton Tolchanov
7083246409 prober: only record latency for successful probes
This will make it easier to track probe latency on a dashboard.

Updates https://github.com/tailscale/corp/issues/9916

Signed-off-by: Anton Tolchanov <anton@tailscale.com>
2023-03-22 09:24:20 +00:00
Maisem Ali
d92047cc30 ssh/tailssh: allow recorders to be configured on the first or final action
Currently we only send down recorders in first action, allow the final action
to replace them but not to drop them.

Updates tailscale/corp#9967

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-21 16:38:39 -07:00
Maisem Ali
7a97e64ef0 ssh/tailssh: add more metadata to recording header
Updates tailscale/corp#9967

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-21 16:35:59 -07:00
Denton Gentry
cc3806056f scripts/installer.sh: Add Ubuntu Lunar Lobster 23.04.
pkgs.tailscale.com added support in January, need to
add it to the installer script.

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2023-03-21 15:17:38 -07:00
Maisem Ali
916aa782af ssh/tailssh: stream SSH recordings to configured recorders
Updates tailscale/corp#9967

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-21 15:06:30 -07:00
Tom DNetto
60cd4ac08d cmd/tailscale/cli: move tskey-wrap functionality under lock sign
Signed-off-by: Tom DNetto <tom@tailscale.com>
2023-03-21 14:01:25 -07:00
Charlotte Brandhorst-Satzkorn
1b78dc1f33 tailcfg: move recorders field from SSHRule to SSHAction
Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2023-03-21 13:11:19 -07:00
Charlotte Brandhorst-Satzkorn
3efd83555f tailcfg: add recorders field to SSHRule struct
This change introduces the Recorders field to the SSHRule struct. The
field is used to store and define addresses where the ssh recorder is
located.

Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2023-03-21 12:38:23 -07:00
Sam Linville
812025a39c words: what?! a llama?! he's supposed to be dead! (#7623)
pull the lever, kronk

Signed-off-by: Sam Linville <samlinville@protonmail.com>
2023-03-21 13:03:20 -04:00
Andrew Dunham
39b289578e ssh/tailssh: make uid an int instead of uint64
Follow-up to #7615

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: Ib4256bff276f6d5cf95838d8e39c87b3643bde37
2023-03-21 12:45:07 -04:00
David Anderson
c9a4dbe383 tool/gocross: correctly embed the git commit into gocross
Previously, the build ended up embedding an empty string, which made
the shell wrapper rebuild gocross on every invocation. This is still
reasonably fast, but fixing the bypass shaves 80% off gocross's overhead
when no rebuild is needed.

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-03-20 22:35:44 -07:00
Brad Fitzpatrick
f11c270c6b go.toolchain.rev: bump Go toolchain
For tailscale/go#60

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-03-20 21:53:13 -07:00
Mihai Parparita
d2dec13392 net/sockstats: export cellular-only clientmetrics
Followup to #7518 to also export client metrics when the active interface
is cellular.

Updates tailscale/corp#9230
Updates #3363

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-03-20 17:02:39 -07:00
David Anderson
e7a78bc28f tool/gocross: support running from outside the repo dir
A bunch of us invoke tool/go from outside the repo that hosts gocross,
as a way of accessing our version-controlled toolchain. This removes
assumptions from gocross that it's being invoked within the repository
that contains its source code and toolchain configuration.

Fixes tailscale/corp#9627

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-03-20 15:01:58 -07:00
David Anderson
df02bb013a tool/gocross: fail if the toolchain revision isn't findable
This used to make sense, but after a refactor somewhere along the line
this results in trying to download from a malformed URL and generally
confusing failures.

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-03-20 15:01:58 -07:00
Denton Gentry
ebc630c6c0 net/interfaces: also allow link-local for AzureAppServices.
In May 2021, Azure App Services used 172.16.x.x addresses:
```
10: eth0@if11: <BROADCAST,MULTICAST,UP,LOWER_UP,M-DOWN> mtu 1500 qdisc noqueue state UP
    link/ether 02:42:ac:10:01:03 brd ff:ff:ff:ff:ff:ff
    inet 172.16.1.3/24 brd 172.16.1.255 scope global eth0
       valid_lft forever preferred_lft forever
```

Now it uses link-local:
```
2: eth0@if6: <BROADCAST,MULTICAST,UP,LOWER_UP,M-DOWN> mtu 1500 qdisc noqueue state UP
    link/ether 8a:30:1f:50:1d:23 brd ff:ff:ff:ff:ff:ff
    inet 169.254.129.3/24 brd 169.254.129.255 scope global eth0
       valid_lft forever preferred_lft forever
```

This is reasonable for them to choose to do, it just broke the handling in net/interfaces.

This PR proposes to:
1. Always allow link-local in LocalAddresses() if we have no better
   address available.
2. Continue to make isUsableV4() conditional on an environment we know
   requires it.

I don't love the idea of having to discover these environments one by
one, but I don't understand the consequences of making isUsableV4()
return true unconditionally. It makes isUsableV4() essentially always
return true and perform no function.

Fixes https://github.com/tailscale/tailscale/issues/7603

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2023-03-20 13:40:38 -07:00
Andrew Dunham
ccace1f7df ssh/tailssh: fix privilege dropping on FreeBSD; add tests
On FreeBSD and Darwin, changing a process's supplementary groups with
setgroups(2) will also change the egid of the process, setting it to the
first entry in the provided list. This is distinct from the behaviour on
other platforms (and possibly a violation of the POSIX standard).

Because of this, on FreeBSD with no TTY, our incubator code would
previously not change the process's gid, because it would read the
newly-changed egid, compare it against the expected egid, and since they
matched, not change the gid. Because we didn't use the 'login' program
on FreeBSD without a TTY, this would propagate to a child process.

This could be observed by running "id -p" in two contexts. The expected
output, and the output returned when running from a SSH shell, is:

    andrew@freebsd:~ $ id -p
    uid         andrew
    groups      andrew

However, when run via "ssh andrew@freebsd id -p", the output would be:

    $ ssh andrew@freebsd id -p
    login       root
    uid         andrew
    rgid        wheel
    groups      andrew

(this could also be observed via "id -g -r" to print just the gid)

We fix this by pulling the details of privilege dropping out into their
own function and prepending the expected gid to the start of the list on
Darwin and FreeBSD.

Finally, we add some tests that run a child process, drop privileges,
and assert that the final UID/GID/additional groups are what we expect.

More information can be found in the following article:
    https://www.usenix.org/system/files/login/articles/325-tsafrir.pdf

Updates #7616
Alternative to #7609

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I0e6513c31b121108b50fe561c89e5816d84a45b9
2023-03-20 16:09:18 -04:00
Mihai Parparita
e1fb687104 cmd/tailscale/cli: fix inconsistency between serve text and example command
Use the same local port number in both, and be more precise about what
is being forwarded

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-03-20 11:52:46 -07:00
Anton Tolchanov
654b5a0616 derp: add optional debug logging for prober clients
This allows tracking packet flow via logs for prober clients. Note that
the new sclient.debug() function is called on every received packet, but
will do nothing for most clients.

I have adjusted sclient logging to print public keys in short format
rather than full. This takes effect even for existing non-debug logging
(mostly client disconnect messages).

Example logs for a packet being sent from client [SbsJn] (connected to
derper [dM2E3]) to client [10WOo] (connected to derper [AVxvv]):

```
derper [dM2E3]:
derp client 10.0.0.1:35470[SbsJn]: register single client mesh("10.0.1.1"): 4 peers
derp client 10.0.0.1:35470[SbsJn]: read frame type 4 len 40 err <nil>
derp client 10.0.0.1:35470[SbsJn]: SendPacket for [10WOo], forwarding via <derphttp_client.Client [AVxvv] url=https://10.0.1.1/derp>: <nil>
derp client 10.0.0.1:35470[SbsJn]: read frame type 0 len 0 err EOF
derp client 10.0.0.1:35470[SbsJn]: read EOF
derp client 10.0.0.1:35470[SbsJn]: sender failed: context canceled
derp client 10.0.0.1:35470[SbsJn]: removing connection

derper [AVxvv]:
derp client 10.0.1.1:50650[10WOo]: register single client
derp client 10.0.1.1:50650[10WOo]: received forwarded packet from [SbsJn] via [dM2E3]
derp client 10.0.1.1:50650[10WOo]: sendPkt attempt 0 enqueued
derp client 10.0.1.1:50650[10WOo]: sendPacket from [SbsJn]: <nil>
derp client 10.0.1.1:50650[10WOo]: read frame type 0 len 0 err EOF
derp client 10.0.1.1:50650[10WOo]: read EOF
derp client 10.0.1.1:50650[10WOo]: sender failed: context canceled
derp client 10.0.1.1:50650[10WOo]: removing connection
```

Signed-off-by: Anton Tolchanov <anton@tailscale.com>
2023-03-20 17:41:37 +00:00
Anton Tolchanov
50d211d1a4 cmd/derpprobe: allow running all probes at the same time
This allows disabling spread mode, which is helpful if you are manually
running derpprobe in `--once` mode against a small number of DERP
machines.

Updates https://github.com/tailscale/corp/issues/9916

Signed-off-by: Anton Tolchanov <anton@tailscale.com>
2023-03-20 17:41:37 +00:00
Anton Tolchanov
e59dc29a55 prober: log client pubkeys on derp mesh probe failures
Updates https://github.com/tailscale/corp/issues/9916

Signed-off-by: Anton Tolchanov <anton@tailscale.com>
2023-03-20 17:41:37 +00:00
dependabot[bot]
60a028a4f6 .github: Bump peter-evans/create-pull-request from 4.1.4 to 4.2.4
Bumps [peter-evans/create-pull-request](https://github.com/peter-evans/create-pull-request) from 4.1.4 to 4.2.4.
- [Release notes](https://github.com/peter-evans/create-pull-request/releases)
- [Commits](ad43dccb4d...38e0b6e68b)

---
updated-dependencies:
- dependency-name: peter-evans/create-pull-request
  dependency-type: direct:production
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <support@github.com>
2023-03-20 15:27:06 +00:00
dependabot[bot]
927e2e3e7c .github: Bump actions/setup-go from 3 to 4
Bumps [actions/setup-go](https://github.com/actions/setup-go) from 3 to 4.
- [Release notes](https://github.com/actions/setup-go/releases)
- [Commits](https://github.com/actions/setup-go/compare/v3...v4)

---
updated-dependencies:
- dependency-name: actions/setup-go
  dependency-type: direct:production
  update-type: version-update:semver-major
...

Signed-off-by: dependabot[bot] <support@github.com>
2023-03-20 15:22:20 +00:00
Nahum Shalman
82e067e0ff build_dist.sh: make cross-compilation friendly
Signed-off-by: Nahum Shalman <nahamu@gmail.com>
2023-03-16 22:01:05 -07:00
Maisem Ali
95494a155e .github: use unique names for jobs
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-16 10:05:27 -07:00
James 'zofrex' Sanderson
9534783758 tailscale/cmd: Warn for up --force-reauth over SSH without accepting the risk (#7575)
Fixes #6377

Signed-off-by: James Sanderson <jsanderson@tailscale.com>
2023-03-16 15:47:24 +00:00
Maisem Ali
f34590d9ed tsnet: add test for Funnel connections
For the logic added in b797f77.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-15 19:49:22 -07:00
Maisem Ali
c6d96a2b61 tsnet: do not start logtail in tests
It was trying to upload logs in tests.

skip-issuebot

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-15 18:31:41 -07:00
David Anderson
0498d5ea86 tool/gocross: delete bootstrap tarball downloads after use
Signed-off-by: David Anderson <danderson@tailscale.com>
2023-03-15 11:55:02 -07:00
David Anderson
1f95bfedf7 tool/gocross: adjust Xcode flags to match new Xcode env
Xcode changed how/what data it exports to build steps at some point
recently, so our old way of figuring out the minimum support version
for clang stopped working.

Updates tailscale/corp#4095

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-03-15 10:58:31 -07:00
Kurnia D Win
9526858b1e control/controlclient: fix accidental backoff reset
Signed-off-by: Kurnia D Win <kurnia.d.win@gmail.com>
2023-03-15 10:25:48 -07:00
David Anderson
df3996cae3 tool/gocross: bootstrap correctly on an older toolchain
Sometimes, our cached toolchain ends up being an older version of
Go, older than our go.mod allows. In that scenario, gocross-wrapper.sh
would find a usable toolchain, but then fail to compile gocross.

This change makes the wrapper script check that the cached toolchain's
minor version is good enough to build tailscale.com, and re-bootstraps
in shell if not.

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-03-15 09:40:30 -07:00
Mihai Parparita
97b6d3e917 sockstats: remove per-interface stats from Get
They're not needed for the sockstats logger, and they're somewhat
expensive to return (since they involve the creation of a map per
label). We now have a separate GetInterfaces() method that returns
them instead (which we can still use in the PeerAPI debug endpoint).

If changing sockstatlog to sample at 10,000 Hz (instead of the default
of 10Hz), the CPU usage would go up to 59% on a iPhone XS. Removing the
per-interface stats drops it to 20% (a no-op implementation of Get that
returns a fixed value is 16%).

Updates tailscale/corp#9230
Updates #3363

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-03-14 15:38:41 -07:00
David Anderson
9ebab961c9 version/mkversion: don't break on tagged go.mod entries
I thought our versioning scheme would make go.mod include a commit hash
even on stable builds. I was wrong. Fortunately, the rest of this code
wants anything that 'git rev-parse' understands (to convert it into a full
git hash), and tags qualify.

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-03-14 14:25:18 -07:00
Denton Gentry
6d3490f399 VERSION.txt: this is 1.39
Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2023-03-14 13:50:57 -07:00
License Updater
51b0169b10 licenses: update win/apple licenses
Signed-off-by: License Updater <noreply+license-updater@tailscale.com>
2023-03-14 12:44:27 -07:00
Maisem Ali
b4d3e2928b tsnet: avoid deadlock on close
tsnet.Server.Close was calling listener.Close with the server mutex
held, but the listener close method tries to grab that mutex, resulting
in a deadlock.

Co-authored-by: David Crawshaw <crawshaw@tailscale.com>
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-13 20:50:52 -07:00
shayne
2b892ad6e7 cmd/tailscale/cli: [serve] rework commands based on feedback (#6521)
```
$ tailscale serve https:<port> <mount-point> <source> [off]
$ tailscale serve tcp:<port> tcp://localhost:<local-port> [off]
$ tailscale serve tls-terminated-tcp:<port> tcp://localhost:<local-port> [off]
$ tailscale serve status [--json]

$ tailscale funnel <serve-port> {on|off}
$ tailscale funnel status [--json]
```

Fixes: #6674

Signed-off-by: Shayne Sweeney <shayne@tailscale.com>
2023-03-13 21:43:28 -04:00
Will Norris
6ef2105a8e log/sockstatlog: only start once; don't copy ticker
Signed-off-by: Will Norris <will@tailscale.com>
2023-03-13 17:02:42 -07:00
Maisem Ali
8c4adde083 log/sockstatlog: also shutdown the poll goroutine
Co-authored-by: Will Norris <will@tailscale.com>
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-13 16:39:27 -07:00
Maisem Ali
c87782ba9d cmd/k8s-operator: drop trailing dot in tagged node name
Also update tailcfg docs.

Updates #5055

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-13 15:39:42 -07:00
Will Norris
09e0ccf4c2 ipn: add c2n endpoint for sockstats logs
Signed-off-by: Will Norris <will@tailscale.com>
2023-03-13 15:25:54 -07:00
Will Norris
a1d9f65354 ipn,log: add logger for sockstat deltas
Signed-off-by: Will Norris <will@tailscale.com>
Co-authored-by: Melanie Warrick <warrick@tailscale.com>
2023-03-13 15:07:28 -07:00
Maisem Ali
5e8a80b845 all: replace /kb/ links with /s/ equivalents
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-13 14:21:15 -07:00
Maisem Ali
558735bc63 cmd/k8s-operator: require HTTPS to be enabled for AuthProxy
Updates #5055

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-13 12:32:55 -07:00
Maisem Ali
489e27f085 cmd/k8s-operator: make auth proxy pass tags as Impersonate-Group
We were not handling tags at all, pass them through as Impersonate-Group headers.
And use the FQDN for tagged nodes as Impersonate-User.

Updates #5055

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-13 12:32:12 -07:00
Maisem Ali
56526ff57f tailcfg: bump capver for 1.38
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-13 11:52:15 -07:00
Maisem Ali
09aed46d44 cmd/tailscale/cli: update docs and unhide configure
Also call out Alpha.

Updates #7220

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-13 11:36:08 -07:00
Maisem Ali
223713d4a1 tailcfg,all: add and use Node.IsTagged()
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-13 08:44:25 -07:00
Andrew Dunham
83fa17d26c various: pass logger.Logf through to more places
Updates #7537

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: Id89acab70ea678c8c7ff0f44792d54c7223337c6
2023-03-12 12:38:38 -04:00
Maisem Ali
958c89470b tsnet: add CertDomains helper (#7533)
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-11 16:12:57 -05:00
shayne
e109cf9fdd tsnet/tsnet: clear ipn.ServeConfig on Up for tsnet apps (#7534)
We persist the ServeConfig, even for tsnet apps. It's quite possible for
the ServeConfig to be out of step with the code. Example: If you run
`ListenFunnel` then later turn it off, the ServeConfig will still show
it enabled, the admin console will show it enabled, but the packet
handler will reject the packets.

Workaround by clearing the ServeConfig in `tsnet.Up`

Signed-off-by: Shayne Sweeney <shayne@tailscale.com>
2023-03-11 16:07:22 -05:00
Maisem Ali
3ff44b2307 ipn: add Funnel port check from nodeAttr
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-11 11:20:52 -08:00
Maisem Ali
ccdd534e81 tsnet: add ListenFunnel
This lets a tsnet binary share a server out over Tailscale Funnel.

Signed-off-by: David Crawshaw <crawshaw@tailscale.com>
Signed-off-by: Maisem Ali <maisem@tailscale.com>
Signed-off-by: Shayne Sweeney <shayne@tailscale.com>
2023-03-11 10:34:52 -08:00
Denton Gentry
047b324933 scripts/installer: add PureOS and Amazon Linux Next
Fixes https://github.com/tailscale/tailscale/issues/7410

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2023-03-10 15:22:27 -08:00
Andrew Dunham
f0d6228c52 ipn/localapi: flesh out the 'debug derp' checks
Updates #6526

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: Ic18d9ff288b9c7b8d5ab1bd77dd59693cd776cc4
2023-03-10 13:47:34 -05:00
License Updater
920de86cee licenses: update android licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2023-03-09 21:46:04 -08:00
Mihai Parparita
b64d78d58f sockstats: refactor validation to be opt-in
Followup to #7499 to make validation a separate function (
GetWithValidation vs. Get). This way callers that don't need it don't
pay the cost of a syscall per active TCP socket.

Also clears the conn on close, so that we don't double-count the stats.

Also more consistently uses Go doc comments for the exported API of the
sockstats package.

Updates tailscale/corp#9230
Updates #3363

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-03-09 14:31:20 -08:00
Mihai Parparita
ea81bffdeb sockstats: export as client metrics
Though not fine-grained enough to be useful for detailed analysis, we
might as well export that we gather as client metrics too, since we have
an upload/analysis pipeline for them.

clientmetric.Metric.Add is an atomic add, so it's pretty cheap to also
do per-packet.

Updates tailscale/corp#9230
Updates #3363

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-03-09 14:22:11 -08:00
Maisem Ali
1e72de6b72 ipn/ipnlocal: remove WIP restriction for Tailscale SSH on macOS
It kinda works fine now on macOS with the recent fixes in 0582829 and
 5787989d.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-09 13:52:37 -08:00
Tom DNetto
92fc243755 cmd/tailscale: annotate tailnet-lock keys which wrap pre-auth keys
Signed-off-by: Tom DNetto <tom@tailscale.com>
2023-03-09 11:21:39 -10:00
Tom DNetto
3471fbf8dc cmd/tailscale: surface node-key for locked out tailnet-lock peers
Signed-off-by: Tom DNetto <tom@tailscale.com>
2023-03-09 11:06:23 -10:00
Maisem Ali
b797f773c7 ipn/ipnlocal: add support for funnel in tsnet
Previously the part that handled Funnel connections was not
aware of any listeners that tsnet.Servers might have had open
so it would check against the ServeConfig and fail.

Adding a ServeConfig for a TCP proxy was also not suitable in this
scenario as that would mean creating two different listeners and have
one forward to the other, which really meant that you could not have
funnel and tailnet-only listeners on the same port.

This also introduces the ipn.FunnelConn as a way for users to identify
whether the call is coming over funnel or not. Currently it only holds
the underlying conn and the target as presented in the "Tailscale-Ingress-Target"
header.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-09 12:53:00 -08:00
Joe Tsai
dad78f31f3 syncs: add WaitGroup wrapper (#7481)
The addition of WaitGroup.Go in the standard library has been
repeatedly proposed and rejected.
See golang/go#18022, golang/go#23538, and golang/go#39863

In summary, the argument for WaitGroup.Go is that it avoids bugs like:

	go func() {
		wg.Add(1)
		defer wg.Done()
		...
	}()

where the increment happens after execution (not before)
and also (to a lesser degree) because:

	wg.Go(func() {
		...
	})

is shorter and more readble.

The argument against WaitGroup.Go is that the provided function
takes no arguments and so inputs and outputs must closed over
by the provided function. The most common race bug for goroutines
is that the caller forgot to capture the loop iteration variable,
so this pattern may make it easier to be accidentally racy.
However, that is changing with golang/go#57969.

In my experience the probability of race bugs due to the former
still outwighs the latter, but I have no concrete evidence to prove it.

The existence of errgroup.Group.Go and frequent utility of the method
at least proves that this is a workable pattern and
the possibility of accidental races do not appear to
manifest as frequently as feared.

A reason *not* to use errgroup.Group everywhere is that there are many
situations where it doesn't make sense for the goroutine to return an error
since the error is handled in a different mechanism
(e.g., logged and ignored, formatted and printed to the frontend, etc.).
While you can use errgroup.Group by always returning nil,
the fact that you *can* return nil makes it easy to accidentally return
an error when nothing is checking the return of group.Wait.
This is not a hypothetical problem, but something that has bitten us
in usages that was only using errgroup.Group without intending to use
the error reporting part of it.

Thus, add a (yet another) variant of WaitGroup here that
is identical to sync.WaitGroup, but with an extra method.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2023-03-09 12:04:38 -08:00
Maisem Ali
be027a9899 control/controlclient: improve handling of concurrent lite map requests
This reverts commit 6eca47b16c and fixes forward.

Previously the first ever streaming MapRequest that a client sent would also
set ReadOnly to true as it didn't have any endpoints and expected/relied on the
map poll to restart as soon as it got endpoints. However with 48f6c1eba4,
we would no longer restart MapRequests as frequently as we used to, so control
would only ever get the first streaming MapRequest which had ReadOnly=true.

Control would treat this as an uninteresting request and would not send it
any further netmaps, while the client would happily stay in the map poll forever
while litemap updates happened in parallel.

This makes it so that we never set `ReadOnly=true` when we are doing a streaming
MapRequest. This is no longer necessary either as most endpoint discovery happens
over disco anyway.

Co-authored-by: Andrew Dunham <andrew@du.nham.ca>
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-09 11:36:44 -08:00
Joe Tsai
87b4bbb94f tstime/rate: add Value (#7491)
Add Value, which measures the rate at which an event occurs,
exponentially weighted towards recent activity.
It is guaranteed to occupy O(1) memory, operate in O(1) runtime,
and is safe for concurrent use.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2023-03-09 11:13:09 -08:00
Mihai Parparita
4c2f67a1d0 net/sockstat: fix per-interface statistics not always being available
withSockStats may be called before setLinkMonitor, in which case we
don't have a populated knownInterfaces map. Since we pre-populate the
per-interface counters at creation time, we would end up with an
empty map. To mitigate this, we do an on-demand request for the list of
interfaces.

This would most often happen with the logtail instrumentation, since we
initialize it very early on.

Updates tailscale/corp#9230

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-03-09 10:38:45 -08:00
Maisem Ali
e69682678f ssh/tailssh: use context.WithCancelCause
It was using a custom implmentation of the context.WithCancelCause,
replace usage with stdlib.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-09 10:22:55 -08:00
Mihai Parparita
a2be1aabfa logtail: remove unncessary response read
Effectively reverts #249, since the server side was fixed (with #251?)
to send a 200 OK/content-length 0 response.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-03-08 15:39:04 -08:00
Tom DNetto
ce99474317 all: implement preauth-key support with tailnet lock
Signed-off-by: Tom DNetto <tom@tailscale.com>
2023-03-08 11:56:46 -10:00
Mihai Parparita
f4f8ed98d9 sockstats: add validation for TCP socket stats
We can use the TCP_CONNECTION_INFO getsockopt() on Darwin to get
OS-collected tx/rx bytes for TCP sockets. Since this API is not available
for UDP sockets (or on Linux/Android), we can't rely on it for actual
stats gathering.

However, we can use it to validate the stats that we collect ourselves
using read/write hooks, so that we can be more confident in them. We
do need additional hooks from the Go standard library (added in
tailscale/go#59) to be able to collect them.

Updates tailscale/corp#9230
Updates #3363

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-03-08 13:39:30 -08:00
Tom DNetto
6eca47b16c Revert "control/controlclient: improve handling of concurrent lite map requests"
This reverts commit 48f6c1eba4.

It unfortunately breaks mapresponse wakeups.

Signed-off-by: Tom DNetto <tom@tailscale.com>
2023-03-08 09:47:44 -10:00
Andrew Dunham
48f6c1eba4 control/controlclient: improve handling of concurrent lite map requests
Prior to this change, if we were in the middle of a lite map update we'd
tear down the entire map session and restart it. With this change, we'll
cancel an in-flight lite map request up to 10 times and restart before
we tear down the streaming map request. We tear down everything after 10
retries to ensure that a steady stream of calls to sendNewMapRequest
doesn't fail to make progress by repeatedly canceling and restarting.

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Co-authored-by: Maisem Ali <maisem@tailscale.com>
Change-Id: I9392bf8cf674e7a58ccd1e476039300a359ef3b1
2023-03-07 19:29:55 -05:00
Maisem Ali
b0cb39cda1 tsnet: only intercept TCP flows that have listeners
Previously, it would accept all TCP connections and then close the ones
it did not care about. Make it only ever accept the connections that it
cares about.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-07 15:48:49 -08:00
M. J. Fromberger
c09578d060 .github: update tibdex/github-app-token to release v1.8.0 (#7495)
The main motivation for this change is to stop using the deprecated
set-output function which triggers deprecation warnings in the action.

Change-Id: I80496c44ea1166b9c40d5cd9e450129778ad4aaf
Signed-off-by: M. J. Fromberger <fromberger@tailscale.com>
2023-03-07 14:30:19 -08:00
M. J. Fromberger
a75360ccd6 util: add truncate package (#7490)
This package handles cases where we need to truncate human-readable text to fit
a length constraint without leaving "ragged" multi-byte rune fragments at the
end of the truncated value.

Change-Id: Id972135d1880485f41b1fedfb65c2b8cc012d416
Signed-off-by: M. J. Fromberger <fromberger@tailscale.com>
2023-03-07 11:51:36 -08:00
David Anderson
5b68dcc8c1 go.mod.sri: update for toolchain change.
Signed-off-by: David Anderson <danderson@tailscale.com>
2023-03-07 11:40:29 -08:00
Kyle Carberry
3862a1e1d5 derp/derphttp: cleanup WebSocket connection on close
This was causing a leak in our CI!

Signed-off-by: Kyle Carberry <kyle@carberry.com>
2023-03-07 11:36:34 -08:00
Andrew Dunham
be107f92d3 wgengine/magicsock: track per-endpoint changes in ringbuffer
This change adds a ringbuffer to each magicsock endpoint that keeps a
fixed set of "changes"–debug information about what updates have been
made to that endpoint.

Additionally, this adds a LocalAPI endpoint and associated
"debug peer-status" CLI subcommand to fetch the set of changes for a given
IP or hostname.

Updates tailscale/corp#9364

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I34f726a71bddd0dfa36ec05ebafffb24f6e0516a
2023-03-07 13:53:03 -05:00
David Crawshaw
9245d813c6 tsnet: explicit message for panic seen in CI
Updates #7488

Signed-off-by: David Crawshaw <crawshaw@tailscale.com>
2023-03-07 10:22:50 -08:00
shayne
f7a7957a11 sniproxy: add promote-https (#7487)
Adds support for an HTTP server that promotes all requests to HTTPS.
The flag is `-promote-https` and defaults to true.

Updates #1748
2023-03-07 11:46:02 -05:00
Brad Fitzpatrick
49e2d3a7bd words: add word we forgot
I explained this tails/scales list to my 5yo and he looked at me like
it was the most obvious idea ever. Of course we'd make such lists at
work!  What else do grown-ups do all day? And then he wouldn't stop
talking about coelacanths and I had no clue what he was saying or how
to spell it until I asked my phone and the phone apparently understood
me and I realized it was a fish and he was helping me? I think?

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-03-06 20:53:46 -08:00
Denton Gentry
b46c5ae82a cmd/sniproxy: draw the rest of the DNS owl.
Add a DNS server which always responds as its own IP addresses.

Additionally add a tsnet TailscaleIPs() function to return the
IP addresses, both IPv4 and IPv6.

Updates https://github.com/tailscale/tailscale/issues/1748

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2023-03-06 19:29:01 -08:00
Joe Tsai
7e6c5a2db4 tstime: rely on stdlib parse functionality (#7482)
The time.Parse function has been optimized to the point
where it is faster than our custom implementation.
See upstream changes in:

* https://go.dev/cl/429862
* https://go.dev/cl/425197
* https://go.dev/cl/425116

Performance:

	BenchmarkGoParse3339/Z     38.75 ns/op    0 B/op    0 allocs/op
	BenchmarkGoParse3339/TZ    54.02 ns/op    0 B/op    0 allocs/op
	BenchmarkParse3339/Z       40.17 ns/op    0 B/op    0 allocs/op
	BenchmarkParse3339/TZ      87.06 ns/op    0 B/op    0 allocs/op

We can see that the stdlib implementation is now faster.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2023-03-06 18:05:51 -08:00
Joe Tsai
9112e78925 tstime: add Sleep (#7480)
Sleep is an interruptible sleep variation.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2023-03-06 17:40:38 -08:00
License Updater
3b18e65c6a licenses: update android licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2023-03-06 16:03:27 -08:00
Mihai Parparita
6ac6ddbb47 sockstats: switch label to enum
Makes it cheaper/simpler to persist values, and encourages reuse of
labels as opposed to generating an arbitrary number.

Updates tailscale/corp#9230
Updates #3363

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-03-06 15:54:35 -08:00
Aaron Klotz
9687f3700d net/dns: deal with Windows wsl.exe hangs
Despite the fact that WSL configuration is still disabled by default, we
continue to log the machine's list of WSL distros as a diagnostic measure.

Unfortunately I have seen the "wsl.exe -l" command hang indefinitely. This patch
adds a (more than reasonable) 10s timeout to ensure that tailscaled does not get
stuck while executing this operation.

I also modified the Windows implementation of NewOSConfigurator to do the
logging asynchronously, since that information is not required in order to
continue starting up.

Fixes #7476

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2023-03-06 16:08:13 -07:00
Tom DNetto
2263d9c44b cmd/tsconnect: pop CTA to make everything work with tailnet lock
Signed-off-by: Tom DNetto <tom@tailscale.com>
2023-03-06 10:07:20 -10:00
David Crawshaw
387b68fe11 tsnet: generalize loopback listener to include SOCKS5
Some languages do not give you any useful access to the sockets
underlying their networking packages. E.g. java.net.http.HttpClient
provides no official access to its dialing logic.

...but everyone supports proxies. So add a SOCKS5 proxy on the listener
we are already running.

(The function being revamped is very new,
I only added it in the last week and it wasn't part of any release,
so I believe it is fine to redo its function signature.)

Signed-off-by: David Crawshaw <crawshaw@tailscale.com>
2023-03-06 09:00:09 -08:00
Andrew Dunham
df2561f6a2 ipn/ipnlocal: stop netmap expiry timer when resetting control client
This prevents a panic where we synthesize a new netmap in
setClientStatus after we've shut down and nil'd out the controlclient,
since that function expects to be called while connected to control.

Fixes #7392

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: Ib631eb90f34f6afa008d69bbb386f70da145e102
2023-03-06 10:59:47 -05:00
David Crawshaw
96a555fc5a net/socks5: add password auth support
Conforms to RFC 1929.

To support Java HTTP clients via libtailscale, who offer no other
reliable hooks into their sockets.

Signed-off-by: David Crawshaw <crawshaw@tailscale.com>
2023-03-05 14:08:34 -08:00
Brad Fitzpatrick
0f4359116e tsnet: add UDP support to Server.Listen
No ListenPacket support yet, but Listen with a udp network type fit
easier into netstack's model to start.

Then added an example of using it to cmd/sniproxy with a little udp
:53 handler.

No tests in tsnet yet because we don't have support for dialing over
UDP in tsnet yet. When that's done, a new test can test both sides.

Updates #5871
Updates #1748

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-03-05 12:40:13 -08:00
Brad Fitzpatrick
9ff51ca17f wgengine/netstack: add support for custom UDP flow handlers
To be used by tsnet and sniproxy later.

Updates #5871
Updates #1748

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-03-05 09:05:43 -08:00
Andrew Dunham
045f995203 ipn/localapi: close portmapper after debug
This ensures that any mappings that are created are correctly cleaned
up, instead of waiting for them to expire in the router.

Updates #7377

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I436248ee7740eded6d8adae5df525e785a8f7ccb
2023-03-05 10:20:04 -05:00
Andrew Dunham
f6cd24499b net/portmapper: relax source port check for UPnP responses
Per a packet capture provided, some gateways will reply to a UPnP
discovery packet with a UDP packet with a source port that does not come
from the UPnP port. Accept these packets with a log message.

Updates #7377

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I5d4d5b2a0275009ed60f15c20b484fe2025d094b
2023-03-04 22:10:14 -05:00
Andrew Dunham
51eb0b2cb7 net/portmapper: send UPnP protocol in upper-case
We were previously sending a lower-case "udp" protocol, whereas other
implementations like miniupnp send an upper-case "UDP" protocol. For
compatibility, use an upper-case protocol instead.

Updates #7377

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I4aed204f94e4d51b7a256d29917af1536cb1b70f
2023-03-04 16:18:26 -05:00
Andrew Dunham
d379a25ae4 net/portmapper: don't pick external ports below 1024
Some devices don't let you UPnP portmap a port below 1024, so let's just
avoid that range of ports entirely.

Updates #7377

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: Ib7603b1c9a019162cdc4fa21744a2cae48bb1d86
2023-03-04 16:04:23 -05:00
Andrew Dunham
69f9c17555 ipn/localapi: fix panic after handler returns
Change-Id: I612f9ebf78d962e094bff908670b3ffd89f756e5
Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
2023-03-04 16:03:36 -05:00
Maisem Ali
1a30b2d73f all: use tstest.Replace more
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-04 12:24:55 -08:00
License Updater
57a44846ae licenses: update win/apple licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2023-03-04 07:13:20 -08:00
Andrew Dunham
a9c17dbf93 ipn/ipnlocal: reject unmasked routes
Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: Ic804efd24f5f536de1f2c910de3a24372d48d54d
2023-03-03 22:39:01 -05:00
Andrew Dunham
2d3ae485e3 net/interfaces: add better test for LikelyHomeRouterIP
Return a mock set of interfaces and a mock gateway during this test and
verify that LikelyHomeRouterIP returns the outcome we expect. Also
verify that we return an error if there are no IPv4 addresses available.

Follow-up to #7447

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I8f06989e7f1f0bebd108861cbff17b820ed2e6e4
2023-03-03 20:52:57 -05:00
Maisem Ali
b9ebf7cf14 tstest: add method to Replace values for tests
We have many function pointers that we replace for the duration of test and
restore it on test completion, add method to do that.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-03 17:02:33 -08:00
Andrew Dunham
12100320d2 net/interfaces: always return an IPv4 LikelyHomeRouterIP
We weren't filtering out IPv6 addresses from this function, so we could
be returning an IPv4 gateway IP and an IPv6 self IP. Per the function
comments, only return IPv4 addresses for the self IP.

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: If19a4aadc343fbd4383fc5290befa0eff006799e
2023-03-03 18:36:07 -05:00
Andrew Dunham
73fa7dd7af util/slicesx: add package for generic slice functions, use
Now that we're using rand.Shuffle in a few locations, create a generic
shuffle function and use it instead. While we're at it, move the
interleaveSlices function to the same package for use.

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I0b00920e5b3eea846b6cedc30bd34d978a049fd3
2023-03-03 16:25:48 -05:00
Tom DNetto
88c7d19d54 tka: compact TKA storage on startup
Signed-off-by: Tom DNetto <tom@tailscale.com>
2023-03-03 10:09:26 -10:00
Tom DNetto
e2d652ec4d ipn,cmd/tailscale: implement resigning nodes on tka key removal
Signed-off-by: Tom DNetto <tom@tailscale.com>
2023-03-03 10:09:05 -10:00
Andrew Dunham
3f8e8b04fd cmd/tailscale, cmd/tailscaled: move portmapper debugging into tailscale CLI
The debug flag on tailscaled isn't available in the macOS App Store
build, since we don't have a tailscaled binary; move it to the
'tailscale debug' CLI that is available on all platforms instead,
accessed over LocalAPI.

Updates #7377

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I47bffe4461e036fab577c2e51e173f4003592ff7
2023-03-03 14:21:38 -05:00
Mihai Parparita
3e71e0ef68 net/sockstats: remove explicit dependency on wgengine/monitor
Followup to #7177 to avoid adding extra dependencies to the CLI. We
instead declare an interface for the link monitor.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-03-03 08:37:14 -08:00
James Tucker
7b73c9628d version/distro,wgengine/router: raise WSL eth0 MTU when too low
WSL has started to set the eth0 default route interface default to 1280
MTU, which is too low to carry 1280 byte packets from tailscale0 once
wrapped in WireGuard. The change down to 1280 is very likely smaller
than necessary for almost all users. We can not easily determine the
ideal MTU, but if all the preconditions match, we raise the MTU to 1360,
which is just enough for Tailscale traffic to work.

Updates #4833
Updates #7346

Signed-off-by: James Tucker <james@tailscale.com>
2023-03-02 21:33:02 -08:00
shayne
d92ef4c215 cmd/derper: randomize IPs on refreshBootstrapDNS (#7440)
This is to address a possible DNS failure on startup. Before this
change IPv6 addresses would be listed first, and the client dialer would
fail for hosts without IPv6 connectivity.
2023-03-02 23:36:12 -05:00
Andrew Dunham
27575cd52d net/dnsfallback: shuffle returned IPs
This ensures that we're trying multiple returned IPs, since the DERP
servers return the same response to all queries. This should increase
the chances that we eventually reach a working IP.

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: Ie8d4fb93df96da910fae49ae71bf3e402b9fdecc
2023-03-02 22:55:58 -05:00
Julia at Tailscale
ef6f66bb9a api.md: refresh of API docs
Update API documentation to include explanation of resources, a cleaner and more consistent structure, updated terminology, and fixes to a few errors and omissions.

Signed-off-by: Julia Stein <julia@tailscale.com>
Signed-off-by: Will Norris <will@tailscale.com>
Co-authored-by: Will Norris <will@tailscale.com>
2023-03-02 17:20:45 -08:00
Brad Fitzpatrick
1410682fb6 cmd/sniproxy: add start of a tsnet-based SNI proxy
$ curl https://canhazip.com/
    170.173.0.21
    $ curl --resolve canhazip.com:443:100.85.165.81 https://canhazip.com/
    34.223.127.151

Updates #1748

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-03-02 14:39:10 -08:00
Joe Tsai
283a84724f types/logid: simplify implementation (#7415)
Share the same underlying implementation for both PrivateID and PublicID.
For the shared methods, declare them in the same order.
Only keep documentation on methods without obvious meaning.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2023-03-02 13:18:04 -08:00
Maisem Ali
e1530cdfcc cmd/containerboot,kube: consolidate the two kube clients
We had two implemenetations of the kube client, merge them.

containerboot was also using a raw http.Transport, this also has
the side effect of making it use a http.Client

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-03-02 11:36:06 -08:00
Flakes Updater
5eb8a2a86a go.mod.sri: update SRI hash for go.mod changes
Signed-off-by: Flakes Updater <noreply@tailscale.com>
2023-03-02 11:02:05 -08:00
Andrew Dunham
d8286d0dc2 go.mod: bump golang.org/x/image to latest version
This resolves a dependabot alert, though the alert does not affect us:
    https://github.com/tailscale/tailscale/security/dependabot/6

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I087de6f22fb4821d0035fc16b603f9692581b9bd
2023-03-02 13:56:37 -05:00
Denton Gentry
51288221ce cmd/tailscale: use request Schema+Host for QNAP authLogin.cgi
QNAP allows users to set the port number for the management WebUI,
which includes authLogin.cgi. If they do, then connecting to
localhost:8080 fails.

https://github.com/tailscale/tailscale-qpkg/issues/74#issuecomment-1407486911

Fixes https://github.com/tailscale/tailscale/issues/7108

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2023-03-01 18:00:06 -08:00
tailscale-license-updater[bot]
06302e30ae licenses: update win/apple licenses (#7423)
Signed-off-by: License Updater <noreply@tailscale.com>
Co-authored-by: License Updater <noreply@tailscale.com>
2023-03-01 17:51:17 -08:00
David Anderson
311352d195 release/dist/cli: add --verbose to print subcommand output
By default, cmd/dist only prints the output of failed commands.
With this, you can turn all the noisy output back on.

Updates tailscale/corp#9045

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-03-01 17:16:31 -08:00
David Anderson
0df11253ec release/dist: add a helper to run commands
The helper suppresses output if the command runs successfully. If the
command fails, it dumps the buffered output to stdout before returning
the error. This means the happy path isn't swamped by debug noise or
xcode being intensely verbose about what kind of day it's having,
but you still get debug output when something goes wrong.

Updates tailscale/corp#9045

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-03-01 17:16:31 -08:00
Aaron Klotz
f18beaa1e4 cmd/mkmanifest, cmd/tailscale, cmd/tailscaled: remove Windows arm32 resources from OSS
Given recent changes in corp, I originally thought we could remove all of the
syso files, but then I realized that we still need them so that binaries built
purely from OSS (without going through corp) will still receive a manifest.

We can remove the arm32 one though, since we don't support 32-bit ARM on Windows.

Updates https://github.com/tailscale/corp/issues/9576

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2023-03-01 15:45:12 -07:00
Sonia Appasamy
7985f5243a cmd/k8s-operator: update device authorization copy
"Device Authorization" was recently renamed to "Device Approval"
on the control side. This change updates the k8s operator to match.

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-03-01 16:39:15 -05:00
Tom DNetto
ff168a806e tka: implement compaction logic
Signed-off-by: Tom DNetto <tom@tailscale.com>
2023-03-01 10:50:07 -10:00
Sonia Appasamy
bb7033174c cmd/tsconnect: update device authorization copy
"Device Authorization" was recently renamed to "Device Approval"
on the control side. This change updates tsconnect to match.

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-03-01 15:23:29 -05:00
Joe Tsai
7e4788e383 logtail: delete ID types and functions (#7412)
These have been moved to the types/logid package.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2023-03-01 12:18:23 -08:00
Mihai Parparita
9cb332f0e2 sockstats: instrument networking code paths
Uses the hooks added by tailscale/go#45 to instrument the reads and
writes on the major code paths that do network I/O in the client. The
convention is to use "<package>.<type>:<label>" as the annotation for
the responsible code path.

Enabled on iOS, macOS and Android only, since mobile platforms are the
ones we're most interested in, and we are less sensitive to any
throughput degradation due to the per-I/O callback overhead (macOS is
also enabled for ease of testing during development).

For now just exposed as counters on a /v0/sockstats PeerAPI endpoint.

We also keep track of the current interface so that we can break out
the stats by interface.

Updates tailscale/corp#9230
Updates #3363

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-03-01 12:09:31 -08:00
Sonia Appasamy
0c1510739c cmd/tailscale/cli: update device authorization copy
"Device Authorization" was recently renamed to "Device Approval"
on the control side. This change updates the linux cli to match.

Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2023-03-01 14:02:28 -05:00
Joe Tsai
06134e9521 types/logid: remove MustParsePublicID (#7405)
Ever since the introduction of the "must" package,
most MustXXX functions are no longer necessary.
Remove this as it is no longer depended upon
from within this repository and by the internal private repository.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2023-02-28 19:00:11 -08:00
Joe Tsai
0d19f5d421 all: replace logtail.{Public,Private}ID with logid.{Public,Private}ID (#7404)
The log ID types were moved to a separate package so that
code that only depend on log ID types do not need to link
in the logic for the logtail client itself.
Not all code need the logtail client.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2023-02-28 19:00:00 -08:00
David Crawshaw
d41f6a8752 tsnet: do not error on NeedsMachineAuth for Up
It turns out even with an AuthKey that pre-approves devices on a tailnet
with machine auth turned on, we still temporarily see the
NeedsMachineAuth state. So remove that error (for now).

Signed-off-by: David Crawshaw <crawshaw@tailscale.com>
2023-02-28 15:36:33 -08:00
David Crawshaw
768df4ff7a tsnet: add a LocalAPI listener on loopback, with basic auth
This is for use by LocalAPI clients written in other languages that
don't appear to be able to talk HTTP over a socket (e.g.
java.net.http.HttpClient).

Signed-off-by: David Crawshaw <crawshaw@tailscale.com>
2023-02-28 13:52:32 -08:00
Vladimir Pouzanov
e3211ff88b Add support for OAuth tokens #7394 (#7393)
Signed-off-by: Vladimir Pouzanov <farcaller@gmail.com>
2023-02-27 18:05:24 -08:00
Maisem Ali
49c206fe1e tailcfg,hostinfo: add App field to identify tsnet uses
This allows us to differentiate between the various tsnet apps that
we have like `golinks` and `k8s-operator`.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-02-27 15:19:33 -08:00
Mihai Parparita
780c56e119 ipn/ipnlocal: add delegated interface information to /interfaces PeerAPI handler
Exposes the delegated interface data added by #7248 in the debug
endpoint. I would have found it useful when working on that PR, and
it may be handy in the future as well.

Also makes the interfaces table slightly easier to parse by adding
borders to it. To make then nicer-looking, the CSP was relaxed to allow
inline styles.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-02-27 09:39:49 -08:00
Charlotte Brandhorst-Satzkorn
e484e1c0fc words: just words, nothing but words (#7384)
nothing in relation to fish at all.

Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2023-02-26 11:29:45 -08:00
Denton Gentry
bf7573c9ee cmd/nginx-auth: build for arm64
Fixes https://github.com/tailscale/tailscale/issues/6978

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2023-02-25 17:16:31 -08:00
Denton Gentry
9ab992e7a1 syncs: re-enable TestWatchMultipleValues
We've updated to a different set of CI machines since this test
was disabled.

Fixes https://github.com/tailscale/tailscale/issues/1513

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2023-02-25 17:03:16 -08:00
Maisem Ali
0582829e00 ssh/tailssh: try launching commands with /usr/bin/login on macOS
Updates #4939

Co-authored-by: Adam Eijdenberg <adam@continusec.com>
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-02-25 15:46:34 -08:00
Charlotte Brandhorst-Satzkorn
e851d134cf words: grasping at straws... wait, do straws have tails? (#7376)
One might argue they have two, but until that hypothesis can be proven
these tails and scales will have to do!

Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2023-02-24 21:10:43 -08:00
David Anderson
04be5ea725 release/dist/cli: default to "all" for list if no filters given
Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-24 15:26:46 -08:00
Jordan Whited
d4122c9f0a cmd/tailscale/cli: fix TestUpdatePrefs over Tailscale SSH (#7374)
Fixes #7373

Signed-off-by: Jordan Whited <jordan@tailscale.com>
2023-02-24 15:26:23 -08:00
David Anderson
b0eba129e6 .github/workflows: add a pass/fail verdict job to the test workflow
Github requires explicitly listing every single job within a workflow
that is required for status checks, instead of letting you list entire
workflows. This is ludicrous, and apparently this nonsense is the
workaround.

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-24 23:00:22 +00:00
David Anderson
0ab6a7e7f5 .github/workflows: try to make the merge queue actually run CI
Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-24 22:31:47 +00:00
David Anderson
587eb32a83 release/dist: add forgotten license headers
Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-24 22:21:28 +00:00
David Anderson
cf74ee49ee release/dist/cli: factor out the CLI boilerplace from cmd/dist
Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-24 22:21:28 +00:00
David Anderson
fc4b25d9fd release: open-source release build logic for unix packages
Updates tailscale/corp#9221

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-24 21:31:09 +00:00
David Crawshaw
44e027abca tsnet: add data transfer test
Signed-off-by: David Crawshaw <crawshaw@tailscale.com>
2023-02-24 19:18:32 +00:00
David Crawshaw
46467e39c2 logtail: allow multiple calls to Shutdown
Signed-off-by: David Crawshaw <crawshaw@tailscale.com>
2023-02-24 19:18:32 +00:00
David Crawshaw
daa2f1c66e tsnet: add Up method to block until ready
Signed-off-by: David Crawshaw <crawshaw@tailscale.com>
2023-02-24 18:57:55 +00:00
David Anderson
64181e17c8 tool/gocross: support local toolchain for development
This makes gocross and its bootstrap script understand an absolute
path in go.toolchain.rev to mean "use the given toolchain directly".

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-24 05:55:46 +00:00
David Anderson
66621ab38e tool/gocross: embed the version explicitly with linker flags
We need to build gocross from multiple repos, but Go's innate
git hash embedding only works when you build gocross from this repo,
not when you build it from elsewhere via 'go build
tailscale.com/tool/gocross'. Instead, explicitly embed the version
found with 'git rev-parse HEAD', which will work from any git repo.

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-24 03:11:29 +00:00
David Anderson
7444dabb68 tool/gocross: do all the bootstrap steps in a subshell
This avoids accidentally overwriting variables from the input
environment, which might non-deterministically change the behavior
of gocross.

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-24 03:11:29 +00:00
Tom DNetto
abc874b04e tka: add public API on NodeKeySignature key information
This is needed in the coordination server.

Signed-off-by: Tom DNetto <tom@tailscale.com>
2023-02-23 19:20:39 +00:00
License Updater
61a345c8e1 licenses: update win/apple licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2023-02-23 18:56:08 +00:00
Maisem Ali
06a10125fc cmd/k8s-operator: set hostinfo.Package
This allows identifying the operator.

Updates #5055

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-02-23 02:33:23 +00:00
David Anderson
7e65a11df5 tool/gocross: write the wrapper script directly, rather than printing
Turns out directing the printed script into the bootstrap location leads
to irritating "text file busy" problems and then having to muck about with
tempfiles and chmod and all that. Instead, have gocross write everything
with the right values.

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-23 02:03:14 +00:00
David Anderson
499d82af8a tool/gocross: add command to print the wrapper shell script
So that when importing and using gocross from other repos, there's
an easy way to get at the right wrapper script that's in sync with
the gocross binary.

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-22 20:48:37 +00:00
David Anderson
860734aed9 tool/gocross: a tool for building Tailscale binaries
Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-22 17:55:16 +00:00
David Anderson
0b8f89c79c cmd/tsconnect: find the build dir independently of -trimpath
trimmed builds don't have absolute path information in executable
metadata, which leads the runtime.Caller approach failing
mysteriously in yarn with complaints about relative package paths.

So, instead of using embedded package metadata to find paths,
expect that we're being invoked within the tailscale repo, and
locate the tsconnect directory that way.

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-22 00:02:47 +00:00
Tom DNetto
f9b746846f tailcfg: add RPC structs for /tka/affected-sigs
These RPCs will be used to power the future 'tailscale lock remove' default behavior
of resigning signatures for which trust is about to be removed.

Signed-off-by: Tom DNetto <tom@tailscale.com>
2023-02-21 21:58:38 +00:00
Andrew Dunham
e220fa65dd util/ringbuffer: move generic ringbuffer from corp repo
Also add some basic tests for this implementation.

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I307ebb6db91d0c172657befb276b38ccb638f828
2023-02-21 19:11:08 +00:00
Shayne Sweeney
cd18bb68a4 gitignore: Add personal .gopath and nix build /result
Signed-off-by: Shayne Sweeney <shayne@tailscale.com>
2023-02-21 03:01:19 +00:00
License Updater
d38abe90be licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2023-02-19 05:43:53 +00:00
David Anderson
5a2fa3aa95 .github/workflows: add armv5 and armv7 cross tests
armv5 because that's what we ship to most downstreams right now,
armv7 becuase that's what we want to ship more of.

Fixes https://github.com/tailscale/tailscale/issues/7269

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-19 05:16:11 +00:00
Maisem Ali
5787989d74 ssh/tailssh: detect user shell correctly on darwin
Updates #6213

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-02-19 01:52:13 +00:00
Denton Gentry
6dabb34c7f scripts/installer.sh: add GalliumOS and Sangoma Linux
Fixes https://github.com/tailscale/tailscale/issues/6541
Fixes https://github.com/tailscale/tailscale/issues/6555

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2023-02-18 23:13:05 +00:00
David Anderson
093139fafd .github/workflows: fix non-collapsing CI status in PRs
CI status doesn't collapse into "everything OK" if a job gets
skipped. Instead, always run the job, but skip its only step in PRs.

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-18 22:31:05 +00:00
Nicolas BERNARD
3db894b78c client/tailscale: add tags field to Device struct
Fixes #7302

Signed-off-by: Nicolas BERNARD <nikkau@nikkau.net>
2023-02-18 21:14:40 +00:00
David Anderson
306c8a713c .github/workflows: run CI and CodeQL in the merge queue
Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-18 19:21:07 +00:00
David Anderson
149de5e6d6 build_dist.sh: use cmd/mkversion to get version data
Replaces the former shell goop, which was a shell reimplementation
of a subset of version/mkversion.

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-18 19:05:39 +00:00
David Anderson
45d9784f9d version/mkversion: allow collecting version only from this repo
With this change, you can collect version info from either a git
checkout of the tailscale.com Go module (this repo), or a git
checkout of a repo that imports the tailscale.com Go module.

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-18 19:05:39 +00:00
Flakes Updater
303048a7d5 go.mod.sri: update SRI hash for go.mod changes
Signed-off-by: Flakes Updater <noreply@tailscale.com>
2023-02-18 18:24:33 +00:00
Brad Fitzpatrick
e8a028cf82 go.mod: bump x/crypto
No particular reason. Just good point of our release cycle for some #cleanup.

It also makes dependabot happy about something we're not using?

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-02-18 18:04:02 +00:00
Maisem Ali
a7eab788e4 metrics: add SetInt64 to ease using LabelMap for gauge metrics
Set is provided by the underlying Map.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-02-18 17:43:43 +00:00
Denton Gentry
1ba0b7fd79 scripts/installer.sh: add postmarketos support.
Fixes https://github.com/tailscale/tailscale/issues/7300

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2023-02-18 16:06:47 +00:00
David Anderson
7ca54c890e version/mkversion: add exports for major/minor/patch
build_dist.sh needs the minor version by itself, for some reason.

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-18 05:21:05 +00:00
David Anderson
8ed27d65ef version/mkversion: add documentation, rename internal terminology
Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-18 05:21:05 +00:00
David Anderson
1dadbbb72a version/mkversion: open-source version generation logic
In preparation for moving more of the release building here too.

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-18 05:21:05 +00:00
Maisem Ali
d811c5a7f0 cmd/tailscale/cli: handle home dir correctly on macOS for kubeconfig
This ensures that we put the kubeconfig in the correct directory from within the macOS Sandbox when
paired with tailscale/corp@3035ef7

Updates #7220

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-02-17 01:18:52 +00:00
Maisem Ali
4a99481a11 .github/workflows: set TS_FUZZ_CURRENTLY_BROKEN to false
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-02-17 01:18:42 +00:00
Will Norris
8b9ee7a558 Makefile: add help text to Makefile
https://rosszurowski.com/log/2022/makefiles#self-documenting-makefiles
Signed-off-by: Will Norris <will@tailscale.com>
2023-02-16 22:39:09 +00:00
License Updater
300664f8ae licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2023-02-16 18:01:08 +00:00
License Updater
4531be4406 licenses: update win/apple licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2023-02-15 13:59:22 +00:00
Flakes Updater
390db46aad go.mod.sri: update SRI hash for go.mod changes
Signed-off-by: Flakes Updater <noreply@tailscale.com>
2023-02-14 23:48:42 +00:00
Brad Fitzpatrick
607c3eb813 go.toolchain.rev: update to Go 1.20.1
And bump x/net for the HTTP/2 fixes.

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-02-14 23:39:08 +00:00
James Tucker
ee471ca1c8 tstest/integration: enable go lookups from $PATH
Fixes tailscale/corp#9261

Signed-off-by: James Tucker <james@tailscale.com>
2023-02-14 23:06:58 +00:00
Maisem Ali
c01c84ea8e cmd/tailscale/cli: add "configure kubeconfig" subcommand
It takes in a node hostname and configures the local kubeconfig file to
point to that.

Updates #7220

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-02-14 06:06:42 +00:00
Maisem Ali
181a3da513 cmd/tailscale/cli: add a hidden configure subcommand
Also make `tailscale configure-host` an alias to `tailscale configure synology`

Updates #7220

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-02-14 06:06:42 +00:00
Andrew Dunham
6927a844b1 util/linuxfw: add build constraints excluding GOARCH=arm
This isn't currently supported due to missing support in upstream
dependencies, and also we don't use this package anywhere right now.
Just conditionally skip this for now.

Fixes #7268

Change-Id: Ie7389c2c0816b39b410c02a7276051a4c18b6450
Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
2023-02-14 06:00:03 +00:00
David Anderson
6de3459bc8 .github/workflows: fix typo
Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-14 05:22:49 +00:00
David Anderson
f145c2b65b .github/workflows: add workflow to update go.mod Nix SRI hash
So that I just get a quick PR to approve and merge instead of
periodically discovering that the SRI hash has bitrotted.

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-14 03:28:43 +00:00
David Anderson
f9667e4946 Dockerfile: fix docker build
The stamp vars got renamed and I forgot to update these scripts.

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-14 00:59:09 +00:00
Denton Gentry
fdc2018d67 wgengine/magicsock: remove superfluous "discokey" from log
The stringification of the discokey type now prepends "discokey:"
Fixes https://github.com/tailscale/tailscale/issues/3074

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2023-02-12 21:05:05 +00:00
License Updater
10b20fd1c7 licenses: update android licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2023-02-12 03:46:15 +00:00
David Anderson
2eb25686d7 .github/workflows: simplify build-only go test invocation
Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-12 02:37:24 +00:00
David Anderson
253333b8a3 .github/workflows: support disabling fuzz testing safely
OSS-Fuzz doesn't update their version of Go as quickly as we do, so
we sometimes end up with OSS-Fuzz being unable to build our code for
a few weeks. We don't want CI to be red for that entire time, but
we also don't want to forget to reenable fuzzing when OSS-Fuzz does
start working again.

This change makes two configurations worthy of a CI pass:
 - Fuzzing works, and we expected it to work. This is a normal
   happy state.
 - Fuzzing didn't compile, and we expected it to not compile. This
   is the "OSS-Fuzz temporarily broken" state.

If fuzzing is unexpectedly broken, or unexpectedly not broken, that's
a CI failure because we need to either address a fuzz finding, or
update TS_FUZZ_CURRENTLY_BROKEN to reflect the state of OSS-Fuzz.

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-12 02:07:10 +00:00
David Anderson
5e186f9fbf .github/workflows: pin version of Windows we run on
Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-12 01:17:16 +00:00
David Anderson
471053a054 .github/workflows: pin version of Ubuntu we run on
Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-12 01:17:16 +00:00
David Anderson
2a43fa4421 .github/workflows: use variant=race instead of race=true for race test
Github's matrix runner formats the race variant as '(amd64, true)' if we
use race=true. So, change the way the variable is defined so that it says
'(amd64, race)' even if that makes the if statements a bit more complex.

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-12 01:17:16 +00:00
David Anderson
9fc3d00c17 .github/workflows: add back forgotten android CI job
Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-12 01:17:16 +00:00
David Anderson
4022796484 .github/workflows: unify and matrixify all our CI steps
Instead of having a dozen files that contribute CI steps with
inconsistent configs, this one file lists out everything that,
for us, constitutes "a CI run". It also enables the slack
notification webhook to notify us exactly once on a mass breakage,
rather than once for every sub-job that fails.

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-12 01:17:16 +00:00
David Anderson
afe19d1d81 tool/go: don't use the names GOOS/GOARCH in script
The use of GOOS to mean "the compiler's host architecture" ends up
overriding whatever GOOS the user passed in, resulting in befuddling
errors like "unsupported GOOS/GOARCH pair linux/wasm" when the caller
requests js/wasm.

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-12 01:17:16 +00:00
Jenny Zhang
fe5558094c cmd/tailscale/cli: add logout and debug info to web
Fixes #7238

Signed-off-by: Jenny Zhang <jz@tailscale.com>
2023-02-12 00:06:36 +00:00
David Anderson
ea8b896c6c .github/workflows: remove 'ci skip' boilerplate
We've never used the "[ci skip]" magic commit header in our history,
across all our repos. This seems to be boilerplate we imported years
ago and have since been copying around our CI configs.

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-11 18:41:14 +00:00
License Updater
11fafdac8f licenses: update android licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2023-02-11 18:28:27 +00:00
Denton Gentry
01d58c9b61 scripts/installer.sh: add Mendel OS and OpenMandriva.
Fixes https://github.com/tailscale/tailscale/issues/6926
Fixes https://github.com/tailscale/tailscale/issues/7076

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2023-02-11 17:57:49 +00:00
David Anderson
bd81d520ab cmd/printdep: print correct toolchain URL
In the switch to static toolchains, we removed a legacy oddity from the
toolchain URL structure, but forgot to update printdep.

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-11 17:57:36 +00:00
David Anderson
b64d900f0f version: fix version output for "go run"
Before (note attempted use of absent date and commit hash):

"short": "1.37.0-dev",
"long": "1.37.0-dev-t",

After:

"short": "1.37.0-ERR-BuildInfo",
"long": "1.37.0-ERR-BuildInfo",

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-11 07:29:55 +00:00
David Anderson
70a2929a12 version: make all exported funcs compile-time constant or lazy
Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-11 07:29:55 +00:00
David Anderson
8b2ae47c31 version: unexport all vars, turn Short/Long into funcs
The other formerly exported values aren't used outside the package,
so just unexport them.

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-11 07:29:55 +00:00
David Anderson
9e6b4d7ad8 types/lazy: helpers for lazily computed values
Co-authored-by: Maisem Ali <maisem@tailscale.com>
Co-authored-by: Brad Fitzpatrick <bradfitz@tailscale.com>
Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-10 20:59:58 -08:00
Denton Gentry
5bca44d572 cmd/sync-containers: update latest and stable tags
Fixes https://github.com/tailscale/tailscale/issues/7251

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2023-02-10 20:47:18 -08:00
Mihai Parparita
fa932fefe7 net/interfaces: redo how we get the default interface on macOS and iOS
With #6566 we added an external mechanism for getting the default
interface, and used it on macOS and iOS (see tailscale/corp#8201).
The goal was to be able to get the default physical interface even when
using an exit node (in which case the routing table would say that the
Tailscale utun* interface is the default).

However, the external mechanism turns out to be unreliable in some
cases, e.g. when multiple cellular interfaces are present/toggled (I
have occasionally gotten my phone into a state where it reports the pdp_ip1
interface as the default, even though it can't actually route traffic).

It was observed that `ifconfig -v` on macOS reports an "effective interface"
for the Tailscale utn* interface, which seems promising. By examining
the ifconfig source code, it turns out that this is done via a
SIOCGIFDELEGATE ioctl syscall. Though this is a private API, it appears
to have been around for a long time (e.g. it's in the 10.13 xnu release
at https://opensource.apple.com/source/xnu/xnu-4570.41.2/bsd/net/if_types.h.auto.html)
and thus is unlikely to go away.

We can thus use this ioctl if the routing table says that a utun*
interface is the default, and go back to the simpler mechanism that
we had before #6566.

Updates #7184
Updates #7188

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-02-10 16:23:37 -08:00
Mihai Parparita
21fda7f670 net/routetable: include unknown flags in the routetable doctor output
As part of the work on #7248 I wanted to know all of the flags on the
RouteMessage struct that we get back from macOS. Though it doesn't turn
out to be useful (when using an exit node/Tailscale is the default route,
the flags for the physical interface routes are the same), it still seems
useful from a debugging/comprehensiveness perspective.

Adds additional Darwin flags that were output once I enabled this mode.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-02-10 15:54:31 -08:00
Mihai Parparita
7d204d89c2 ipn/ipnlocal: fix passthrough of formatting arguments in PeerAPI doctor output
Followup to #7235, we were not treating the formatting arguments as
variadic. This worked OK for single values, but stopped working when
we started passing multiple values (noticed while trying out #7244).

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-02-10 15:53:41 -08:00
David Anderson
9ad36d17a3 version: undo previous "optimization", do more work lazily
Commit 59c254579e moved a lot of work
from functions that could be eliminated at compile time (because
tests against runtime.GOOS are compile-time constant), into code
that must always run before main().

So, revert that, and instead optimize the package only by moving the
remaining string processing code behind sync.Onces.

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-10 15:27:14 -08:00
Tom DNetto
2ca6dd1f1d wgengine: start logging DISCO frames to pcap stream
Signed-off-by: Tom DNetto <tom@tailscale.com>
2023-02-10 11:22:34 -10:00
David Anderson
da75e49223 version: return correct Meta.MajorMinorPatch in non-dev builds
Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-10 13:00:44 -08:00
License Updater
78980a4ccf licenses: update win/apple licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2023-02-09 15:35:39 -08:00
Mihai Parparita
6799ef838f ipn/ipnlocal: add PeerAPI endpoint for doctor output
Useful when debugging issues (e.g. to see the full routing table), and
easier to refer to the output via a browser than trying to read it from
the logs generated by `bugreport --diagnose`.

Behind a canDebug() check, similar to the /magicsock and /interfaces
endpoints.

Updates #7184

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-02-09 15:09:56 -08:00
Brad Fitzpatrick
9e4d99305b go.toolchain.rev: bump Go toolchain
For tailscale/go#55 experimentation in another repo primarily,
but this is our source of truth, so we bump here.

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-02-09 15:07:55 -08:00
David Anderson
0e4f2bdd0c pull-toolchain.sh: don't run update-flake.sh
We no longer carry an SRI hash for the toolchain, so flake
updating is no longer needed for toolchain changes.

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-09 15:04:01 -08:00
David Anderson
33f29a1532 go.toolchain.rev: update toolchain to test iOS Go fix
Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-09 12:59:51 -08:00
Andrew Dunham
ba48ec5e39 util/linuxfw: initial implementation of package
This package is an initial implementation of something that can read
netfilter and iptables rules from the Linux kernel without needing to
shell out to an external utility; it speaks directly to the kernel using
syscalls and parses the data returned.

Currently this is read-only since it only knows how to parse a subset of
the available data.

Signed-off-by: Andrew Dunham <andrew@tailscale.com>
Change-Id: Iccadf5dcc081b73268d8ccf8884c24eb6a6f1ff5
2023-02-09 14:20:24 -05:00
Colin Adler
3c107ff301 net/connstats: fix ticker in NewStatistics (#7225)
`:=` was accidentally used, so `maxPeriod` never worked.

Signed-off-by: Colin Adler <colin1adler@gmail.com>
2023-02-09 01:24:52 -08:00
Will Norris
6ef834a6b7 get-authkey: require tags to be specified
Tailnet-owned auth keys (which all OAuth-created keys are) must include tags, since there is no user to own the registered devices.

Signed-off-by: Will Norris <will@tailscale.com>
2023-02-08 17:12:47 -08:00
Maisem Ali
89bd414be6 ipn/ipnstate: update field docs on PeerStatus.
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-02-08 15:23:05 -08:00
Mihai Parparita
2f4df30c75 .github/workflows: re-enable CIFuzz job
Having an empty `on` spec results in the job still running, but it
immediately fails with a "No jobs were run" message.

Go back to the original `on: [pull_request]` spec, and disable the
workflow in the GitHub UI instead.

This reverts commit f7b3156f16.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-02-08 13:51:14 -08:00
Mihai Parparita
62f4df3257 net/interfaces, net/netns: add node attributes to control default interface getting and binding
With #6566 we started to more aggressively bind to the default interface
on Darwin. We are seeing some reports of the wrong cellular interface
being chosen on iOS. To help with the investigation, this adds to knobs
to control the behavior changes:
- CapabilityDebugDisableAlternateDefaultRouteInterface disables the
  alternate function that we use to get the default interface on macOS
  and iOS (implemented in tailscale/corp#8201). We still log what it
  would have returned so we can see if it gets things wrong.
- CapabilityDebugDisableBindConnToInterface is a bigger hammer that
  disables binding of connections to the default interface altogether.

Updates #7184
Updates #7188

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-02-08 13:15:10 -08:00
Brad Fitzpatrick
fb84ccd82d control/controlhttp: don't require valid TLS cert for Noise connection
We don't require any cert at all for Noise-over-plaintext-port-80-HTTP,
so why require a valid cert chain for Noise-over-HTTPS? The reason we use
HTTPS at all is to get through firewalls that allow tcp/443 but not tcp/80,
not because we need the security properties of TLS.

Updates #3198

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-02-08 12:47:01 -08:00
Brad Fitzpatrick
2477fc4952 net/netutil: only check Linux sysctls w/ procfs, assume absent means false
Fixes #7217

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-02-08 12:23:36 -08:00
Maisem Ali
05adf22383 cmd/k8s-operator: add support for running an auth proxy
Updates #5055

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-02-08 11:45:10 -08:00
Mihai Parparita
31e2e9a300 ipn: remove unused NLKeyStateKey constant
We stopped writing network lock keys as separate items with #6315,
the constant is no longer used.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-02-08 11:19:28 -08:00
Mihai Parparita
f0f2b2e22b logtail: increase maximum log line size in low memory mode
The 255 byte limit was chosen more than 3 years ago (tailscale/corp@929635c9d9),
when iOS was operating under much more significant memory constraints.
With iOS 15 the network extension has an increased limit, so increasing
it to 4K should be fine.

The motivating factor was that the network interfaces being logged
by linkChange in wgengine/userspace.go were getting truncated, and it
would be useful to know why in some cases we're choosing the pdp_ip1
cell interface instead of the pdp_ip0 one.

Updates #7184
Updates #7188

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-02-07 22:00:14 -08:00
M. J. Fromberger
9be47f789c ipn/ipnlocal: fix the path for writing cert files (#7203)
Fixes #7202.

Change-Id: I1f8e9c59d5e42e7df7a3fbbd82ae2b4293845916
Signed-off-by: M. J. Fromberger <fromberger@tailscale.com>
2023-02-07 14:34:04 -08:00
Andrew Dunham
cab2b2b59e ipn/localapi: print envknobs on bugreport
Previously, we only printed these at startup; print those when the user
generates a bugreport as we so we don't have to go spelunking through
the logs.

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: If5b0970f09fcb4cf8839958af5d37f84e0ba6ed2
2023-02-07 11:59:32 -05:00
David Anderson
59c254579e version: unify and optimize the various not-version funcs
Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-06 22:24:14 -08:00
Maisem Ali
0fd2f71a1e ipn/ipnlocal: use presence of NodeID to identify logins
The profileManager was using the LoginName as a proxy to figure out if the profile
had logged in, however the LoginName is not present if the node was created with an
Auth Key that does not have an associated user.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-02-06 21:52:35 -08:00
Maisem Ali
2a094181df .github/workflows: use ./tool/go in go mod tidy
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-02-06 21:34:07 -08:00
Andrew Dunham
6d84f3409b ipn/ipnlocal: handle more edge cases in netmap expiry timer
We now handle the case where the NetworkMap.SelfNode has already expired
and do not return an expiry time in the past (which causes an ~infinite
loop of timers to fire).

Additionally, we now add an explicit check to ensure that the next
expiry time is never before the current local-to-the-system time, to
ensure that we don't end up in a similar situation due to clock skew.

Finally, we add more tests for this logic to ensure that we don't
regress on these edge cases.

Fixes #7193

Change-Id: Iaf8e3d83be1d133a7aab7f8d62939e508cc53f9c
Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
2023-02-06 20:32:25 -05:00
Tom DNetto
99b9d7a621 all: implement pcap streaming for datapath debugging
Updates: tailscale/corp#8470

Signed-off-by: Tom DNetto <tom@tailscale.com>
2023-02-04 15:54:20 -10:00
David Anderson
1acdcff63e go.toolchain.rev: update toolchain to test ios workaround
Updates tailscale/corp#9061

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-04 15:10:42 -08:00
Denton Gentry
4daba23cd4 cmd/get-authkey: add an OAuth API client to produce an authkey
Updates https://github.com/tailscale/tailscale/issues/3243

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2023-02-03 22:52:54 -08:00
Maisem Ali
6bae55e351 ipn/ipnlocal: add support to store certs in k8s secrets
Fixes #5676

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-02-03 19:12:21 -08:00
Mihai Parparita
0e3fb91a39 net/dns/resolver: remove maxDoHInFlight
It was originally added to control memory use on iOS (#2490), but then
was relaxed conditionally when running on iOS 15 (#3098). Now that we
require iOS 15, there's no need for the limit at all, so simplify back
to the original state.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-02-03 17:07:12 -08:00
Mihai Parparita
b6908181ff net/tshttpproxy: more directly use Transport proxy CONNECT hooks
GetProxyConnectHeader (golang/go#41048) was upstreamed in Go 1.16 and
OnProxyConnectResponse (golang/go#54299) in Go 1.20, thus we no longer
need to guard their use by the tailscale_go build tag.

Updates #7123

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-02-03 16:51:50 -08:00
License Updater
0e1403ec39 licenses: update win/apple licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2023-02-03 11:29:04 -08:00
David Crawshaw
8cf2805cca tailcfg, localapi: plumb device token to server
Updates tailscale/corp#8940

Signed-off-by: David Crawshaw <crawshaw@tailscale.com>
2023-02-03 10:28:11 -08:00
Brad Fitzpatrick
38b32be926 tailcfg: add wire fields/docs for resuming streaming map sessions
No implementation yet.

Updates #7175

Change-Id: Id242d47cdd83afe4d254c8c5826f058fe39c8bfd
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-02-03 09:59:30 -08:00
Andrew Dunham
880a41bfcc net/dns/resolver: add envknob to debug exit node DNS queries on on Windows
Add the envknob TS_DEBUG_EXIT_NODE_DNS_NET_PKG, which enables more
verbose debug logging when calling the handleExitNodeDNSQueryWithNetPkg
function. This function is currently only called on Windows and Android.

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: Ieb3ca7b98837d7dc69cd9ca47609c1c52e3afd7b
2023-02-03 12:09:00 -05:00
Andrew Dunham
d2301db49c ipn/localapi: print node IDs, pubkeys, and expiry on bugreport
Having this information near the "user bugreport" line makes it easier
to identify the node and expiry without spelunking through the rest of
the logs.

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I1597c783efc06574fa4c8f211e68d835f20b6ccb
2023-02-03 11:44:39 -05:00
License Updater
0aa7b495d5 licenses: update win/apple licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2023-02-02 21:19:33 -08:00
David Anderson
02a2dcfc86 go.toolchain.rev: use new statically built toolchain
Also removes the toolchain builds from flake.nix. For now the flake
build uses upstream Go 1.20, a followup change will switch it back to
our custom toolchain.

Updates tailscale/corp#9005

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-02-02 20:44:12 -08:00
Andrew Dunham
2dc3dc21a8 util/multierr: implement Go 1.20+'s multiple error Unwrap
Now that Go 1.20 is released, multierr.Error can implement
Unwrap() []error

Updates #7123

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: Ic28c2579de6799801836c447afbca8cdcba732cf
2023-02-02 14:03:51 -05:00
Andrew Dunham
5ba2543828 ipn/ipnlocal: print warning about DNS servers in bugreport --diagnose
If the user passes the --diagnose flag, print a warning if any of the
default or fallback DNS resolvers are Tailscale IPs. This can interfere
with the ability to connect to the controlplane, and is typically
something to pay attention to if there's a connectivity issue.

Change-Id: Ib14bf6228c037877fbdcd22b069212b1a4b2c456
Signed-off-by: Andrew Dunham <andrew@tailscale.com>
2023-02-02 13:09:05 -05:00
License Updater
c4eb857405 licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2023-02-02 07:51:07 -08:00
Brad Fitzpatrick
03645f0c27 net/{netns,netstat}: use new x/sys/cpu.IsBigEndian
See golang/go#57237

Change-Id: If47ab6de7c1610998a5808e945c4177c561eab45
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-02-02 07:41:49 -08:00
Andrew Dunham
2755f3843c health, net/tlsdial: add healthcheck for self-signed cert
When we make a connection to a server, we previously would verify with
the system roots, and then fall back to verifying with our baked-in
Let's Encrypt root if the system root cert verification failed.

We now explicitly check for, and log a health error on, self-signed
certificates. Additionally, we now always verify against our baked-in
Let's Encrypt root certificate and log an error if that isn't
successful. We don't consider this a health failure, since if we ever
change our server certificate issuer in the future older non-updated
versions of Tailscale will no longer be healthy despite being able to
connect.

Updates #3198

Change-Id: I00be5ceb8afee544ee795e3c7a2815476abc4abf
Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
2023-02-01 23:17:41 -05:00
Andrew Dunham
7393ce5e4f wgengine/magicsock: add envknob to print information about port selection
To aid in debugging where a customer has static port-forwards set up and
there are issues establishing a connection through that port.

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: Ic5558bcdb40c9119b83f79dcacf2233b07777f2a
2023-02-01 22:44:22 -05:00
Brad Fitzpatrick
cf8dd7aa09 all: use Go 1.20's bytes.Clone
Updates #7123
Updates #6257 (more to do in other repos)

Change-Id: I073e2a6d81a5d7fbecc29caddb7e057ff65239d0
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-02-01 17:39:18 -08:00
Brad Fitzpatrick
f7b3156f16 .github/workflows: delete CIFuzz job
It doesn't yet support Go 1.20. We can bring it back later.

Updates #7123

Change-Id: I6c4a4090e910d06f34c3f4d612e737989fe85812
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-02-01 17:39:04 -08:00
Brad Fitzpatrick
b1248442c3 all: update to Go 1.20, use strings.CutPrefix/Suffix instead of our fork
Updates #7123
Updates #5309

Change-Id: I90bcd87a2fb85a91834a0dd4be6e03db08438672
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-02-01 15:23:54 -08:00
Brad Fitzpatrick
623176ebc9 go.toolchain.branch: update to Go 1.20
Updates #7123

Change-Id: I64f6d8de5bb511a23318118b4ea1146247f1ad7c
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-02-01 15:14:05 -08:00
Will Norris
10085063fb util/vizerror: add As function to get wrapped Error
Signed-off-by: Will Norris <will@tailscale.com>
2023-02-01 14:39:13 -08:00
Will Norris
51e1ab5560 fixup! util/vizerror: add new package for visible errors
Signed-off-by: Will Norris <will@tailscale.com>
2023-02-01 12:04:04 -08:00
Will Norris
648aa00a28 fixup! util/vizerror: add new package for visible errors
Signed-off-by: Will Norris <will@tailscale.com>
2023-02-01 12:04:04 -08:00
Will Norris
a6c6979b85 fixup! util/vizerror: add new package for visible errors
Signed-off-by: Will Norris <will@tailscale.com>
2023-02-01 12:04:04 -08:00
Will Norris
598ec463bc fixup! util/vizerror: add new package for visible errors
Signed-off-by: Will Norris <will@tailscale.com>
2023-02-01 12:04:04 -08:00
Will Norris
8e6a1ab175 util/vizerror: add new package for visible errors
Signed-off-by: Will Norris <will@tailscale.com>
2023-02-01 12:04:04 -08:00
Brad Fitzpatrick
27d146d4f8 .github/ISSUE_TEMPLATE: add link to wiki/OtherSoftwareInterop
Add question about https://github.com/tailscale/tailscale/wiki/OtherSoftwareInterop
in the issue template.

Change-Id: I6ca374654e9f67be9cb447bb5d5f66a9087fd945
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-02-01 11:44:13 -08:00
Brad Fitzpatrick
ca45fe2d46 cmd/tailscale/cli: delete ActLikeCLI
It's since been rewritten in Swift.

 #cleanup

Change-Id: I0860d681e8728697804ce565f63c5613b8b1088c
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-02-01 09:37:31 -08:00
shayne
30e0156430 nix: update nixpkgs flake, override go_1_20 for tailscale_go (#7139)
Bleeding edge Tailscale Nix flake broke after updating to go1.20rc3.

Go 1.20 moved to Go 1.17 as a bootstarp toolchain. Fortunately nixpkgs
nixos-unstable already had a 1.20.nix with bootstrap117.nix.

```
❯ ./result/bin/tailscale version
1.37.0-dev
  track: unstable (dev); frequent updates and bugs are likely
  go version: go1.20rc3-ts6a17f14c05
```

Signed-off-by: Shayne Sweeney <shayne@tailscale.com>
2023-02-01 12:27:04 -05:00
David Anderson
f8fc3db59c flake.nix: update SRI hash.
Signed-off-by: David Anderson <danderson@tailscale.com>
2023-01-31 22:58:09 -08:00
David Crawshaw
4136f27f35 ipn/localapi: fix validHost parsing logic
Signed-off-by: David Crawshaw <crawshaw@tailscale.com>
2023-01-31 15:04:51 -08:00
Mihai Parparita
0039993359 cmd/tsconnect: update to xterm.js 5.1
It includes xtermjs/xterm.js#4216, which improves handling of some
escape sequences. Unfortunately it's not enough to fix the issue
with `ponysay`, but it does not hurt to be up to date.

Updates #6090

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-01-31 13:07:28 -08:00
License Updater
d560a4697a licenses: update win/apple licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2023-01-31 13:06:29 -08:00
Andrew Dunham
d1146dc701 ipn/ipnlocal: rate-limit diagnose logs in bugreport
We can log too quickly for logtail to catch up, even when we opt out of
log rate-limiting. When the user passes the --diagnose flag to
bugreport, we use a token bucket to control how many logs per second are
printed and sleep until we're able to write more.

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: If27672d66b621b589280bd0fe228de367ffcbd8f
2023-01-31 14:29:21 -05:00
M. J. Fromberger
3eae75b1b8 ci: make gofmt check fail for a non-empty diff (#7131)
Fixes #7130.

Change-Id: If47eb472ea98a8d8b250c5c681c7862d252645fb
Signed-off-by: M. J. Fromberger <fromberger@tailscale.com>
2023-01-31 11:16:39 -08:00
Anton Tolchanov
100d8e909e cmd/derpprobe: migrate to the prober framework
`prober.DERP` was created in #5988 based on derpprobe. Having used it
instead of derpprobe for a few months, I think we have enough confidence
that it works and can now migrate derpprobe to use the prober framework
and get rid of code duplication.

A few notable changes in behaviour:
- results of STUN probes over IPv4 and IPv6 are now reported separately;
- TLS probing now includes OCSP verification;
- probe names in the output have changed;
- ability to send Slack notification from the prober has been removed.
  Instead, the prober now exports metrics in Expvar (/debug/vars) and
  Prometheus (/debug/varz) formats.

Fixes https://github.com/tailscale/corp/issues/8497

Signed-off-by: Anton Tolchanov <anton@tailscale.com>
2023-01-31 10:47:42 +00:00
Nick Kirby
fac1632ed9 Update CodeQL action to v2
There's an error in the `Perform CodeQL Analysis` step saying to upgrade to v2 as v1 was deprecated on 18th January.

Signed-off-by: Nick Kirby <nrkirb@gmail.com>
2023-01-30 22:54:05 -08:00
Jordan Whited
39e52c4b0a wgengine/magicsock: fix de-dup disco ping handling for netmap endpoints (#7118)
Fixes #7116

Signed-off-by: Jordan Whited <jordan@tailscale.com>
2023-01-30 22:38:20 -08:00
Brad Fitzpatrick
01e736e1d5 go.toolchain.rev: update to Go 1.20rc3
Updates #7123

Change-Id: Ibdf53530251c120e7e20c24abcf4a05f2ff7ac97
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-01-30 21:55:13 -08:00
Maisem Ali
04b57a371e ipn/ipnlocal: drop not required StateKey parameter
This is #cleanup now that #7121 is merged.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-01-30 17:58:55 -08:00
Mihai Parparita
73d33e3f20 cmd/tsconnect: use empty string as the default state store key
Makes the Wasm client more similar to the others, and allows the default
profile to be correctly picked up when restarting the client in dev
mode (where we persist the state in sessionStorage).

Also update README to reflect that Go wasm changes can be picked up
with just a reload (as of #5383)

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-01-30 17:18:41 -08:00
Maisem Ali
5bba65e978 net/memnet: rename from net/nettest
This is just #cleanup to resolve a TODO

Also add a package doc.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-01-30 13:03:32 -08:00
Maisem Ali
4441609d8f safesocket: remove the now unused WindowsLocalPort
Also drop the port param from safesocket.Listen. #cleanup

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2023-01-30 10:33:02 -08:00
David Anderson
fede3cd704 flake.nix: update SRI hash for Go modules.
Signed-off-by: David Anderson <danderson@tailscale.com>
2023-01-28 22:00:52 -08:00
David Anderson
e51cf1b09d cmd/k8s-operator: use unstable tailscale image as well
We need a post-1.36 tailscale image to handle custom hostnames correctly.

Updates #502

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-01-27 21:34:28 -08:00
Jordan Whited
7921198c05 wgengine/magicsock: de-dup disco pings (#7093)
Fixes #7078

Signed-off-by: Jordan Whited <jordan@tailscale.com>
2023-01-27 21:04:32 -08:00
David Anderson
0dc9cbc9ab cmd/k8s-operator: use the unstable operator image
There is no stable release yet, and for alpha we want people on the
unstable build while we iterate.

Updates #502

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-01-27 19:05:09 -08:00
David Anderson
4950e6117e build_docker.sh: use docker hub for base image hosting.
Signed-off-by: David Anderson <danderson@tailscale.com>
2023-01-27 18:33:05 -08:00
David Anderson
969b9ed91f build_docker.sh: set good repo defaults based on the target.
Signed-off-by: David Anderson <danderson@tailscale.com>
2023-01-27 17:39:19 -08:00
License Updater
5242e0f291 licenses: update win/apple licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2023-01-27 17:35:18 -08:00
David Anderson
f991288ceb build_docker.sh: don't push to ghcr by default.
Signed-off-by: David Anderson <danderson@tailscale.com>
2023-01-27 16:36:12 -08:00
Mihai Parparita
4973956419 ipn/ipnlocal: add /reset-auth LocalAPI endpoint
The iOS has a command to reset the persisted state of the app, but it
was doing its own direct keychain manipulation. This proved to be
brittle (since we changed how preferences are stored with #6022), so
we instead add a LocalAPI endpoint to do do this, which can be updated
in tandem.

This clears the same state as the iOS implementation (tailscale/corp#3186),
that is the machine key and preferences (which includes the node key).
Notably this does not clear the logtail ID, so that logs from the device
still end up in the same place.

Updates tailscale/corp#8923

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-01-27 16:32:35 -08:00
Will Norris
947c14793a all: update tools that manage copyright headers
Update all code generation tools, and those that check for license
headers to use the new standard header.

Also update copyright statement in LICENSE file.

Fixes #6865

Signed-off-by: Will Norris <will@tailscale.com>
2023-01-27 15:36:29 -08:00
Will Norris
71029cea2d all: update copyright and license headers
This updates all source files to use a new standard header for copyright
and license declaration.  Notably, copyright no longer includes a date,
and we now use the standard SPDX-License-Identifier header.

This commit was done almost entirely mechanically with perl, and then
some minimal manual fixes.

Updates #6865

Signed-off-by: Will Norris <will@tailscale.com>
2023-01-27 15:36:29 -08:00
Walter Poupore
11f7f7d4a0 docs/k8s: Use TS_AUTHKEY instead of TS_AUTH_KEY (#7092)
Updates https://github.com/tailscale/tailscale-www/issues/2199.

Signed-off-by: Walter Poupore <walterp@tailscale.com>
2023-01-27 15:05:03 -08:00
Andrew Dunham
50da265608 net/netns: add post-review comments
Follow-up to #7065 with some comments from Brad's review.

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: Ia1219f4fa25479b2dada38ffe421065b408c5954
2023-01-27 17:25:03 -05:00
Brad Fitzpatrick
2fc8de485c net/netstat: document the Windows netstat code a bit more
And defensively bound allocation.

Updates tailscale/corp#8878

Change-Id: Iaa07479ea2ea28ee1ac3326ab025046d6d785b00
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-01-27 10:12:04 -08:00
Mihai Parparita
8c20da2568 util/httpm: add another HTTP method
Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-01-27 10:07:18 -08:00
Aaron Klotz
4a869048bf net/netstat: add nil checks to Windows OSMetadata implementation
The API documentation does claim to output empty strings under certain
conditions, but we're sometimes seeing nil pointers in the wild, not empty
strings.

Fixes https://github.com/tailscale/corp/issues/8878

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2023-01-27 09:41:48 -07:00
License Updater
8c03a31d10 licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2023-01-27 07:50:22 -08:00
Brad Fitzpatrick
0d794a10ff go.mod: bump wintun-go
For https://git.zx2c4.com/wintun-go/commit/?id=0fa3db229ce2036ae779de8ba03d336b7aa826bd

Updates #6647

Change-Id: I1686b2c77df331fcb9fa4fae88e08232bb95f10b
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-01-27 07:29:35 -08:00
Brad Fitzpatrick
a1b4ab34e6 util/httpm: add new package for prettier HTTP method constants
See package doc.

Change-Id: Ibbfc8e1f98294217c56f3a9452bd93ffa3103572
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-01-26 19:44:07 -08:00
Andrew Dunham
2703d6916f net/netns: add functionality to bind outgoing sockets based on route table
When turned on via environment variable (off by default), this will use
the BSD routing APIs to query what interface index a socket should be
bound to, rather than binding to the default interface in all cases.

Updates #5719
Updates #5940

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: Ib4c919471f377b7a08cd3413f8e8caacb29fee0b
2023-01-26 20:58:58 -05:00
Denton Gentry
7439bc7ba6 cmd/sync-containers: add github.Keychain
Running sync-containers in a GitHub workflow will be
simpler if we check github.Keychain, which uses the
GITHUB_TOKEN if present.

Updates https://github.com/tailscale/corp/issues/8461

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2023-01-25 19:55:15 -08:00
David Anderson
9bd6a2fb8d cmd/k8s-operator: support setting a custom hostname.
Updates #502

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-01-25 15:38:48 -08:00
Kris Brandow
d5cb016cef tailcfg: add caps and SSH action for SSH hauling
Add capabilities and an SSH action for SSH session hauling.

Updates #7069

Signed-off-by: Kris Brandow <kris@tailscale.com>
2023-01-25 17:41:45 -05:00
shayne
6f992909f0 hostinfo: [windows] check if running via Scoop (#7068)
You can now install Tailscale on Windows via [Scoop](https://scoop.sh).

This change adds a check to `packageTypeWindows()`, looking at the exe's path, and
checking if it starts with: `C:\User\<NAME>\scoop\apps\tailscale`. If so, it
returns `"scoop"` as the package type.

Fixes: #6988

Signed-off-by: Shayne Sweeney <shayne@tailscale.com>
2023-01-25 16:58:23 -05:00
Xe Iaso
038d25bd04 cmd/nginx-auth: update Expected-Tailnet documentation (#6055)
Signed-off-by: Xe Iaso <xe@tailscale.com>
2023-01-25 13:47:19 -05:00
phirework
2d29f77b24 cmd/tailscale/cli: fix TUNmode display on synology web page (#7064)
Fixes #7059

Signed-off-by: Jenny Zhang <jz@tailscale.com>

Signed-off-by: Jenny Zhang <jz@tailscale.com>
2023-01-25 13:22:19 -05:00
License Updater
2adbb48632 licenses: update android licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2023-01-24 20:26:21 -08:00
Denton Gentry
9af7e8a0ff VERSION.txt: this is 1.37
Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2023-01-24 15:32:02 -08:00
Andrew Dunham
44d73ce932 ipn/ipnlocal, net/dnscache: allow configuring dnscache logging via capability
This allows users to temporarily enable/disable dnscache logging via a
new node capability, to aid in debugging strange connectivity issues.

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I46cf2596a8ae4c1913880a78d0033f8b668edc08
2023-01-24 17:21:43 -05:00
Brad Fitzpatrick
d8feeeee4c wgengine/magicsock: fix buggy fast path in Conn.SetNetworkMap
Spotted by Maisem.

Fixes #6680

Change-Id: I5fdc01de8b006a1c43a2a4848f69397f54b4453a
Co-authored-By: Maisem Ali <maisem@tailscale.com>
Co-authored-By: Andrew Dunham <andrew@tailscale.com>
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-01-24 14:19:15 -08:00
Vince Prignano
30380403d0 cmd/k8s-operator: remove use of InjectClient (deprecated)
The dependency injection functionality has been deprecated a while back
and it'll be removed in the 0.15 release of Controller Runtime. This
changeset sets the Client after creating the Manager, instead of using
InjectClient.

Signed-off-by: Vince Prignano <vince@prigna.com>
2023-01-24 09:11:45 -08:00
Anton Tolchanov
b49aa6ac31 scripts: explicitly install tailscale-archive-keyring
This will ensure that the `tailscale-archive-keyring` Debian package
gets installed by the installer script.

Updates #3151

Signed-off-by: Anton Tolchanov <anton@tailscale.com>
2023-01-24 17:05:23 +00:00
Anton Tolchanov
586a88c710 hostinfo: add an environment type for Replit
Signed-off-by: Anton Tolchanov <anton@tailscale.com>
2023-01-24 14:43:06 +00:00
Anton Tolchanov
e8b695626e cmd/mkpkg: allow specifying recommended dependencies
Updates #3151

Signed-off-by: Anton Tolchanov <anton@tailscale.com>
2023-01-24 12:43:24 +00:00
Harry Bowron
c1daa42c24 client/tailscale/keys: fix client.Keys unmarshalling
Signed-off-by: Author Name hbowron@gmail.com
Signed-off-by: Harry Bowron <harry@bolt.com>

Fixes #7020
2023-01-24 12:01:47 +00:00
Brad Fitzpatrick
6e5faff51e ipn/ipnlocal: add health warning for Tailscale SSH + SELinux
Updates #4908

Change-Id: If46be5045b13dd5c3068c334642f89b5917ec861
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-01-23 20:12:46 -08:00
Brad Fitzpatrick
c8db70fd73 cmd/tailscale/cli: add debug set-expire command for testing
Updates tailscale/corp#8811
Updates tailscale/corp#8613

Change-Id: I1c87806ca3ccc5c43e7ddbd6b4d521f73f7d29f1
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-01-23 19:12:26 -08:00
Andrew Dunham
140b9aad5c ipn/ipnlocal: fire expiry timer when the current node expires
The current node isn't in NetMap.Peers, so without this we would not
have fired this timer on self expiry.

Updates #6932

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: Id57f96985397e372f9226802d63b42ff92c95093
2023-01-23 20:23:11 -05:00
James Tucker
e002260b62 wgengine/wglog: add a prefix for all wireguard logs
Fixes #7041

Signed-off-by: James Tucker <james@tailscale.com>
2023-01-23 16:38:10 -08:00
Brad Fitzpatrick
06fff461dc ipn/ipnstate: add PeerStatus.KeyExpiry for tailscale status --json
Fixes #6712

Change-Id: I817cd5342fac8a956fcefda2d63158fa488f3395
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-01-23 12:45:09 -08:00
Brad Fitzpatrick
b6aa1c1f22 envknob, hostinfo, ipn/ipnlocal: add start of opt-in remote update support
Updates #6907

Change-Id: I85db4f6f831dd5ff7a9ef4bfa25902607e0c1558
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-01-23 12:12:42 -08:00
Andrew Dunham
b74db24149 tstest/integration: mark all integration tests as flaky
Updates #7036

Change-Id: I3aec5ad680078199ba984bf8afc20b2f2eb37257
Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
2023-01-23 14:36:16 -05:00
License Updater
65c9ce5a1b licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2023-01-23 10:32:34 -08:00
Brad Fitzpatrick
64547b2b86 tailcfg,hostinfo: add Hostinfo.Machine and Hostinfo.GoArchVar
For detecting a non-ideal binary running on the current CPU.

And for helping detect the best Synology package to update to.

Updates #6995

Change-Id: I722f806675b60ce95364471b11c388150c0d4aea
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-01-22 14:13:56 -08:00
Brad Fitzpatrick
fd92fbd69e cmd/tailscale/cli: only give systemctl hint on systemd systems
Per recent user confusion on a QNAP issue.

Change-Id: Ibda00013df793fb831f4088b40be8a04dfad17c2
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-01-21 13:19:54 -08:00
Brad Fitzpatrick
d5100e0910 net/connstats: mark TestConcurrent as flaky
Updates #7030

Change-Id: Ic46da5e5690b90b95028a68a3cf967ad86881e28
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-01-21 11:04:31 -08:00
Brad Fitzpatrick
ba5aa2c486 version, cmd/tailscale: add version.Meta, tailscale version --json
Add `tailscale version --json` JSON output mode. This will be used
later for a double-opt-in (per node consent like Tailscale SSH +
control config) to let admins do remote upgrades via `tailscale
update` via a c2n call, which would then need to verify the
cmd/tailscale found on disk for running tailscale update corresponds
to the running tailscaled, refusing if anything looks amiss.

Plus JSON output modes are just nice to have, rather than parsing
unstable/fragile/obscure text formats.

Updates #6995
Updates #6907

Change-Id: I7821ab7fbea4612f4b9b7bdc1be1ad1095aca71b
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-01-20 21:04:30 -08:00
Brad Fitzpatrick
5ca22a0068 cmd/tailscale/cli: make 'tailscale update' support Debian/Ubuntu apt
Updates #6995

Change-Id: I3355435db583755e0fc73d76347f6423b8939dfb
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-01-20 13:22:19 -08:00
shayne
4471e403aa ipn/ipnlocal: [serve] listen on all-interfaces for macOS sandboxed (#6771)
On macOS (AppStore and macsys), we need to bind to ""/all-interfaces
due to the network sandbox. Ideally we would only bind to the
Tailscale interface, but macOS errors out if we try to
to listen on privileged ports binding only to a specific
interface.

We also implement the lc.Control hook, same as we do for
peerapi. It doesn't solve our problem but it's better that
we do and would likely be required when Apple gets around to
fixing per-interface priviliged port binding.

Fixes: #6364

Signed-off-by: Shayne Sweeney <shayne@tailscale.com>
2023-01-20 13:40:56 -05:00
Brad Fitzpatrick
6793685bba go.mod: bump AWS SDK past a breaking API change of theirs
They changed a type in their SDK which meant others using the AWS APIs
in their Go programs (with newer AWS modules in their caller go.mod)
and then depending on Tailscale (for e.g. tsnet) then couldn't compile
ipn/store/awsstore.

Thanks to @thisisaaronland for bringing this up.

Fixes #7019

Change-Id: I8d2919183dabd6045a96120bb52940a9bb27193b
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-01-20 10:14:56 -08:00
shayne
73399f784b cmd/tailscale/cli: use mock impl of LocalClient for serve cmd (#6422)
Create an interface and mock implementation of tailscale.LocalClient for
serve command tests.

Updates #6304
Closes #6372

Signed-off-by: Shayne Sweeney <shayne@tailscale.com>
2023-01-20 12:36:25 -05:00
Jordan Whited
fec888581a wgengine/magicsock: retry failed single packet ops across rebinds (#6990)
The single packet WriteTo() through RebindingUDPConn.WriteBatch() was
not checking for a rebind between loading the PacketConn and writing to
it. Same with ReadFrom()/ReadBatch().

Fixes #6989

Signed-off-by: Jordan Whited <jordan@tailscale.com>
2023-01-20 09:15:32 -08:00
Brad Fitzpatrick
6edf357b96 all: start groundwork for using capver for localapi & peerapi
Updates #7015

Change-Id: I3d4c11b42a727a62eaac3262a879f29bb4ce82dd
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-01-19 14:53:47 -08:00
Brad Fitzpatrick
c129bf1da1 cmd/tailscale/cli: un-alpha login+switch in ShortUsage docs
Change-Id: I580d4417cf03833dfa8f6a295fb416faa667c477
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-01-19 11:59:27 -08:00
Brad Fitzpatrick
71a7b8581d cmd/tailscale/cli: make "update" work on Windows
Updates #6995

Co-authored-by: Aaron Klotz <aaron@tailscale.com>
Change-Id: I16622f43156a70b6fbc8205239fd489d7378d57b
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-01-19 10:02:19 -08:00
Andrew Dunham
4fb663fbd2 various: mark more tests as flaky
Updates #2855
Updates #3598
Updates #7008

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I2b849e04646456b9f0c8a01563f2add752f4b2a4
2023-01-19 10:17:43 -05:00
Andrew Dunham
58ad21b252 wgengine/netstack: fix data race in tests
This uses the helper function added in #6173 to avoid flakes like:
    https://github.com/tailscale/tailscale/actions/runs/3826912237/jobs/6511078024

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: If3f1d3b9c0f64ffcb4ba9a30d3522ec49484f993
2023-01-19 10:17:34 -05:00
Andrew Dunham
dd7057682c tailcfg: bump capver for Node.Expired
Updates #6932

Change-Id: I96c2467fa49201eb3d8df5cb36486370f598928c
Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
2023-01-18 13:17:55 -08:00
Andrew Dunham
aea251d42a cmd/testwrapper: move from corp; mark magicsock test as flaky
Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: Ibab5860f5797b3db151d3c27855333e43a9088a4
2023-01-18 12:08:23 -05:00
Brad Fitzpatrick
2df38b1feb wgengine/magicsock: quiet log flood at tailscaled shutdown
When you hit control-C on a tailscaled (notably in dev mode, but
also on any systemctl stop/restart), there is a flood of messages like:

magicsock: doing cleanup for discovery key d:aa9c92321db0807f
magicsock: doing cleanup for discovery key d:bb0f16aacadbfd46
magicsock: doing cleanup for discovery key d:b5b2d386296536f2
magicsock: doing cleanup for discovery key d:3b640649f6796c91
magicsock: doing cleanup for discovery key d:71d7b1afbcce52cd
magicsock: doing cleanup for discovery key d:315b61d7e0111377
magicsock: doing cleanup for discovery key d:9301f63dce69bf45
magicsock: doing cleanup for discovery key d:376141884d6fe072
....

It can be hundreds or even tens of thousands.

So don't do that. Not a useful log message during shutdown.

Change-Id: I029a8510741023f740877df28adff778246c18e5
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-01-17 19:05:59 -08:00
Brad Fitzpatrick
3addcacfe9 net/dns: fix recently added URL scheme from http to https
I typoed/brainoed in the earlier 3582628691

Change-Id: Ic198a6f9911f195d9da9fc5259b5784a4b15e5e3
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-01-17 18:50:04 -08:00
salman
eec734a578 ipn/{ipnlocal,localapi}: ensure watcher is installed before /watch-ipn-bus/ responds with 200
This change delays the first flush in the /watch-ipn-bus/ handler
until after the watcher has been successfully installed on the IPN
bus. It does this by adding a new onWatchAdded callback to
LocalBackend.WatchNotifications().

Without this, the endpoint returns a 200 almost immediatly, and
only then installs a watcher for IPN events.  This means there's a
small window where events could be missed by clients after calling
WatchIPNBus().

Fixes tailscale/corp#8594.

Signed-off-by: salman <salman@tailscale.com>
2023-01-17 22:59:39 +00:00
Brad Fitzpatrick
3eb986fe05 control/controlhttp: add TS_FORCE_NOISE_443, TS_DEBUG_NOISE_DIAL envknobs
Updates tailscale/docker-extension#49

Change-Id: I99a154c16c92228bfdf4d2cf6c58cda00e22d72f
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-01-17 11:30:22 -08:00
Tom DNetto
ee6d18e35f cmd/tailscale/cli: implement --json for lock status and lock log cmds
Signed-off-by: Tom DNetto <tom@tailscale.com>
2023-01-17 10:10:35 -08:00
License Updater
287fe83f91 licenses: update android licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2023-01-17 09:35:45 -08:00
License Updater
ef1c902c21 licenses: update win/apple licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2023-01-17 09:35:26 -08:00
Brad Fitzpatrick
b657187a69 cmd/tailscale, logtail: add 'tailscale debug daemon-logs' logtail mechanism
Fixes #6836

Change-Id: Ia6eb39ff8972e1aa149aeeb63844a97497c2cf04
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-01-15 11:23:28 -08:00
andig
5f96d6211a Remove redundant type declaration
Signed-off-by: andig <cpuidle@gmx.de>
2023-01-15 07:32:02 -08:00
David Anderson
72cc70ebfc flake.nix: update vendor hash.
Signed-off-by: David Anderson <danderson@tailscale.com>
2023-01-14 18:12:25 -08:00
Brad Fitzpatrick
3582628691 net/dns/resolvconffile: link to FAQ about resolv.conf being overwritten
Add link to new http://tailscale.com/s/resolvconf-overwrite page,
added in tailscale/tailscale-www#2243

Change-Id: I9718399487f2ed18bf1a112581fd168aea30f232
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-01-14 13:54:45 -08:00
Andrew Dunham
3a018e51bb ipn/ipnlocal: move handling of expired nodes to LocalBackend
In order to be able to synthesize a new NetMap when a node expires, have
LocalBackend start a timer when receiving a new NetMap that fires
slightly after the next node expires. Additionally, move the logic that
updates expired nodes into LocalBackend so it runs on every netmap
(whether received from controlclient or self-triggered).

Updates #6932

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I833390e16ad188983eac29eb34cc7574f555f2f3
2023-01-14 16:35:02 -05:00
Brad Fitzpatrick
6d85a94767 net/{packet,tstun}: fix typo in test helper docs
Change-Id: Ifc1684fe77c7d2585e049e0dfd7340910c47a67a
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-01-14 13:01:15 -08:00
Brad Fitzpatrick
c1a2e2c380 net/{packet,tstun},wgengine/filter: fix unknown IP protocol handling
01b90df2fa added SCTP support before
(with explicit parsing for ports) and
69de3bf7bf tried to add support for
arbitrary IP protocols (as long as the ACL permited a port of "*",
since we might not know how to find ports from an arbitrary IP
protocol, if it even has such a concept). But apparently that latter
commit wasn't tested end-to-end enough. It had a lot of tests, but the
tests made assumptions about layering that either weren't true, or
regressed since 1.20. Notably, it didn't remove the (*Filter).pre
bidirectional filter that dropped all "unknown" protocol packets both
leaving and entering, even if there were explicit protocol matches
allowing them in.

Also, don't map all unknown protocols to 0. Keep their IP protocol
number parsed so it's matchable by later layers. Only reject illegal
things.

Fixes #6423
Updates #2162
Updates #2163

Change-Id: I9659b3ece86f4db51d644f9b34df78821758842c
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-01-14 10:32:18 -08:00
Brad Fitzpatrick
3386a59cf1 wgengine/filter: include IP proto number in unknown protocol errors
Updates #6423

Change-Id: I9e363922e2c24fdc42687707c069af5bba68b93e
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-01-14 08:35:14 -08:00
Brad Fitzpatrick
006ec659e6 wgengine/filter: reorder RunOut disjunctive cases to match RunIn above
Change-Id: Ia422121cde1687044b18be7bea9e7bf51a4183b9
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-01-14 08:35:14 -08:00
Brad Fitzpatrick
d9144c73a8 cmd/tailscale: add start of "tailscale update" command
Goal: one way for users to update Tailscale, downgrade, switch tracks,
regardless of platform (Windows, most Linux distros, macOS, Synology).

This is a start.

Updates #755, etc

Change-Id: I23466da1ba41b45f0029ca79a17f5796c2eedd92
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-01-14 07:53:41 -08:00
Mihai Parparita
67f82e62a1 ipn/ipnlocal: add Expired to PeerStatus
Needed for clients that get information via the /v0/status LocalAPI
endpoint (e.g. to not offer expired exit nodes as options).

Updates tailscale/corp#8702

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-01-13 18:21:56 -08:00
phirework
f011a0923a cmd/tailscale/cli: style synology outgoing access info (#6959)
Follow-up to #6957.

Updates #4015

Signed-off-by: Jenny Zhang <jz@tailscale.com>
2023-01-13 20:01:28 -05:00
Andrew Dunham
11ce5b7e57 ipn/ipnlocal, wgengine/magicsock: check Expired bool on Node; print error in Ping
Change-Id: Ic5f533f175a6e1bb73d4957d8c3f970add42e82e
Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
2023-01-13 16:56:34 -05:00
Brad Fitzpatrick
5eded58924 cmd/tailscale/cli: make web show/link Synology outgoing connection mode/docs
Fixes #4015

Change-Id: I8230bb0cc3d621b6fa02ab2462cea104fa1e9cf9
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-01-13 13:44:41 -08:00
Matthias Gabriel
355c3b2be7 control/controlhttp: fix header case-sensitivity
Change-Id: I49269bc969a80382997ec5c9de33c4f56d9dc787
Signed-off-by: Matthias Gabriel <matthias.gabriel@etit.tu-chemnitz.de>
2023-01-13 11:31:57 -08:00
Brad Fitzpatrick
61dfbc0a6e cmd/tailscale/cli: plumb TUN mode into tailscale web template
UI works remains, but data is there now.

Updates #4015

Change-Id: Ib91e94718b655ad60a63596e59468f3b3b102306
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-01-13 07:59:40 -08:00
salman
8a1201ac42 cmd/tailscale: correct order for -terminate-tls flag in serve tcp usage
The -terminate-tls flag is for the tcp subsubcommand, not the serve
subcommand like the usage example suggests.

Signed-off-by: salman <salman@tailscale.com>
2023-01-13 14:43:42 +00:00
Brad Fitzpatrick
faf2d30439 version: advertise unstable track in CLI, daemon start-up
Fixes #865

Change-Id: I166e56c3744b0a113973682b9a5327d7aec189f1
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-01-13 06:36:58 -08:00
Jordan Whited
25a0091f69 net/portmapper: relax handling of UPnP resp (#6946)
Gateway devices operating as an HA pair w/VRRP or CARP may send UPnP
replies from static addresses rather than the floating gateway address.
This commit relaxes our source address verification such that we parse
responses from non-gateway IPs, and re-point the UPnP root desc
URL to the gateway IP. This ensures we are still interfacing with the
gateway device (assuming L2 security intact), even though we got a
root desc from a non-gateway address.

This relaxed handling is required for ANY port mapping to work on certain
OPNsense/pfsense distributions using CARP at the time of writing, as
miniupnpd may only listen on the static, non-gateway interface address
for PCP and PMP.

Fixes #5502

Signed-off-by: Jordan Whited <jordan@tailscale.com>
2023-01-12 16:57:02 -08:00
License Updater
b76dffa594 licenses: update win/apple licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2023-01-12 16:41:20 -08:00
Andrew Dunham
6f18fbce8d tailcfg: document zero value for KeyExpiry
Change-Id: I50889f0205ecf66c415f50f9019c190448c991fc
Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
2023-01-12 13:13:46 -05:00
Tom DNetto
2ac5474be1 net/flowtrack,wgengine/filter: refactor Cache to use generics
Signed-off-by: Tom DNetto <tom@tailscale.com>
2023-01-11 15:29:09 -08:00
Will Norris
3becf82dd3 types/views: add SliceEqualAnyOrder func
This is based on the tagsEqual func from corp/control/control.go, moved
here so that it can be reused in other places.

Signed-off-by: Will Norris <will@tailscale.com>
2023-01-11 15:18:40 -08:00
Andrew Dunham
1e67947cfa control/controlclient, tailcfg: add Node.Expired field, set for expired nodes
Nodes that are expired, taking into account the time delta calculated
from MapResponse.ControlTime have the newly-added Expired boolean set.
For additional defense-in-depth, also replicate what control does and
clear the Endpoints and DERP fields, and additionally set the node key
to a bogus value.

Updates #6932

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: Ia2bd6b56064416feee28aef5699ca7090940662a
2023-01-11 09:45:21 -05:00
Denton Gentry
22ebb25e83 cmd/tailscale: disable HTTPS verification for QNAP auth.
QNAP's "Force HTTPS" mode redirects even localhost HTTP to
HTTPS, but uses a self-signed certificate which fails
verification. We accommodate this by disabling checking
of the cert.

Fixes https://github.com/tailscale/tailscale/issues/6903

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2023-01-10 21:49:28 -08:00
James Tucker
2afa1672ac ipn/ipnlocal: disallow unsigned peers from WoL
Unsigned peers should not be allowed to generate Wake-on-Lan packets,
only access Funnel.

Updates #6934
Updates #7515
Updates #6475

Signed-off-by: James Tucker <james@tailscale.com>
2023-01-10 15:54:48 -08:00
License Updater
237b1108b3 licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2023-01-10 09:39:19 -08:00
Will Norris
fff617c988 go.mod: bump golang.org/x/net and dependencies
I don't think CVE-2022-41717 necessarily impacts us (maybe as part of
funnel?), but it came up in a recent security scan so worth updating
anyway.

Signed-off-by: Will Norris <will@tailscale.com>
2023-01-10 09:30:44 -08:00
License Updater
c684ca7a0c licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2023-01-09 14:36:00 -08:00
Brad Fitzpatrick
1116602d4c ssh/tailssh: add OpenBSD support for Tailscale SSH
And bump go.mod for https://github.com/u-root/u-root/pull/2593

Change-Id: I36ec94c5b2b76d671cb739f1e9a1a43ca1d9d1b1
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-01-09 12:58:15 -08:00
Brad Fitzpatrick
be67b8e75b ssh/tailssh: fix Tailscale SSH to non-root tailscaled
Fix regression from 337c77964b where
tailscaled started calling Setgroups. Prior to that, SSH to a non-root
tailscaled was working.

Instead, ignore any failure calling Setgroups if the groups are
already correct.

Fixes #6888

Change-Id: I561991ddb37eaf2620759c6bcaabd36e0fb2a22d
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-01-06 13:19:12 -08:00
Brad Fitzpatrick
8047dfa2dc ssh/tailssh: unify some of the incubator_* GOOS files into incubator.go
In prep for fix for #6888

Change-Id: I79f780c6467a9b7ac03017b27d412d6b0d2f7e6b
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-01-06 13:19:12 -08:00
Brad Fitzpatrick
ebbf5c57b3 README.md: update with some new links, refresh
And remove Darwin from the list, as macOS was already there.

Change-Id: I76bdcad97c926771f44a67140af21f07a8334796
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-01-05 13:06:45 -08:00
David Anderson
39efba528f cmd/containerboot: use TS_AUTHKEY as the parameter for auth keys
We still accept the previous TS_AUTH_KEY for backwards compatibility, but the documented option name is the spelling we use everywhere else.

Updates #6321

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-01-05 13:03:39 -08:00
Brad Fitzpatrick
69c0b7e712 ipn/ipnlocal: add c2n handler to flush logtail for support debugging
Updates tailscale/corp#8564

Change-Id: I0c619d4007069f90cffd319fba66bd034d63e84d
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-01-05 12:06:07 -08:00
Tom DNetto
673b3d8dbd net/dns,userspace: remove unused DNS paths, normalize query limit on iOS
With a42a594bb3, iOS uses netstack and
hence there are no longer any platforms which use the legacy MagicDNS path. As such, we remove it.

We also normalize the limit for max in-flight DNS queries on iOS (it was 64, now its 256 as per other platforms).
It was 64 for the sake of being cautious about memory, but now we have 50Mb (iOS-15 and greater) instead of 15Mb
so we have the spare headroom.

Signed-off-by: Tom DNetto <tom@tailscale.com>
2023-01-05 11:56:14 -08:00
Brad Fitzpatrick
10eec37cd9 scripts: permit 2023 in license headers
Change-Id: Ia018cb8491871c8bf756c454d085780b75512962
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-01-05 11:41:47 -08:00
Mihai Parparita
8f2bc0708b logtail: make logs flush delay dynamic
Instead of a static FlushDelay configuration value, use a FlushDelayFn
function that we invoke every time we decide send logs. This will allow
mobile clients to be more dynamic about when to send logs.

Updates #6768

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2023-01-04 16:59:25 -08:00
Tom DNetto
0088c5ddc0 health,ipn/ipnlocal: report the node being locked out as a health issue
Signed-off-by: Tom DNetto <tom@tailscale.com>
2023-01-04 16:20:47 -08:00
Tom DNetto
907f85cd67 cmd/tailscale,tka: make KeyID return an error instead of panicking
Signed-off-by: Tom DNetto <tom@tailscale.com>
2023-01-04 09:51:31 -08:00
Tom DNetto
8724aa254f cmd/tailscale,tka: implement compat for TKA messages, minor UX tweaks
Signed-off-by: Tom DNetto <tom@tailscale.com>
2023-01-04 09:51:31 -08:00
Kristoffer Dalby
c4e262a0fc ipn/profiles: set default prefs based on Windows registry (#6803)
Co-authored-by: Maisem Ali maisem@tailscale.com
2023-01-04 18:34:31 +01:00
Brad Fitzpatrick
eafbf8886d ipn/localapi: add localapi debug endpoints for packet filter/matches
For debugging #6423. This is easier than TS_DEBUG_MAP, as this means I
can pipe things into jq, etc.

Updates #6423

Change-Id: Ib3e7496b2eb3f47d4bed42e9b8045a441424b23c
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-01-03 15:54:51 -08:00
Brad Fitzpatrick
b2b8e62476 util/codegen: permit running in directories without copyright headers
It broke in our corp repo that lacks copyright headers.

Change-Id: Iafc433e6b6affe83b45477899455527658dc4f12
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-01-03 11:09:35 -08:00
David Anderson
91e64ca74f cmd/tailscale/cli: redact private key in debug netmap output by default
This makes `tailscale debug watch-ipn` safe to use for troubleshooting
user issues, in addition to local debugging during development.

Signed-off-by: David Anderson <danderson@tailscale.com>
2023-01-03 10:06:24 -08:00
License Updater
d72575eaaa licenses: update android licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2023-01-03 09:48:39 -08:00
James Tucker
b2c55e62c8 net/tlsdial,tstest,version: use go command from $PATH
Go now includes the GOROOT bin directory in $PATH while running tests
and generate, so it is no longer necessary to construct a path using
runtime.GOROOT().

Fixes #6689

Signed-off-by: James Tucker <james@tailscale.com>
2023-01-03 09:30:23 -08:00
Denton Gentry
467ace7d0c cmd/tailscale: use localhost for QNAP authLogin.cgi
When the user clicks on the Tailscale app in the QNAP App Center,
we do a GET from /cgi-bin/authLogin.cgi to look up their SID.

If the user clicked "secure login" on the QNAP login page to use
HTTPS, then our access to authLogin.cgi will also use HTTPS
but the certiciate is self-signed. Our GET fails with:
    Get "https://10.1.10.41/cgi-bin/authLogin.cgi?sid=abcd0123":
    x509: cannot validate certificate for 10.1.10.41 because it
    doesn't contain any IP SANs
or similar errors.

Instead, access QNAP authentication via http://localhost:8080/
as documented in
https://download.qnap.com/dev/API_QNAP_QTS_Authentication.pdf

Fixes https://github.com/tailscale/tailscale-qpkg/issues/62

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2023-01-03 06:09:10 -08:00
Brad Fitzpatrick
aad6830df0 util/codegen, all: use latest year, not time.Now, in generated files
Updates #6865

Change-Id: I6b86c646968ebbd4553cf37df5e5612fbf5c5f7d
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-01-02 20:38:32 -08:00
Brad Fitzpatrick
ea70aa3d98 net/dns/resolvconffile: fix handling of multiple search domains
Fixes #6875

Change-Id: I57eb9312c9a1c81792ce2b5a0a0f254213b05df2
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2023-01-02 20:19:16 -08:00
License Updater
692eac23ad licenses: update android licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-12-29 21:01:02 -08:00
David Anderson
c86d9f2ab1 flake.nix: rename package to just "tailscale".
There is no unstability inherent in this package, it's just
unstable if you choose to import the flake at the main branch.

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-12-24 18:17:24 -08:00
David Anderson
7bfb9999ee cmd/printdep: support printing the toolchain SRI hash.
Updates #6845.

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-12-24 15:40:22 -08:00
David Anderson
d2beaea523 update-flake.sh: tooling to keep Nix SRI hashes in sync.
Also fixes the Go toolchain SRI hash from a7f05c6bb0,
it turns out I initialized the file with an SRI hash for an older
toolchain version, and because of the unique way fixed-output derivations
work in nix, nix didn't tell me about the mismatch because it just
cache-hit on the older toolchain and moved on. Sigh.

Updates #6845.

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-12-24 15:22:41 -08:00
Brad Fitzpatrick
3599364312 cmd/nardump: Go tool to build Nix NARs and compute their hashes.
Updates #6845.

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-12-24 15:22:41 -08:00
David Anderson
a7f05c6bb0 flake.nix: init to ship unstable tailscale packages.
With this, you can import "github:tailscale/tailscale" as a nix flake,
and get access to the "tailscale-unstable" package.

Updates #6845.

Signed-off-by: David Anderson <dave@natulte.net>
2022-12-24 14:49:03 -08:00
David Anderson
eb682d2a0b version: construct short hash in dev mode if GitCommit is given.
Allows a dev built to provide GitCommit and have the short hash
computed correctly, even if the Go embedded build info lacks a
git commit.

Signed-off-by: David Anderson <dave@natulte.net>
2022-12-24 14:49:03 -08:00
Denton Gentry
2a1f1c79ca scripts/installer.sh: add SUSE Enterprise Server.
Fixes https://github.com/tailscale/tailscale/issues/6840

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-12-24 08:12:01 -08:00
License Updater
6107c65f1e licenses: update win/apple licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-12-23 14:54:26 -08:00
Claire Wang
a45c9f982a wgengine/netstack: change netstack API to require LocalBackend
The macOS client was forgetting to call netstack.Impl.SetLocalBackend.
Change the API so that it can't be started without one, eliminating this
class of bug. Then update all the callers.

Updates #6764

Change-Id: I2b3a4f31fdfd9fdbbbbfe25a42db0c505373562f
Signed-off-by: Claire Wang <claire@tailscale.com>
Co-authored-by: Brad Fitzpatrick <bradfitz@tailscale.com>
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-12-23 14:01:26 -08:00
Brad Fitzpatrick
84eaef0bbb ssh/tailssh: don't swallow process exit code in be-child
Thanks to @nshalman and @Soypete for debugging!

Updates #6054

Change-Id: I74550cc31f8a257b37351b8152634c768e1e0a8a
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-12-23 12:56:10 -08:00
License Updater
f3c83a06ff licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-12-22 15:46:14 -08:00
License Updater
011f661d5b licenses: update win/apple licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-12-22 15:45:53 -08:00
Brad Fitzpatrick
caa2fe394f wgengine/netstack: delete some dead code, old comment, use atomic int types
Noticed while looking at something else; #cleanup.

Change-Id: Icde7749363014eab9bebe1dd80708f5491f933d1
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-12-22 13:04:21 -08:00
Anton Tolchanov
82b9689e25 ipn/ipnlocal: maintain a proxy handler per backend (#6804)
By default, `http.Transport` keeps idle connections open hoping to re-use them in the future. Combined with a separate transport per request in HTTP proxy this results in idle connection leak.

Fixes #6773
2022-12-21 18:36:58 +00:00
Andrew Dunham
1011e64ad7 wgengine/monitor: don't log unhandled RTM_{NEW,DEL}LINK messages
These aren't handled, but it's not an error to get one.

Fixes #6806

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I1fcb9032ac36420aa72a048bf26f58360b9461f9
2022-12-21 12:11:45 -05:00
Brad Fitzpatrick
be10b529ec wgengine/magicsock: add TS_DISCO_PONG_IPV4_DELAY knob to bias IPv6 paths
Fixes #6818

Change-Id: I71597a045c5b4117af69fba869cb616271c0dfe1
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-12-21 08:34:49 -08:00
Brad Fitzpatrick
e36cdacf70 envknob: add time.Duration knob support
Updates #6818

Change-Id: I9c8147c02fb514f9f6f1f272bdb0f974c8b3ccbb
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-12-21 08:34:49 -08:00
andig
14e8afe444 go.mod, etc: bump gvisor
Fixes #6554

Change-Id: Ia04ae37a47b67fa57091c9bfe1d45a1842589aa8
Signed-off-by: andig <cpuidle@gmx.de>
2022-12-20 22:02:40 -08:00
Brad Fitzpatrick
8aac77aa19 cmd/tailscale: fix "up" warning about netfilter-mode on Synology
Fixes #6811

Change-Id: Ia43723e6ebedc9b01729897cec271c462b16e9ae
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-12-20 12:03:17 -08:00
Brad Fitzpatrick
f837d179b9 ssh/tailssh: fix typo in error message
"look up" is the verb. "lookup" is a noun.

Change-Id: I81c99e12c236488690758fb5c121e7e4e1622a36
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-12-20 11:42:26 -08:00
Brad Fitzpatrick
2eff9c8277 wgengine/magicsock: avoid ReadBatch/WriteBatch on old Linux kernels
Fixes #6807

Change-Id: I161424ef8a7338e1941d5e43d72dc6529993a0e3
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-12-20 10:54:24 -08:00
Andrew Dunham
0372e14d79 net/dns: bump DNS-over-TCP size limit to 4k
We saw a few cases where we hit this limit; bumping to 4k seems
relatively uncontroversial.

Change-Id: I218fee3bc0d2fa5fde16eddc36497a73ebd7cbda
Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
2022-12-20 12:08:19 -05:00
License Updater
98daf99775 licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-12-19 20:56:17 -08:00
Brad Fitzpatrick
7c77c48bd4 go.toolchain.rev: bump Go
For:
dc0ce6324d
and
2cf198bc80

Updates #6792
Updates #6799

Change-Id: I58f022b5fb790e968938f90eb76e9dfdb74041fc
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-12-19 20:30:34 -08:00
Brad Fitzpatrick
243490f932 go.mod: bump x/sys for linux/arm64 cpu SIGILL fix
Bump to get 2204b6615f

Updates #5793

Change-Id: I6ab78824047cb2c8d042f3f3bf47368ec6da5a34
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-12-19 19:18:33 -08:00
David Anderson
a1ded4c166 cmd/sync-containers: add a dry-run option.
Updates tailscale/corp#8461

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-12-19 19:00:53 -08:00
David Anderson
e5fe205c31 cmd/sync-containers: program to sync tags between container registries.
Updates tailscale/corp#8461

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-12-19 18:17:34 -08:00
License Updater
237f030cd9 licenses: update android licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-12-19 14:05:59 -08:00
Aaron Klotz
296f53524c netstat, portlist: update Windows implementation to disambiguate svchost processes
We change our invocations of GetExtendedTcpTable to request additional
information about the "module" responsible for the port. In addition to pid,
this output also includes sufficient metadata to enable Windows to resolve
process names and disambiguate svchost processes.

We store the OS-specific output in an OSMetadata field in netstat.Entry, which
portlist may then use as necessary to actually resolve the process/module name.

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2022-12-19 15:38:49 -06:00
Brad Fitzpatrick
a06217a8bd cmd/tailscale/cli: hide Windows named pipe default name in flag help
It's long & distracting for how low value it is.

Fixes #6766

Change-Id: I51364f25c0088d9e63deb9f692ba44031f12251b
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-12-19 13:38:08 -08:00
Brad Fitzpatrick
5caf609d7b go.toolchain.rev: bump Go to 1.19.4
Updates tailscale/go#36

Change-Id: I0b741c18ef0286b511a79ec39b1e91464c7ce77b
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-12-19 13:30:12 -08:00
Brad Fitzpatrick
0f604923d3 ipn/ipnlocal: fix StatusWithoutPeers not populating parts of Status
Fixes #4311

Change-Id: Iaae0615148fa7154f4ef8f66b455e3a6c2fa9df3
Co-authored-by: Claire Wang <claire@tailscale.com>
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-12-19 13:15:28 -08:00
Aaron Klotz
3c452b9880 util/winutil: fix erroneous condition in implementation of getRegIntegerInternal
We only want to log when err != registry.ErrNotExist. The condition was backward.

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2022-12-19 15:12:53 -06:00
License Updater
14d07b7b20 licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-12-19 11:55:27 -08:00
Jordan Whited
914d115f65 go.mod: bump tailscale/wireguard-go for big-endian fix (#6785)
Signed-off-by: Jordan Whited <jordan@tailscale.com>
2022-12-19 11:49:06 -08:00
David Anderson
af3127711a cmd/containerboot: allow disabling secret storage in k8s.
In some configurations, user explicitly do not want to store
tailscale state in k8s secrets, because doing that leads to
some annoying permission issues with sidecar containers.
With this change, TS_KUBE_SECRET="" and TS_STATE_DIR=/foo
will force storage to file when running in kubernetes.

Fixes #6704.

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-12-16 15:46:38 -08:00
License Updater
6d5527e4b3 licenses: update win/apple licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-12-16 12:02:42 -08:00
Joe Tsai
d9df023e6f net/connstats: enforce maximum number of connections (#6760)
The Tailscale logging service has a hard limit on the maximum
log message size that can be accepted.
We want to ensure that netlog messages never exceed
this limit otherwise a client cannot transmit logs.

Move the goroutine for periodically dumping netlog messages
from wgengine/netlog to net/connstats.
This allows net/connstats to manage when it dumps messages,
either based on time or by size.

Updates tailscale/corp#8427

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-12-16 10:14:00 -08:00
Brad Fitzpatrick
651e0d8aad ssh/tailssh: add envknob for default PATH
As backup plan, just in case the earlier fix's logic wasn't correct
and we want to experiment in the field or have users have a quicker
fix.

Updates #5285

Change-Id: I7447466374d11f8f609de6dfbc4d9a944770826d
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-12-15 15:01:04 -08:00
License Updater
fc0fe99edf licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-12-15 10:49:12 -08:00
Brad Fitzpatrick
c02ccf6424 go.mod: bump dhcp dep to remove another endian package from our tree
To pull in insomniacslk/dhcp#484 to pull in u-root/uio#8

Updates golang/go#57237

Change-Id: I1e56656e0dc9ec0b870f799fe3bc18b3caac1ee4
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-12-15 10:47:25 -08:00
License Updater
97c615889d licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-12-15 10:10:19 -08:00
License Updater
a8f07153a6 licenses: update win/apple licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-12-15 09:11:33 -08:00
Anton Tolchanov
53c4892841 ipn/ipnserver: propagate http.Serve error
This ensures that we capture error returned by `Serve` and exit with a
non-zero exit code if it happens.

Signed-off-by: Anton Tolchanov <anton@tailscale.com>
2022-12-15 15:01:56 +00:00
David Anderson
8171eb600c cmd/k8s-operator: move the operator into its own namespace.
The operator creates a fair bit of internal cluster state to manage proxying,
dumping it all in the default namespace is handy for development but rude
for production.

Updates #502

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-12-14 20:05:35 -08:00
Brad Fitzpatrick
56f7da0cfd ssh/tailssh: set default Tailscale SSH $PATH for non-interactive commands
Fixes #5285

Co-authored-by: Andrew Dunham <andrew@tailscale.com>
Change-Id: Ic7e967bf6a53b056cac5f21dd39565d9c31563af
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-12-14 18:45:35 -08:00
Joe Tsai
350aab05e5 util/multierr: optimize New for nil cases (#6750)
Consider the following pattern:

	err1 := foo()
	err2 := bar()
	err3 := baz()
	return multierr.New(err1, err2, err3)

If err1, err2, and err3 are all nil, then multierr.New should not allocate.
Thus, modify the logic of New to count the number of distinct error values
and allocate the exactly needed slice. This also speeds up non-empty error
situation since repeatedly growing with append is slow.

Performance:

	name         old time/op    new time/op    delta
	Empty-24       41.8ns ± 2%     6.4ns ± 1%   -84.73%  (p=0.000 n=10+10)
	NonEmpty-24     120ns ± 3%      69ns ± 1%   -42.01%  (p=0.000 n=9+10)

	name         old alloc/op   new alloc/op   delta
	Empty-24        64.0B ± 0%      0.0B       -100.00%  (p=0.000 n=10+10)
	NonEmpty-24      168B ± 0%       88B ± 0%   -47.62%  (p=0.000 n=10+10)

	name         old allocs/op  new allocs/op  delta
	Empty-24         1.00 ± 0%      0.00       -100.00%  (p=0.000 n=10+10)
	NonEmpty-24      3.00 ± 0%      2.00 ± 0%   -33.33%  (p=0.000 n=10+10)

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-12-14 18:17:38 -08:00
Jordan Whited
55b24009f7 net/tstun: don't return early from a partial tun.Read() (#6745)
Fixes #6730

Signed-off-by: Jordan Whited <jordan@tailscale.com>
2022-12-14 16:29:34 -08:00
David Anderson
3a5fc233aa cmd/k8s-operator: use oauth credentials for API access.
This automates both the operator's initial login, and
provisioning/deprovisioning of proxies.

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-12-14 14:05:28 -08:00
David Anderson
a7ab3429b6 cmd/k8s-operator: refactor reconcile loop, un-plumbing reconcile.Result.
We used to need to do timed requeues in a few places in the reconcile logic,
and the easiest way to do that was to plumb reconcile.Result return values
around. But now we're purely event-driven, so the only thing we care about
is whether or not an error occurred.

Incidentally also fix a very minor bug where headless services would get
completely ignored, rather than reconciled into the correct state. This
shouldn't matter in practice because you can't transition from a headful
to a headless service without a deletion, but for consistency let's avoid
having a path that takes no definite action if a service of interest does
exist.

Updates #502.

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-12-14 11:35:59 -08:00
Denton Gentry
da53b1347b cmd/gitops-pusher: support alternate api-server URLs
Fixes https://github.com/tailscale/coral/issues/90

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-12-14 05:07:12 -08:00
David Anderson
835a73cc1f cmd/k8s-operator: remove unnecessary timed requeue.
Previously, we had to do blind timed requeues while waiting for
the tailscale hostname, because we looked up the hostname through
the API. But now the proxy container image writes back its hostname
to the k8s secret, so we get an event-triggered reconcile automatically
when the time is right.

Updates #502

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-12-13 17:15:06 -08:00
David Anderson
d857fd00b3 cmd/k8s-operator: sprinkle debug logging throughout.
As is convention in the k8s world, use zap for structured logging. For
development, OPERATOR_LOGGING=dev switches to a more human-readable output
than JSON.

Updates #502

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-12-13 17:15:06 -08:00
David Anderson
8ccd707218 cmd/k8s-operator: remove times requeues in proxy deletion path.
Our reconcile loop gets triggered again when the StatefulSet object
finally disappears (in addition to when its deletion starts, as indicated
by DeletionTimestamp != 0). So, we don't need to queue additional
reconciliations to proceed with the remainder of the cleanup, that
happens organically.

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-12-13 13:49:35 -08:00
David Anderson
c0fcab01ac client/tailscale: fix request object for key creation.
The request takes key capabilities as an argument, but wrapped in a parent
object.

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-12-13 13:49:35 -08:00
Andrew Dunham
3f4d51c588 net/dns: don't send on closed channel when message too large
Previously, if a DNS-over-TCP message was received while there were
existing queries in-flight, and it was over the size limit, we'd close
the 'responses' channel. This would cause those in-flight queries to
send on the closed channel and panic.

Instead, don't close the channel at all and rely on s.ctx being
canceled, which will ensure that in-flight queries don't hang.

Fixes #6725

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I8267728ac37ed7ae38ddd09ce2633a5824320097
2022-12-13 15:54:17 -05:00
Brad Fitzpatrick
44be59c15a wgengine/magicsock: fix panic in wireguard-go rate limiting path
Fixes #6686

Change-Id: I1055a87141b07261afed8e36c963a69f3be26088
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-12-13 10:51:55 -08:00
Andrew Dunham
0d47cd2284 wgengine/monitor: fix panic due to race on Windows
It's possible for the 'somethingChanged' callback to be registered and
then trigger before the ctx field is assigned; move the assignment
earlier so this can't happen.

Change-Id: Ia7ee8b937299014a083ab40adf31a8b3e0db4ec5
Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
2022-12-13 13:28:12 -05:00
David Anderson
d81a2b2ce2 Makefile: add a target for doing dev builds of the k8s operator.
Updates #502.

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-12-13 09:50:57 -08:00
David Anderson
9c77205ba1 cmd/k8s-operator: add more tests for "normal" paths.
Tests cover configuring a proxy through an annotation rather than a
LoadBalancerClass, and converting between those two modes at runtime.

Updates #502.

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-12-13 09:31:01 -08:00
David Anderson
c902190e67 cmd/k8s-operator: factor out some of the larger expected test outputs.
For other test cases, the operator is going to produce similar generated
objects in several codepaths, and those objects are large. Move them out
to helpers so that the main test code stays a bit more intelligible.

The top-level Service that we start and end with remains in the main test
body, because its shape at the start and end is one of the main things that
varies a lot between test cases.

Updates #502.

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-12-13 09:31:01 -08:00
David Anderson
8dbb3b8bbe cmd/k8s-operator: remove unused structs. Cleanup missed in #6718.
Signed-off-by: David Anderson <danderson@tailscale.com>
2022-12-12 21:31:06 -08:00
David Anderson
53a9cc76c7 cmd/k8s-operator: rename main.go -> operator.go.
Signed-off-by: David Anderson <danderson@tailscale.com>
2022-12-12 21:18:31 -08:00
David Anderson
bc8f5a7734 cmd/k8s-operator: add a basic unit test.
The test verifies one of the successful reconcile paths, where
a client requests an exposed service via a LoadBalancer class.

Updates #502.

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-12-12 21:18:31 -08:00
David Anderson
3b7ae39a06 cmd/k8s-operator: use the client's authkey method to create auth keys.
Also introduces an intermediary interface for the tailscale client, in
preparation for operator tests that fake out the Tailscale API interaction.

Updates #502.

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-12-12 21:18:31 -08:00
Brad Fitzpatrick
ca08e316af util/endian: delete package; use updated josharian/native instead
See josharian/native#3

Updates golang/go#57237

Change-Id: I238c04c6654e5b9e7d9cfb81a7bbc5e1043a84a2
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-12-12 20:12:45 -08:00
Joe Tsai
bd2995c14b ipn/ipnlocal: simplify redactErr (#6716)
Use multierr.Range to iterate through an error tree
instead of multiple invocations of errors.As.
This scales better as we add more Go error types to the switch.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-12-12 17:51:03 -08:00
Joe Tsai
c47578b528 util/multierr: add Range (#6643)
Errors in Go are no longer viewed as a linear chain, but a tree.
See golang/go#53435.

Add a Range function that iterates through an error
in a pre-order, depth-first order.
This matches the iteration order of errors.As in Go 1.20.

This adds the logic (but currently commented out) for having
Error implement the multi-error version of Unwrap in Go 1.20.
It is commented out currently since it causes "go vet"
to complain about having the "wrong" signature.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-12-12 16:48:11 -08:00
Dave Anderson
041a0e3c27 client/tailscale: add APIs for auth key management. (#6715)
client/tailscale: add APIs for key management.

Updates #502.

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-12-12 16:01:04 -08:00
David Anderson
b2d4abf25a cmd/k8s-operator: add a kubernetes operator.
This was initially developed in a separate repo, but for build/release
reasons and because go module management limits the damage of importing
k8s things now, moving it into this repo.

At time of commit, the operator enables exposing services over tailscale,
with the 'tailscale' loadBalancerClass. It also currently requires an
unreleased feature to access the Tailscale API, so is not usable yet.

Updates #502.

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-12-12 13:20:02 -08:00
Mihai Parparita
47002d93a3 ipn/ipnlocal: add a few metrics for PeerAPI and LocalAPI
Mainly motivated by wanting to know how much Taildrop is used, but
also useful when tracking down how many invalid requests are
generated.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-12-12 10:07:18 -08:00
Aaron Klotz
53e2010b8a cmd/tailscaled: change Windows implementation to shut down subprocess via closing its stdin
We've been doing a hard kill of the subprocess, which is only safe as long as
both the cli and gui are not running and the subprocess has had the opportunity
to clean up DNS settings etc. If unattended mode is turned on, this is definitely
unsafe.

I changed babysitProc to close the subprocess's stdin to make it shut down, and
then I plumbed a cancel function into the stdin reader on the subprocess side.

Fixes https://github.com/tailscale/corp/issues/5621

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2022-12-12 12:02:26 -06:00
缘生
9c67395334 feat(build): add support on Loongnix-Server (loong64) (#6233)
Makefile, .github/workflow: add tests, targets for GOARCH=loong64 (Loongnix)

Signed-off-by: ysicing <i@ysicing.me>
2022-12-11 20:16:40 -08:00
Brad Fitzpatrick
7b65b7f85c go.mod: bump tailscale/wireguard-go for loong64
Updates tailscale/tailscale#6233

Change-Id: I5ba1826e79be51c03b19f2b31d73024410be4970
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-12-10 22:24:43 -08:00
Brad Fitzpatrick
5a523fdc7f go.mod: update deps to add support for GOARCH=loong64
Updates tailscale/tailscale#6233

Change-Id: Ibbc8e42607342e4ab4fc0b365ed628d82b56864d
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-12-10 15:01:39 -08:00
shayne
9d335aabb2 cmd/tailscale/cli: [ssh] fix typo in help text (#6694)
arugments => arguments

Signed-off-by: shayne <79330+shayne@users.noreply.github.com>
2022-12-10 00:07:27 -05:00
License Updater
ab4992e10d licenses: update win/apple licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-12-09 16:11:21 -08:00
Jordan Whited
ea5ee6f87c all: update golang.zx2c4.com/wireguard to github.com/tailscale/wireguard-go (#6692)
This is temporary while we work to upstream performance work in
https://github.com/WireGuard/wireguard-go/pull/64. A replace directive
is less ideal as it breaks dependent code without duplication of the
directive.

Signed-off-by: Jordan Whited <jordan@tailscale.com>
2022-12-09 15:12:20 -08:00
Andrew Dunham
b63094431b wgengine/router: fix tests on systems with older Busybox 'ip' binary
Adjust the expected system output by removing the unsupported mask
component including and after the slash in expected output like:
  fwmask 0xabc/0xdef

This package's tests now pass in an Alpine container when the 'go' and
'iptables' packages are installed (and run as privileged so /dev/net/tun
exists).

Fixes #5928

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: Id1a3896282bfa36b64afaec7a47205e63ad88542
2022-12-09 13:37:35 -05:00
Maisem Ali
eb1adf629f net/tstun: reuse buffered packet from pool
We would call parsedPacketPool.Get() for all packets received in Read/Write.
This was wasteful and not necessary, fetch a single *packet.Parsed for
all packets.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-12-09 23:37:15 +05:00
Walter Poupore
383e203fd2 cmd/tailscale/cli: update lock status help strings (#6675)
Signed-off-by: Walter Poupore <walterp@tailscale.com>

Signed-off-by: Walter Poupore <walterp@tailscale.com>
2022-12-09 10:24:21 -08:00
Jordan Whited
76389d8baf net/tstun, wgengine/magicsock: enable vectorized I/O on Linux (#6663)
This commit updates the wireguard-go dependency and implements the
necessary changes to the tun.Device and conn.Bind implementations to
support passing vectors of packets in tailscaled. This significantly
improves throughput performance on Linux.

Updates #414

Signed-off-by: Jordan Whited <jordan@tailscale.com>
Signed-off-by: James Tucker <james@tailscale.com>
Co-authored-by: James Tucker <james@tailscale.com>
2022-12-08 17:58:14 -08:00
James Tucker
389238fe4a cmd/tailscale/cli: add workaround for improper named socket quoting in ssh command
This avoids the issue in the common case where the socket path is the
default path, avoiding the immediate need for a Windows shell quote
implementation.

Updates #6639

Signed-off-by: James Tucker <james@tailscale.com>
2022-12-08 16:43:06 -08:00
Mihai Parparita
bdc45b9066 wgengine/magicsock: fix panic when rebinding fails
We would replace the existing real implementation of nettype.PacketConn
with a blockForeverConn, but that violates the contract of atomic.Value
(where the type cannot change). Fix by switching to a pointer value
(atomic.Pointer[nettype.PacketConn]).

A longstanding issue, but became more prevalent when we started binding
connections to interfaces on macOS and iOS (#6566), which could lead to
the bind call failing if the interface was no longer available.

Fixes #6641

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-12-08 16:34:14 -08:00
Tom DNetto
e27f4f022e cmd/tailscale/cli: add progress to tailscale file cp
Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-12-08 14:05:11 -08:00
Xe Iaso
d1a5757639 tsnet: add HTTP client method to tsnet.Server (#6669)
This allows tsnet services to make requests to other services in the
tailnet with the tsnet service identity instead of the identity of the
host machine. This also enables tsnet services to make requests to other
tailnet services without having to have the host machine join the
tailnet.

Signed-off-by: Xe Iaso <xe@tailscale.com>

Signed-off-by: Xe Iaso <xe@tailscale.com>
2022-12-08 16:08:17 -05:00
salman
2d271f3bd1 ipn/ipnlocal: disallow exit nodes from using exit nodes
Nodes which have both -advertise-exit-node and -exit-node in prefs
should continue have them until the next invocation of `tailscale up`.

Updates #3569.

Signed-off-by: salman <salman@tailscale.com>
2022-12-08 17:10:33 +03:00
License Updater
5f68763cb2 licenses: update win/apple licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-12-07 21:20:39 -08:00
shayne
98114bf608 cmd/tailscale/cli, ipn/localapi: add funnel status to status command (#6402)
Fixes #6400

open up GETs for localapi serve-config to allow read-only access to
ServeConfig

`tailscale status` will include "Funnel on" status when Funnel is
configured. Prints nothing if Funnel is not running.

Example:

 $ tailscale status
 <nodes redacted>

 # Funnel on:
 #     - https://node-name.corp.ts.net
 #     - https://node-name.corp.ts.net:8443
 #     - tcp://node-name.corp.ts.net:10000

Signed-off-by: Shayne Sweeney <shayne@tailscale.com>
2022-12-07 22:17:40 -05:00
David Anderson
1b65630e83 cmd/containerboot: switch to IPN bus monitoring instead of polling.
We still have to shell out to `tailscale up` because the container image's
API includes "arbitrary flags to tailscale up", unfortunately. But this
should still speed up startup a little, and also enables k8s-bound containers
to update their device information as new netmap updates come in.

Fixes #6657

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-12-07 13:31:15 -08:00
Tom DNetto
55e0512a05 ipn/ipnlocal,cmd/tailscale: minor improvements to lock modify command
* Do not print the status at the end of a successful operation
 * Ensure the key of the current node is actually trusted to make these changes

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-12-07 10:28:21 -08:00
Aaron Klotz
98f21354c6 cmd/tailscaled: add a special command to tailscaled's Windows service for removing WinTun
WinTun is installed lazily by tailscaled while it is running as LocalSystem.
Based upon what we're seeing in bug reports and support requests, removing
WinTun as a lesser user may fail under certain Windows versions, even when that
user is an Administrator.

By adding a user-defined command code to tailscaled, we can ask the service to
do the removal on our behalf while it is still running as LocalSystem.

* The uninstall code is basically the same as it is in corp;
* The command code will be sent as a service control request and is protected by
  the SERVICE_USER_DEFINED_CONTROL access right, which requires Administrator.

I'll be adding follow-up patches in corp to engage this functionality.

Updates https://github.com/tailscale/tailscale/issues/6433

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2022-12-07 12:12:02 -06:00
David Anderson
367228ef82 cmd/containerboot: gracefully degrade if missing patch permissions in k8s.
Fixes #6629.

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-12-07 09:11:32 -08:00
Andrew Dunham
a887ca7efe ipn/ipnlocal: improve redactErr to handle more cases
This handles the case where the inner *os.PathError is wrapped in
another error type, and additionally will redact errors of type
*os.LinkError. Finally, add tests to verify that redaction works.

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: Ie83424ff6c85cdb29fb48b641330c495107aab7c
2022-12-06 19:37:15 -05:00
David Anderson
e36c27bcd1 cmd/containerboot: check that k8s secret permissions are correct.
Updates #6629.

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-12-06 15:54:04 -08:00
David Anderson
e79a1eb24a cmd/containerboot: refactor tests to have more explicit phases.
In preparation for making startup more complex with IPN bus watches.

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-12-06 15:32:04 -08:00
David Anderson
e04aaa7575 cmd/containerboot: split tailscaled bringup and auth phases.
In preparation for reworking auth to use IPN bus watch.

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-12-06 15:32:04 -08:00
David Anderson
a469ec8ff6 cmd/containerboot: fix some lint.
Signed-off-by: David Anderson <danderson@tailscale.com>
2022-12-06 15:32:04 -08:00
License Updater
c084c7d7ed licenses: update win/apple licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-12-06 10:31:53 -08:00
Anton Tolchanov
5ff946a9e6 cmd/containerboot: fix TS_STATE_DIR environment variable
It's supposed to set `--statedir` rather than `--state` file.

Fixes #6634.

Signed-off-by: Anton Tolchanov <anton@tailscale.com>
2022-12-06 08:44:58 -08:00
License Updater
7048024e04 licenses: update win/apple licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-12-06 04:54:26 -08:00
Brad Fitzpatrick
1598cd0361 net/tsaddr: remove ContainsFunc helpers (they're now in x/exp/slices)
x/exp/slices now has ContainsFunc (golang/go#53983) so we can delete
our versions.

Change-Id: I5157a403bfc1b30e243bf31c8b611da25e995078
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-12-05 18:50:24 -08:00
License Updater
4b34c88426 licenses: update android licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-12-05 16:04:16 -08:00
Mihai Parparita
79f3a5d753 net/netns, net/interfaces: explicitly bind sockets to the default interface on all Darwin variants
We were previously only doing this for tailscaled-on-Darwin, but it also
appears to help on iOS. Otherwise, when we rebind magicsock UDP
connections after a cellular -> WiFi interface change they still keep
using cellular one.

To do this correctly when using exit nodes, we need to exclude the
Tailscale interface when getting the default route, otherwise packets
cannot leave the tunnel. There are native macOS/iOS APIs that we can
use to do this, so we allow those clients to override the implementation
of DefaultRouteInterfaceIndex.

Updates #6565, may also help with #5156

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-12-05 13:33:20 -08:00
Mihai Parparita
cb525a1aad cmd/tailscaled: fix typo in netstack variable name
Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-12-05 11:53:48 -08:00
Julia Stein
3f16dec1bb api.md: change "admin panel" to "admin console"
Signed-off-by: Julia Stein <julia@tailscale.com>
2022-12-05 11:21:55 -08:00
Tom DNetto
9c773af04c ipn/ipnlocal: fix use of stale profile while processing netmap
Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-12-05 11:06:32 -08:00
Denton Gentry
c933b8882c VERSION.txt: this is v1.35.0
Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-12-05 09:51:51 -08:00
Brad Fitzpatrick
964d723aba ipn/{ipnserver,localapi}: fix InUseOtherUser handling with WatchIPNBus
Updates tailscale/corp#8222

Change-Id: I2d6fa6514c7b8d0f89fded35a2d44e7df27e6fb1
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-12-03 18:58:19 -08:00
Maisem Ali
86b6ff61e6 ipn/ipnlocal: fix Prefs access without mu being held
Noticed while working on a different fix.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-12-03 11:44:39 +05:00
Maisem Ali
cdb924f87b ipn/ipnlocal: sanitize prefs in more notify code paths
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-12-03 11:44:39 +05:00
Denton Gentry
7c4d017636 paths: set QNAP socket to /tmp.
Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-12-02 22:07:42 -08:00
Brad Fitzpatrick
57124e2126 ipn/localapi: add debug (root-required) access to inject debug Notify
For testing of Windows GUI client.

Updates #6480

Change-Id: I42f7526d95723e14bed7085fb759e371b43aa9da
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-12-02 20:26:08 -08:00
Maisem Ali
96cad35870 cmd/tailscaled: rename variables to be more descriptive
renamed from `useNetstack` to `onlyNetstack` which is 1 letter more but
more descriptive because we always have netstack enabled and `useNetstack`
doesn't convey what it is supposed to be used for. e.g. we always use
netstack for Tailscale SSH.

Also renamed shouldWrapNetstack to handleSubnetsInNetstack as it was only used
to configure subnet routing via netstack.

Updates tailscale/corp#8020

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-12-03 03:11:13 +05:00
Mihai Parparita
a87e0b4ea8 ipn: update comments that refer to Options.Prefs
Things are slightly less tangled now that we've migrated prefs to the
backend (and renamed the field to LegacyMigrationPrefs).

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-12-02 11:55:54 -08:00
Brad Fitzpatrick
b9dd3fa534 paths, version/distro: detect Synology DSM version better, use for socket path
Resolves a TODO in the code noted while discussing QNAP defaults.

Tested on DSM6 and DSM7.

Change-Id: Icce03ff41fafd7b3a358cfee16f2ed13d5cc3c5d
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-12-02 09:54:08 -08:00
Mihai Parparita
5b8323509f cmd/tailscale/cli: use "account" instead of "profile" in user-visible text
Matches the UI clients

Updates #713

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-12-02 09:01:44 -08:00
Anton Tolchanov
d6dbefaa91 api.md: lowercase ACL field names
Making this match https://tailscale.com/kb/1018/acls

Signed-off-by: Anton Tolchanov <anton@tailscale.com>
2022-12-02 13:17:59 +00:00
Anton Tolchanov
71c0e8d428 api.md: update documentation for the "set ACL" endpoint
This documents the `If-Match: ts-default` header that can be set to only
overwrite the default ACL contents, and also briefly mentions a few of
the new top-level ACL fields.

Updates tailscale/terraform-provider-tailscale#182

Signed-off-by: Anton Tolchanov <anton@tailscale.com>
2022-12-02 13:17:59 +00:00
Brad Fitzpatrick
e1d7d072a3 ipn/ipnlocal: set Notify.Version on initial Notifies
Missed when added recently in 8dd1418774

Change-Id: Id682640a54c3717afe084edaf69258ad23031b6c
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-12-01 19:36:57 -08:00
Maya Kaczorowski
d5b4d2e276 cmd/tailscale/cli: improve tailnet lock help (#6583)
Signed-off-by: Maya Kaczorowski <15946341+mayakacz@users.noreply.github.com>

Signed-off-by: Maya Kaczorowski <15946341+mayakacz@users.noreply.github.com>
2022-12-01 09:19:28 -08:00
Walter Poupore
74b47eaad6 cmd/tailscale/cli: Fix 'tailscale switch' error message (#6585)
Updates #713.

Signed-off-by: Walter Poupore <walterp@tailscale.com>

Signed-off-by: Walter Poupore <walterp@tailscale.com>
2022-12-01 08:17:16 -08:00
Maisem Ali
99aa335923 net/dns: [linux] log and add metric for dnsMode
I couldn't find any logs that indicated which mode it was running in so adding that.
Also added a gauge metric for dnsMode.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-12-01 19:57:08 +05:00
Maisem Ali
a5a3188b7e cmd/tailscale/cli: unhide login and switch subcommands
Updates #713

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-12-01 18:38:04 +05:00
Maya Kaczorowski
a1084047ce cmd/tailscale/cli: capitalize Get (#6586)
Signed-off-by: Maya Kaczorowski <15946341+mayakacz@users.noreply.github.com>

Signed-off-by: Maya Kaczorowski <15946341+mayakacz@users.noreply.github.com>
2022-11-30 21:32:14 -08:00
Tom DNetto
74c1f632f6 types/key,cmd/tailscale/cli: support tlpub prefix for tailnet-lock keys
Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-11-30 18:04:47 -08:00
Brad Fitzpatrick
8dd1418774 ipn{,/ipnlocal}: add ipn.NotifyInitial* flags to WatchIPNBus
To simplify clients getting the initial state when they subscribe.

Change-Id: I2490a5ab2411253717c74265a46a98012b80db82
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-30 17:50:51 -08:00
Brad Fitzpatrick
197a4f1ae8 types/ptr: move all the ptrTo funcs to one new package's ptr.To
Change-Id: Ia0b820ffe7aa72897515f19bd415204b6fe743c7
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-30 17:50:51 -08:00
Brad Fitzpatrick
a277eb4dcf ipn/ipnlocal: add missing context cancel
If user's fn returned false and never canceled their ctx, we never
stopped the NotifyWatchEngineUpdates goroutine.

This was introduced recently (this cycle).

Change-Id: I3453966ac71e00727296ddd237ef845782f4e52e
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-30 17:50:51 -08:00
Mihai Parparita
978d6af91a ipn/ipnlocal: tweak error handling in interfaces PeerAPI debug endpoint
We were writing the error when getting the default interface before
setting the content type, so we'd get HTML treated as plain text.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-11-30 17:47:37 -08:00
Brad Fitzpatrick
5bdca747b7 ipn/ipnlocal: fix netstack peerapi crash over IPv6
The peerapi IPv6 listener has a nil listener.
But we didn't need the listener's address anyway, so don't
try to use it.

Change-Id: I8e8a1a895046d129a3683973e732d9bed82f3b02
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-30 16:28:53 -08:00
Tom DNetto
f1ab11e961 ipn/ipnlocal,tailcfg: introduce capability to gate TKA init paths
Previously, `TAILSCALE_USE_WIP_CODE` was needed to hit a bunch of the TKA paths. With
this change:

 - Enablement codepaths (NetworkLockInit) and initialization codepaths (tkaBootstrapFromGenesisLocked via tkaSyncIfNeeded)
   require either the WIP envknob or CapabilityTailnetLockAlpha.
 - Normal operation codepaths (tkaSyncIfNeeded, tkaFilterNetmapLocked) require TKA to be initialized, or either-or the
   envknob / capability.
 - Auxillary commands (ie: changing tka keys) require TKA to be initialized.

The end result is that it shouldn't be possible to initialize TKA (or subsequently use any of its features) without being
sent the capability or setting the envknob on tailscaled yourself.

I've also pulled out a bunch of unnecessary checks for CanSupportNetworkLock().

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-11-30 13:50:22 -08:00
Tom DNetto
9a80b8fb10 cmd/tailscale,ipn: surface TKA-filtered peers in lock status command
Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-11-30 13:25:31 -08:00
Tom DNetto
731be07777 cmd/tailscale/cli: show rotation key when suggesting lock sign command
Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-11-30 13:25:21 -08:00
Andrew Dunham
a6dff4fb74 docs/webhooks: use subtle.ConstantTimeCompare for comparing signatures
Fixes #6572

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I58610c46e0ea1d3a878f91d154db3da4de9cae00
2022-11-30 11:58:25 -05:00
Brad Fitzpatrick
74744b0a4c ipn: be more consistent with omitempty on debug/rare Prefs
Change-Id: Ib0ec72f243cdb2aca8dd392644d4eed33c3f92e6
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-30 04:33:27 -08:00
Brad Fitzpatrick
f710d1cb20 cmd/tailscale/cli: add set --unattended on Windows
Fixes #6567

Change-Id: I8cb57196c601466401f8602eb50456e7cf7c31ef
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-30 04:33:03 -08:00
License Updater
d2a51f03ce licenses: update win/apple licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-11-29 16:24:40 -08:00
Denton Gentry
a200a23f97 Revert "cmd/tailscale: access QNAP via localhost"
When running `tailscale web` as a standalone process,
it was necessary to send auth requests to QTS using
localhost to avoid hitting the proxy recursively.

However running `tailscale web` as a process means it is
consuming RAM all the time even when it isn't actively
doing anything.

After switching back to the `tailscale web` CGI mode, we
don't need to specifically use localhost for QNAP auth.

This reverts commit e0cadc5496.

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-11-29 16:17:34 -08:00
Maisem Ali
82ad585b5b ipn/ipnlocal: account for ControlURL when merging profiles
We merge/dedupe profiles based on UserID and NodeID, however we were not accounting for ControlURLs.

Updates #713

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-30 04:39:06 +05:00
Maisem Ali
adc302f428 all: use named pipes on windows
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-30 04:05:26 +05:00
Tom DNetto
45042a76cd cmd/tailscale,ipn: store disallowed TKA's in prefs, lock local-disable
Take 2 of https://github.com/tailscale/tailscale/pull/6546

Builds on https://github.com/tailscale/tailscale/pull/6560

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-11-29 13:43:38 -08:00
Tom DNetto
c4980f33f7 ipn,types/persist: add DisallowedTKAStateIDs, refactor as view type
Supercedes https://github.com/tailscale/tailscale/pull/6557, precursor to trying https://github.com/tailscale/tailscale/pull/6546 again

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-11-29 12:29:42 -08:00
Brad Fitzpatrick
6d012547b6 ipn/ipnlocal: use double dash flag style
The Go style weirds people out so we try to stick to the more
well-known double hyphen style in docs.

Change-Id: Iad6db5c82cda37f6b7687eed7ecd9276f8fd94d6
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-29 11:34:08 -08:00
Brad Fitzpatrick
390d1bb871 Revert "ipn,types/persist: store disallowed TKA's in prefs, lock local-disable"
This reverts commit f1130421f0.

It was submitted with failing tests (go generate checks)

Requires a lot of API changes to fix so rolling back instead of
forward.

Change-Id: I024e8885c0ed44675d3028a662f386dda811f2ad
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-29 11:20:26 -08:00
Tom DNetto
f1130421f0 ipn,types/persist: store disallowed TKA's in prefs, lock local-disable
Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-11-29 10:31:02 -08:00
Aaron Klotz
659e7837c6 health, ipn/ipnlocal: when -no-logs-no-support is enabled, deny access to tailnets that have network logging enabled
We want users to have the freedom to start tailscaled with `-no-logs-no-support`,
but that is obviously in direct conflict with tailnets that have network logging
enabled.

When we detect that condition, we record the issue in health, notify the client,
set WantRunning=false, and bail.

We clear the item in health when a profile switch occurs, since it is a
per-tailnet condition that should not propagate across profiles.

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2022-11-29 11:42:20 -06:00
Maisem Ali
ad41cbd9d5 ipn/ipnlocal: sanitize prefs before sending over IPN Bus
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-29 12:43:38 +05:00
Brad Fitzpatrick
0a10a5632b cmd/tailscaled: add TS_DEBUG_BACKEND_DELAY_SEC for testing async startup
This adds an envknob to make testing async startup more reproducible.
We want the Windows GUI to behave well when wintun is not (or it's
doing its initial slow driver installation), but during testing it's often
too fast to see that it's working. This lets it be slowed down.

Updates #6522

Change-Id: I6ae19f46e270ea679cbaea32a53888efcf2943a7
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-28 21:19:33 -08:00
Brad Fitzpatrick
256ba62e00 README.md: add commit message style bit
Change-Id: I0c9423b76f773e20f0216d826620e169f82ee37c
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-28 20:45:18 -08:00
Brad Fitzpatrick
0cb2ccce7f safesocket: remove the IPN protocol support
Updates #6417

Change-Id: I78908633de842d83b2cc8b10a864a0f88ab1b113
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-28 20:44:59 -08:00
Brad Fitzpatrick
06c4c47d46 ipn: remove unused Backend interface
Only the macOS/iOS clients care about it still, so we'll move it
to their repo.

But keep a test that makes sure that LocalBackend continues to
implement it so we get an early warning sign before we break
macOS/iOS.

Change-Id: I56392b740fe55b4d28468b77124c821b5c46c22b
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-28 19:03:27 -08:00
Joe Tsai
2e5d08ec4f net/connstats: invert network logging data flow (#6272)
Previously, tstun.Wrapper and magicsock.Conn managed their
own statistics data structure and relied on an external call to
Extract to extract (and reset) the statistics.
This makes it difficult to ensure a maximum size on the statistics
as the caller has no introspection into whether the number
of unique connections is getting too large.

Invert the control flow such that a *connstats.Statistics
is registered with tstun.Wrapper and magicsock.Conn.
Methods on non-nil *connstats.Statistics are called for every packet.
This allows the implementation of connstats.Statistics (in the future)
to better control when it needs to flush to ensure
bounds on maximum sizes.

The value registered into tstun.Wrapper and magicsock.Conn could
be an interface, but that has two performance detriments:

1. Method calls on interface values are more expensive since
they must go through a virtual method dispatch.

2. The implementation would need a sync.Mutex to protect the
statistics value instead of using an atomic.Pointer.

Given that methods on constats.Statistics are called for every packet,
we want reduce the CPU cost on this hot path.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-11-28 15:59:33 -08:00
Joe Tsai
35c10373b5 types/logid: move logtail ID types here (#6336)
Many packages reference the logtail ID types,
but unfortunately pull in the transitive dependencies of logtail.
Fix this problem by putting the log ID types in its own package
with minimal dependencies.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-11-28 15:25:47 -08:00
Anton Tolchanov
6cc6c70d70 derp: prevent concurrent access to multiForwarder map
Instead of iterating over the map to determine the preferred forwarder
on every packet (which could happen concurrently with map mutations),
store it separately in an atomic variable.

Fixes #6445

Signed-off-by: Anton Tolchanov <anton@tailscale.com>
2022-11-28 22:49:06 +00:00
Aaron Klotz
6e33d2da2b ipn/ipnauth, util/winutil: add temporary LookupPseudoUser workaround to address os/user.LookupId errors on Windows
I added util/winutil/LookupPseudoUser, which essentially consists of the bits
that I am in the process of adding to Go's standard library.

We check the provided SID for "S-1-5-x" where 17 <= x <= 20 (which are the
known pseudo-users) and then manually populate a os/user.User struct with
the correct information.

Fixes https://github.com/tailscale/tailscale/issues/869
Fixes https://github.com/tailscale/tailscale/issues/2894

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2022-11-28 15:53:34 -06:00
Brad Fitzpatrick
3b0de97e07 cmd/tailscaled: unify the two Windows paths + separate IPN server path
tailscaled on Windows had two entirely separate start-up paths for running
as a service vs in the foreground. It's been causing problems for ages.
This unifies the two paths, making them be the same as the path used
for every other platform.

Also, it uses the new async LocalBackend support in ipnserver.Server
so the Server can start serving HTTP immediately, even if tun takes
awhile to come up.

Updates #6535

Change-Id: Icc8c4f96d4887b54a024d7ac15ad11096b5a58cf
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-28 13:31:49 -08:00
Brad Fitzpatrick
ea25ef8236 util/set: add new set package for SetHandle type
We use this pattern in a number of places (in this repo and elsewhere)
and I was about to add a fourth to this repo which was crossing the line.
Add this type instead so they're all the same.

Also, we have another Set type (SliceSet, which tracks its keys in
order) in another repo we can move to this package later.

Change-Id: Ibbdcdba5443fae9b6956f63990bdb9e9443cefa9
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-28 10:44:17 -08:00
Tom DNetto
5c8d2fa695 cmd/tailscale,ipn: improve UX of lock init command, cosmetic changes
Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-11-28 10:39:04 -08:00
Brad Fitzpatrick
e8cc78b1af ipn/ipnserver: change Server to let LocalBackend be supplied async
This is step 1 of de-special-casing of Windows and letting the
LocalAPI HTTP server start serving immediately, even while the rest of
the world (notably the Engine and its TUN device) are being created,
which can take a few to dozens of seconds on Windows.

With this change, the ipnserver.New function changes to not take an
Engine and to return immediately, not returning an error, and let its
Run run immediately. If its ServeHTTP is called when it doesn't yet
have a LocalBackend, it returns an error. A TODO in there shows where
a future handler will serve status before an engine is available.

Future changes will:

* delete a bunch of tailscaled_windows.go code and use this new API
* add the ipnserver.Server ServerHTTP handler to await the engine
  being available
* use that handler in the Windows GUI client

Updates #6522

Change-Id: Iae94e68c235e850b112a72ea24ad0e0959b568ee
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-28 09:48:33 -08:00
Brad Fitzpatrick
8049053f86 ipn/*: make new WindowsUserID type to consolidate docs
The "userID is empty everywhere but Windows" docs on lots of places
but not everywhere while using just a string type was getting
confusing. This makes a new type to wrap up those rules, however
weird/historical they might be.

Change-Id: I142e85a8e38760988d6c0c91d0efecedade81b9b
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-27 12:08:07 -08:00
Brad Fitzpatrick
3b73727e39 cmd/tailscale: de-punycode hostnames in status display
Still show original, but show de-punycode version in parens,
similar to how we show DNS-less hostnames.

Change-Id: I7e57da5e4029c5b49e8cd3014c350eddd2b3c338
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-27 03:11:49 -08:00
Brad Fitzpatrick
5676d201d6 ipn: add a WatchIPNBus option bit to subscribe to EngineStatus changes
So GUI clients don't need to poll for it.

We still poll internally (for now!) but that's still cheaper. And will
get much cheaper later, without having to modify clients once they
start sending this bit.

Change-Id: I36647b701c8d1fe197677e5eb76f6894e8ff79f7
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-26 15:51:33 -08:00
Brad Fitzpatrick
f45106d47c ipn/ipnserver: move Windows-specific code to tailscaled_windows.go
We'll eventually remove it entirely, but for now move get it out of ipnserver
where it's distracting and move it to its sole caller.

Updates #6522

Change-Id: I9c6f6a91bf9a8e3c5ea997952b7c08c81723d447
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-26 15:51:22 -08:00
Brad Fitzpatrick
109aa3b2fb cmd/tailscale: add start of "debug derp" subcommand
Updates #6526

Change-Id: I84e440a8bd837c383000ce0cec4ff36b24249e8b
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-26 15:40:25 -08:00
Brad Fitzpatrick
b0545873e5 ipn/ipnserver: remove protoSwitchConn shenanigans; just use http.Server early
Now that everything's just HTTP, there's no longer a need to have a
header-sniffing net.Conn wraper that dispatches which route to
take. Refactor to just use an http.Server earlier instead.

Updates #6417

Change-Id: I12a2054db4e56f48660c46f81233db224fdc77cb
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-26 11:02:54 -08:00
shayne
e567902aa9 gitignore: ignore direnv nix-shell environment cache (#6520)
Also, updated ignore desc for .vscode/.

Signed-off-by: Shayne Sweeney <shayne@tailscale.com>
2022-11-26 09:30:00 -05:00
Brad Fitzpatrick
f3ba268a96 ipn/ipnserver: move BabysitProc to tailscaled_windows.go
It's only used by Windows. No need for it to be in ipn/ipnserver,
which we're trying to trim down.

Change-Id: Idf923ac8b6cdae8b5338ec26c16fb8b5ea548071
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-25 12:26:38 -08:00
Maisem Ali
699b39dec1 ipn/ipnlocal: drop LocalBackend.inServerMode
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-25 22:16:37 +05:00
Brad Fitzpatrick
7e016c1d90 ipn/ipnserver: remove IPN protocol server
Unused in this repo as of the earlier #6450 (300aba61a6)
and unused in the Windows GUI as of tailscale/corp#8065.

With this ipn.BackendServer is no longer used and could also be
removed from this repo. The macOS and iOS clients still temporarily
depend on it, but I can move it to that repo instead while and let its
migration proceed on its own schedule while we clean this repo up.

Updates #6417
Updates tailscale/corp#8051

Change-Id: Ie13f82af3eb9f96b3a21c56cdda51be31ddebdcf
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-25 08:12:06 -08:00
License Updater
624d9c759b licenses: update win/apple licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-11-25 20:58:08 +05:00
Denton Gentry
b8fe89d15f net/portmapper: add test for Huawei router
Updates https://github.com/tailscale/tailscale/issues/6320

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-11-25 07:42:31 -08:00
Brad Fitzpatrick
1fdfb0dd08 ipn/localapi: add "enginestatus" debug command to LocalAPI
To force an EngineStatus update to the IPN bus.

This is a temporary measure while migrating the Windows GUI entirely
to the LocalAPI and off the old IPN protocol. The old IPN protocol
had RequestEngineStatus and LocalAPI didn't.

Updates #6417

Change-Id: I8ff525fc3dd82bdd9d92c2bdad6db5b75609eacd
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-25 07:28:09 -08:00
Maisem Ali
c258015165 ipn/ipnlocal,ipnserver: rename {,Set}CurrentUser to {,Set}CurrentUserID
Address comments from https://github.com/tailscale/tailscale/pull/6506#discussion_r1032454064

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-25 19:48:04 +05:00
Brad Fitzpatrick
0a842f353c ipn/ipnserver: move more connection acceptance logic to LocalBackend
Follow-up to #6467 and #6506.

LocalBackend knows the server-mode state, so move more auth checking
there, removing some bookkeeping from ipnserver.Server.

Updates #6417
Updates tailscale/corp#8051

Change-Id: Ic5d14a077bf0dccc92a3621bd2646bab2cc5b837
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-25 06:24:29 -08:00
Brad Fitzpatrick
5ea7c7d603 ipn/{ipnlocal,ipnserver}: add some comments
Change-Id: Ieb5917edaf572342b755caa458693512c7aece81
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-25 06:05:45 -08:00
Maisem Ali
732c3d2ed0 .github/workflows: use ubuntu-22.04 for qemu tests
Fixes #6507

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-25 18:43:24 +05:00
Maisem Ali
a3cd171773 ipn/ipnserver: remove Server.serverModeUser
We can just rely on LocalBackend.CurrentUser

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-25 18:43:16 +05:00
Maisem Ali
d321b0ea4f ipn/ipnlocal: add docs to LocalBackend.SetCurrentUserID
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-25 18:43:16 +05:00
Maisem Ali
992749c44c tsnet/example/tshello: use the correct LocalClient for certs
Fixes #6485

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-25 16:05:50 +05:00
shayne
0c4c66948b cmd/tailscale/cli: Improve messaging when Funnel is unavailable. (#6502)
There are three specific requirements for Funnel to work:
1) They must accept an invite.
2) They must enable HTTPS.
3) The "funnel" node attribute must be appropriately set up in the ACLs.

Signed-off-by: Shayne Sweeney <shayne@tailscale.com>
2022-11-24 22:40:48 -05:00
License Updater
344abaf3d3 licenses: update android licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-11-24 16:23:03 -08:00
Brad Fitzpatrick
250edeb3da ipn/ipnserver: only permit the pre-HTTP LocalAPI protocol on Windows
Updates #6417

Change-Id: I1c9dbee3f72969f703b3ff2dbbaa145a17db868b
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-24 14:56:04 -08:00
Aaron Klotz
033bd94d4c cmd/tailscaled, wgengine/router: use wingoes/com for COM initialization instead of go-ole
This patch removes the crappy, half-backed COM initialization used by `go-ole`
and replaces that with the `StartRuntime` function from `wingoes`, a library I
have started which, among other things, initializes COM properly.

In particular, we should always be initializing COM to use the multithreaded
apartment. Every single OS thread in the process becomes implicitly initialized
as part of the MTA, so we do not need to concern ourselves as to whether or not
any particular OS thread has initialized COM. Furthermore, we no longer need to
lock the OS thread when calling methods on COM interfaces.

Single-threaded apartments are designed solely for working with Win32 threads
that have a message pump; any other use of the STA is invalid.

Fixes https://github.com/tailscale/tailscale/issues/3137

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2022-11-24 14:52:23 -06:00
Charlotte Brandhorst-Satzkorn
d6021ae71c words: hybrid theory (#6404)
The animal, not the car kind.

Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2022-11-24 10:28:11 -08:00
Brad Fitzpatrick
b68d008fee envknob: add CanTaildrop (TS_DISABLE_TAILDROP) to disable taildrop on device
This matches CanSSHD (TS_DISABLE_SSH_SERVER) for administratively
disabling the code on a node, regardless of local or server configs.

This can be configured in /etc/default/tailscaled on Linux,
%ProgramData%\Tailscale\tailscaled-env.txt on Windows,
or /etc/tailscale/tailscaled-env.txt on Synology. (see getPlatformEnvFile)

Also delete some dead code and tidy up some docs.

Change-Id: I79a87c03e33209619466ea8aeb0f6651afcb8789
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-24 07:51:17 -08:00
Brad Fitzpatrick
20b27df4d0 tailcfg, ipn, controlclient: add MapResponse.ClientVersion, plumb to IPN bus
Updates #6480

Change-Id: I6321071425cd091148d8140d1eb24dd536bb7984
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-23 20:24:12 -08:00
Brad Fitzpatrick
4d3713f631 envknob: add GOOS func
Centralize the fake GOOS stuff, start to use it more. To be used more
in the future.

Change-Id: Iabacfbeaf5fca0b53bf4d5dbcdc0367f05a205f9
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-23 18:35:43 -08:00
Brad Fitzpatrick
6e6f27dd21 ipn/ipnlocal: lock down unsigned peers more
Apparently there's no tracking bug?

Updates tailscale/corp#7515 for ingress/funnel at least.

Change-Id: I03bc54fdc1f53f9832ab8b51475b2d676c38d897
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-23 18:20:39 -08:00
James Tucker
dc75b7cfd1 cmd/derpprobe: add -once flag for one-off CLI diagnostics
Updates #6478

Signed-off-by: James Tucker <james@tailscale.com>
2022-11-23 17:41:12 -08:00
James Tucker
b1441d0044 cmd/stunc: add command for making debug stun requests
Signed-off-by: James Tucker <james@tailscale.com>
2022-11-23 15:38:54 -08:00
Brad Fitzpatrick
7bff7345cc ipn/ipnauth: start splitting ipnserver into new ipnauth package
We're trying to gut 90% of the ipnserver package. A lot will get
deleted, some will move to LocalBackend, and a lot is being moved into
this new ipn/ipnauth package which will be leaf-y and testable.

This is a baby step towards moving some stuff to ipnauth.

Update #6417
Updates tailscale/corp#8051

Change-Id: I28bc2126764f46597d92a2d72565009dc6927ee0
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-23 10:57:02 -08:00
Brad Fitzpatrick
5f6fec0eba cmd/tailscale: fix 'debug local-creds' hostname
Fixes #6446

Change-Id: I82f0a3dcf6aca25b7f67265533ee30a9d939d86f
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-23 09:58:32 -08:00
Andrew Dunham
ec790e58df net/dns: retry overwriting hosts file on Windows
Updates #5753

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I60f81bd3325d5ba5383b947c7a7aaa5b14e460f6
2022-11-23 11:36:50 -05:00
Maisem Ali
3a5d02cb31 ipn/ipnlocal: update comment about using FallbackResolvers for exit nodes
While reading the DNS code noticed that we were still using FallbackResolvers
in this code path but the comment was out of date.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-23 16:52:22 +05:00
Brad Fitzpatrick
300aba61a6 ipn, cmd/tailscale/cli: add LocalAPI IPN bus watch, Start, convert CLI
Updates #6417
Updates tailscale/corp#8051

Change-Id: I1ca360730c45ffaa0261d8422877304277fc5625
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-22 13:11:44 -08:00
Maisem Ali
d4f6efa1df ipn/ipnlocal: handle case when selected profile is deleted
Profile keys are not deleted but are instead set to `nil` which results
in getting a nil error and we were not handling that correctly.

Updates #713

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-23 00:42:18 +05:00
Tom DNetto
b45b948776 ipn/ipnlocal: call initTKALocked on backend start
Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-11-22 11:06:52 -08:00
License Updater
1ef4be2f86 licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-11-22 10:43:22 -08:00
Tom DNetto
aeb80bf8cb ipn/ipnlocal,tka: generate a nonce for each TKA
Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-11-22 10:31:22 -08:00
Tom DNetto
6708f9a93f cmd/tailscale,ipn: implement lock log command
This commit implements `tailscale lock log [--limit N]`, which displays an ordered list
of changes to network-lock state in a manner familiar to `git log`.

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-11-22 10:30:59 -08:00
Tom DNetto
ed1fae6c73 ipn/ipnlocal: always tx TKA sync after enablement
By always firing off a sync after enablement, the control plane should know the node's TKA head
at all times.

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-11-22 10:25:13 -08:00
Brad Fitzpatrick
0f7da5c7dc ipn{,/ipnlocal}, client/tailscale: move Taildrop recv notifications to LocalAPI HTTP method
Updates #6417

Change-Id: Iec544c477a0e5e9f1c6bf23555afec06255e2e22
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-22 08:49:13 -08:00
Anton Tolchanov
f053f16460 tsweb: export version metrics to Prometheus
This will allow tracking build versions and runtime versions in
Prometheus.

Signed-off-by: Anton Tolchanov <anton@tailscale.com>
2022-11-22 15:50:10 +00:00
Maisem Ali
8d84178884 ipn/ipnlocal: stop storing serverURL in LocalBackend
It's only read in a couple of places and we can read from Prefs directly.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-22 16:51:36 +05:00
Maisem Ali
aeac4bc8e2 ipn/ipnlocal: account for currentUserID when iterating over knownProfiles
We were not checking the currentUserID in all code paths that looped over
knownProfiles. This only impacted multi-user Windows setups.

Updates #713

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-22 15:31:17 +05:00
Maisem Ali
18c7c3981a ipn/ipnlocal: call checkPrefs in Start too
We were not calling checkPrefs on `opts.*Prefs` in (*LocalBackend).Start().

Updates #713

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-22 15:13:00 +05:00
Maisem Ali
41dd49391f tstest/integration: add --accept-risk=all to tailscale down
The test would fail if I was running it over SSH.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-21 17:33:37 -08:00
Brad Fitzpatrick
0480a925c1 ipn/ipnlocal: send Content-Security-Policy, etc to peerapi browser requests
Updates tailscale/corp#7948

Change-Id: Ie70e0d042478338a37b7789ac63225193e47a524
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-21 17:33:06 -08:00
Luke Rewega
b190c1667b words: add some cloven-hoofed ruminants (#6393)
The Bovini tribe is sorely underrepresented.

Signed-off-by: Luke Rewega <lrewega@c32.ca>
2022-11-21 16:49:00 -08:00
License Updater
5c9203669a licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-11-21 15:21:30 -08:00
Andrew Dunham
a0ef51f570 cmd/{tailscale,tailscaled}: embed manifest into Windows binaries
This uses a go:generate statement to create a bunch of .syso files that
contain a Windows resource file. We check these in since they're less
than 1KiB each, and are only included on Windows.

Fixes #6429

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I0512c3c0b2ab9d8d8509cf2037b88b81affcb81f
2022-11-21 18:15:51 -05:00
Maisem Ali
b94b91c168 cmd/tailscale/cli: add ability to set short names for profiles
This adds a `--nickname` flag to `tailscale login|set`.

Updates #713

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-22 04:03:24 +05:00
Maisem Ali
575fd5f22b ipn: add ability to name profiles
Updates #713

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-22 04:03:24 +05:00
Mihai Parparita
33520920c3 all: use strs.CutPrefix and strs.CutSuffix more
Updates places where we use HasPrefix + TrimPrefix to use the combined
function.

Updates #5309

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-11-21 14:32:16 -08:00
Aaron Klotz
41e1d336cc net/dns: change windows DNS manager to use pointer receiver
This is safer given that we need to close the NRPT database.

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2022-11-21 15:46:51 -06:00
shayne
bdd8ce6692 cmd/tailscale/cli: disallow empty text "" from serve CLI (#6416)
Current behavior is broken. tailscale serve text / "" returns no error
and shows up in tailscale serve status but requests return a 500
"empty handler".

Adds an error if the user passes in an empty string for the text
handler.

Closes #6405

Signed-off-by: Shayne Sweeney <shayne@tailscale.com>
2022-11-20 15:04:58 -05:00
shayne
d1e1c025b0 tailcfg: add TailscaleFunnelEnabled to HostInfo (#6414)
Adding this convenience for tailscale/corp#8015 and to avoid leaking
WireIngress.

Signed-off-by: Shayne Sweeney <shayne@tailscale.com>
2022-11-20 13:22:54 -05:00
Charlotte Brandhorst-Satzkorn
538f431d5d words: no explanation necessary (#6413)
Scales do not exist without a banana.

Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2022-11-20 00:01:01 -05:00
Charlotte Brandhorst-Satzkorn
aac3d5bdd1 words: good vibes only (#6412)
After consultation with Tom, it has been agreed that a vibe, or vibes,
can be felt in different quantifiable measures. That makes a vibe, or
vibes, a scale thus it must be immortalized.

Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2022-11-19 23:28:30 -05:00
Brad Fitzpatrick
039ea51ca6 ipn/ipnlocal: add health warning for unstable builds
Like the macOS About dialog.

Change-Id: Ic27f091e66e29d5eebe4e195eda97ed331d748fd
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-19 14:22:39 -08:00
Brad Fitzpatrick
a26f23d949 ipn/ipnlocal: actually fill out PeerAPIURLs in PeerStatus
The earlier 5f6d63936f was not complete.

Updates tailscale/corp#7515

Change-Id: I35efca51d1584c48ef6834a7d29cd42d7c943628
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-19 13:35:39 -08:00
Charlotte Brandhorst-Satzkorn
063eeefdca words: where do penguins go when they lose their tail? (#6403)
To the retail store.

Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2022-11-19 12:37:48 -05:00
Charlotte Brandhorst-Satzkorn
92fa0313d0 words: this list is really sheeping up to be something (#6399)
Ewe wouldn't have thought it was started as a joke.


Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2022-11-19 07:17:00 -08:00
shayne
f52a6d1b8c cmd/tailscale/cli, ipn: move serve CLI funcs on to ServeConfig (#6401)
Signed-off-by: Shayne Sweeney <shayne@tailscale.com>
2022-11-19 09:42:14 -05:00
Charlotte Brandhorst-Satzkorn
2847dd2aef words: you goatta be kid'in me (#6397)
My puns are so baaaaaaad

Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2022-11-19 00:45:45 -05:00
mel
e2f8b84170 words: add "coyote" to the wordlist for tailnet names (#6396)
Signed-off-by: yotes <yotes@fastmail.com>
2022-11-19 00:22:46 -05:00
License Updater
2eb0687969 licenses: update win/apple licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-11-18 19:10:05 -08:00
Brad Fitzpatrick
3a168cc1ff wgengine/magicsock: ignore pre-disco (pre-0.100) peers
There aren't any in the wild, other than one we ran on purpose to keep
us honest, but we can bump that one forward to 0.100.

Change-Id: I129e70724b2d3f8edf3b496dc01eba3ac5a2a907
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-18 17:52:08 -08:00
Tom DNetto
2a991a3541 ipn/{localapi,ipnserver}: set a CSP for ServeHTMLStatus, refactor host check
Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-11-18 16:13:09 -08:00
phirework
a011320370 magicsock: cleanup canp2p (#6391)
This renames canP2P in magicsock to canP2PLocked to reflect
expectation of mutex lock, fixes a race we discovered in the meantime,
and updates the current stats.

Co-authored-by: Brad Fitzpatrick <bradfitz@tailscale.com>
Signed-off-by: Jenny Zhang <jz@tailscale.com>
2022-11-18 12:23:22 -08:00
Maisem Ali
f1ad26f694 ipn/ipnlocal: strip NetworkLockKey from Prefs
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-19 00:57:49 +05:00
Anton Tolchanov
f40bb199f5 tsweb: cache prometheus metric names & types
Signed-off-by: Anton Tolchanov <anton@tailscale.com>
2022-11-18 19:52:37 +00:00
Anton Tolchanov
3c27632ffe tsweb: avoid dashes in Prometheus metric names
Ideally we should strip other invalid characters too, but that would
call for a regexp replacement which increases the number of allocations
and makes `TestVarzHandlerSorting` fail.

Signed-off-by: Anton Tolchanov <anton@tailscale.com>
2022-11-18 19:52:37 +00:00
Maisem Ali
dd50dcd067 ipn/ipnlocal: handle untagging nodes better
We would end up with duplicate profiles for the node as the UserID
would have chnaged. In order to correctly deduplicate profiles, we
need to look at both the UserID and the NodeID. A single machine can
only ever have 1 profile per NodeID and 1 profile per UserID.

Note: UserID of a Node can change when the node is tagged/untagged,
and the NodeID of a device can change when the node is deleted so we
need to check for both.

Updates #713

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-18 14:00:19 +05:00
Brad Fitzpatrick
f18dde6ad1 ipn/ipnserver: validate Host header on debug ServeHTMLStatus status
Updates tailscale/corp#7948

Change-Id: I3a8c64f353af1eeae620812b2700ce4af4fbbc88
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-17 23:02:40 -08:00
Brad Fitzpatrick
a13753ae1e ipn/localapi: require POST to add a bugreport marker
The LocalClient.BugReport method already sends it via POST.

Updates tailscale/corp#7948

Change-Id: I98dbd558c99d4296d934baa5ebc97052c7413073
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-17 21:54:06 -08:00
Maisem Ali
b5299d7d0e portlist: wait for lsof cmd to exit
We were leaking processes otherwise.

Co-authored-by: Mihai Parparita <mihai@tailscale.com>
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-18 03:42:35 +05:00
shayne
a97369f097 cmd/tailscale/cli: flesh out serve CLI and tests (#6304)
Signed-off-by: Shayne Sweeney <shayne@tailscale.com>
2022-11-17 16:09:43 -05:00
Maisem Ali
5f6d63936f ipn/ipnlocal: fill out PeerAPIURLs in PeerStatus
Updates tailscale/corp#7515

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-18 01:49:32 +05:00
Andrew Dunham
0af61f7c40 cmd/tailscale, util/quarantine: set quarantine flags on files from Taildrop
This sets the "com.apple.quarantine" flag on macOS, and the
"Zone.Identifier" alternate data stream on Windows.

Change-Id: If14f805467b0e2963067937d7f34e08ba1d1fa85
Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
2022-11-17 15:06:02 -05:00
Andrew Dunham
cec48743fb ipn/localapi: set security headers
Change-Id: I028b6ab91229e2f824e5a69856ca9e1844f7486e
Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
2022-11-17 10:59:13 -05:00
Will Norris
1b8c13e18a words: help mercat get her sparkle back
Signed-off-by: Will Norris <will@tailscale.com>
2022-11-16 23:27:13 -08:00
Maisem Ali
f3519f7b29 cmd/tailscale/cli: add login and switch subcommands
Updates #713

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-17 10:27:56 +05:00
Joe Tsai
ec1e67b1ab tstime: fix ParseDuration for '6' digit (#6363)
The cutset provided to strings.TrimRight was missing the digit '6',
making it such that we couldn't parse something like "365d".

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-11-16 21:01:09 -08:00
Joe Tsai
eff62b7b1b logtail: remove MustParsePublicID (#6335)
This function is no longer necessary as you can trivially rewrite:

	logtail.MustParsePublicID(...)

with:

	must.Get(logtail.ParsePublicID(...))

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-11-16 15:38:27 -08:00
Maisem Ali
1de64e89cd ipn/ipnlocal: set Hostinfo.WireIngress when ingress enabled
Optimization for control.

Updates tailscale/corp#7515

Change-Id: Ie93b232ab3e543d53062b462bdc13e279176f7a9
Co-authored-by: Brad Fitzpatrick <bradfitz@tailscale.com>
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-17 02:39:25 +05:00
Mihai Parparita
b3da5de10f ipn/localapi: also allow localhost as the LocalAPI host
The Mac and iOS LocalAPI clients make requests to it.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-11-16 12:11:45 -08:00
Maisem Ali
b0736fe6f7 ipn/ipnlocal: move selfNode from peerAPIServer to peerAPIHandler
The peerAPIHandler is instantiated per PeerAPI call so it is
guaranteed to have the latest selfNode.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-17 01:02:03 +05:00
Maisem Ali
2f4fca65a1 ipn/ipnlocal: prevent duplicate profiles of the same user
Updates #713

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-17 00:59:55 +05:00
Brad Fitzpatrick
e9c851b04b ipn/ipnlocal: also accept service IP IPv6 literal in brackets for quad100
The fix in 4fc8538e2 was sufficient for IPv6. Browsers (can?) send the
IPv6 literal, even without a port number, in brackets.

Updates tailscale/corp#7948

Change-Id: I0e429d3de4df8429152c12f251ab140b0c8f6b77
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-16 11:47:42 -08:00
Maisem Ali
296e712591 tailcfg: add CapabilityDebug
Updates tailscale/corp#7948

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-17 00:21:10 +05:00
Maisem Ali
1e78fc462c ipn/ipnlocal: add some validation to PeerAPI
Updates tailscale/corp#7948

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-16 23:33:53 +05:00
Maisem Ali
1f4669a380 all: standardize on LocalAPI
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-16 23:15:24 +05:00
Maisem Ali
22238d897b all: standardize on PeerAPI
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-16 22:49:13 +05:00
Brad Fitzpatrick
1b56acf513 ipn/ipnlocal: move LocalBackend.validPopBrowserURL empty check from caller
I was too late with review feedback to 513780f4f8.

Updates tailscale/corp#7948

Change-Id: I8fa3b4eba4efaff591a2d0bfe6ab4795638b7c3a
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-16 09:43:43 -08:00
Maisem Ali
513780f4f8 ipn/ipnlocal: move URL validation to LocalBackend
Updates tailscale/corp#7948

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-16 21:54:58 +05:00
Andrew Dunham
4caca8619e ipn/localapi: serve files with application/octet-stream Content-Type
Updates tailscale/corp#7948

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I5f570c04974598c7abae4017e4a7a0f63492c87c
2022-11-16 11:36:15 -05:00
Brad Fitzpatrick
4fc8538e2f ipn/ipnlocal: check quad100 Host header in info page
Updates tailscale/corp#7948

Change-Id: I0ab61c764bff9ba8afaf9070db73e971eb018477
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-16 08:18:12 -08:00
Maisem Ali
49b0ce8180 ipn/ipnlocal: update profile on server sent profile changes
We were not updating the LoginProfile.UserProfile when a netmap
updated the UserProfile (e.g. when a node was tagged via the admin panel).

Updates #713

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-16 21:08:53 +05:00
Brad Fitzpatrick
976e88d430 client/tailscale/apitype: add LocalAPIHost const, use it
Removes duplication.

Updates tailcale/corp#7948

Change-Id: I564c912ecfde31ba2293124bb1316e433c2a10f1
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-16 08:07:51 -08:00
Brad Fitzpatrick
97319a1970 control/controlclient: filter PopBrowserURL values to https schemes
No need for http://, etc. In case a control server sends a bogus value
and GUIs don't also validate.

Updates tailscale/corp#7948

Change-Id: I0b7dd86aa396bdabd88f0c4fe51831fb2ec4175a
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-16 07:54:52 -08:00
Maisem Ali
2d653230ef ssh/tailssh: only call CloseWrite when both stdout and stderr are done
Updates #5209

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-16 16:22:47 +05:00
Brad Fitzpatrick
6ea2d01626 ipn/ipnlocal: be more assertive about rules for applyPrefsToHostinfo (now Locked)
The old docs were too cagey.

Change-Id: I92c4fdc4165e7ca35c4537aebe51eb3604b56f6d
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-15 21:32:01 -08:00
Mihai Parparita
d3878ecd62 ipn/ipnlocal: add client metrics for profile switching
Updates #713

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-11-15 21:30:39 -08:00
Brad Fitzpatrick
b08f37d069 tailcfg: add Hostinfo.WireIngress bool
Yet unused. Future optimization for control.

Updates tailscale/corp#7515

Change-Id: Icd755aa8b1d6ca61d16dfc124c28c9c56ebdfee5
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-15 21:06:18 -08:00
Mihai Parparita
6d48a54b3d version: make IsSandboxedMacOS handle the IPNExtension binary too
It was previously only invoked from the CLI, which only runs from the
main .app. However, starting with #6022 we also invoke it from the
network extension.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-11-15 17:54:10 -08:00
Maisem Ali
235309adc4 all: store NL keys per profile
This moves the NetworkLock key from a dedicated StateKey to be part of the persist.Persist struct.
This struct is stored as part for ipn.Prefs and is also the place where we store the NodeKey.

It also moves the ChonkDir from "/tka" to "/tka-profile/<profile-id>". The rename was intentional
to be able to delete the "/tka" dir if it exists.

This means that we will have a unique key per profile, and a unique directory per profile.

Note: `tailscale logout` will delete the entire profile, including any keys. It currently does not
delete the ChonkDir.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-15 19:51:52 +00:00
License Updater
751f866f01 licenses: update win/apple licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-11-15 10:57:53 -08:00
Maisem Ali
fe81ee62d7 ipn/ipnlocal: do controlclient.Shutdown in a different goroutine
We do not need to wait for it to complete. And we might have to
call Shutdown from callback from the controlclient which might
already be holding a lock that Shutdown requires.

Updates #713

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-15 20:45:38 +05:00
Denton Gentry
e0cadc5496 cmd/tailscale: access QNAP via localhost
QNAP 5.x works much better if we let Apache proxy
tailscale web, which means the URLs can no longer
be relative since apache sends us an internal
URL. Access QNAP authentication via
http://localhost:8080/ as documented in
https://download.qnap.com/dev/API_QNAP_QTS_Authentication.pdf

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-11-14 21:43:52 -08:00
Brad Fitzpatrick
1950e56478 tsnet: add Server.ControlURL option
As requested in #6250 from @majst01.

Change-Id: Ia4bc5c4ebc98cd67d07328a1a42b87574261ddde
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-14 12:57:48 -08:00
Brad Fitzpatrick
f81351fdef portlist: fix data race
Maisem spotted the bug. The initial getList call in NewPoller wasn't
making a clone (only the Run loop's getList calls).

Fixes #6314

Change-Id: I8ab8799fcccea8e799140340d0ff88a825bb6ff0
Co-authored-by: Maisem Ali <maisem@tailscale.com>
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-14 12:34:18 -08:00
Tom DNetto
42855d219b ipn/ipnlocal: fix checks for node-key presence in TKA logic
Found by tests in another repo. TKA code wasn't always checking enough to be sure a node-key was set for the current state.

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-11-14 20:33:31 +00:00
Mihai Parparita
0cc65b4bbe ipn/localapi: add LocalAPI endpoints for profile switching
Exposes a REST-y API for interacting with the profile switching
introduced in #6022.

Updates #713

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-11-14 11:37:10 -08:00
Tom DNetto
3271daf7a3 cmd/tailscale,ipn: support disablement args in lock cli, implement disable
* Support specifiying disablement values in lock init command
 * Support specifying rotation key in lock sign command
 * Implement lock disable command
 * Implement disablement-kdf command

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-11-14 19:22:33 +00:00
Brad Fitzpatrick
fb392e34b5 net/tshttpproxy: don't ignore env-based HTTP proxies after system lookups fail
There was a mechanism in tshttpproxy to note that a Windows proxy
lookup failed and to stop hitting it so often. But that turns out to
fire a lot (no PAC file configured at all results in a proxy lookup),
so after the first proxy lookup, we were enabling the "omg something's
wrong, stop looking up proxies" bit for awhile, which was then also
preventing the normal Go environment-based proxy lookups from working.

This at least fixes environment-based proxies.

Plenty of other Windows-specific proxy work remains (using
WinHttpGetIEProxyConfigForCurrentUser instead of just PAC files,
ignoring certain types of errors, etc), but this should fix
the regression reported in #4811.

Updates #4811

Change-Id: I665e1891897d58e290163bda5ca51a22a017c5f9
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-14 09:11:33 -08:00
Brad Fitzpatrick
96e1582298 cmd/tailscale/cli: add debug 2021 --verbose flag
Change-Id: Ic93c2a8451518755fb44b5c35272d9b9353fe4d4
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-14 09:11:33 -08:00
Maisem Ali
a255a08ea6 tailcfg: bump capver for ingress
Updates tailscale/corp#7515

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-14 09:03:16 +05:00
Brad Fitzpatrick
13bee8e91c cmd/tailscale/cli: update serve debug set command after FUS profile change
The key changed, but also we have a localapi method to set it anyway, so
use that.

Updates tailscale/corp#7515

Change-Id: Ia08ea2509f0bdd9b59e4c5de53aacf9a7d7eda36
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-13 12:55:23 -08:00
Brad Fitzpatrick
7c285fe7ee ipn/ipnlocal: fix error message typo in ingress peerapi handler
Updates tailscale/corp#7515

Change-Id: I81edd7d9f8958eef61be71d3d34e545cd3347008
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-13 12:54:38 -08:00
Brad Fitzpatrick
3114eacbb8 ipn/ipnlocal: don't warn about serve listener failing on IPv6-less machines
Fixes #6303

Change-Id: Ie1ce12938f68dfa0533246bbe3b9d7f3e749a243
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-13 10:11:25 -08:00
Brad Fitzpatrick
90bd74fc05 net/dns: add a health warning when Linux /etc/resolv.conf is overwritten
Change-Id: I925b4d904bc7ed920bc5afee11e6dcb2ffc2fbfd
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-13 08:00:27 -08:00
Brad Fitzpatrick
3f8e185003 health: add Warnable, move ownership of warnable items to callers
The health package was turning into a rando dumping ground. Make a new
Warnable type instead that callers can request an instance of, and
then Set it locally in their code without the health package being
aware of all the things that are warnable. (For plenty of things the
health package will want to know details of how Tailscale works so it
can better prioritize/suppress errors, but lots of the warnings are
pretty leaf-y and unrelated)

This just moves two of the health warnings. Can probably move more
later.

Change-Id: I51e50e46eb633f4e96ced503d3b18a1891de1452
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-13 08:00:27 -08:00
License Updater
b1a6d8e2b1 licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-11-13 03:23:30 -08:00
Brad Fitzpatrick
001f482aca net/dns: make "direct" mode on Linux warn on resolv.conf fights
Run an inotify goroutine and watch if another program takes over
/etc/inotify.conf. Log if so.

For now this only logs. In the future I want to wire it up into the
health system to warn (visible in "tailscale status", etc) about the
situation, with a short URL to more info about how you should really
be using systemd-resolved if you want programs to not fight over your
DNS files on Linux.

Updates #4254 etc etc

Change-Id: I86ad9125717d266d0e3822d4d847d88da6a0daaa
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-12 22:19:13 -08:00
Maisem Ali
b87cb2c4a5 ipn/ipnlocal: call restart backend on user changes
This makes it so that the backend also restarts when users change,
otherwise an extra call to Start was required.

Updates #713

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-13 09:00:15 +05:00
Maisem Ali
8e85227059 cmd/tailscale/cli: [set] handle selectively modifying routes/exit node
Noticed this while debugging something else, we would reset all routes if
either `--advertise-exit-node` or `--advertise-routes` were set. This handles
correctly updating them.

Also added tests.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-13 08:17:51 +05:00
Maisem Ali
26d1fc867e ipn/ipnlocal: delete profile on logout
Updates #713

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-13 07:32:24 +05:00
Brad Fitzpatrick
0544d6ed04 cmd/tailscale/cli: continue fleshing out serve CLI tests
The serve CLI doesn't exist yet, but we want nice tests for it when it
does exist.

Updates tailscale/corp#7515

Change-Id: Ib4c73d606242c4228f87410bbfd29bec52ca6c60
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-12 16:48:27 -08:00
Brad Fitzpatrick
b5ac9172fd cmd/tailscale/cli: move earlier shell test to its own files
(I should've done this to start with.)

Updates tailscale/corp#7515

Change-Id: I7fb88cf95772790fd415ecf28fc52bde95507641
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-12 14:07:27 -08:00
Maisem Ali
9e70daad6f ipn/ipnlocal: make TKA tests not have side effects
It left the envknob turned on which meant that running all the tests
in the package had different behavior than running just any one test.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-12 20:56:48 +05:00
Brad Fitzpatrick
29bc021dcd cmd/tailscale/cli: add outline of serve CLI tests
Updates tailscale/corp#7515

Change-Id: Ib3956d4756bdcea0da89238a3c520ce8ac8004ec
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-11 19:13:07 -08:00
shayne
74e892cbc2 ipn/ipnlocal: listen to serve ports on netmap addrs (#6282)
Updates tailscale/corp#7515

Signed-off-by: Shayne Sweeney <shayne@tailscale.com>
2022-11-11 21:46:26 -05:00
Brad Fitzpatrick
cbc89830c4 tsnet: be stricter about arguments to Server.Listen
Fixes #6201

Change-Id: I14b2b8ce9bee838344a3fad4f305c78ab775f72e
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-11 18:23:23 -08:00
Brad Fitzpatrick
08e110ebc5 cmd/tailscale: make "up", "status" warn if routes and --accept-routes off
Example output:

    # Health check:
    #     - Some peers are advertising routes but --accept-routes is false

Also, move "tailscale status" health checks to the bottom, where they
won't be lost in large netmaps.

Updates #2053
Updates #6266

Change-Id: I5ae76a0cd69a452ce70063875cd7d974bfeb8f1a
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-11 10:56:50 -08:00
Brad Fitzpatrick
66b4a363bd net/dns/resolver: add yet another 4via6 DNS form that's hopefully more robust
$ dig +short @100.100.100.100 aaaa 10-2-5-3-via-7.foo-bar.ts.net
fd7a:115c:a1e0:b1a:0:7:a02:503

$ dig +short @100.100.100.100 aaaa 10-2-5-3-via-7
fd7a:115c:a1e0:b1a:0:7:a02:503

$ ping 10-2-5-3-via-7
PING 10-2-5-3-via-7(fd7a:115c:a1e0:b1a:0:7:a02:503 (fd7a:115c:a1e0:b1a:0:7:a02:503)) 56 data bytes
...

Change-Id: Ice8f954518a6a2fca8b2c04da7f31f61d78cdec4
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-11 09:30:48 -08:00
License Updater
e0cd9e9dec licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-11-11 08:11:23 -08:00
Brad Fitzpatrick
6aab4fb696 cmd/tailscale/cli: start making cert output support pkcs12 (p12) output
If the --key-file output filename ends in ".pfx" or ".p12", use pkcs12
format.

This might not be working entirely correctly yet but might be enough for
others to help out or experiment.

Updates #2928
Updates #5011

Change-Id: I62eb0eeaa293b9fd5e27b97b9bc476c23dd27cf6
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-11 07:55:09 -08:00
Maisem Ali
d585cbf02a wgengine/router: [bsd/darwin] remove and readd routes on profile change
Noticed when testing FUS on tailscale-on-macOS, that routing would break
completely when switching between profiles. However, it would start working
again when going back to the original profile tailscaled started with.

Turns out that if we change the addrs on the interface we need to remove and readd
all the routes.

Updates #713

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-11 19:49:01 +05:00
Tom DNetto
4c31183781 cmd/tailscale,ipn: minor fixes to tailscale lock commands
* Fix broken add/remove key commands
 * Make lock status display whether the node is signed

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-11-11 07:48:40 -06:00
License Updater
c60e444696 licenses: update win/apple licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-11-11 04:20:29 -08:00
Maisem Ali
ae18cd02c1 ipn: add AdvertisesExitNode and AdminPageURL accessors to PrefsView
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-11 16:03:15 +05:00
Maisem Ali
6cc0036b40 ipn/ipnlocal: use updated prefs in tkaSyncIfNeeded
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-11 12:03:17 +05:00
Brad Fitzpatrick
329a0a8406 client/tailscale: remove some json.Unmarshal repetition, add helper
Change-Id: I73ece09895ad04c7d8c4a5673f9bd360be873b9f
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-10 21:54:56 -08:00
Maisem Ali
f00a49667d control/controlclient: make Status.Persist a PersistView
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-11 10:45:47 +05:00
Maisem Ali
4d330bac14 ipn/ipnlocal: add support for multiple user profiles
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-11 10:45:47 +05:00
Brad Fitzpatrick
c9d6a9cb4d ipn/ipnlocal: add optional TLS termination on proxied TCP connections
Updates tailscale/corp#7515

Change-Id: Ib250fa20275971563adccfa72db48e0cec02b7a5
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-10 21:35:16 -08:00
shayne
56dfdbe190 repo: add .vscode/ to .gitignore (#6278)
Signed-off-by: Shayne Sweeney <shayne@tailscale.com>
2022-11-11 00:10:47 -05:00
Brad Fitzpatrick
f4a522fd67 client/tailscale: make a helper for json.Marshal'ed request bodies
Change-Id: I59eb1643addf8793856089690407fb45053c8e4d
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-10 20:47:51 -08:00
License Updater
13cadeabcd licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-11-10 20:43:52 -08:00
Brad Fitzpatrick
69e4b8a359 client/tailscale: document ServeConfig accessors a bit more
Updates tailscale/corp#7515

Change-Id: Iecae581e4b34ce70b2df531bc95c6c390a398c38
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-10 20:38:07 -08:00
Pat Maddox
9bf3ef4167 ssh/tailssh: add Tailscale SSH (server) support on FreeBSD
Change-Id: I607194b6ef99205e777f3df93a74ffe1a2e0344c
Signed-off-by: Pat Maddox <pat@ratiopbc.com>
2022-11-10 20:25:23 -08:00
shayne
e3a66e4d2f ipn/localapi: introduce get/set config for serve (#6243)
Updates tailscale/corp#7515

Signed-off-by: Shayne Sweeney <shayne@tailscale.com>
2022-11-10 22:58:40 -05:00
Brad Fitzpatrick
7b5866ac0a ipn/ipnlocal: support serving files/directories too
Updates tailscale/corp#7515

Change-Id: I7b4c924005274ba57763264313d70d2a0c55da30
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-10 18:09:35 -08:00
Denton Gentry
446057d613 scripts/installer.sh: add Nobara Linux.
Fixes https://github.com/tailscale/tailscale/issues/5763

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-11-10 14:25:26 -08:00
Mihai Parparita
7a07bc654b ipn/localapi: rename /profile to /pprof
Avoids name collision with profiles for user switching.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-11-10 12:02:16 -08:00
Joe Tsai
9a05cdd2b5 syncs: add Map (#6260)
Map is a concurrent safe map that is a trivial wrapper
over a Go map and a sync.RWMutex.

It is optimized for use-cases where the entries change often,
which is the opposite use-case of what sync.Map is optimized for.

The API is patterned off of sync.Map, but made generic.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-11-10 10:55:26 -08:00
Brad Fitzpatrick
d7bfef12cf ipn/ipnlocal: support https+insecure:// backend proxy targets
Updates tailscale/corp#7515

Change-Id: Ie50295c09e4a16959b37087d8165c4d7360db37f
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-10 10:09:49 -08:00
Brad Fitzpatrick
9dfb0916c2 ipn/ipnlocal, tailcfg: wire up ingress peerapi
Updates tailscale/corp#7515

Co-authored-by: Shayne Sweeney <shayne@tailscale.com>
Change-Id: I7eac7b4ac37fd8e8a9e0469594c1e9e7dd0da666
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-10 09:48:10 -08:00
David Anderson
65f3dab4c6 cmd/containerboot: make a tests table, add more tests.
Also fix a bugs found while adding the tests, oops.

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-11-10 09:14:27 -08:00
Aaron Klotz
73b8968404 ipn/ipnlocal: ensure Persist information is saved to server mode start state
Numerous issues have been filed concerning an inability to install and run
Tailscale headlessly in unattended mode, particularly after rebooting. The
server mode `Prefs` stored in `server-state.conf` were not being updated with
`Persist` state once the node had been succesfully logged in.

Users have been working around this by finagling with the GUI to make it force
a state rewrite. This patch makes that unnecessary by ensuring the required
server mode state is updated when prefs are updated by the control client.

Fixes https://github.com/tailscale/tailscale/issues/3186

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2022-11-10 10:43:40 -06:00
Brad Fitzpatrick
32a4ff3e5f ipn/ipnlocal: implement the reverse proxy HTTP handler type
Updates tailscale/corp#7515

Change-Id: Icbfe57f44b9516388edc0556eb04a370a9e3e009
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-10 06:12:33 -08:00
Brad Fitzpatrick
6beb3184d5 ipn/ipnlocal: don't serve a TLS cert unless it has webserver config
Even if the name is right, or is configured on a different port.

Updates tailscale/corp#7515

Change-Id: I8b721968f3241af10d98431e1b5ba075223e6cd3
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-10 06:12:33 -08:00
Brad Fitzpatrick
1a94c309ea ipn/ipnlocal: support web TLS ports other than 443
Updates tailscale/corp#7515

Change-Id: I87df50b1bc92efd1d8c538c2ad4f1222361e4d6b
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-10 06:12:33 -08:00
Brad Fitzpatrick
4797bacb7c ipn/ipnlocal: send RST when serving an actionless TCPPortHandler
Updates tailscale/corp#7515

Change-Id: I790f1b5d1e8a887e39bb573b4610b8f37a3f5963
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-10 06:12:33 -08:00
David Anderson
2111357568 cmd/containerboot: add tests.
Signed-off-by: David Anderson <danderson@tailscale.com>
2022-11-09 19:15:55 -08:00
Brad Fitzpatrick
b683921b87 ipn/ipnlocal: add start of handling TCP proxying
Updates tailscale/corp#7515

Change-Id: I82d19b5864674b2169f25ec8e429f60a543e0c57
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-09 16:38:11 -08:00
Brad Fitzpatrick
4bccc02413 ipn/ipnlocal: use ServerConfig views internally
Updates tailscale/corp#7515

Change-Id: Ica2bc44b92d281d5ce16cee55b7ca51c7910145c
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-09 16:38:11 -08:00
Joe Tsai
4de643b714 types/netlogtype: add constants for maximum serialized sizes of ConnectionCounts (#6163)
There is a finite limit to the maximum message size that logtail can upload.
We need to make sure network logging messages remain under this size.
These constants allow us to compute the maximum number of ConnectionCounts
we can buffer before we must flush.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-11-09 15:50:07 -08:00
Brad Fitzpatrick
25e26c16ee ipn/ipnlocal: start implementing web server bits of serve
Updates tailscale/corp#7515

Change-Id: I96f4016161ba3c370492da941274c6d9a234c2bb
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-09 07:38:10 -08:00
Brad Fitzpatrick
c35dcd427f cmd/tailscale/cli: make dev-store-set debug command a bit more magic
Temporarily at least. Makes sharing scripts during development easier.

Updates tailscale/corp#7515

Change-Id: I0e7aa461accd2c60740c1b37f3492b6bb58f1be3
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-09 06:47:42 -08:00
Brad Fitzpatrick
df5e40f731 ipn: add WebServerConfig, add views
cmd/viewer couldn't deal with that map-of-map. Add a wrapper type
instead, which also gives us a place to add future stuff.

Updates tailscale/corp#7515

Change-Id: I44a4ca1915300ea8678e5b0385056f0642ccb155
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-09 06:17:45 -08:00
Brad Fitzpatrick
79472a4a6e wgengine/netstack: optimize shouldProcessInbound, avoiding 4via6 lookups
All IPv6 packets for the self address were doing netip.Prefix.Contains
lookups.

If if we know they're for a self address (which we already previously
computed and have sitting in a bool), then they can't be for a 4via6
range.

Change-Id: Iaaaf1248cb3fecec229935a80548ead0eb4cb892
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-08 20:28:28 -08:00
Brad Fitzpatrick
2daf0f146c ipn/ipnlocal, wgengine/netstack: start handling ports for future serving
Updates tailscale/corp#7515

Change-Id: I966e936e72a2ee99be8d0f5f16872b48cc150258
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-08 19:39:07 -08:00
Andrew Dunham
acf5839dd2 wgengine/netstack: add tests for shouldProcessInbound
Inspired by #6235, let's explicitly test the behaviour of this function
to ensure that we're not processing things we don't expect to.

Change-Id: I158050a63be7410fb99452089ea607aaf89fe91a
Signed-off-by: Andrew Dunham <andrew@tailscale.com>
2022-11-08 15:59:57 -08:00
Andrew Dunham
e85613aa2d net/netcheck: don't use a space in the captive portal challenge
The derpers don't allow whitespace in the challenge.

Change-Id: I93a8b073b846b87854fba127b5c1d80db205f658
Signed-off-by: Andrew Dunham <andrew@tailscale.com>
2022-11-08 16:58:54 -05:00
ysicing
cba1312dab util/endian: add support on Loongnix-Server (loong64)
Change-Id: I8275d158779c749a4cae2b4457d390871b4b8e3c
Signed-off-by: ysicing <i@ysicing.me>
2022-11-08 08:24:15 -08:00
Brad Fitzpatrick
abfdcd0f70 wgengine/netstack: fix shouldProcessInbound peerapi non-SYN handling
It was eating TCP packets to peerapi ports to subnet routers.  Some of
the TCP flow's packets went onward, some got eaten.  So some TCP flows
to subnet routers, if they used an unfortunate TCP port number, got
broken.

Change-Id: Ifea036119ccfb081f4dfa18b892373416a5239f8
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-08 08:07:56 -08:00
Brad Fitzpatrick
6d8320a6e9 ipn/{ipnlocal,localapi}: move most of cert.go to ipnlocal
Leave only the HTTP/auth bits in localapi.

Change-Id: I8e23fb417367f1e0e31483e2982c343ca74086ab
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-07 21:50:04 -08:00
Brad Fitzpatrick
9be8d15979 ipn/localapi: refactor some cert code in prep for a move
I want to move the guts (after the HTTP layer) of the certificate
fetching into the ipnlocal package, out of localapi.

As prep, refactor a bit:

* add a method to do the fetch-from-cert-or-as-needed-with-refresh,
  rather than doing it in the HTTP hander

* convert two methods to funcs, taking the one extra field (LocalBackend)
  then needed from their method receiver. One of the methods needed
  nothing from its receiver.

This will make a future change easier to reason about.

Change-Id: I2a7811e5d7246139927bb86e7db8009bf09b3be3
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-07 21:07:22 -08:00
Mihai Parparita
847a8cf917 api.md: make it clearer where to get the tailnet name in API calls
We added the tailnet organization name to to the settings page with
tailscale/corp#6977, but the docs were not updated to reflect this.
We later also changed "tailnet name" to refer to the MagicDNS hostname
(tailscale/corp#7537), which further confuses things (see https://stackoverflow.com/questions/74132318).

Make it slightly clearer what is the expected value for tailnet names in
API calls and how to get it.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-11-07 16:33:19 -08:00
David Anderson
5e703bdb55 docs/k8s: add secrets patching permission to the tailscale role.
Fixes #6225.

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-11-07 16:18:01 -08:00
David Anderson
6acc27a92f cmd/containerboot: be more targeted when enabling IP forwarding.
Only enable forwarding for an IP family if any forwarding is required
for that family.

Fixes #6221.

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-11-07 15:55:34 -08:00
Brad Fitzpatrick
5bb7e0307c cmd/tailscale, ipn/ipnlocal: add debug command to write to StateStore for dev
Not for end users (unless directed by support). Mostly for ease of
development for some upcoming webserver work.

Change-Id: I43acfed217514567acb3312367b24d620e739f88
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-07 15:34:43 -08:00
David Anderson
bf2d3cd074 cmd/containerboot: don't write device ID when not in Kubernetes.
Fixes #6218.

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-11-07 15:02:29 -08:00
David Anderson
e0669555dd cmd/containerboot: don't write device ID into non-existent secret.
Fixes #6211

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-11-07 12:51:58 -08:00
Xe Iaso
be7556aece tsnet/example/tshello: use strings.Cut (#6198)
strings.Cut allows us to be more precise here. This example was written
before strings.Cut existed.

Signed-off-by: Xe <xe@tailscale.com>

Signed-off-by: Xe <xe@tailscale.com>
2022-11-07 15:06:34 -05:00
Andrew Dunham
c2d7940ec0 cmd/tailscaled, net/tstun: add build tags to omit BIRD and TAP
Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I7a39f4eeeb583b73ecffaf4c5f086a38e3a53e2e
2022-11-07 11:13:14 -05:00
Brad Fitzpatrick
036334e913 net/netcheck: deflake (maybe) magicsock's TestNewConn
Updates #6207

Change-Id: I51d200d0b42b9a1ef799d0abfc8d4bd871c50cf2
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-05 22:02:13 -07:00
Brad Fitzpatrick
db2cc393af util/dirwalk, metrics, portlist: add new package for fast directory walking
This is similar to the golang.org/x/tools/internal/fastwalk I'd
previously written but not recursive and using mem.RO.

The metrics package already had some Linux-specific directory reading
code in it. Move that out to a new general package that can be reused
by portlist too, which helps its scanning of all /proc files:

    name                old time/op    new time/op    delta
    FindProcessNames-8    2.79ms ± 6%    2.45ms ± 7%  -12.11%  (p=0.000 n=10+10)

    name                old alloc/op   new alloc/op   delta
    FindProcessNames-8    62.9kB ± 0%    33.5kB ± 0%  -46.76%  (p=0.000 n=9+10)

    name                old allocs/op  new allocs/op  delta
    FindProcessNames-8     2.25k ± 0%     0.38k ± 0%  -82.98%  (p=0.000 n=9+10)

Change-Id: I75db393032c328f12d95c39f71c9742c375f207a
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-05 16:26:51 -07:00
Brad Fitzpatrick
21ef7e5c35 portlist: add macOS osImpl, finish migration to new style
Previously:

* 036f70b7b4 for linux
* 35bee36549 for windows

This does macOS.

And removes all the compat code for the old style. (e.g. iOS, js are
no longer mentioned; all platforms without implementations just
default to not doing anything)

One possible regression is that platforms without explicit
implementations previously tried to do the "netstat -na" style to get
open ports (but not process names). Maybe that worked on FreeBSD and
OpenBSD previously, but nobody ever really tested it. And it was kinda
useless without associated process names. So better off removing those
for now until they get a good implementation.

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-04 10:58:23 -07:00
Brad Fitzpatrick
da8def8e13 all: remove old +build tags
The //go:build syntax was introduced in Go 1.17:

https://go.dev/doc/go1.17#build-lines

gofmt has kept the +build and go:build lines in sync since
then, but enough time has passed. Time to remove them.

Done with:

    perl -i -npe 's,^// \+build.*\n,,' $(git grep -l -F '+build')

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-04 07:25:42 -07:00
Maisem Ali
bb2cba0cd1 ipn: add missing check for nil Notify.Prefs
This was missed in 6afe26575c

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-04 04:12:53 +05:00
Maisem Ali
6afe26575c ipn: make Notify.Prefs be a *ipn.PrefsView
It is currently a `ipn.PrefsView` which means when we do a JSON roundtrip,
we go from an invalid Prefs to a valid one.

This makes it a pointer, which fixes the JSON roundtrip.

This was introduced in 0957bc5af2.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-04 04:00:26 +05:00
Adrian Dewhurst
c3a5489e72 util/winutil: remove log spam for missing registry keys
It's normal for HKLM\SOFTWARE\Policies\Tailscale to not exist but that
currently produces a lot of log spam.

Signed-off-by: Adrian Dewhurst <adrian@tailscale.com>
2022-11-03 18:55:39 -04:00
David Anderson
76904b82e7 cmd/containerboot: PID1 for running tailscaled in a container.
This implements the same functionality as the former run.sh, but in Go
and with a little better awareness of tailscaled's lifecycle.

Also adds TS_AUTH_ONCE, which fixes the unfortunate behavior run.sh had
where it would unconditionally try to reauth every time if you gave it
an authkey, rather than try to use it only if auth is actually needed.
This makes it a bit nicer to deploy these containers in automation, since
you don't have to run the container once, then go and edit its definition
to remove authkeys.

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-11-03 15:30:32 -07:00
Maisem Ali
0759d78f12 tailcfg: bump CurrentCapabilityVersion for EarlyNoise
Updates #5972

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-04 02:44:56 +05:00
Maisem Ali
a413fa4f85 control/controlclient: export NoiseClient
This allows reusing the NoiseClient in other repos without having to reimplement the earlyPayload logic.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-04 01:44:43 +05:00
Brad Fitzpatrick
d57cba8655 net/tshttpproxy: add clientmetrics on Windows proxy lookup paths
To collect some data on how widespread this is and whether there's
any correlation between different versions of Windows, etc.

Updates #4811

Change-Id: I003041d0d7e61d2482acd8155c1a4ed413a2c5c4
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-03 12:16:42 -07:00
Brad Fitzpatrick
e55ae53169 tailcfg: add Node.UnsignedPeerAPIOnly to let server mark node as peerapi-only
capver 48

Change-Id: I20b2fa81d61ef8cc8a84e5f2afeefb68832bd904
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-02 21:55:04 -07:00
Brad Fitzpatrick
3367136d9e wgengine/netstack: remove old unused handleSSH hook
It's leftover from an earlier Tailscale SSH wiring and I forgot to
delete it apparently.

Change-Id: I14f071f450e272b98d90080a71ce68ba459168d1
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-02 20:44:31 -07:00
License Updater
18fa1a0ad7 licenses: update win/apple licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-11-02 14:52:33 -07:00
Joe Tsai
2327c6b05f wgengine/netlog: preserve Tailscale addresses for exit traffic (#6165)
Exit node traffic is aggregated to protect the privacy
of those using an exit node. However, it is reasonable to
at least log which nodes are making most use of an exit node.

For a node using an exit node,
the source will be the taiscale IP address of itself,
while the destination will be zeroed out.

For a node that serves as an exit node,
the source will be zeroed out,
while the destination will be tailscale IP address
of the node that initiated the exit traffic.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-11-02 14:25:31 -07:00
Andrew Dunham
e975cb6b05 ipn/ipnlocal: fix test flake when we log after a test completes
This switches from using an atomic.Bool to a mutex for reasons that are
described in the commit, and should address the flakes that we're still
seeing.

Fixes #3020

Change-Id: I4e39471c0eb95886db03020ea1ccf688c7564a11
Signed-off-by: Andrew Dunham <andrew@tailscale.com>
2022-11-02 16:17:59 -04:00
Tom DNetto
0af57fce4c cmd/tailscale,ipn: implement lock sign command
Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-11-02 15:00:01 -05:00
Joe Tsai
7d6775b082 wgengine: respect --no-logs-no-support flag for network logging (#6172)
In the future this will cause a node to be unable to join the tailnet
if network logging is enabled.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-11-02 12:57:04 -07:00
Brad Fitzpatrick
910db02652 client/tailscale, tsnet, ipn/ipnlocal: prove nodekey ownership over noise
Fixes #5972

Change-Id: Ic33a93d3613ac5dbf172d6a8a459ca06a7f9e547
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-02 09:22:26 -07:00
License Updater
8c790207a0 licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-11-02 09:15:24 -07:00
Brad Fitzpatrick
a0ed2c2eb5 go.mod: bump golang-x-crypto
Fixes #5533

Change-Id: I403de0e9ed5a9a63055242a86720d6f4e0899af7
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-02 09:01:11 -07:00
Andrew Dunham
06b55ab50f prober: fix test flake
This was tested by running 10000 test iterations and observing no flakes
after this change was made.

Change-Id: Ib036fd03a3a17800132c53c838cc32bfe2961306
Signed-off-by: Andrew Dunham <andrew@tailscale.com>
2022-11-02 09:58:40 -04:00
Brad Fitzpatrick
988c1f0ac7 control/controlclient, tailcfg: add support for EarlyNoise payload before http/2
Not yet used, but skipped over, parsed, and tested.

Updates #5972

Change-Id: Icd00196959ce266ae16a6c9244bd5e458e2c2947
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-01 15:11:22 -07:00
Brad Fitzpatrick
a7f7e79245 cmd/tailscale/cli: hide old, useless --host-routes flag
It was from very early Tailscale and no longer makes sense.

Change-Id: I31b4e728789f26b0376ebe73aa1b4bbbb1d62607
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-01 10:54:49 -07:00
Brad Fitzpatrick
f4ff26f577 types/pad32: delete package
Use Go 1.19's new 64-bit alignment ~hidden feature instead.

Fixes #5356

Change-Id: Ifcbcb115875a7da01df3bc29e9e7feadce5bc956
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-11-01 09:03:54 -07:00
Aoang
60f77ba515 Fix vm ci tests clogging in fork repository pull request
fix: https://github.com/tailscale/tailscale/issues/5771
Signed-off-by: Aoang <aoang@x2oe.com>
2022-11-01 08:43:07 -07:00
Maisem Ali
1440742a1c ssh/tailssh: use root / as cmd.Dir when users HomeDir doesn't exist
Fixes #5224

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-11-01 16:33:44 +05:00
Mihai Parparita
2be951a582 cmd/tsconnect: fix null pointer dereference when DNS lookups fail
If we never had a chance to open the SSH session we should not try to
close it.

Fixes #6089

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-10-31 14:23:44 -07:00
License Updater
e2519813b1 licenses: update win/apple licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-10-31 12:11:10 -07:00
Maisem Ali
42f7ef631e wgengine/netstack: use 72h as the KeepAlive Idle time for Tailscale SSH
Setting TCP KeepAlives for Tailscale SSH connections results in them
unnecessarily disconnecting. However, we can't turn them off completely
as that would mean we start leaking sessions waiting for a peer to come
back which may have gone away forever (e.g. if the node was deleted from
the tailnet during a session).

Updates #5021

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-10-31 21:33:50 +05:00
Tom DNetto
d98305c537 cmd,ipn/ipnlocal,tailcfg: implement TKA disablement
* Plumb disablement values through some of the internals of TKA enablement.
 * Transmit the node's TKA hash at the end of sync so the control plane understands each node's head.
 * Implement /machine/tka/disable RPC to actuate disablement on the control plane.

There is a partner PR for the control server I'll send shortly.

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-10-31 11:05:44 -05:00
Denton Gentry
3d8eda5b72 scripts/install.sh: add RHEL7.
Fixes https://github.com/tailscale/tailscale/issues/5729

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-10-31 05:35:32 -07:00
Denton Gentry
5677ed1e85 scripts/installer.sh: add Debian Sid (rolling release)
There is no VERSION_ID.

root@sid:~# cat /etc/os-release
PRETTY_NAME="Debian GNU/Linux bookworm/sid"
NAME="Debian GNU/Linux"
VERSION_CODENAME=bookworm
ID=debian
HOME_URL="https://www.debian.org/"
SUPPORT_URL="https://www.debian.org/support"
BUG_REPORT_URL="https://bugs.debian.org/"

Fixes https://github.com/tailscale/tailscale/issues/5522

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-10-31 05:35:32 -07:00
Denton Gentry
798dba14eb scripts/install.sh: add openSUSE Leap 15.4
Fixes https://github.com/tailscale/tailscale/issues/6095

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-10-31 05:35:32 -07:00
Brad Fitzpatrick
ea24895e08 client/tailscale/apitype, tailcfg: delete never used mysterious PerDomain field
It does nothing and never did and I don't think anybody remembers what
the original goal for it was.

Updates #5229 (fixes, but need to clean it up in another repo too)

Change-Id: I81cc6ff44d6d2888bc43e9145437f4c407907ea6
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-10-30 20:46:36 -07:00
Brad Fitzpatrick
7ad636f5b7 cmd/tailscale/cli: flesh out "tailscale ssh" CLI docs
Per user feedback.

Fixes #5877

Change-Id: Ib70ad57ec2507244fc54745f4e43c0ce13f51e9c
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-10-30 20:09:41 -07:00
Brad Fitzpatrick
3336d08d59 cmd/tailscale/cli: make set without args print usage
Make "tailscale set" by itself be equivalent to "tailscale set -h"
rather than just say "you did it wrong" and make people do another -h
step.

Change-Id: Iad2b2ddb2595c0121d2536de5b78648f3eded3e3
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-10-30 16:09:02 -07:00
Brad Fitzpatrick
7b6cd4e659 cmd/tailscale/cli: make set's usage match up's, other than defaults
Fixes #6082

Change-Id: I92dc4726d866dcfd87e93ff09772601851d92ccf
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-10-30 15:59:51 -07:00
Brad Fitzpatrick
231b88cc51 control/controlclient: add start of noise+http2 upgrade test
Basic HTTP/2-over-noise client test. To be fleshed out in subsequent
commits that add more functionality to the noise client.

Updates #5972

Change-Id: I0178343523ef4ae8e8fc87bae53cbc81f4e32fde
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-10-30 05:17:59 -07:00
Anton Tolchanov
e25ab75795 net/dns: getting base DNS config is not supported on macOS
Instead of returning a custom error, use ErrGetBaseConfigNotSupported
that seems to be intended for this use case. This fixes DNS resolution
on macOS clients compiled from source.

Signed-off-by: Anton Tolchanov <anton@tailscale.com>
2022-10-30 08:57:33 +00:00
Anton Tolchanov
193afe19cb ipn/ipnlocal: add tags and a few other details to self status
This makes tags, creation time, exit node option and primary routes
for the current node exposed via `tailscale status --json`

Signed-off-by: Anton Tolchanov <anton@tailscale.com>
2022-10-29 10:00:06 +01:00
Brad Fitzpatrick
120bfc97ce control/controlclient: refactor noiseClient, connections, http2
In prep for stateful http2 noise connections.

Updates #5972

Change-Id: I9ebecc3b2d5d193621b87d39b506f231d6c82145
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-10-28 15:49:36 -07:00
Mihai Parparita
4e6e3bd13d ipn/ipnlocal: fix a log line having function pointers instead of values
Followup to using ipn.PrefsView (#6031).

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-10-28 15:46:41 -07:00
Joe Tsai
cfef47ddcc wgengine: perform router reconfig for netlog-only changes (#6118)
If the network logging configruation changes (and nothing else)
we will tear down the network logger and start it back up.
However, doing so will lose the router configuration state.
Manually reconfigure it with the routing state.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-10-28 15:33:24 -07:00
Brad Fitzpatrick
dfe67afb4a control/controlhttp: remove ClientConn.UntrustedUpgradeHeaders
It was just added and unreleased but we've decided to go a different route.

Details are in 5e9e57ecf5.

Updates #5972

Change-Id: I49016af469225f58535f63a9b0fbe5ab6a5bf304
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-10-28 12:25:22 -07:00
Joe Tsai
b2035a1dca cmd/netlogfmt: handle any stream of network logs (#6108)
Make netlogfmt useful regardless of the exact schema of the input.
If a JSON object looks like a network log message,
then unmarshal it as one and then print it.
This allows netlogfmt to support both a stream of JSON objects
directly serialized from netlogtype.Message, or the schema
returned by the /api/v2/tailnet/{{tailnet}}/network-logs API endpoint.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-10-28 10:40:45 -07:00
Joe Tsai
48ddb3af2a wgengine/netlog: enforce hard limit on network log message sizes (#6109)
This is a temporary hack to prevent logtail getting stuck
uploading the same excessive message over and over.
A better solution will be discussed and implemented.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-10-28 10:13:35 -07:00
Joe Tsai
a3602c28bd wgengine/netlog: embed the StableNodeID of the authoring node (#6105)
This allows network messages to be annotated with which node it came from.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-10-28 10:09:30 -07:00
Joe Tsai
81fd259133 wgengine/magicsock: gather physical-layer statistics (#5925)
There is utility in logging traffic statistics that occurs at the physical layer.
That is, in order to send packets virtually to a particular tailscale IP address,
what physical endpoints did we need to communicate with?

This functionality logs IP addresses identical to
what had always been logged in magicsock prior to #5823,
so there is no increase in PII being logged.

ExtractStatistics returns a mapping of connections to counts.
The source is always a Tailscale IP address (without port),
while the destination is some endpoint reachable on WAN or LAN.
As a special case, traffic routed through DERP will use 127.3.3.40
as the destination address with the port being the DERP region.

This entire feature is only enabled if data-plane audit logging
is enabled on the tailnet (by default it is disabled).

Example of type of information logged:

	------------------------------------  Tx[P/s]    Tx[B/s]  Rx[P/s]   Rx[B/s]
	PhysicalTraffic:                       25.80      3.39Ki   38.80     5.57Ki
	    100.1.2.3 -> 143.11.22.33:41641    15.40      2.00Ki   23.20     3.37Ki
	    100.4.5.6 -> 192.168.0.100:41641   10.20      1.38Ki   15.60     2.20Ki
	    100.7.8.9 -> 127.3.3.40:2           0.20      6.40      0.00     0.00

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-10-27 16:26:52 -07:00
Brad Fitzpatrick
5e9e57ecf5 control/controlhttp: add AcceptHTTP hook to add coalesced Server->Client write
New plan for #5972. Instead of sending the public key in the clear
(from earlier unreleased 246274b8e9) where the client might have to
worry about it being dropped or tampered with and retrying, we'll
instead send it post-Noise handshake but before the HTTP/2 connection
begins.

This replaces the earlier extraHeaders hook with a different sort of
hook that allows us to combine two writes on the wire in one packet.

Updates #5972

Change-Id: I42cdf7c1859b53ca4dfa5610bd1b840c6986e09c
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-10-27 15:07:53 -07:00
Joe Tsai
c21a3c4733 types/netlogtype: new package for network logging types (#6092)
The netlog.Message type is useful to depend on from other packages,
but doing so would transitively cause gvisor and other large packages
to be linked in.

Avoid this problem by moving all network logging types to a single package.

We also update staticcheck to take in:

	003d277bcf

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-10-27 14:14:18 -07:00
Aaron Klotz
a44687e71f wgengine/winnet: invoke some COM methods directly instead of through IDispatch.
Intermittently in the wild we are seeing failures when calling
`INetworkConnection::GetNetwork`. It is unclear what the root cause is, but what
is clear is that the error is happening inside the object's `IDispatch` invoker
(as opposed to the method implementation itself).

This patch replaces our wrapper for `INetworkConnection::GetNetwork` with an
alternate implementation that directly invokes the method, instead of using
`IDispatch`. I also replaced the implementations of `INetwork::SetCategory` and
`INetwork::GetCategory` while I was there.

This patch is speculative and tightly-scoped so that we could possibly add it
to a dot-release if necessary.

Updates https://github.com/tailscale/tailscale/issues/4134
Updates https://github.com/tailscale/tailscale/issues/6037

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2022-10-27 14:05:31 -05:00
Brad Fitzpatrick
4021ae6b9d types/key: add missing ChallengePublic.UnmarshalText
Forgot it when adding the Challenge types earlier.

Change-Id: Ie0872c4e6dc25e5d832aa58c7b3f66d450bf6b71
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-10-27 11:12:38 -07:00
Adrian Dewhurst
8c09ae9032 tka, types/key: add NLPublic.KeyID
This allows direct use of NLPublic with tka.Authority.KeyTrusted() and
similar without using tricks like converting the return value of Verifier.

Signed-off-by: Adrian Dewhurst <adrian@tailscale.com>
2022-10-26 15:51:23 -04:00
Sonia Appasamy
944f43f1c8 docs/webhooks: add sample endpoint code
Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2022-10-26 14:28:00 -05:00
Andrew Dunham
95f3dd1346 net/interfaces: don't dereference null pointer if no destination/netmask
Fixes #6065

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I7159b8cbb8d5f47c0668cf83e59167f182f1defd
2022-10-26 10:28:26 -04:00
Maisem Ali
19b5586573 cmd/tailscale/cli: add beginnings of tailscale set
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-10-25 22:27:37 -07:00
Jordan Whited
a471681e28 wgengine/netstack: enable TCP SACK (#6066)
TCP selective acknowledgement can improve throughput by an order
of magnitude in the presence of loss.

Signed-off-by: Jordan Whited <jordan@tailscale.com>
2022-10-25 16:09:20 -07:00
Mihai Parparita
d60f7fe33f cmd/tsconnect: run wasm-opt on the generated wasm file
Saves about 1.4MB from the generated wasm file. The Brotli size is
basically unchanged (it's actually slightly larger, by 40K), suggesting
that most of the size delta is due to not inlining and other changes
that were easily compressible.

However, it still seems worthwhile to have a smaller final binary, to
reduce parse time and increase likelihood that we fit in the browser's
disk cache. Actual performance appears to be unchanged.

Updates #5142

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-10-25 13:16:37 -07:00
Maisem Ali
2a9ba28def ipn/ipnlocal: set prefs before calling tkaSyncIfNeeded
Caught this in a test in a different repo.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-10-25 11:57:42 -07:00
Will Norris
bff202a290 cmd/nginx-auth: add experimental status badge to README 2022-10-25 11:03:40 -07:00
Brad Fitzpatrick
35bee36549 portlist: use win32 calls instead of running netstat process [windows]
Turns out using win32 instead of shelling out to child processes is a
bit faster:

    name                  old time/op    new time/op    delta
    GetListIncremental-4     278ms ± 2%       0ms ± 7%  -99.93%  (p=0.000 n=8+10)

    name                  old alloc/op   new alloc/op   delta
    GetListIncremental-4     238kB ± 0%       9kB ± 0%  -96.12%  (p=0.000 n=10+8)

    name                  old allocs/op  new allocs/op  delta
    GetListIncremental-4     1.19k ± 0%     0.02k ± 0%  -98.49%  (p=0.000 n=10+10)

Fixes #3876 (sadly)

Change-Id: I1195ac5de21a8a8b3cdace5871d263e81aa27e91
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-10-25 10:55:25 -07:00
Andrew Dunham
527741d41f shell.nix: add graphviz
Change-Id: Ic25e11a056a7624ebba923d2b87d947e24c41a20
Signed-off-by: Andrew Dunham <andrew@tailscale.com>
2022-10-25 13:03:31 -04:00
License Updater
a1a2c165e9 licenses: update win/apple licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-10-25 09:49:50 -07:00
Denton Gentry
dafc822654 cmd/nginx-auth: increment version.
We need a new release to handle TCD changes
after MagicDNS GA

Updates https://github.com/tailscale/tailscale/issues/6048

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-10-25 08:38:54 -07:00
Maisem Ali
9f39c3b10f ipn/ipnlocal: make EditPrefs strip private keys before returning
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-10-24 15:57:00 -07:00
Maisem Ali
a2d15924fb types/persist: add PublicNodeKey helper
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-10-24 15:57:00 -07:00
Maisem Ali
0957bc5af2 ipn/ipnlocal: use ipn.PrefsView
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-10-24 15:57:00 -07:00
Maisem Ali
20324eeebc ipn/prefs: add views
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-10-24 15:57:00 -07:00
Andrew Dunham
ba459aeef5 net/interfaces: don't call GetList in List.ForeachInterface
It looks like this was left by mistake in 4a3e2842.

Change-Id: Ie4e3d5842548cd2e8533b3552298fb1ce9ba761a
Signed-off-by: Andrew Dunham <andrew@tailscale.com>
2022-10-24 16:55:24 -04:00
Mihai Parparita
660abd7309 cmd/tsconnect: add README to generated NPM package
Makes the landing page at https://www.npmjs.com/package/@tailscale/connect
look slightly nicer.

Fixes #5976

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-10-24 13:51:32 -07:00
Denton Gentry
9beb07b4ff scripts/install.sh: add Ubuntu Kinetic Kudu
Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-10-24 07:17:00 -07:00
Brad Fitzpatrick
575c599410 portlist: add a test that verifies changes are picked up over time
To avoid annoying firewall dialogs on macOS and Windows, only run it
on Linux by default without the flag.

Change-Id: If8486c31d4243ade54b0131f673237c6c9184c08
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-10-23 22:02:22 -07:00
Brad Fitzpatrick
036f70b7b4 portlist: refactor, introduce OS-specific types
Add an osImpl interface that can be stateful and thus more efficient
between calls. It will later be implemented by all OSes but for now
this change only adds a Linux implementation.

Remove Port.inode. It was only used by Linux and moves into its osImpl.

Don't reopen /proc/net/* files on each run. Turns out you can just
keep then open and seek to the beginning and reread and the contents
are fresh.

    name                    old time/op    new time/op    delta
    GetListIncremental-8    7.29ms ± 2%    6.53ms ± 1%  -10.50%  (p=0.000 n=9+9)

    name                   old alloc/op   new alloc/op   delta
    GetListIncremental-8    1.30kB ±13%    0.70kB ± 5%  -46.38%  (p=0.000 n=9+10)

    name                  old allocs/op  new allocs/op  delta
    GetListIncremental-8      33.2 ±11%      18.0 ± 0%  -45.82%  (p=0.000 n=9+10)

Updates #5958

Change-Id: I4be83463cbd23c2e2fa5d0bdf38560004f53401b
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-10-23 20:29:23 -07:00
Peter Cai
4597ec1037 net/dnscache: Handle 4-in-6 addresses in DNS responses
On Android, the system resolver can return IPv4 addresses as IPv6-mapped
addresses (i.e. `::ffff:a.b.c.d`). After the switch to `net/netip`
(19008a3), this case is no longer handled and a response like this will
be seen as failure to resolve any IPv4 addresses.

Handle this case by simply calling `Unmap()` on the returned IPs. Fixes #5698.

Signed-off-by: Peter Cai <peter@typeblog.net>
2022-10-23 08:41:51 -07:00
Brad Fitzpatrick
70dde89c34 portlist: add package doc, file comments, move a method to the right file
And respect envknob earlier. NewPoller has one caller and ignores
errors; they just signal ipnlocal to log a warning and not use the
portlist poller.

Change-Id: I4a33af936fe780cca8c7197d4d74ac31a1dc01e3
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-10-22 21:44:40 -07:00
Brad Fitzpatrick
774fa72d32 portlist: add BenchmarkGetListIncremental
In contrast to BenchmarkGetList, this new BenchmarkGetListIncremental
acts like what happens in practice, remembering the previous run and
avoiding work that's already been done previously.

Currently:

    BenchmarkGetList
    BenchmarkGetList-8                           100          11011100 ns/op           68411 B/op       2211 allocs/op
    BenchmarkGetList-8                           100          11443410 ns/op           69073 B/op       2223 allocs/op
    BenchmarkGetList-8                           100          11217311 ns/op           68421 B/op       2197 allocs/op
    BenchmarkGetList-8                           100          11035559 ns/op           68801 B/op       2220 allocs/op
    BenchmarkGetList-8                           100          10921596 ns/op           69226 B/op       2225 allocs/op
    BenchmarkGetListIncremental
    BenchmarkGetListIncremental-8                168           7187217 ns/op            1192 B/op         28 allocs/op
    BenchmarkGetListIncremental-8                172           7004525 ns/op            1194 B/op         28 allocs/op
    BenchmarkGetListIncremental-8                162           7235889 ns/op            1221 B/op         29 allocs/op
    BenchmarkGetListIncremental-8                164           7035671 ns/op            1219 B/op         29 allocs/op
    BenchmarkGetListIncremental-8                174           7095448 ns/op            1114 B/op         27 allocs/op

Updates #5958

Change-Id: I1bd5a4b206df4173e2cb8e8a780429d9daa6ef1d
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-10-22 20:52:28 -07:00
Pontus Leitzler
f36ddd9275 words: even the odds with something that reminds you of vacation (#6025)
The cute little salak belongs there. It also evens the odds if tails
start a mutiny against scales. Even though they outnumber scales, they
should still know their place. Behind.

Signed-off-by: Pontus Leitzler <leitzler@gmail.com>
2022-10-22 14:43:57 -07:00
Brad Fitzpatrick
3697609aaa portlist: remove unix.Readlink allocs on Linux
name       old time/op    new time/op    delta
    GetList-8    11.2ms ± 5%    11.1ms ± 3%     ~     (p=0.661 n=10+9)

    name       old alloc/op   new alloc/op   delta
    GetList-8    83.3kB ± 1%    67.4kB ± 1%  -19.05%  (p=0.000 n=10+10)

    name       old allocs/op  new allocs/op  delta
    GetList-8     2.89k ± 2%     2.19k ± 1%  -24.24%  (p=0.000 n=10+10)

(real issue is we're calling this code as much as we are, but easy
enough to make it efficient because it'll still need to be called
sometimes in any case)

Updates #5958

Change-Id: I90c20278d73e80315a840aed1397d24faa308d93
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-10-22 11:30:53 -07:00
Brad Fitzpatrick
7149155b80 portlist: further reduce allocations on Linux
Make Linux parsePorts also an append-style API and attach it to
caller's provided append base memory.

And add a little string intern pool in front of the []byte to string
for inode names.

    name       old time/op    new time/op    delta
    GetList-8    11.1ms ± 4%     9.8ms ± 6%  -11.68%  (p=0.000 n=9+10)

    name       old alloc/op   new alloc/op   delta
    GetList-8    92.8kB ± 2%    79.7kB ± 0%  -14.11%  (p=0.000 n=10+9)

    name       old allocs/op  new allocs/op  delta
    GetList-8     2.94k ± 1%     2.76k ± 0%   -6.16%  (p=0.000 n=10+10)

More coming. (the bulk of the allocations are in addProcesses and
filesystem operations, most of which we should usually be able to
skip)

Updates #5958

Change-Id: I3f0c03646d314a16fef7f8346aefa7d5c96701e7
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-10-22 10:50:51 -07:00
Brad Fitzpatrick
def089f9c9 portlist: unexport all Poller fields, removing unused one, rework channels
Poller.C and Poller.c were duplicated for one caller. Add an accessor
returning the receive-only version instead. It'll inline.

Poller.Err was unused. Remove.

Then Poller is opaque.

The channel usage and shutdown was a bit sketchy. Clean it up.

And document some things.

Change-Id: I5669e54f51a6a13492cf5485c83133bda7ea3ce9
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-10-22 05:47:34 -07:00
Brad Fitzpatrick
46ce80758d portlist: update some internals to use append-style APIs
In prep for reducing garbage, being able to reuse memory.  So far this
doesn't actually reuse much. This is just changing signatures around.

But some improvement in any case:

    bradfitz@tsdev:~/src/tailscale.com$ ~/go/bin/benchstat before after
    name       old time/op    new time/op    delta
    GetList-8    11.8ms ± 9%     9.9ms ± 3%  -15.98%  (p=0.000 n=10+10)

    name       old alloc/op   new alloc/op   delta
    GetList-8    99.5kB ± 2%    91.9kB ± 0%   -7.62%  (p=0.000 n=9+9)

    name       old allocs/op  new allocs/op  delta
    GetList-8     3.05k ± 1%     2.93k ± 0%   -3.83%  (p=0.000 n=8+9)

More later, once parsers can reuse strings from previous parses.

Updates #5958

Change-Id: I76cd5048246dd24d11c4e263d8bb8041747fb2b0
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-10-21 22:26:37 -07:00
Brad Fitzpatrick
67597bfc9e portlist: unexport GetList
It's an internal implementation detail, and I plan to refactor it
for performance (garbage) reasons anyway, so start by hiding it.

Updates #5958

Change-Id: I2c0d1f743d3495c5f798d1d8afc364692cd9d290
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-10-21 20:48:52 -07:00
Will Norris
7b745a1a50 .github: run CI on release branches
Signed-off-by: Will Norris <will@tailscale.com>
2022-10-21 15:18:43 -07:00
Andrew Dunham
74693793be net/netcheck, tailcfg: track whether OS supports IPv6
We had previously added this to the netcheck report in #5087 but never
copied it into the NetInfo struct. Additionally, add it to log lines so
it's visible to support.

Change-Id: Ib6266f7c6aeb2eb2a28922aeafd950fe1bf5627e
Signed-off-by: Andrew Dunham <andrew@tailscale.com>
2022-10-21 15:31:42 -04:00
Maisem Ali
42d9e7171c Makefile: add publishdevimage target
This builds and publishes the tailscale container image for dev testing.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-10-21 10:19:06 -07:00
Anton Tolchanov
bd47e28638 prober: optionally spread probes over time
By default all probes with the same probe interval that have been added
together will run on a synchronized schedule, which results in spiky
resource usage and potential throttling by third-party systems (for
example, OCSP servers used by the TLS probes).

To address this, prober can now run in "spread" mode that will
introduce a random delay before the first run of each probe.

Signed-off-by: Anton Tolchanov <anton@tailscale.com>
2022-10-21 09:41:53 +01:00
Charlotte Brandhorst-Satzkorn
adec726fee words: for charlotte, by charlotte (#6002)
What's better than getting a community request?

A community request from another Charlotte!

Bun and hops!

Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2022-10-20 14:50:28 -07:00
Maisem Ali
74637f2c15 wgengine/router: [linux] add before deleting interface addrs
Deleting may temporarily result in no addrs on the interface, which results in
all other rules (like routes) to get dropped by the OS.

I verified this fixes the problem.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-10-20 13:39:33 -07:00
Charlotte Brandhorst-Satzkorn
95f630ced0 words: beaver, the cutest of them all (#6001)
Beavers have scales, on their tails.

Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2022-10-20 12:18:15 -07:00
phirework
d13c9cdfb4 wgengine/magicsock: set up pathfinder (#5994)
Sets up new file for separate silent disco goroutine, tentatively named
pathfinder for now.

Updates #540

Co-authored-by: Brad Fitzpatrick <bradfitz@tailscale.com>
Signed-off-by: Jenny Zhang <jz@tailscale.com>
2022-10-20 14:34:49 -04:00
Brad Fitzpatrick
deac82231c wgengine/magicsock: add start of alternate send path
During development of silent disco (#540), an alternate send policy
for magicsock that doesn't wake up the radio frequently with
heartbeats, we want the old & new policies to coexist, like we did
previously pre- and post-disco.

We started to do that earlier in 5c42990c2f but only set up the
env+control knob plumbing to set a bool about which path should be
used.

This starts to add a way for the silent disco code to update the send
path from a separate goroutine. (Part of the effort is going to
de-state-machinify the event based soup that is the current disco
code and make it more Go synchronous style.)

So far this does nothing. (It does add an atomic load on each send
but that should be noise in the grand scheme of things, and a even more
rare atomic store of nil on node config changes.)

Baby steps.

Updates #540

Co-authored-by: Jenny Zhang <jz@tailscale.com>
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-10-20 08:45:42 -07:00
Anton Tolchanov
69f61dcad8 prober: add a DERP probe manager based on derpprobe
This ensures that each DERP server is probed individually (TLS and STUN)
and also manages per-region mesh probing. Actual probing code has been
copied from cmd/derpprobe.

Signed-off-by: Anton Tolchanov <anton@tailscale.com>
2022-10-20 13:54:34 +01:00
Charlotte Brandhorst-Satzkorn
f39847aa52 words: double double tails and trouble, scales aflame and puns abubble (#5992)
Months upon months I ponder about this,
Adding new words onto our little lists.
Given our integrity I should not have missed,
Including the creatures from folklore and myth.
Carefully curated, many of them hiss,
Don't forget about the ones hiding in the abyss.
Now they are added, I cannot resist,
Searching for more words for me to enlist.

Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2022-10-19 21:14:55 -07:00
Brad Fitzpatrick
afce773aae ipn: remove handle.go
It was unused in this repo. The Windows client used it, but it can move there.

Change-Id: I572816fd80cbbf1b8db734879b6280857d5bd2a7
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-10-19 20:52:22 -07:00
Brad Fitzpatrick
18c61afeb9 types/key: add ChallengePublic, ChallengePrivate, NewChallenge
Updates #5972

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-10-19 19:17:53 -07:00
Maisem Ali
d0b7a44840 api.md: add expirySeconds as parameter to post Tailnet keys
Updates #4570

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-10-19 12:05:54 -07:00
Andrew Dunham
e966f024b0 net/dns: print systemd-resolved ResolvConfMode
The ResolvConfMode property is documented to return how systemd-resolved
is currently managing /etc/resolv.conf. Include that information in the
debug line, when available, to assist in debugging DNS issues.

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I1ae3a257df1d318d0193a8c7f135c458ec45093e
2022-10-19 11:25:36 -04:00
Andrew Dunham
223126fe5b cmd/derper, net/netcheck: add challenge/response to generate_204 endpoint
The Lufthansa in-flight wifi generates a synthetic 204 response to the
DERP server's /generate_204 endpoint. This PR adds a basic
challenge/response to the endpoint; something sufficiently complicated
that it's unlikely to be implemented by a captive portal. We can then
check for the expected response to verify whether we're being MITM'd.

Follow-up to #5601

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I94a68c9a16a7be7290200eea6a549b64f02ff48f
2022-10-19 11:10:18 -04:00
Anton Tolchanov
d499afac78 net/interfaces: improve default route detection
Instead of treating any interface with a non-ifscope route as a
potential default gateway, now verify that a given route is
actually a default route (0.0.0.0/0 or ::/0).

Fixes #5879

Signed-off-by: Anton Tolchanov <anton@tailscale.com>
2022-10-19 11:10:19 +01:00
Anton Tolchanov
9c2ad7086c net/interfaces: deduplicate route table parsing on Darwin and FreeBSD
Signed-off-by: Anton Tolchanov <anton@tailscale.com>
2022-10-19 11:10:19 +01:00
Mihai Parparita
9d04ffc782 net/wsconn: add back custom wrapper for turning a websocket.Conn into a net.Conn
We removed it in #4806 in favor of the built-in functionality from the
nhooyr.io/websocket package. However, it has an issue with deadlines
that has not been fixed yet (see nhooyr/websocket#350). Temporarily
go back to using a custom wrapper (using the fix from our fork) so that
derpers will stop closing connections too aggressively.

Updates #5921

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-10-18 15:39:32 -07:00
Maya Kaczorowski
d00b095f14 .github: update issue templates (#5978)
Signed-off-by: Maya Kaczorowski <15946341+mayakacz@users.noreply.github.com>

Signed-off-by: Maya Kaczorowski <15946341+mayakacz@users.noreply.github.com>
2022-10-18 09:00:22 -07:00
Brad Fitzpatrick
9475801ebe ipn/ipnlocal: fix E.G.G. port number accounting
Change-Id: Id35461fdde79448372271ba54f6e6af586f2304d
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-10-18 06:43:47 -07:00
Mihai Parparita
37da617380 .github/workflows: use fast compression for NPM package CI check
Starting with #5946 we're compressing main.wasm when building the
package, but that should not show down the CI check.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-10-17 15:29:54 -07:00
Mihai Parparita
7741e9feb0 cmd/tsconnect: add progress and connection callbacks
Allows UI to display slightly more fine-grained progress when the SSH
connection is being established.

Updates tailscale/corp#7186

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-10-17 15:26:59 -07:00
Brad Fitzpatrick
246274b8e9 control/controlhttp: allow setting, getting Upgrade headers in Noise upgrade
Not currently used, but will allow us to usually remove a round-trip for
a future feature.

Updates #5972

Change-Id: I2770ea28e3e6ec9626d1cbb505a38ba51df7fba2
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-10-17 15:11:03 -07:00
License Updater
03ecf335f7 licenses: update android licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-10-17 14:09:10 -07:00
Joe Tsai
14100c0985 wgengine/magicsock: restore allocation-free endpoint.DstToString (#5971)
The wireguard-go code unfortunately calls this unconditionally
even when verbose logging is disabled.

Partial revert of #5911.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-10-17 13:22:48 -07:00
Brad Fitzpatrick
45b7e8c23c cmd/tailscale: make tailscale cert --serve-demo accept optional listen argument
Change-Id: I48f2f4f74c9996b9ed4bee02c61f125d42154a34
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-10-17 13:16:41 -07:00
Maisem Ali
630bcb5b67 tsnet,client/tailscale: add APIClient which runs API over Noise.
Updates tailscale/corp#4383

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-10-17 11:37:17 -07:00
Tom DNetto
e8a11f6181 tka: make rotation signatures use nested keyID
Duplicating this at each layer doesnt make any sense, and is another
invariant where things could go wrong.

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-10-17 10:59:15 -07:00
Xe Iaso
86c5bddce2 tsnet/examples/tshello: update example for LocalClient method (#5966)
Before this would silently fail if this program was running on a machine
that was not already running Tailscale. This patch changes the WhoIs
call to use the tsnet.Server LocalClient instead of the global tailscale
LocalClient.

Signed-off-by: Xe <xe@tailscale.com>

Signed-off-by: Xe <xe@tailscale.com>
2022-10-17 13:43:46 -04:00
Joe Tsai
9116e92718 cmd/netlogfmt: new package to pretty print network traffic logs (#5930)
This package parses a JSON stream of netlog.Message from os.Stdin
and pretty prints the contents as a stream of tables.

It supports reverse lookup of tailscale IP addresses if given
an API key and the tailnet that these traffic logs belong to.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-10-17 10:36:28 -07:00
Joe Tsai
9ee3df02ee wgengine/magicsock: remove endpoint.wgEndpoint (#5911)
This field seems seldom used and the documentation is wrong.
It is simpler to just derive its original value dynamically
when endpoint.DstToString is called.

This method is potentially used by wireguard-go,
but not in any code path is performance sensitive.
All calls to it use it in conjunction with fmt.Printf,
which is going to be slow anyways since it uses Go reflection.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-10-17 10:36:08 -07:00
dependabot[bot]
3a33895f1b .github: Bump peter-evans/create-pull-request from 4.1.1 to 4.1.4 (#5965)
* .github: Bump peter-evans/create-pull-request from 4.1.1 to 4.1.4
* Update semantic version comment.

Bumps [peter-evans/create-pull-request](https://github.com/peter-evans/create-pull-request) from 4.1.1 to 4.1.4.
- [Release notes](https://github.com/peter-evans/create-pull-request/releases)
- [Commits](18f90432be...ad43dccb4d)

---
updated-dependencies:
- dependency-name: peter-evans/create-pull-request
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>
Signed-off-by: M. J. Fromberger <fromberger@tailscale.com>
Co-authored-by: dependabot[bot] <49699333+dependabot[bot]@users.noreply.github.com>
Co-authored-by: M. J. Fromberger <fromberger@tailscale.com>
2022-10-17 09:25:29 -07:00
Andrew Dunham
a4e707bcf0 control/controlhttp: try to avoid flakes in TestDialPlan
Updates tailscale/corp#7446

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: Ifcf3b5176f065c2e67cbb8943f6356dea720a9c5
2022-10-17 11:34:57 -04:00
Denton Gentry
b55761246b prober: add utilities to generate alerts and warnings.
sendAlert will trigger the Incident Response system.
sendWarning will post to Slack.

Co-authored-by: M. J. Fromberger <fromberger@tailscale.com>
Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-10-16 23:34:04 -07:00
Maisem Ali
af966391c7 kube: handle 201 as a valid status code.
Fixes tailscale/corp#7478

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-10-16 14:47:27 -07:00
Denton Gentry
19dfdeb1bb cmd/tailscale: correct --cpu-profile help text
Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-10-16 09:07:24 -07:00
Charlotte Brandhorst-Satzkorn
4eed2883db words: space, the final frontier (#5952)
Captains log. Stardate 100386.37.

Work is proceeding on the Words list as Tailscalars are forced to scavenge for more taily and scaley things.

Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2022-10-15 12:46:19 -07:00
Andrew Dunham
c32f9f5865 cmd/tailscale, ipn: enable debug logs when --report flag is passed to bugreport (#5830)
Change-Id: Id22e9f4a2dcf35cecb9cd19dd844389e38c922ec
Signed-off-by: Andrew Dunham <andrew@tailscale.com>
2022-10-15 13:31:35 -04:00
Andrew Dunham
64ea60aaa3 derp: add TCP RTT metric on Linux (#5949)
Periodically poll the TCP RTT metric from all open TCP connections and
update a (bucketed) histogram metric.

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
Change-Id: I6214902196b05bf7829c9d0ea501ce0e13d984cf
2022-10-15 12:57:10 -04:00
Brad Fitzpatrick
a04f1ff9e6 logtail: default to 2s log flush delay on all platforms
Per chat. This is close enough to realtime but massively reduces
number of HTTP requests. (which you can verify with
TS_DEBUG_LOGTAIL_WAKES and watching tailscaled run at start)

By contrast, this is set to 2 minutes on mobile.

Change-Id: Id737c7924d452de5c446df3961f5e94a43a33f1f
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-10-15 09:25:12 -07:00
Mihai Parparita
63ad49890f cmd/tsconnect: pre-compress main.wasm when building the NPM package
This way we can do that once (out of band, in the GitHub action),
instead of increasing the time of each deploy that uses the package.

.wasm is removed from the list of automatically pre-compressed
extensions, an OSS bump and small change on the corp side is needed to
make use of this change.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-10-14 15:08:06 -07:00
License Updater
899b4cae10 licenses: update win/apple licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-10-14 13:28:10 -07:00
Tom DNetto
a515fc517b ipn/ipnlocal: make tkaSyncIfNeeded exclusive with a mutex
Running corp/ipn#TestNetworkLockE2E has a 1/300 chance of failing, and
deskchecking suggests thats whats happening are two netmaps are racing each
other to be processed through tkaSyncIfNeededLocked. This happens in the
first place because we release b.mu during network RPCs.

To fix this, we make the tka sync logic an exclusive section, so two
netmaps will need to wait for tka sync to complete serially (which is what
we would want anyway, as the second run through probably wont need to
sync).

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-10-14 12:42:43 -07:00
Tom DNetto
227777154a control/controlclient,ipn/ipnlocal,tailcfg: rotate node-key signature on register
CAPVER 47

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-10-14 10:23:40 -07:00
Anton Tolchanov
26af329fde prober: expand certificate verification logic in the TLS prober
TLS prober now checks validity period for all server certificates
and verifies OCSP revocation status for the leaf cert.

Signed-off-by: Anton Tolchanov <anton@tailscale.com>
2022-10-14 15:00:38 +01:00
License Updater
39d03b6b63 licenses: update win/apple licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-10-13 21:34:22 -07:00
Maisem Ali
3555a49518 net/dns: always attempt to read the OS config on macOS/iOS
Also reconfigure DNS on iOS/macOS on link changes.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-10-13 15:11:07 -07:00
James Tucker
539c073cf0 wgengine/magicsock: set UDP socket buffer sizes to 7MB
- At high data rates more buffer space is required in order to avoid
  packet loss during any cause of delay.
- On slower machines more buffer space is required in order to avoid
  packet loss while decryption & tun writing is underway.
- On higher latency network paths more buffer space is required in order
  to overcome BDP.
- On Linux set with SO_*BUFFORCE to bypass net.core.{r,w}mem_max.
- 7MB is the current default maximum on macOS 12.6
- Windows test is omitted, as Windows does not support getsockopt for
  these options.

Signed-off-by: James Tucker <james@tailscale.com>
2022-10-13 14:46:25 -07:00
Brad Fitzpatrick
a315336287 logtail: change batched upload mechanism to not use CPU when idle
The mobile implementation had a 2 minute ticker going all the time
to do a channel send. Instead, schedule it as needed based on activity.

Then we can be actually idle for long periods of time.

Updates #3363

Change-Id: I0dba4150ea7b94f74382fbd10db54a82f7ef6c29
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-10-13 14:45:05 -07:00
Will Norris
d05dd41bc1 api.md: document using '-' value as default tailnet
Signed-off-by: Will Norris <will@tailscale.com>
2022-10-13 14:13:28 -07:00
Brad Fitzpatrick
9a264dac01 net/netcheck: fix crash in checkCaptivePortal
If netcheck happens before there's a derpmap.

This seems to only affect Headscale because it doesn't send a derpmap
as early?

Change-Id: I51e0dfca8e40623e04702bc9cc471770ca20d2c2
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-10-13 13:09:21 -07:00
Mihai Parparita
b2855cfd86 derp/derphttp: fix nil pointer dereference when closing a netcheck client
NewNetcheckClient only initializes a subset of fields of derphttp.Client,
and the Close() call added by #5707 was result in a nil pointer dereference.
Make Close() safe to call when using NewNetcheckClient() too.

Fixes #5919

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-10-13 11:49:27 -07:00
James Tucker
4ec6d41682 wgengine/router: fix MTU configuration on Windows
Always set the MTU to the Tailscale default MTU. In practice we are
missing applying an MTU for IPv6 on Windows prior to this patch.

This is the simplest patch to fix the problem, the code in here needs
some more refactoring.

Fixes #5914

Signed-off-by: James Tucker <james@tailscale.com>
2022-10-13 10:48:03 -07:00
Joe Tsai
a1a43ed266 wgengine/netlog: add support for magicsock statistics (#5913)
This sets up Logger to handle statistics at the magicsock layer,
where we can correlate traffic between a particular tailscale IP address
and any number of physical endpoints used to contact the node
that hosts that tailscale address.

We also export Message and TupleCounts to better document the JSON format
that is being sent to the logging infrastructure.

This commit does NOT yet enable the actual logging of magicsock statistics.
That will be a future commit.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-10-13 10:46:29 -07:00
License Updater
db863bf00f licenses: update android licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-10-13 07:49:42 -07:00
Joe Tsai
f9120eee57 wgengine: start network logger in Userspace.Reconfig (#5908)
If the wgcfg.Config is specified with network logging arguments,
then Userspace.Reconfig starts up an asynchronous network logger,
which is shutdown either upon Userspace.Close or when Userspace.Reconfig
is called again without network logging or route arguments.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-10-12 15:05:21 -07:00
Joe Tsai
49bae7fd5c wgengine: fix typo in Engine.PeerForIP (#5912)
Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-10-12 14:14:22 -07:00
Sonia Appasamy
5363a90272 types/view: add ContainsNonExitSubnetRoutes func
Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2022-10-12 15:19:36 -05:00
Mihai Parparita
b49eb7d55c cmd/tsconnect: move NPM package to being under the @tailscale org
Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-10-12 13:18:45 -07:00
Joe Tsai
1b4e4cc1e8 wgengine/netlog: new package for traffic flow logging (#5864)
The Logger type managers a logtail.Logger for extracting
statistics from a tstun.Wrapper.
So long as Shutdown is called, it ensures that logtail
and statistic gathering resources are properly cleared up.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-10-12 11:57:13 -07:00
Brad Fitzpatrick
79755d3ce5 tstest/natlab: add Firewall.Reset method to drop firewall state
For future use in magicsock tests.

Updates #540

Change-Id: I2f07d1a2924f20b36e357c4533ff0a1a974d5061
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-10-12 10:16:16 -07:00
Denton Gentry
1b9ed9f365 VERSION.txt: this is 1.33.
We did not get this VERSION.txt file checked in at the correct time,
the prior 10 commits in `main` between the v1.32.0 tag point and
this commit were not part of release 1.32. We did no unstable builds
during this time, so the error should have no impact.

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-10-12 09:53:06 -07:00
License Updater
e7519adc18 licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-10-11 15:11:34 -07:00
Brad Fitzpatrick
e24de8a617 ssh/tailssh: add password-forcing workaround for buggy SSH clients
If the username includes a suffix of +password, then we accept
password auth and just let them in like it were no auth.

This exists purely for SSH clients that get confused by seeing success
to their initial auth type "none".

Co-authored-by: Maisem Ali <maisem@tailscale.com>
Change-Id: I616d4c64d042449fb164f615012f3bae246e91ec
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-10-11 15:03:02 -07:00
Anton Tolchanov
c070d39287 cmd/tailscaled: handle tailscaled symlink on macOS
When Tailscale is installed via Homebrew, `/usr/local/bin/tailscaled`
is a symlink to the actual binary.

Now when `tailscaled install-system-daemon` runs, it will not attempt
to overwrite that symlink if it already points to the tailscaled binary.
However, if executed binary and the link target differ, the path will
he overwritten - this can happen when a user decides to replace
Homebrew-installed tailscaled with a one compiled from source code.

Fixes #5353

Signed-off-by: Anton Tolchanov <anton@tailscale.com>
2022-10-11 16:09:26 +01:00
Denton Gentry
51d488673a scripts/installer.sh: add OSMC
Fixes https://github.com/tailscale/tailscale/issues/4960

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-10-11 04:24:41 -07:00
Emmanuel T Odeke
680f8d9793 all: fix more resource leaks found by staticmajor
Updates #5706

Signed-off-by: Emmanuel T Odeke <emmanuel@orijtech.com>
2022-10-10 20:46:56 -07:00
Brad Fitzpatrick
614a24763b tsweb: sort top-level expvars after removing type prefixes
Fixes #5778

Change-Id: I56c367338fa5686da288cc6545209ef4d6b88549
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-10-10 20:28:44 -07:00
Brad Fitzpatrick
0475ed4a7e cmd/ssh-auth-none-demo: put the hostname in the package doc
188.166.70.128 port 2222 for now. Some hostname later maybe.

Change-Id: I9c329410035221ed6cdff7a482727d30b77eea8b
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-10-10 10:47:31 -07:00
Maisem Ali
7df85c6031 cmd/ssh-auth-none-demo: add banner as part of the demo
Send two banners with a second in between, this demonstrates the case
where all banners are shown after auth completes and not during.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-10-10 10:43:31 -07:00
Brad Fitzpatrick
718914b697 tsweb: remove allocs introduced by earlier change
This removes the ~9 allocs added by #5869, while still keeping struct
fields sorted (the previous commit's tests still pass). And add a test
to lock it in that this shouldn't allocate.

Updates #5778

Change-Id: I4c12b9e2a1334adc1ea5aba1777681cb9fc18fbf
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-10-10 10:23:54 -07:00
License Updater
529e893f70 licenses: update win/apple licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-10-09 21:25:19 -07:00
Brad Fitzpatrick
8a187159b2 cmd/ssh-auth-none-demo: add demo SSH server that acts like Tailscale SSH
For SSH client authors to fix their clients without setting up
Tailscale stuff.

Change-Id: I8c7049398512de6cb91c13716d4dcebed4d47b9c
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-10-09 18:07:04 -07:00
Brad Fitzpatrick
b2994568fe ipn/localapi: put all the LocalAPI methods into a map
Rather than a bunch of switch cases.

Change-Id: Id1db813ec255bfab59cbc982bee351eb36373245
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-10-09 18:05:55 -07:00
Maisem Ali
f172fc42f7 ssh/tailssh: close sshContext on context cancellation
This was preventing tailscaled from shutting down properly if there were
active sessions in certain states (e.g. waiting in check mode).

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-10-09 17:17:03 -07:00
Hasnain Lakhani
8fe04b035c tsweb: sort varz by name after stripping prefix (#5778)
This makes it easier to view prometheus metrics.

Added a test case which demonstrates the new behavior - the test
initially failed as the output was ordered in the same order
as the fields were declared in the struct (i.e. foo_a, bar_a, foo_b,
bar_b). For that reason, I also had to change an existing test case
to sort the fields in the new expected order.

Signed-off-by: Hasnain Lakhani <m.hasnain.lakhani@gmail.com>
2022-10-09 16:55:51 -07:00
License Updater
d29ec4d7a4 licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-10-09 16:49:03 -07:00
Maisem Ali
4de1601ef4 ssh/tailssh: add support for sending multiple banners
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-10-09 14:59:48 -07:00
License Updater
91b5c50b43 licenses: update win/apple licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-10-09 11:43:06 -07:00
Maisem Ali
ecf6cdd830 ssh/tailssh: add TestSSHAuthFlow
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-10-09 10:27:31 -07:00
Maisem Ali
f16b77de5d ssh/tailssh: do the full auth flow during ssh auth
Fixes #5091

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-10-09 10:27:31 -07:00
License Updater
c8a3d02989 licenses: update android licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-10-09 08:23:16 -07:00
Brad Fitzpatrick
6d76764f37 ipn/ipnlocal: fix taildrop target list UI bug
The macOS and iOS apps that used the /localapi/v0/file-targets handler
were getting too many candidate targets. They wouldn't actually accept
the file. This is effectively just a UI glitch in the wrong hosts
being listed as valid targets from the source side.

Change-Id: I6907a5a1c3c66920e5ec71601c044e722e7cb888
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-10-07 21:21:23 -07:00
Maisem Ali
b84ec521bf ssh/tailssh: do not send EOT on session disconnection
This was assumed to be the fix for mosh not working, however turns out
all we really needed was the duplicate fd also introduced in the same
commit (af412e8874).

Fixes #5103

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-10-07 07:52:35 -07:00
Joe Tsai
82f5f438e0 wgengine/wgcfg: plumb down audit log IDs (#5855)
The node and domain audit log IDs are provided in the map response,
but are ultimately going to be used in wgengine since
that's the layer that manages the tstun.Wrapper.

Do the plumbing work to get this field passed down the stack.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-10-06 16:19:38 -07:00
Mihai Parparita
92ad56ddcb cmd/tsconnect: close the SSH session an unload event instead of beforeunload
The window may not end up getting unloaded (if other beforeunload
handlers prevent the event), thus we should only close the SSH session
if it's truly getting unloaded.

Updates tailscale/corp#7304

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-10-06 13:17:15 -07:00
Joe Tsai
84e8f25c21 net/tstun: rename statististics method (#5852)
Rename StatisticsEnable as SetStatisticsEnabled to be consistent
with other similarly named methods.

Rename StatisticsExtract as ExtractStatistics to follow
the convention where methods start with a verb.
It was originally named with Statistics as a prefix so that
statistics related methods would sort well in godoc,
but that property no longer holds.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-10-06 10:46:09 -07:00
Joe Tsai
dd045a3767 net/flowtrack: add json tags to Tuple (#5849)
By convention, JSON serialization uses camelCase.
Specify such names on the Tuple type.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-10-05 19:40:49 -07:00
Joe Tsai
a73c423c8a net/tunstats: add Counts.Add (#5848)
The Counts.Add method merges two Counts together.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-10-05 13:18:08 -07:00
Joe Tsai
3af0d4d0f2 logtail: always record timestamps in UTC (#5732)
Upstream optimizations to the Go time package will make
unmarshaling of time.Time 3-6x faster. See:
* https://go.dev/cl/425116
* https://go.dev/cl/425197
* https://go.dev/cl/429862

The last optimization avoids a []byte -> string allocation
if the timestamp string less than than 32B.
Unfortunately, the presence of a timezone breaks that optimization.
Drop recording of timezone as this is non-essential information.

Most of the performance gains is upon unmarshal,
but there is also a slight performance benefit to
not marshaling the timezone as well.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-10-05 12:27:52 -07:00
Joe Tsai
c321363d2c logtail: support a copy ID (#5851)
The copy ID operates similar to a CC in email where
a message is sent to both the primary ID and also the copy ID.
A given log message is uploaded once, but the log server
records it twice for each ID.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-10-05 12:25:10 -07:00
Joe Tsai
24ebf161e8 net/tstun: instrument Wrapper with statistics gathering (#5847)
If Wrapper.StatisticsEnable is enabled,
then per-connection counters are maintained.
If enabled, Wrapper.StatisticsExtract must be periodically called
otherwise there is unbounded memory growth.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-10-05 12:24:30 -07:00
Tom DNetto
a37ee8483f ipn/ipnlocal: fix data race from missing lock in NetworkLockStatus
Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-10-05 11:51:49 -07:00
Brad Fitzpatrick
7714261566 go.toolchain.rev: update to Go 1.19.2
Changes: https://github.com/tailscale/go/commits/build-3fd24dee31726924c1b61c8037a889b30b8aa0f6

Change-Id: I61b83eef2b812879544a5226687606ae792b0786
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-10-05 11:22:00 -07:00
Tom DNetto
8602061f32 ipn/ipnlocal,tka: Fix bugs found by integration testing
* tka.State.staticValidateCheckpoint could call methods on a contained key prior to calling StaticValidate on that key
 * Remove broken backoff / RPC retry logic from tka methods in ipn/ipnlocal, to be fixed at a later time
 * Fix NetworkLockModify() which would attempt to take b.mu twice and deadlock, remove now-unused dependence on netmap
 * Add methods on ipnlocal.LocalBackend to be used in integration tests
 * Use TAILSCALE_USE_WIP_CODE as the feature flag so it can be manipulated in tests

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-10-05 11:12:34 -07:00
Tom DNetto
73db56af52 ipn/ipnlocal: filter peers with bad signatures when tka is enabled
Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-10-05 10:56:17 -07:00
Kristoffer Dalby
01ebef0f4f tailcfg: add views for ControlDialPlan (#5843) 2022-10-05 16:18:26 +02:00
Will Norris
62bc1052a2 tsweb: allow HTTPError to unwrap errors
Signed-off-by: Will Norris <will@tailscale.com>
2022-10-04 21:15:44 -07:00
License Updater
2243dbccb7 licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-10-04 20:11:30 -07:00
Brad Fitzpatrick
b1bd96f114 go.mod, ssh/tailssh: fix ImplictAuthMethod typo
Fixes #5745

Change-Id: Ie8bc88bd465a9cb35b0ae7782d61ce96480473ee
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-10-04 19:51:05 -07:00
David Anderson
fde20f3403 cmd/pgproxy: link to blog post at the top.
Signed-off-by: David Anderson <danderson@tailscale.com>
2022-10-04 16:47:12 -07:00
Mihai Parparita
7ffd2fe005 cmd/tsconnect: switch to non-beta versions of xterm and related packages
xterm 5.0 was released a few weeks ago, and it picks up
xtermjs/xterm.js#4069, which was the main reason why we were on a 5.0
beta.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-10-04 15:51:36 -07:00
Joe Tsai
2934c5114c net/tunstats: new package to track per-connection counters (#5818)
High-level API:

	type Statistics struct { ... }
	type Counts struct { TxPackets, TxBytes, RxPackets, RxBytes uint64 }
	func (*Statistics) UpdateTx([]byte)
	func (*Statistics) UpdateRx([]byte)
	func (*Statistics) Extract() map[flowtrack.Tuple]Counts

The API accepts a []byte instead of a packet.Parsed so that a future
implementation can directly hash the address and port bytes,
which are contiguous in most IP packets.
This will be useful for a custom concurrent-safe hashmap implementation.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-10-04 15:10:33 -07:00
David Anderson
bdf3d2a63f cmd/pgproxy: open-source our postgres TLS-enforcing proxy.
From the original commit that implemented it:

  It accepts Postgres connections over Tailscale only, dials
  out to the configured upstream database with TLS (using
  strong settings, not the swiss cheese that postgres defaults to),
  and proxies the client through.

  It also keeps an audit log of the sessions it passed through,
  along with the Tailscale-provided machine and user identity
  of the connecting client.

In our other repo, this was:
commit 92e5edf98e8c2be362f564a408939a5fc3f8c539,
Change-Id I742959faaa9c7c302bc312c7dc0d3327e677dc28.

Co-authored-by: Brad Fitzpatrick <bradfitz@tailscale.com>
Signed-off-by: David Anderson <danderson@tailscale.com>
2022-10-04 14:54:52 -07:00
License Updater
c5ce355756 licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-10-04 11:09:26 -07:00
Florian Lehner
7e0ffc17fd Address GO-2022-0969
HTTP/2 server connections can hang forever waiting for a clean
shutdown that was preempted by a fatal error. This condition can
be exploited by a malicious client to cause a denial of service.

Signed-off-by: Florian Lehner <dev@der-flo.net>
2022-10-04 11:06:25 -07:00
Florian Lehner
17348915fa Address GO-2020-0042
Due to improper path santization, RPMs containing relative file
paths can cause files to be written (or overwritten) outside of the
target directory.

Signed-off-by: Florian Lehner <dev@der-flo.net>
2022-10-04 11:06:25 -07:00
Brad Fitzpatrick
1841d0bf98 wgengine/magicsock: make debug-level stuff not logged by default
And add a CLI/localapi and c2n mechanism to enable it for a fixed
amount of time.

Updates #1548

Change-Id: I71674aaf959a9c6761ff33bbf4a417ffd42195a7
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-10-04 11:05:50 -07:00
Andrew Dunham
5c69961a57 cmd/tailscale/cli: add --record flag to bugreport (#5826)
Change-Id: I02bdc37a5c1a5a5d030c136ec5e84eb4c9ab1752
Signed-off-by: Andrew Dunham <andrew@tailscale.com>
2022-10-04 14:03:46 -04:00
Andrew Dunham
e5636997c5 wgengine: don't re-allocate trimmedNodes map (#5825)
Change-Id: I512945b662ba952c47309d3bf8a1b243e05a4736
Signed-off-by: Andrew Dunham <andrew@tailscale.com>
2022-10-04 13:20:09 -04:00
License Updater
445c8a4671 licenses: update win/apple licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-10-03 12:55:16 -07:00
Andrew Dunham
d7c0410ea8 ipn/localapi: print hostinfo and health on bugreport (#5816)
This information is super helpful when debugging and it'd be nice to not
have to scroll around in the logs to find it near a bugreport.

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
2022-10-03 10:54:46 -04:00
Maisem Ali
4102a687e3 tsnet: fix netstack leak on Close
Identified while investigating a goroutine leak in a different repo.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-10-01 16:44:54 -07:00
Maisem Ali
5fc8843c4c docs/k8s: [proxy] fix sysctl command
Fixes #5805

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-10-01 14:10:05 -07:00
Mihai Parparita
8343b243e7 all: consistently initialize Logf when creating tsdial.Dialers
Most visible when using tsnet.Server, but could have resulted in dropped
messages in a few other places too.

Fixes #5743

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-09-30 14:40:56 -07:00
Cuong Manh Le
a7efc7bd17 util/singleflight: sync with upstream
Sync with golang.org/x/sync/singleflight at commit
8fcdb60fdcc0539c5e357b2308249e4e752147f1

Fixes #5790

Signed-off-by: Cuong Manh Le <cuong.manhle.vn@gmail.com>
2022-09-30 06:55:04 -07:00
Josh Soref
d4811f11a0 all: fix spelling mistakes
Signed-off-by: Josh Soref <2119212+jsoref@users.noreply.github.com>
2022-09-29 13:36:13 -07:00
Joe Tsai
e73657d7aa logpolicy: directly expose the logtail server URL (#5788)
Callers of LogHost often jump through hoops to undo the
loss of information dropped by LogHost (e.g., the HTTP scheme).

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-09-29 13:28:51 -07:00
Brad Fitzpatrick
bb7be74756 net/dns/publicdns: permit more NextDNS profile bits in its IPv6 suffix
I brain-o'ed the math earlier. The NextDNS prefix is /32 (actually
/33, but will guarantee last bit is 0), so we have 128-32 = 96 bits
(12 bytes) of config/profile ID that we can extract. NextDNS doesn't
currently use all those, but might.

Updates #2452

Change-Id: I249bd28500c781e45425fd00fd3f46893ae226a2
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-09-29 12:23:38 -07:00
Adrian Dewhurst
c581ce7b00 cmd/tailscale, client, ipn, tailcfg: add network lock modify command
Signed-off-by: Adrian Dewhurst <adrian@tailscale.com>
2022-09-29 11:28:47 -07:00
Andrew Dunham
420d841292 wgengine: log subnet router decision at v1 if we have a BIRD client (#5786)
Updates tailscale/coral#82

Change-Id: I398d75f7e178ff7c531ca09899c82cf974fc30c9
Signed-off-by: Andrew Dunham <andrew@tailscale.com>
2022-09-29 14:14:14 -04:00
Tom DNetto
58ffe928af ipn/ipnlocal, tka: Implement TKA synchronization with the control plane
Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-09-29 11:07:02 -07:00
Tom DNetto
ab591906c8 wgengine/router: Increase range of rule priorities when detecting mwan3
Context: https://github.com/tailscale/tailscale/pull/5588#issuecomment-1260655929

It seems that if the interface at index 1 is down, the rule is not installed. As such,
we increase the range we detect up to 2004 in the hope that at least one of the interfaces
1-4 will be up.

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-09-29 10:09:06 -07:00
Mihai Parparita
9214b293e3 tstime: add ParseDuration helper function
More expressive than time.ParseDuration, also accepting d (days) and
w (weeks) literals.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-09-28 18:07:27 -07:00
Aaron Klotz
44f13d32d7 cmd/tailscaled, util/winutil: log Windows service diagnostics when the wintun device fails to install
I added new functions to winutil to obtain the state of a service and all
its depedencies, serialize them to JSON, and write them to a Logf.

When tstun.New returns a wrapped ERROR_DEVICE_NOT_AVAILABLE, we know that wintun
installation failed. We then log the service graph rooted at "NetSetupSvc".
We are interested in that specific service because network devices will not
install if that service is not running.

Updates https://github.com/tailscale/tailscale/issues/5531

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2022-09-28 16:09:10 -06:00
Brad Fitzpatrick
18159431ab logpolicy: fix, test LogHost to work as documented
Change-Id: I225c9602a7587c69c237e336d0714fc8315ea6bd
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-09-28 14:02:35 -07:00
Andrew Dunham
a5fab23e8f net/dns: format OSConfig correctly with no pointers (#5766)
Fixes tailscale/tailscale#5669

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
2022-09-27 19:30:39 -04:00
Andrew Dunham
4b996ad5e3 util/deephash: add AppendSum method (#5768)
This method can be used to obtain the hex-formatted deephash.Sum
instance without allocations.

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
2022-09-27 18:22:31 -04:00
Tom DNetto
ebd1637e50 ipn/ipnlocal,tailcfg: Identify client using NodeKey in tka RPCs
Updates https://github.com/tailscale/corp/pull/7024

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-09-27 09:37:28 -07:00
Mihai Parparita
e97d5634bf control/controlhttp: use custom port for non-localhost JS noise client connections
Control may not be bound to (just) localhost when sharing dev servers,
allow the Wasm client to connect to it in that case too.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-09-26 17:19:32 -07:00
Emmanuel T Odeke
f981b1d9da all: fix resource leaks with missing .Close() calls
Fixes #5706

Signed-off-by: Emmanuel T Odeke <emmanuel@orijtech.com>
2022-09-26 15:31:54 -07:00
Brad Fitzpatrick
9bdf0cd8cd ipn/ipnlocal: add c2n /debug/{goroutines,prefs,metrics}
* and move goroutine scrubbing code to its own package for reuse
* bump capver to 45

Change-Id: I9b4dfa5af44d2ecada6cc044cd1b5674ee427575
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-09-26 11:16:38 -07:00
Josh Soref
7686446c60 Drop duplicated $
Signed-off-by: Josh Soref <2119212+jsoref@users.noreply.github.com>
2022-09-26 10:10:50 -07:00
Andrew Dunham
b1867457a6 doctor: add package for running in-depth healthchecks; use in bugreport (#5413)
Change-Id: Iaa4e5b021a545447f319cfe8b3da2bd3e5e5782b
Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
2022-09-26 13:07:28 -04:00
Tom DNetto
e3beb4429f tka: Checkpoint every 50 updates
Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-09-26 10:07:14 -07:00
Brad Fitzpatrick
8a0cb4ef20 control/controlclient: fix recent set-dns regression
SetDNS calls were broken by 6d04184325 the other day. Unreleased.

Caught by tests in another repo.

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-09-25 16:23:55 -07:00
Brad Fitzpatrick
fb4e23506f control/controlclient: stop restarting map polls on health change
At some point we started restarting map polls on health change, but we
don't remember why. Maybe it was a desperate workaround for something.
I'm not sure it ever worked.

Rather than have a haunted graveyard, remove it.

In its place, though, and somewhat as a safety backup, send those
updates over the HTTP/2 noise channel if we have one open. Then if
there was a reason that a map poll restart would help we could do it
server-side. But mostly we can gather error stats and show
machine-level health info for debugging.

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-09-24 08:51:34 -07:00
Brad Fitzpatrick
6d04184325 control/controlclient: add a noiseClient.post helper method
In prep for a future change that would've been very copy/paste-y.

And because the set-dns call doesn't currently use a context,
so timeouts/cancelations are plumbed.

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-09-23 13:18:22 -07:00
Will Norris
8c72aabbdf licenses: remove win.md file
This was renamed to windows.md
2022-09-23 11:21:25 -07:00
James Tucker
f7cb535693 net/speedtest: retune to meet iperf on localhost in a VM
- removed some in-flow time calls
- increase buffer size to 2MB to overcome syscall cost
- move relative time computation from record to report time

Signed-off-by: James Tucker <james@tailscale.com>
2022-09-23 10:46:04 -07:00
James Tucker
146f51ce76 net/packet: fix filtering of short IPv4 fragments
The fragment offset is an 8 byte offset rather than a byte offset, so
the short packet limit is now in fragment block size in order to compare
with the offset value.

The packet flags are in the first 3 bits of the flags/frags byte, and
so after conversion to a uint16 little endian value they are at the
start, not the end of the value - the mask for extracting "more
fragments" is adjusted to match this byte.

Extremely short fragments less than 80 bytes are dropped, but fragments
over 80 bytes are now accepted.

Fixes #5727

Signed-off-by: James Tucker <james@tailscale.com>
2022-09-23 10:43:28 -07:00
Mihai Parparita
c66e15772f tsweb: consider 304s as successful for quiet logging
Static resource handlers will generate lots of 304s, which are
effectively successful responses.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-09-23 10:40:32 -07:00
Andrew Dunham
e1bdbfe710 tailcfg, control/controlhttp, control/controlclient: add ControlDialPlan field (#5648)
* tailcfg, control/controlhttp, control/controlclient: add ControlDialPlan field

This field allows the control server to provide explicit information
about how to connect to it; useful if the client's link status can
change after the initial connection, or if the DNS settings pushed by
the control server break future connections.

Change-Id: I720afe6289ec27d40a41b3dcb310ec45bd7e5f3e
Signed-off-by: Andrew Dunham <andrew@tailscale.com>
2022-09-23 13:06:55 -04:00
Aaron Klotz
acc7baac6d tailcfg, util/deephash: add DataPlaneAuditLogID to Node and DomainDataPlaneAuditLogID to MapResponse
We're adding two log IDs to facilitate data-plane audit logging: a node-specific
log ID, and a domain-specific log ID.

Updated util/deephash/deephash_test.go with revised expectations for tailcfg.Node.

Updates https://github.com/tailscale/corp/issues/6991

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2022-09-22 17:18:28 -06:00
Kyle Carberry
91794f6498 wgengine/magicsock: move firstDerp check after nil derpMap check
This fixes a race condition which caused `c.muCond.Broadcast()` to
never fire in the `firstDerp` if block. It resulted in `Close()`
hanging forever.

Signed-off-by: Kyle Carberry <kyle@carberry.com>
2022-09-22 11:54:56 -07:00
Brad Fitzpatrick
2c447de6cc cmd/tailscaled: use explicit equal sign in --port=$PORT in tailscaled.service
Personal preference (so it's obvious it's not a bool flag), but it
also matches the --state= before it.

Bonus: stop allowing PORT to sneak in extra flags to be passed as
their own arguments, as $FOO and ${FOO} expand differently. (${FOO} is
required to concat to strings)

Change-Id: I994626a5663fe0948116b46a971e5eb2c4023216
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-09-22 11:54:22 -07:00
Anton Schubert
021bedfb89 docker: add ability to use a custom control socket
Signed-off-by: Anton Schubert <anton.schubert@riedel.net>
2022-09-22 08:48:26 -07:00
hlts2
d988c9f098 fix auth key name
Signed-off-by: hlts2 <hiroto.funakoshi.hiroto@gmail.com>
2022-09-22 03:55:05 -07:00
Andrew Dunham
0607832397 wgengine/netstack: always respond to 4via6 echo requests (#5712)
As the comment in the code says, netstack should always respond to ICMP
echo requests to a 4via6 address, even if the netstack instance isn't
normally processing subnet traffic.

Follow-up to #5709

Change-Id: I504d0776c5824071b2a2e0e687bc33e24f6c4746
Signed-off-by: Andrew Dunham <andrew@tailscale.com>
2022-09-21 18:07:57 -04:00
Will Norris
565dbc599a Revert "licenses: update win/apple licenses"
This reverts commit aadf63da1d.
2022-09-21 14:28:43 -07:00
License Updater
aadf63da1d licenses: update win/apple licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-09-21 14:19:57 -07:00
Maisem Ali
d5781f61a9 ipn/ipnlocal: return usernames when Tailscale SSH is enabled
It was checking if the sshServer was initialized as a proxy, but that
could either not have been initialized yet or Tailscale SSH could have
been disabled after intialized.

Also bump tailcfg.CurrentCapabilityVersion

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-09-21 14:06:40 -07:00
Mihai Parparita
a7a0baf6b9 cmd/tsconnect: add error callback for SSH sessions
We were just logging them to the console, which is useful for debugging,
but we may want to show them in the UI too.

Updates tailscale/corp#6939

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-09-21 13:09:53 -07:00
Tom DNetto
e9b98dd2e1 control/controlclient,ipn/ipnlocal: wire tka enable/disable
Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-09-21 12:57:59 -07:00
Andrew Dunham
b9b0bf65a0 wgengine/netstack: handle 4via6 packets when pinging (#5709)
Change-Id: Ib6ebbaa11219fb91b550ed7fc6ede61f83262e89
Signed-off-by: Andrew Dunham <andrew@tailscale.com>
2022-09-21 14:19:34 -04:00
Andrew Dunham
c6162c2a94 net/netcheck: add check for captive portal (#5593)
This doesn't change any behaviour for now, other than maybe running a
full netcheck more often. The intent is to start gathering data on
captive portals, and additionally, seeing this in the 'tailscale
netcheck' command should provide a bit of additional information to
users.

Updates #1634

Change-Id: I6ba08f9c584dc0200619fa97f9fde1a319f25c76
Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
2022-09-20 15:31:49 -04:00
Brad Fitzpatrick
aa5e494aba tsweb: export go_version in standard expvar vars
For monitoring.

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-09-20 09:59:43 -07:00
Berk D. Demir
ff13c66f55 cmd/tailscale: fix configure-host command for Synology
d5e7e309 changed the `hostinfo.GetVersion` from distro and distro version
to UTS Name Release and moved distribution information under
`hostinfo.Distro*`.

`tailscale configure-host` command implementation for Synology DSM
environments relies on the old semantics of this string for matching DSM
Major version so it's been broken for a few days.

Pull in `hostinfo` and prefix match `hostinfo.DistroVersion` to match
DSM major version.

Signed-off-by: Berk D. Demir <bdd@mindcast.org>
2022-09-19 21:15:21 -07:00
Brad Fitzpatrick
ed248b04a7 cmd/tailscale: remove leftover debug prints from earlier commit
From 6632504f45

Change-Id: If21789232b3ecc14c1639cf87814af6fa73f535f
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-09-19 21:13:56 -07:00
Mihai Parparita
8158dd2edc cmd/tsconnect: allow SSH connection timeout to be overridden
5 seconds may not be enough if we're still loading the derp map and
connecting to a slow machine.

Updates #5693

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-09-19 18:00:12 -07:00
Maisem Ali
6632504f45 cmd/tailscale/cli: [up] move lose-ssh check after other validations
The check was happening too early and in the case of error would wait 5
s and then error out. This makes it so that it does validations before
the SSH check.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-09-19 12:04:14 -07:00
Maisem Ali
054ef4de56 tailcfg: mark CapabilityFileSharingTarget as inter-node
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-09-19 11:08:34 -07:00
Brad Fitzpatrick
d045462dfb ipn/ipnlocal: add c2n method to get SSH username candidates
For control to fetch a list of Tailscale SSH username candidates to
filter against the Tailnet's SSH policy to present some valid
candidates to a user.

Updates #3802
Updates tailscale/corp#7007

Change-Id: I3dce57b7a35e66891d5e5572e13ae6ef3c898498
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-09-19 10:37:04 -07:00
Brad Fitzpatrick
d8eb111ac8 .github/workflows: add cross-android
This would've caught the regression from 7c49db02a before it was
submitted so 42f1d92ae0 wouldn't have been necessary to fix it.

Updates #4482

Change-Id: Ia4a9977e21853f68df96f043672c86a86c0181db
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-09-18 09:56:19 -07:00
Brad Fitzpatrick
832031d54b wgengine/magicsock: fix recently introduced data race
From 5c42990c2f, not yet released in a stable build.
Caught by existing tests.

Fixes #5685

Change-Id: Ia76bb328809d9644e8b96910767facf627830600
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-09-18 08:07:57 -07:00
Denton Gentry
42f1d92ae0 net/netns: implement UseSocketMark for Android.
Build fails on Android:
`../../../../go/pkg/mod/tailscale.com@v1.1.1-0.20220916223019-65c24b6334e9/wgengine/magicsock/magicsock_linux.go:133:12: undefined: netns.UseSocketMark`

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-09-17 23:19:24 -07:00
Brad Fitzpatrick
41bb47de0e cmd/tailscaled: respect $PORT on all platforms, not just Linux
Updates #5114

Change-Id: I6c6e28c493d6a026a03088157d08f9fd182ef373
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-09-17 12:30:29 -07:00
Brad Fitzpatrick
3562b5bdfa envknob, health: support Synology, show parse errors in status
Updates #5114

Change-Id: I8ac7a22a511f5a7d0dcb8cac470d4a403aa8c817
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-09-17 08:42:41 -07:00
phirework
5c42990c2f wgengine/magicsock: add client flag and envknob to disable heartbeat (#5638)
Baby steps towards turning off heartbeat pings entirely as per #540.
This doesn't change any current magicsock functionality and requires additional
changes to send/disco paths before the flag can be turned on.

Updates #540

Change-Id: Idc9a72748e74145b068d67e6dd4a4ffe3932efd0
Signed-off-by: Jenny Zhang <jz@tailscale.com>

Signed-off-by: Jenny Zhang <jz@tailscale.com>
2022-09-16 23:48:46 -04:00
Brad Fitzpatrick
65c24b6334 envknob: generalize Windows tailscaled-env.txt support
ipnserver previously had support for a Windows-only environment
variable mechanism that further only worked when Windows was running
as a service, not from a console.

But we want it to work from tailscaed too, and we want it to work on
macOS and Synology. So move it to envknob, now that envknob can change
values at runtime post-init.

A future change will wire this up for more platforms, and do something
more for CLI flags like --port, which the bug was originally about.

Updates #5114

Change-Id: I9fd69a9a91bb0f308fc264d4a6c33e0cbe352d71
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-09-16 15:30:19 -07:00
Brad Fitzpatrick
4bda41e701 Dockerfile: add test that build-env Alpine version matches go.mod
So things like #5660 don't happen in the future.

Change-Id: I01234f241e297d5b7bdd18da1bb3cc5420ad2225
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-09-16 12:19:09 -07:00
Andrew Dunham
9b71008ef2 control/controlhttp: move Dial options into options struct (#5661)
This turns 'dialParams' into something more like net.Dialer, where
configuration fields are public on the struct.

Split out of #5648

Change-Id: I0c56fd151dc5489c3c94fb40d18fd639e06473bc
Signed-off-by: Andrew Dunham <andrew@tailscale.com>
2022-09-16 15:06:25 -04:00
Luis Peralta
5623ef0271 Update Dockerfile to use golang:1.19-alpine
Tailscale @4a82b31 does not build in the container image due to using golang:1.18 image

Signed-off-by: Luis Peralta <luis.peralta@gmail.com>
2022-09-16 11:40:31 -07:00
Tyler Lee
486eecc063 Switched Secret snippet to match run.sh
Signed-off-by: Tyler Lee <tyler.lee@radius.ai>
2022-09-16 11:20:33 -07:00
Tyler Lee
b830c9975f Updated secret example in readme to match the sidecar key value
Signed-off-by: Tyler Lee <tyler.lee@radius.ai>
2022-09-16 11:20:33 -07:00
Brad Fitzpatrick
4a82b317b7 ipn/{ipnlocal,localapi}: use strs.CutPrefix, add more domain validation
The GitHub CodeQL scanner flagged the localapi's cert domain usage as a problem
because user input in the URL made it to disk stat checks.

The domain is validated against the ipnstate.Status later, and only
authenticated root/configured users can hit this, but add some
paranoia anyway.

Change-Id: I373ef23832f1d8b3a27208bc811b6588ae5a1ddd
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-09-16 05:52:33 -07:00
Eng Zer Jun
f0347e841f refactor: move from io/ioutil to io and os packages
The io/ioutil package has been deprecated as of Go 1.16 [1]. This commit
replaces the existing io/ioutil functions with their new definitions in
io and os packages.

Reference: https://golang.org/doc/go1.16#ioutil
Signed-off-by: Eng Zer Jun <engzerjun@gmail.com>
2022-09-15 21:45:53 -07:00
Mihai Parparita
027111fb5a derp: update DERP acronym expansion
Makes the package description consistent with other documentation.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-09-15 16:08:12 -07:00
Mihai Parparita
1ce0e558a7 cmd/derper, control/controlhttp: disable WebSocket compression
The data that we send over WebSockets is encrypted and thus not
compressible. Additionally, Safari has a broken implementation of compression
(see nhooyr/websocket#218) that makes enabling it actively harmful.

Fixes tailscale/corp#6943

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-09-15 15:35:49 -07:00
Brad Fitzpatrick
74674b110d envknob: support changing envknobs post-init
Updates #5114

Change-Id: Ia423fc7486e1b3f3180a26308278be0086fae49b
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-09-15 15:04:02 -07:00
Brad Fitzpatrick
33ee2c058e wgengine: update comments, remove redundant code in forceFullWireguardConfig
Change-Id: I464a0bce36e3a362c7d7ace0e8d2dd77fa825ee2
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-09-15 13:03:18 -07:00
Brad Fitzpatrick
d34dd43562 ipn/ipnlocal: remove unused envknob
Change-Id: I6d18af2c469eb660e6ca81d1dcc2af33c9e628aa
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-09-15 11:06:15 -07:00
Andrew Dunham
cf61070e26 net/dnscache: add better logging to bootstrap DNS path (#5640)
Change-Id: I4cde3a72e06dac18df856a0cfeac10ab7e3a9108
Signed-off-by: Andrew Dunham <andrew@tailscale.com>
2022-09-15 10:41:45 -04:00
Kristoffer Dalby
81574a5c8d portlist: normalise space delimited process names (#5634) 2022-09-15 12:17:31 +02:00
Mihai Parparita
9c6bdae556 cmd/tsconnect: use the parent window for beforeunload event listener
The SSH session may be rendered in a different window that the one that
is executing the script.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-09-14 11:35:13 -07:00
Mihai Parparita
82e82d9b7a net/dns/resolver: remove unused responseTimeout constant
Timeout is now enforced elsewhere, see discussion in https://github.com/tailscale/tailscale/pull/4408#discussion_r970092333.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-09-13 18:12:11 -07:00
nyghtowl
0f16640546 net/dns: fix fmt error on Revert print
Fixes #5619

Signed-off-by: nyghtowl <warrick@tailscale.com>
2022-09-13 16:36:15 -07:00
Joe Tsai
aa0064db4d logpolicy: add NewWithConfigPath (#5625)
The version.CmdName implementation is buggy such that it does not correctly
identify the binary name if it embeds other go binaries.
For now, add a NewWithConfigPath API that allows the caller to explicitly
specify this information.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-09-13 16:30:40 -07:00
Brad Fitzpatrick
45a3de14a6 cmd/tailscaled, tailcfg, hostinfo: add flag to disable logging + support
As noted in #5617, our documented method of blocking log.tailscale.io
DNS no longer works due to bootstrap DNS.

Instead, provide an explicit flag (--no-logs-no-support) and/or env
variable (TS_NO_LOGS_NO_SUPPORT=true) to explicitly disable logcatcher
uploads. It also sets a bit on Hostinfo to say that the node is in that
mode so we can end any support tickets from such nodes more quickly.

This does not yet provide an easy mechanism for users on some
platforms (such as Windows, macOS, Synology) to set flags/env. On
Linux you'd used /etc/default/tailscaled typically. Making it easier
to set flags for other platforms is tracked in #5114.

Fixes #5617
Fixes tailscale/corp#1475

Change-Id: I72404e1789f9e56ec47f9b7021b44c025f7a373a
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-09-13 11:47:36 -07:00
Tom DNetto
f6da2220d3 wgengine: set fwmark masks in netfilter & ip rules
This change masks the bitspace used when setting and querying the fwmark on packets. This allows
tailscaled to play nicer with other networking software on the host, assuming the other networking
software is also using fwmarks & a different mask.

IPTables / mark module has always supported masks, so this is safe on the netfilter front.

However, busybox only gained support for parsing + setting masks in 1.33.0, so we make sure we
arent such a version before we add the "/<mask>" syntax to an ip rule command.

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-09-13 09:52:26 -07:00
Mihai Parparita
b22b565947 cmd/tsconnect: allow xterm.js terminal options to be passed in
Allows clients to use a custom theme and other xterm.js customization
options.

Fixes #5610

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-09-12 16:39:02 -07:00
David Anderson
7c49db02a2 wgengine/magicsock: don't use BPF receive when SO_MARK doesn't work.
Fixes #5607

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-09-12 15:05:44 -07:00
Mihai Parparita
c312e0d264 cmd/tsconnect: allow hostname to be specified
The auto-generated hostname is nice as a default, but there are cases
where the client has a more specific name that it can generate.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-09-12 14:26:50 -07:00
Mihai Parparita
11fcc3a7b0 cmd/tsconnect: fix xterm.js link opening not working when rendered into another window
The default WebLinksAddon handler uses window.open(), but that gets blocked
by the popup blocker when the event being handled is another window. We
instead need to invoke open() on the window that the event was triggered
in.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-09-12 13:54:27 -07:00
Will Norris
f03a63910d cmd/tailscale: add licenses link to web UI
The `tailscale web` UI is the primary interface for Synology and Home
Assistant users (and perhaps others), so is the logical place to put our
open source license notices.  I don't love adding things to what is
currently a very minimal UI, but I'm not sure of a better option.

Updates tailscale/corp#5780

Signed-off-by: Will Norris <will@tailscale.com>
2022-09-12 12:06:44 -07:00
Brad Fitzpatrick
024257ef5a net/stun: unmap IPv4 addresses in 16 byte STUN replies
Updates #5602

Change-Id: I2276ad2bfb415b9ff52f37444f2a1d74b38543b1
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-09-12 12:03:27 -07:00
Andrew Dunham
eb5939289c cmd/derper: add /generate_204 endpoint (#5601)
For captive portal detection.

Signed-off-by: Andrew Dunham <andrew@tailscale.com>
2022-09-12 13:43:50 -04:00
Brad Fitzpatrick
16939f0d56 hostinfo: detect being run in a container in more ways
Change-Id: I038ff7705ba232e6cf8dcc9775357ef708d43762
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-09-12 07:02:01 -07:00
Brad Fitzpatrick
d5e7e3093d hostinfo, tailcfg: split Hostinfo.OSVersion into separate fields
Stop jamming everything into one string.

Fixes #5578

Change-Id: I7dec8d6c073bddc7dc5f653e3baf2b4bf6b68378
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-09-11 21:40:28 -07:00
Brad Fitzpatrick
708b7bff3d net/dns/publicdns: also support NextDNS DoH query parameters
The plan has changed. Doing query parameters rather than path +
heades. NextDNS added support for query parameters.

Updates #2452

Change-Id: I4783c0a06d6af90756d9c80a7512644ba702388c
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-09-11 09:01:03 -07:00
Brad Fitzpatrick
81bc4992f2 net/netns: add TS_FORCE_LINUX_BIND_TO_DEVICE for Linux
For debugging a macOS-specific magicsock issue. macOS runs in
bind-to-interface mode always. This lets me force Linux into the same
mode as macOS, even if the Linux kernel supports SO_MARK, as it
usually does.

Updates #2331 etc

Change-Id: Iac9e4a7429c1781337e716ffc914443b7aa2869d
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-09-10 18:33:30 -07:00
Brad Fitzpatrick
f3ce1e2536 util/mak: deprecate NonNil, add type-safe NonNilSliceForJSON, NonNilMapForJSON
And put the rationale in the name too to save the callers the need for a comment.

Change-Id: I090f51b749a5a0641897ee89a8fb2e2080c8b782
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-09-10 12:19:22 -07:00
Brad Fitzpatrick
e7376aca25 net/dns/resolver: set DNS-over-HTTPS Accept and User-Agent header on requests
Change-Id: I14b821771681e70405a507f43229c694159265ff
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-09-10 08:57:26 -07:00
Tom DNetto
ed2b8b3e1d wgengine/router: reduce routing rule priority for openWRT + mwan3
Fixes #3659

Signed-off-by: Tom DNetto <tom@tailscale.com>
Co-authored-by: Ian Foster <ian@vorsk.com>
2022-09-09 18:21:24 -07:00
Brad Fitzpatrick
c14361e70e net/dns/publicdns: support NextDNS DoH URLs with path parameters
Updates #2452

Change-Id: I0f1c34cc1672e87e7efd0adfe4088724dd0de3ed
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-09-09 14:16:23 -07:00
Mihai Parparita
b302742137 cmd/tsconnect: enable web links addon in the terminal
More user friendly, and as a side-effect we handle SSH check mode better,
since the URL that's output is now clickable.

Fixes #5247

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-09-09 11:05:01 -07:00
Mihai Parparita
62035d6485 cmd/tsconnect: switch back to public version of xterm npm package
xtermjs/xterm.js#4069 was merged and published (in 5.0.0-beta.58),
no need for the fork added by 01e6565e8a.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-09-09 10:50:43 -07:00
Brad Fitzpatrick
89fee056d3 cmd/derper: add robots.txt to disallow all
Fixes #5565

Change-Id: I5626ec2116d9be451caef651dc301b7a82e35550
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-09-09 10:29:46 -07:00
License Updater
3ed366ee1e licenses: update android licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-09-09 09:14:22 -07:00
Brad Fitzpatrick
2aade349fc net/dns, types/dnstypes: update some comments, tests for DoH
Clarify & verify that some DoH URLs can be sent over tailcfg
in some limited cases.

Updates #2452

Change-Id: Ibb25db77788629c315dc26285a1059a763989e24
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-09-08 17:16:13 -07:00
Brad Fitzpatrick
58abae1f83 net/dns/{publicdns,resolver}: add NextDNS DoH support
NextDNS is unique in that users create accounts and then get
user-specific DNS IPs & DoH URLs.

For DoH, the customer ID is in the URL path.

For IPv6, the IP address includes the customer ID in the lower bits.

For IPv4, there's a fragile "IP linking" mechanism to associate your
public IPv4 with an assigned NextDNS IPv4 and that tuple maps to your
customer ID.

We don't use the IP linking mechanism.

Instead, NextDNS is DoH-only. Which means using NextDNS necessarily
shunts all DNS traffic through 100.100.100.100 (programming the OS to
use 100.100.100.100 as the global resolver) because operating systems
can't usually do DoH themselves.

Once it's in Tailscale's DoH client, we then connect out to the known
NextDNS IPv4/IPv6 anycast addresses.

If the control plane sends the client a NextDNS IPv6 address, we then
map it to the corresponding NextDNS DoH with the same client ID, and
we dial that DoH server using the combination of v4/v6 anycast IPs.

Updates #2452

Change-Id: I3439d798d21d5fc9df5a2701839910f5bef85463
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-09-08 12:50:32 -07:00
Mihai Parparita
01e6565e8a cmd/tsconnect: temporarily switch to xterm.js fork that handles popup windows
Allows other work to be unblocked while xtermjs/xterm.js#4069 is worked
through.

To enable testing the popup window handling, the standalone app allows
opening of SSH sessions in new windows by holding down the alt key
while pressing the SSH button.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-09-08 09:30:52 -07:00
Mihai Parparita
2400ba28b1 cmd/tsconnect: handle terminal resizes before the SSH session is created
Store the requested size is a struct field, and use that when actually
creating the SSH session.

Fixes #5567

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-09-08 09:30:52 -07:00
Brad Fitzpatrick
2266b59446 go.toolchain.rev: bump to Go 1.19.1
See https://github.com/tailscale/go/pull/34

Change-Id: I56806358cd1be4a2b8f509883e47c93083d82bdf
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-09-07 22:13:01 -07:00
Brad Fitzpatrick
ad7546fb9f tailcfg: fix broken test from comment change
Fix broken build from 255c0472fb

"Oh, that's safe to commit because most tests are passing and it's
just a comment change!", I thought, forgetting I'd added a test that
parses its comments.

Change-Id: Iae93d595e06fec48831215a98adbb270f3bfda05
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-09-07 22:03:38 -07:00
Brad Fitzpatrick
255c0472fb tailcfg: reformat CurrentCapabilityVersion to be a bulleted list
gofmt in 1.19 is now opinionated about structured text formatting in
comments. It did not like our style and kept fighting us whenever we
changed these lines. Give up the fight and be a bulleted list for it.

See:

* https://go.dev/doc/go1.19#go-doc and
* https://go.dev/doc/comment

Updates #4872

Change-Id: Ifae431218471217168c003ab3b4e03c394ca8105
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-09-07 21:53:16 -07:00
License Updater
c5adc5243c licenses: update win/apple licenses
Signed-off-by: GitHub <noreply@github.com>
2022-09-07 14:28:24 -07:00
Andrew Dunham
c9961b8b95 cmd/derper: filter out useless HTTP error logs (#5563)
These errors aren't actionable and just fill up logs with useless data.
See the following Go issue for more details:
  https://golang.org/issue/26918

Signed-off-by: Andrew Dunham <andrew@tailscale.com>
2022-09-07 16:31:06 -04:00
License Updater
8fdf137571 licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-09-06 19:19:15 -07:00
Colin Adler
9c8bbc7888 wgengine/magicsock: fix panic in http debug server
Fixes an panic in `(*magicsock.Conn).ServeHTTPDebug` when the
`recentPongs` ring buffer for an endpoint wraps around.

Signed-off-by: Colin Adler <colin1adler@gmail.com>
2022-09-06 15:02:07 -07:00
Andrew Dunham
9240f5c1e2 wgengine/netstack: only accept connection after dialing (#5503)
If we accept a forwarded TCP connection before dialing, we can
erroneously signal to a client that we support IPv6 (or IPv4) without
that actually being possible. Instead, we only complete the client's TCP
handshake after we've dialed the outbound connection; if that fails, we
respond with a RST.

Updates #5425 (maybe fixes!)

Signed-off-by: Andrew Dunham <andrew@tailscale.com>
2022-09-06 16:04:10 -04:00
Mihai Parparita
2f702b150e cmd/tsconnect: add dev-pkg command for two-sided development
Allows imports of the NPM package added by 1a093ef482
to be replaced with import("http://localhost:9090/pkg/pkg.js"), so that
changes can be made in parallel to both the module and code that uses
it (without any need for NPM publishing or even building of the package).

Updates #5415

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-09-06 12:42:58 -07:00
James Tucker
672c2c8de8 wgengine/magicsock: add filter to ignore disco to old/other ports
Incoming disco packets are now dropped unless they match one of the
current bound ports, or have a zero port*.

The BPF filter passes all packets with a disco header to the raw packet
sockets regardless of destination port (in order to avoid needing to
reconfigure BPF on rebind).

If a BPF enabled node has just rebound, due to restart or rebind, it may
receive and reply to disco ping packets destined for ports other than
those which are presently bound. If the pong is accepted, the pinging
node will now assume that it can send WireGuard traffic to the pinged
port - such traffic will not reach the node as it is not destined for a
bound port.

*The zero port is ignored, if received. This is a speculative defense
and would indicate a problem in the receive path, or the BPF filter.
This condition is allowed to pass as it may enable traffic to flow,
however it will also enable problems with the same symptoms this patch
otherwise fixes.

Fixes #5536

Signed-off-by: James Tucker <james@tailscale.com>
2022-09-06 12:25:04 -07:00
James Tucker
be140add75 wgengine/magicsock: fix regression in initial bind for js
1f959edeb0 introduced a regression for JS
where the initial bind no longer occurred at all for JS.

The condition is moved deeper in the call tree to avoid proliferation of
higher level conditions.

Updates #5537

Signed-off-by: James Tucker <james@tailscale.com>
2022-09-06 12:23:44 -07:00
James Tucker
1f959edeb0 wgengine/magicksock: remove nullability of RebindingUDPConns
Both RebindingUDPConns now always exist. the initial bind (which now
just calls rebind) now ensures that bind is called for both, such that
they both at least contain a blockForeverConn. Calling code no longer
needs to assert their state.

Signed-off-by: James Tucker <james@tailscale.com>
2022-09-06 12:08:31 -07:00
Brad Fitzpatrick
56f6fe204b go.mod, wgengine/wgint: bump wireguard-go
For b51010ba13

Change-Id: Ibf767dfad98aef7e9f0505d91c0d26f924e046d5
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-09-06 11:34:30 -07:00
Andrew Dunham
f52a659076 net/dnsfallback: allow setting log function (#5550)
This broke a test in corp that enforces we don't use the log package.

Signed-off-by: Andrew Dunham <andrew@tailscale.com>
2022-09-06 11:19:50 -04:00
Andrew Dunham
b8596f2a2f net/dnsfallback: cache most recent DERP map on disk (#5545)
This is especially helpful as we launch newer DERPs over time, and older
clients have progressively out-of-date static DERP maps baked in. After
this, as long as the client has successfully connected once, it'll cache
the most recent DERP map it knows about.

Resolves an in-code comment from @bradfitz

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
2022-09-05 14:36:30 -04:00
Maisem Ali
060ecb010f docs/k8s: make run.sh handle SIGINT
It was previously using jobcontrol to achieve this, but that apparently
doesn't work when there is no tty. This makes it so that it directly
handles SIGINT and SIGTERM and passes it on to tailscaled. I tested this
works on a Digital Ocean K8s cluster.

Fixes #5512

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-09-04 15:50:02 -07:00
Brad Fitzpatrick
02de34fb10 cmd/derper: add flag to run derper in bootstrap-dns-only mode
Change-Id: Iba128e94464afa605bc9df1f06a91d296380eed0
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-09-03 19:51:00 -07:00
Will Norris
3344c3b89b tsnet: add Server method to listener
Allow callers to verify that a net.Listener is a tsnet.listener by type
asserting against this Server method, as well as providing access to the
underlying Server.

This is initially being added to support the caddy integration in
caddyserver/caddy#5002.

Signed-off-by: Will Norris <will@tailscale.com>
2022-09-02 16:29:49 -07:00
Andrew Dunham
a0bae4dac8 cmd/derper: add support for unpublished bootstrap DNS entries (#5529)
Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
2022-09-02 14:48:30 -04:00
Tom DNetto
9132b31e43 tailcfg: refactor/implement wire structs for TKA
Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-09-02 10:29:46 -07:00
Kris Brandow
19008a3023 net/dnscache: use net/netip
Removes usage of net.IP and net.IPAddr where possible from net/dnscache.

Fixes #5282

Signed-off-by: Kris Brandow <kris.brandow@gmail.com>
2022-09-01 17:54:19 -04:00
Brad Fitzpatrick
ba3cc08b62 cmd/tailscale/cli: add backwards compatibility 'up' processing for legacy client
Updates tailscale/corp#6781

Change-Id: I843fc810cbec0140d423d65db81e90179d6e0fa5
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-09-01 14:21:48 -07:00
License Updater
d8bfb7543e licenses: update win/apple licenses
Signed-off-by: GitHub <noreply@github.com>
2022-09-01 14:10:55 -07:00
James Tucker
265b008e49 wgengine: fix race on endpoints in getStatus
Signed-off-by: James Tucker <james@tailscale.com>
2022-09-01 10:58:04 -07:00
Bertrand Lorentz
a5ad57472a cli/cert: Fix help message for --key-file
Signed-off-by: Bertrand Lorentz <bertrand.lorentz@gmail.com>
2022-09-01 10:57:00 -07:00
Xe Iaso
3564fd61b5 cmd/gitops-pusher: standardize hujson before posting to validate (#5525)
Apparently the validate route doesn't check content-types or handle
hujson with comments correctly. This patch makes gitops-pusher convert
the hujson to normal json.

Signed-off-by: Xe <xe@tailscale.com>

Signed-off-by: Xe <xe@tailscale.com>
2022-09-01 13:38:32 -04:00
nyghtowl
cfbbcf6d07 cmd/nginx-auth/nginx-auth: update auth to allow for new domains
With MagicDNS GA, we are giving every tailnet a tailnet-<hex>.ts.net name.
We will only parse out if legacy domains include beta.tailscale.net; otherwise,
set tailnet to the full domain format going forward.

Signed-off-by: nyghtowl <warrick@tailscale.com>
2022-08-31 20:18:13 -07:00
License Updater
9c66dce8e0 licenses: update win/apple licenses
Signed-off-by: GitHub <noreply@github.com>
2022-08-31 15:38:41 -07:00
Brad Fitzpatrick
e470893ba0 wgengine/magicsock: use mak in another spot
Change-Id: I0a46d6243371ae6d126005a2bd63820cb2d1db6b
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-08-31 15:30:26 -07:00
Andrew Dunham
c72caa6672 wgengine/magicsock: use AF_PACKET socket + BPF to read disco messages
This is entirely optional (i.e. failing in this code is non-fatal) and
only enabled on Linux for now. Additionally, this new behaviour can be
disabled by setting the TS_DEBUG_DISABLE_AF_PACKET environment variable.

Updates #3824
Replaces #5474

Co-authored-by: Andrew Dunham <andrew@du.nham.ca>
Signed-off-by: David Anderson <danderson@tailscale.com>
2022-08-31 14:52:31 -07:00
Mihai Parparita
58f35261d0 cmd/tsconnect: remove debugging code
Remove test prefix added to validate the error code from 27f36f77c3.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-08-31 10:46:47 -07:00
Tom DNetto
be95aebabd tka: implement credential signatures (key material delegation)
This will be needed to support preauth-keys with network lock in the future,
so getting the core mechanics out of the way now.

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-08-31 10:13:13 -07:00
License Updater
490acdefb6 licenses: update android licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-08-31 09:55:41 -07:00
License Updater
84b74825f0 licenses: update tailscale{,d} licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-08-31 08:38:55 -07:00
Brad Fitzpatrick
9bd9f37d29 go.mod: bump wireguard/windows, which moves to using net/netip
Updates #5162

Change-Id: If99a3f0000bce0c01bdf44da1d513f236fd7cdf8
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-08-31 08:36:56 -07:00
Charlotte Brandhorst-Satzkorn
185f2e4768 words: this title should have been a pun, but I chickened out (#5506)
Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>

Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2022-08-31 07:02:49 -07:00
Denton Gentry
53e08bd7ea VERSION.txt: this is 1.31
Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-08-31 06:48:24 -07:00
Andrew Dunham
70ed22ccf9 util/uniq: add ModifySliceFunc (#5504)
Follow-up to #5491. This was used in control... oops!

Signed-off-by: Andrew Dunham <andrew@tailscale.com>
2022-08-30 18:51:18 -04:00
Tom DNetto
7ca17b6bdb tka: validate key after UpdateKey before applying state
Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-08-30 15:23:30 -07:00
Andrew Dunham
e945d87d76 util/uniq: use generics instead of reflect (#5491)
This takes 75% less time per operation per some benchmarks on my mac.

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
2022-08-30 17:56:51 -04:00
Andrew Dunham
1ac4a26fee ipn/localapi: send Tailscale version in ACME User-Agent (#5499)
Requested by a friend at Let's Encrypt.

Signed-off-by: Andrew Dunham <andrew@tailscale.com>
2022-08-30 16:48:59 -04:00
Brad Fitzpatrick
761163815c tailcfg: add Hostinfo.Userspace{,Router} bits
Change-Id: Iad47f904872f2df146c1f63945f79cfddeac7fe8
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-08-30 12:39:03 -07:00
Brad Fitzpatrick
9f6c8517e0 net/dns: set OS DNS to 100.100.100.100 for route-less ExtraRecords [cap 41]
If ExtraRecords (Hosts) are specified without a corresponding split
DNS route and global DNS is specified, then program the host OS DNS to
use 100.100.100.100 so it can blend in those ExtraRecords.

Updates #1543

Change-Id: If49014a5ecc8e38978ff26e54d1f74fe8dbbb9bc
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-08-30 12:36:25 -07:00
Mihai Parparita
27f36f77c3 cmd/tsconnect: output errors to the JS console too
We were just outputting them to the terminal, but that's hard to debug
because we immediately tear down the terminal when getting an error.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-08-30 10:46:44 -07:00
Xe Iaso
122bd667dc cmd/gitops-pusher: be less paranoid about external modifications (#5488)
This makes a "modified externally" error turn into a "modified externally" warning. It means CI won't fail if someone does something manually in the admin console.

Signed-off-by: Xe <xe@tailscale.com>
2022-08-30 09:41:25 -04:00
Joe Tsai
21cd402204 logtail: do not log when backing off (#5485) 2022-08-30 06:21:03 -07:00
Denton Gentry
0ae0439668 docs/k8s: add IPv6 forwarding in proxy.yaml
Fixes https://github.com/tailscale/tailscale/issues/4999

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-08-30 06:03:15 -07:00
Denton Gentry
6dcc6313a6 CI: add go mod tidy workflow
Fixes https://github.com/tailscale/tailscale/issues/4567

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-08-30 06:02:34 -07:00
Denton Gentry
78dbb59a00 CI: make all workflows get Go version from go.mod
The next time we update the toolchain, all of the CI
Actions will automatically use it when go.mod is updated.

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-08-30 06:02:14 -07:00
Joe Tsai
7e40071571 util/deephash: handle slice edge-cases (#5471)
It is unclear whether the lack of checking nil-ness of slices
was an oversight or a deliberate feature.
Lacking a comment, the assumption is that this was an oversight.

Also, expand the logic to perform cycle detection for recursive slices.
We do this on a per-element basis since a slice is semantically
equivalent to a list of pointers.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-08-30 00:33:18 -07:00
James Tucker
90dc0e1702 wgengine: remove unused singleflight group
Signed-off-by: James Tucker <james@tailscale.com>
2022-08-29 18:16:30 -07:00
Mihai Parparita
2c18517121 cmd/tsconnect: add npm publish workflow
Adds an on-demand GitHub Action that publishes the package to the npm
registry (currently under tailscale-connect, will be moved to
@tailscale/connect once we get control of the npm org).

Makes the package.json for the NPM package be dynamically generated to
have the current Tailscale client version.

Updates #5415

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-08-29 18:02:51 -07:00
Andrew Dunham
d6c3588ed3 wgengine/wgcfg: only write peer headers if necessary (#5449)
On sufficiently large tailnets, even writing the peer header (~95 bytes)
can result in a large amount of data that needs to be serialized and
deserialized. Only write headers for peers that need to have their
configuration changed.

Signed-off-by: Andrew Dunham <andrew@tailscale.com>
2022-08-29 20:47:52 -04:00
James Tucker
81dba3738e wgengine: remove all peer status from open timeout diagnostics
Avoid contention from fetching status for all peers, and instead fetch
status for a single peer.

Updates tailscale/coral#72
Signed-off-by: James Tucker <james@tailscale.com>
2022-08-29 15:54:33 -07:00
James Tucker
ad1cc6cff9 wgengine: use Go API rather than UAPI for status
Signed-off-by: James Tucker <james@tailscale.com>
2022-08-29 15:38:16 -07:00
Maisem Ali
68d9d161f4 net/dns: [win] fix regression in disableDynamicUpdate
Somehow I accidentally set the wrong registry value here.
It should be DisableDynamicUpdate=1 and not EnableDNSUpdate=0.

This is a regression from 545639e.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-08-29 15:28:59 -07:00
Brad Fitzpatrick
c66f99fcdc tailcfg, control/controlclient, ipn/ipnlocal: add c2n (control-to-node) system
This lets the control plane can make HTTP requests to nodes.

Then we can use this for future things rather than slapping more stuff
into MapResponse, etc.

Change-Id: Ic802078c50d33653ae1f79d1e5257e7ade4408fd
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-08-29 15:18:40 -07:00
Brad Fitzpatrick
08b3f5f070 wgengine/wgint: add shady temporary package to get at wireguard internals
For #5451

Change-Id: I43482289e323ba9142a446d551ab7a94a467c43a
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-08-29 10:03:51 -07:00
Nahum Shalman
66d7d2549f logger: migrate rusage syscall use to x/sys/unix
This will be helpful for illumos (#697) and should be safe
everywhere else.

Signed-off-by: Nahum Shalman <nahamu@gmail.com>
2022-08-28 08:29:41 -07:00
Nahum Shalman
d20392d413 cmd/tailscale: add emoji for illumos in status subcommand
Signed-off-by: Nahum Shalman <nahamu@gmail.com>
2022-08-28 08:29:31 -07:00
Andrew Dunham
58cc049a9f util/cstruct: add package for decoding padded C structures (#5429)
I was working on my "dump iptables rules using only syscalls" branch and
had a bunch of C structure decoding to do. Rather than manually
calculating the padding or using unsafe trickery to actually cast
variable-length structures to Go types, I'd rather use a helper package
that deals with padding for me.

Padding rules were taken from the following article:
  http://www.catb.org/esr/structure-packing/

Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
2022-08-28 11:12:09 -04:00
Andrew Dunham
9b77ac128a wgengine: print in-flight operations on watchdog trigger (#5447)
In addition to printing goroutine stacks, explicitly track all in-flight
operations and print them when the watchdog triggers (along with the
time they were started at). This should make debugging watchdog failures
easier, since we can look at the longest-running operation(s) first.

Signed-off-by: Andrew Dunham <andrew@tailscale.com>

Signed-off-by: Andrew Dunham <andrew@tailscale.com>
2022-08-27 22:06:18 -04:00
Andrew Dunham
e1738ea78e chirp: add a 10s timeout when communicating with BIRD (#5444)
Prior to this change, if BIRD stops responding wgengine.watchdogEngine
will crash tailscaled.

This happens because in wgengine.userspaceEngine, we end up blocking
forever trying to write a request to or read a response from BIRD with
wgLock held, and then future watchdog'd calls will block on acquiring
that mutex until the watchdog kills the process. With the timeout, we at
least get the chance to print an error message and decide whether we
want to crash or not.

Updates tailscale/coral#72

Signed-off-by: Andrew Dunham <andrew@tailscale.com>

Signed-off-by: Andrew Dunham <andrew@tailscale.com>
2022-08-27 20:49:31 -04:00
Joe Tsai
9bf13fc3d1 util/deephash: remove getTypeInfo (#5469)
Add a new lookupTypeHasher function that is just a cached front-end
around the makeTypeHasher function.
We do not need to worry about the recursive type cycle issue that
made getTypeInfo more complicated since makeTypeHasher
is not directly recursive. All calls to itself happen lazily
through a sync.Once upon first use.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-08-27 17:39:51 -07:00
Joe Tsai
ab7e6f3f11 util/deephash: require pointer in API (#5467)
The entry logic of Hash has extra complexity to make sure
we always have an addressable value on hand.
If not, we heap allocate the input.
For this reason we document that there are performance benefits
to always providing a pointer.
Rather than documenting this, just enforce it through generics.

Also, delete the unused HasherForType function.
It's an interesting use of generics, but not well tested.
We can resurrect it from code history if there's a need for it.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-08-27 16:08:31 -07:00
Joe Tsai
c5b1565337 util/deephash: move pointer and interface logic to separate function (#5465)
This helps pprof better identify which Go kinds take the most time
since the kind is always in the function name.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-08-27 15:51:34 -07:00
Joe Tsai
d2e2d8438b util/deephash: move map logic to separate function (#5464)
This helps pprof better identify which Go kinds take the most time
since the kind is always in the function name.

There is a minor adjustment where we hash the length of the map
to be more on the cautious side.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-08-27 15:49:26 -07:00
Joe Tsai
23c3831ff9 util/deephash: coalesce struct logic (#5466)
Rather than having two copies []fieldInfo,
just maintain one and perform merging in the same pass.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-08-27 15:39:46 -07:00
Joe Tsai
296b008b9f util/deephash: move array and slice logic to separate function (#5463)
This helps pprof better identify which Go kinds take the most time
since the kind is always in the function name.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-08-27 15:37:36 -07:00
Joe Tsai
31bf3874d6 util/deephash: use unsafe.Pointer instead of reflect.Value (#5459)
Use of reflect.Value.SetXXX panics if the provided argument was
obtained from an unexported struct field.
Instead, pass an unsafe.Pointer around and convert to a
reflect.Value when necessary (i.e., for maps and interfaces).
Converting from unsafe.Pointer to reflect.Value guarantees that
none of the read-only bits will be populated.

When running in race mode, we attach type information to the pointer
so that we can type check every pointer operation.
This also type-checks that direct memory hashing is within
the valid range of a struct value.

We add test cases that previously caused deephash to panic,
but now pass.

Performance:

	name              old time/op    new time/op    delta
	Hash              14.1µs ± 1%    14.1µs ± 1%    ~     (p=0.590 n=10+9)
	HashPacketFilter  2.53µs ± 2%    2.44µs ± 1%  -3.79%  (p=0.000 n=9+10)
	TailcfgNode       1.45µs ± 1%    1.43µs ± 0%  -1.36%  (p=0.000 n=9+9)
	HashArray         318ns ± 2%     318ns ± 2%    ~      (p=0.541 n=10+10)
	HashMapAcyclic    32.9µs ± 1%    31.6µs ± 1%  -4.16%  (p=0.000 n=10+9)

There is a slight performance gain due to the use of unsafe.Pointer
over reflect.Value methods. Also, passing an unsafe.Pointer (1 word)
on the stack is cheaper than passing a reflect.Value (3 words).

Performance gains are diminishing since SHA-256 hashing now dominates the runtime.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-08-27 12:30:35 -07:00
Joe Tsai
e0c5ac1f02 util/deephash: add debug printer (#5460)
When built with "deephash_debug", print the set of HashXXX methods.

Example usage:

	$ go test -run=GetTypeHasher/string_slice -tags=deephash_debug
	U64(2)+U64(3)+S("foo")+U64(3)+S("bar")+FIN

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-08-27 12:14:07 -07:00
Andrew Dunham
e8f09d24c7 wgengine: use a singleflight.Group to reduce status contention (#5450)
Updates tailscale/coral#72

Signed-off-by: Andrew Dunham <andrew@tailscale.com>

Signed-off-by: Andrew Dunham <andrew@tailscale.com>
2022-08-27 12:36:07 -04:00
Joe Tsai
70f9fc8c7a util/deephash: rely on direct memory hashing for primitive kinds (#5457)
Rather than separate functions to hash each kind,
just rely on the fact that these are direct memory hashable,
thus simplifying the code.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-08-26 20:50:56 -07:00
Brad Fitzpatrick
f1c9812188 tailcfg: add Hostinfo.GoVersion
So next time something like #5340 happens we can identify all affected
nodes and have the control plane send them health warnings.

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-08-26 18:04:15 -07:00
Nahum Shalman
214242ff62 net/dns/publicdns: Add Mullvad DoH
See https://mullvad.net/en/help/dns-over-https-and-dns-over-tls/

The Mullvad DoH servers appear to only speak HTTP/2 and
the use of a non-nil DialContext in the http.Transport
means that ForceAttemptHTTP2 must be set to true to be
able to use them.

Signed-off-by: Nahum Shalman <nahamu@gmail.com>
2022-08-26 17:46:30 -07:00
Joe Tsai
531ccca648 util/deephash: delete slow path (#5423)
Every implementation of typeHasherFunc always returns true,
which implies that the slow path is no longer executed.
Delete it.

h.hashValueWithType(v, ti, ...) is deleted as it is equivalent to:
	ti.hasher()(h, v)

h.hashValue(v, ...) is deleted as it is equivalent to:
	ti := getTypeInfo(v.Type())
	ti.hasher()(h, v)

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-08-26 17:46:22 -07:00
Will Norris
3d328b82ee .github/actions: add signoff to go-licenses commits
also set git committer, which is apparently what this action uses for
signoff rather than git author.  Remove branch-suffix, which isn't
proving useful, and add installation_id, which isn't technically
necessary in the tailscale/tailscale repo, but makes this consistent
with the workflows in other repos.

Signed-off-by: Will Norris <will@tailscale.com>
2022-08-26 16:45:36 -07:00
License Updater
d95b95038c licenses: update android licenses
Signed-off-by: License Updater <noreply@tailscale.com>
2022-08-26 16:44:33 -07:00
License Updater
ceb8c5d1e9 licenses: update win/apple licenses
Signed-off-by: GitHub <noreply@github.com>
2022-08-26 14:12:52 -07:00
Will Norris
d1dd04e327 cmd/tailscale: use platform specific license link 2022-08-26 13:40:56 -07:00
Will Norris
79cf550823 cmd/tailscale: add licenses subcommand
Signed-off-by: Will Norris <will@tailscale.com>
2022-08-26 13:40:56 -07:00
Tom DNetto
79905a1162 tka: make storage a parameter rather than an Authority struct member
Updates #5435

Based on the discussion in #5435, we can better support transactional data models
by making the underlying storage layer a parameter (which can be specialized for
the request) rather than a long-lived member of Authority.

Now that Authority is just an instantaneous snapshot of state, we can do things
like provide idempotent methods and make it cloneable, too.

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-08-26 10:44:28 -07:00
Mihai Parparita
7d1357162e cmd/tsconnect: expose runSSHSession in npm package
Move it to lib/ so that it can be used in both the app and the package.

Updates #5415

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-08-26 09:24:44 -07:00
License Updater
e4b5b92b82 licenses: update android licenses 2022-08-25 15:28:25 -07:00
License Updater
ff97a97f08 licenses: update win/apple licenses 2022-08-25 14:42:58 -07:00
Tom DNetto
f580f4484f tka: move disablement logic out-of-band from AUMs
It doesn't make a ton of sense for disablement to be communicated as an AUM, because
any failure in the AUM or chain mechanism will mean disablement wont function.

Instead, tracking of the disablement secrets remains inside the state machine, but
actual disablement and communication of the disablement secret is done by the caller.

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-08-25 14:25:34 -07:00
Mihai Parparita
7a5cf39d0d ipn/ipnlocal: fix Taildrop not returning any sharing targets
The CapabilityFileSharingTarget capability added by eb32847d85
is meant to control the ability to share with nodes not owned by the
current user, not to restrict all sharing (the coordination server is
not currently populating the capability at all)

Fixes tailscale/corp#6669

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-08-25 12:47:20 -07:00
Tom DNetto
f81723ceac tailcfg: implement wire format for map request/response tka comms
Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-08-25 11:02:58 -07:00
License Updater
9ccc52cd04 licenses: update tailscale{,d} licenses 2022-08-25 10:52:46 -07:00
Will Norris
5c7e960fa8 licenses: add GitHub Action to update license notices (#5433)
This will update a licenses/tailscale.md file with all of our go
dependencies and their respective licenses. Notices for other clients
will be triggered by similar actions in other repos.

Co-authored-by: Andrew Dunham <andrew@tailscale.com>
Signed-off-by: Will Norris <will@tailscale.com>
Signed-off-by: Andrew Dunham <andrew@tailscale.com>
2022-08-25 10:28:10 -07:00
Mihai Parparita
1a093ef482 cmd/tsconnect: extract NPM package for reusing in other projects
`src/` is broken up into several subdirectories:
- `lib/` and `types`/ for shared code and type definitions (more code
  will be moved here)
- `app/` for the existing Preact-app
- `pkg/` for the new NPM package

A new `build-pkg` esbuild-based command is added to generate the files
for the NPM package. To generate type definitions (something that esbuild
does not do), we set up `dts-bundle-generator`.

Includes additional cleanups to the Wasm type definitions (we switch to
string literals for enums, since exported const enums are hard to use
via packages).

Also allows the control URL to be set a runtime (in addition to the
current build option), so that we don't have to rebuild the package
for dev vs. prod use.

Updates #5415

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-08-24 17:29:52 -07:00
Tom DNetto
472529af38 tka: optimize common case of processing updates built from head
Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-08-24 11:35:55 -07:00
Tom DNetto
039def3b50 ipn,tailcfg: transmit NodeID in tka init RPCs
Needed to identify the node. A serverside-check the machine key (used
to authenticate the noise session) is that of the specified NodeID
ensures the authenticity of the request.

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-08-24 11:35:55 -07:00
Tom DNetto
a78f8fa701 tka: support rotating node-keys in node-key signatures
Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-08-24 10:41:01 -07:00
Will Norris
b3cc719add cmd/nginx-auth: allow use of shared nodes
When sharing nodes, the name of the sharee node is not exposed (instead
it is hardcoded to "device-of-shared-to-user"), which means that we
can't determine the tailnet of that node.  Don't immediately fail when
that happens, since it only matters if "Expected-Tailnet" is used.

Signed-off-by: Will Norris <will@tailscale.com>
2022-08-24 09:41:56 -07:00
Joe Tsai
3fc8683585 util/deephash: expand fast-path capabilities (#5404)
Add support for maps and interfaces to the fast path.
Add cycle-detection to the pointer handling logic.
This logic is mostly copied from the slow path.

A future commit will delete the slow path once
the fast path never falls back to the slow path.

Performance:

	name                 old time/op    new time/op    delta
	Hash-24                18.5µs ± 1%    14.9µs ± 2%  -19.52%  (p=0.000 n=10+10)
	HashPacketFilter-24    2.54µs ± 1%    2.60µs ± 1%   +2.19%  (p=0.000 n=10+10)
	HashMapAcyclic-24      31.6µs ± 1%    30.5µs ± 1%   -3.42%  (p=0.000 n=9+8)
	TailcfgNode-24         1.44µs ± 2%    1.43µs ± 1%     ~     (p=0.171 n=10+10)
	HashArray-24            324ns ± 1%     324ns ± 2%     ~     (p=0.425 n=9+9)

The additional cycle detection logic doesn't incur much slow down
since it only activates if a type is recursive, which does not apply
for any of the types that we care about.

There is a notable performance boost since we switch from the fath path
to the slow path less often. Most notably, a struct with a field that
could not be handled by the fast path would previously cause
the entire struct to go through the slow path.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-08-24 01:31:01 -07:00
Mihai Parparita
78b90c3685 cmd/tsconnect: stop writing build artifacts into src/
We can't write to src/ when tsconnect is used a dependency in another
repo (see also b763a12331). We therefore
need to switch from writing to src/ to using esbuild plugins to handle
the requests for wasm_exec.js (the Go JS runtime for Wasm) and the
Wasm build of the Go module.

This has the benefit of allowing Go/Wasm changes to be picked up without
restarting the server when in dev mode (Go compilation is fast enough
that we can do this on every request, CSS compilation continues to be
the long pole).

Fixes #5382

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-08-23 15:44:59 -07:00
Tom DNetto
facafd8819 client,cmd/tailscale,ipn,tka,types: implement tka initialization flow
This PR implements the client-side of initializing network-lock with the
Coordination server.

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-08-22 11:35:16 -07:00
Tom DNetto
18edd79421 control/controlclient,tailcfg: [capver 40] create KeySignature field in tailcfg.Node
We calve out a space to put the node-key signature (used on tailnets where network lock is enabled).

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-08-22 11:25:41 -07:00
Kris Brandow
5d559141d5 wgengine/magicsock: remove mention of Start
The Start method was removed in 4c27e2fa22, but the comment on NewConn
still mentioned it doesn't do anything until this method is called.

Signed-off-by: Kris Brandow <kris.brandow@gmail.com>
2022-08-22 11:26:41 -04:00
Kamal Nasser
f983962fc6 fix typo in incomplete default routes error message
Signed-off-by: Kamal Nasser <hello@kamal.io>
2022-08-20 14:02:17 -07:00
Aaron Klotz
b997304bf6 tailcfg: add CapabilityDataPlaneAuditLogs.
We're going to want to enable audit logging on a per-Tailnet basis. When this
happens, we want control to inform the Tailnet's clients of this capability.

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2022-08-19 14:21:17 -06:00
Maisem Ali
9197dd14cc net/dns: [win] add MagicDNS entries to etc/hosts
This works around the 2.3s delay in short name lookups when SNR is
enabled.
C:\Windows\System32\drivers\etc\hosts file. We only add known hosts that
match the search domains, and we populate the list in order of
Search Domains so that our matching algorithm mimics what Windows would
otherwise do itself if SNR was off.

Updates #1659

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-08-19 12:38:11 -05:00
Denton Gentry
3c8d257b3e cmd/tailscale: set /dev/net perms in configure-host
Several customers have had issues due to the permissions
on /dev/net. Set permissions to 0755.

Fixes https://github.com/tailscale/tailscale/issues/5048

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-08-19 06:55:34 -07:00
Joe Tsai
d32700c7b2 util/deephash: specialize for netip.Addr and drop AppendTo support (#5402)
There are 5 types that we care about that implement AppendTo:

	key.DiscoPublic
	key.NodePublic
	netip.Prefix
	netipx.IPRange
	netip.Addr

The key types are thin wrappers around [32]byte and are memory hashable.
The netip.Prefix and netipx.IPRange types are thin wrappers over netip.Addr
and are hashable by default if netip.Addr is hashable.
The netip.Addr type is the only one with a complex structure where
the default behavior of deephash does not hash it correctly due to the presence
of the intern.Value type.

Drop support for AppendTo and instead add specialized hashing for netip.Addr
that would be semantically equivalent to == on the netip.Addr values.

The AppendTo support was already broken prior to this change.
It was fully removed (intentionally or not) in #4870.
It was partially restored in #4858 for the fast path,
but still broken in the slow path.
Just drop support for it altogether.

This does mean we lack any ability for types to self-hash themselves.
In the future we can add support for types that implement:

	interface { DeepHash() Sum }

Test and fuzz cases were added for the relevant types that
used to rely on the AppendTo method.
FuzzAddr has been executed on 1 billion samples without issues.

Signed-off-by: Joe Tsai joetsai@digital-static.net
2022-08-18 22:54:56 -07:00
Brad Fitzpatrick
0de66386d4 cmd/viewer: add flag to support Clone generation without Views
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-08-17 15:15:27 -07:00
Kris Brandow
9ae1161e85 net/dnscache: fix v4addrs to return only v4 addrs
Update the v4addrs function to filter out IPv6 addresses.

Fixes regression from 8725b14056.

Signed-off-by: Kris Brandow <kris.brandow@gmail.com>
2022-08-17 14:19:37 -04:00
Joe Tsai
03f7e4e577 util/hashx: move from sha256x (#5388) 2022-08-16 13:15:33 -07:00
Joe Tsai
f061d20c9d util/sha256x: rename Hash as Block512 (#5351)
Rename Hash as Block512 to indicate that this is a general-purpose
hash.Hash for any algorithm that operates on 512-bit block sizes.

While we rename the package as hashx in this commit,
a subsequent commit will move the sha256x package to hashx.
This is done separately to avoid confusing git.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-08-16 09:49:48 -07:00
Joe Tsai
44d62b65d0 util/deephash: move typeIsRecursive and canMemHash to types.go (#5386)
Also, rename canMemHash to typeIsMemHashable to be consistent.
There are zero changes to the semantics.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-08-16 09:31:19 -07:00
Joe Tsai
d53eb6fa11 util/deephash: simplify typeIsRecursive (#5385)
Any type that is memory hashable must not be recursive since
there are definitely no pointers involved to make a cycle.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-08-15 23:29:06 -07:00
Joe Tsai
23ec3c104a util/deephash: remove unused stack slice in typeIsRecursive (#5363)
No operation ever reads from this variable.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-08-15 22:36:08 -07:00
Joe Tsai
c200229f9e util/deephash: simplify canMemHash (#5384)
Put the t.Size() == 0 check first since this is applicable in all cases.
Drop the last struct field conditional since this is covered by the
sumFieldSize check at the end.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-08-15 22:22:18 -07:00
Brad Fitzpatrick
766ea96adf cmd/tailscaled: enable hybrid netstack mode on openbsd too
Apparently OpenBSD can forward packets with manual configuration,

https://github.com/tailscale/tailscale/issues/2498#issuecomment-1114216999

But this makes it work by default. People doing things by hand can
set TS_DEBUG_WRAP_NETSTACK=0 in the environment.

Change-Id: Iee5f32252f83af2baa0ebbe3f20ce9fec5f29e96
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-08-15 14:48:15 -07:00
Juan Font
ffc67806ef tailcfg: bump capver for clients to talk Noise over any HTTPS port [capver 39]
Signed-off-by: Juan Font Alonso <juanfontalonso@gmail.com>
2022-08-15 12:18:14 -07:00
Joe Tsai
32a1a3d1c0 util/deephash: avoid variadic argument for Update (#5372)
Hashing []any is slow since hashing of interfaces is slow.
Hashing of interfaces is slow since we pessimistically assume
that cycles can occur through them and start cycle tracking.

Drop the variadic signature of Update and fix callers to pass in
an anonymous struct so that we are hashing concrete types
near the root of the value tree.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-08-15 11:22:28 -07:00
Denton Gentry
1c0286e98a scripts/installer.sh: add -y for unattended install
Fixes https://github.com/tailscale/tailscale/issues/5377

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-08-15 10:28:55 -07:00
Kris Brandow
8f38afbf8e net/stun: convert to use net/netip.AddrPort
Convert ParseResponse and Response to use netip.AddrPort instead of
net.IP and separate port.

Fixes #5281

Signed-off-by: Kris Brandow <kris.brandow@gmail.com>
2022-08-15 12:46:01 -04:00
Maisem Ali
c3270af52b Makefile: add target for wasm and make it part of check
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-08-15 09:43:35 -07:00
Tom DNetto
06eac9bbff tka: Use strict decoding settings, implement Unserialize()
Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-08-15 09:20:53 -07:00
Maisem Ali
dbcc34981a cmd/tailscale/cli: fix build break
Accidental break from 64d482ff48.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-08-15 07:31:03 -07:00
Maisem Ali
d4916a8be3 .github/workflows: cancel previous CI runs on PR update
Currently scheduled runs are not canceled when we update PRs, those
results are unused and the resources are just wasted. Instead of doing
that, this PR makes it so that when a PR is updated (force-pushed or new
commit added) the previous runs are canceled.

https://docs.github.com/en/actions/using-workflows/workflow-syntax-for-github-actions#example-using-a-fallback-value

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-08-15 07:27:24 -07:00
Juan Font Alonso
64d482ff48 Allow any port for HTTPS when using Noise over TLS
Signed-off-by: Juan Font Alonso <juanfontalonso@gmail.com>
2022-08-15 06:43:43 -07:00
Maisem Ali
25865f81ee net/dns: disable NetBIOS on Tailscale interfaces
Like LLMNR, NetBIOS also adds resolution delays and we don't support it
anyway so just disable it on the interface.

Updates #1659

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-08-14 22:55:08 -07:00
Maisem Ali
545639ee44 util/winutil: consolidate interface specific registry keys
Code movement to allow reuse in a follow up PR.

Updates #1659

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-08-14 22:34:59 -07:00
Maisem Ali
23f37b05a3 atomicfile: update docs to clarify behavior of argument
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-08-13 21:31:40 -07:00
Maisem Ali
1cff719015 net/dns: [win] respond with SERVFAIL queries when no resolvers
Currently we forward unmatched queries to the default resolver on
Windows. This results in duplicate queries being issued to the same
resolver which is just wasted.

Updates #1659

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-08-12 17:09:30 -07:00
Joe Tsai
548fa63e49 util/deephash: use binary encoding of time.Time (#5352)
Formatting a time.Time as RFC3339 is slow.
See https://go.dev/issue/54093

Now that we have efficient hashing of fixed-width integers,
just hash the time.Time as a binary value.

Performance:

	Hash-24                19.0µs ± 1%    18.6µs ± 1%   -2.03%  (p=0.000 n=10+9)
	TailcfgNode-24         1.79µs ± 1%    1.40µs ± 1%  -21.74%  (p=0.000 n=10+9)

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-08-12 14:42:51 -07:00
Brad Fitzpatrick
0476c8ebc6 .github/workflows: delete flaky windows-race.yml
It flakes more often than it runs. It provides no value and builds
failure blindness, making people get used to submitting on red.

Bye.

Change-Id: If5491c70737b4c9851c103733b1855af2a90a9e9
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-08-12 13:20:00 -07:00
Joe Tsai
1f7479466e util/deephash: use sha256x (#5339)
Switch deephash to use sha256x.Hash.

We add sha256x.HashString to efficiently hash a string.
It uses unsafe under the hood to convert a string to a []byte.
We also modify sha256x.Hash to export the underlying hash.Hash
for testing purposes so that we can intercept all hash.Hash calls.

Performance:

	name                 old time/op    new time/op    delta
	Hash-24                19.8µs ± 1%    19.2µs ± 1%  -3.01%  (p=0.000 n=10+10)
	HashPacketFilter-24    2.61µs ± 0%    2.53µs ± 1%  -3.01%  (p=0.000 n=8+10)
	HashMapAcyclic-24      31.3µs ± 1%    29.8µs ± 0%  -4.80%  (p=0.000 n=10+9)
	TailcfgNode-24         1.83µs ± 1%    1.82µs ± 2%    ~     (p=0.305 n=10+10)
	HashArray-24            344ns ± 2%     323ns ± 1%  -6.02%  (p=0.000 n=9+10)

The performance gains is not as dramatic as sha256x over sha256 due to:
1. most of the hashing already occurring through the direct memory hashing logic, and
2. what does not go through direct memory hashing is slowed down by reflect.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-08-11 17:44:09 -07:00
Andrew Dunham
d942a2ff56 net/dnscache: try IPv6 addresses first (#5349)
Signed-off-by: Andrew Dunham <andrew@tailscale.com>

Signed-off-by: Andrew Dunham <andrew@tailscale.com>
2022-08-11 19:00:39 -04:00
Brad Fitzpatrick
90555c5cb2 tailcfg, control/controlclient: add PingRequest.URLIsNoise [capver 38]
Change-Id: I19bb63b6d99e96b2f9fd2c440afcc31d38137ded
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-08-11 09:41:06 -07:00
Brad Fitzpatrick
b33c337baa tailcfg: actually bump capver to 37, add test
I documented capver 37 in 4ee64681a but forgot to bump the actual
constant. I've done this previously too, so add a test to prevent
it from happening again.

Change-Id: I6f7659db1243d30672121a384beb386d9f9f5b98
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-08-11 09:28:54 -07:00
Joe Tsai
77a92f326d util/deephash: avoid using sync.Pool for reflect.MapIter (#5333)
In Go 1.19, the reflect.Value.MapRange method uses "function outlining"
so that the allocation of reflect.MapIter is inlinable by the caller.
If the iterator doesn't escape the caller, it can be stack allocated.
See https://go.dev/cl/400675

Performance:

	name               old time/op    new time/op    delta
	HashMapAcyclic-24    31.9µs ± 2%    32.1µs ± 1%   ~     (p=0.075 n=10+10)

	name               old alloc/op   new alloc/op   delta
	HashMapAcyclic-24     0.00B          0.00B        ~     (all equal)

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-08-11 00:33:40 -07:00
Denton Gentry
5d731ca13f installer.sh: add manjaro-arm & EndeavourOS.
Fixes https://github.com/tailscale/tailscale/issues/5192
Fixes https://github.com/tailscale/tailscale/issues/5284

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-08-10 20:10:48 -07:00
Joe Tsai
1c3c6b5382 util/sha256x: make Hash.Sum non-escaping (#5338)
Since Hash is a concrete type, we can make it such that
Sum never escapes the input.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-08-10 17:31:44 -07:00
Joe Tsai
76b0e578c5 util/sha256x: new package (#5337)
The hash.Hash provided by sha256.New is much more efficient
if we always provide it with data a multiple of the block size.
This avoids double-copying of data into the internal block
of sha256.digest.x. Effectively, we are managing a block ourselves
to ensure we only ever call hash.Hash.Write with full blocks.

Performance:

	name    old time/op    new time/op    delta
	Hash    33.5µs ± 1%    20.6µs ± 1%  -38.40%  (p=0.000 n=10+9)

The logic has gone through CPU-hours of fuzzing.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-08-10 15:49:36 -07:00
Brad Fitzpatrick
090033ede5 cmd/derper: fix data race & server panic in manual cert mode
(Thanks for debugging, Roland!)

Fixes #4082

Change-Id: I400a64001c3c58899bb570b759b08e745abc0be1
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-08-10 15:14:09 -07:00
dependabot[bot]
9996d94b3c build(deps): bump github.com/u-root/u-root from 0.8.0 to 0.9.0
Bumps [github.com/u-root/u-root](https://github.com/u-root/u-root) from 0.8.0 to 0.9.0.
- [Release notes](https://github.com/u-root/u-root/releases)
- [Changelog](https://github.com/u-root/u-root/blob/main/RELEASES)
- [Commits](https://github.com/u-root/u-root/compare/v0.8.0...v0.9.0)

---
updated-dependencies:
- dependency-name: github.com/u-root/u-root
  dependency-type: direct:production
...

Signed-off-by: dependabot[bot] <support@github.com>
2022-08-10 09:52:57 -07:00
Brad Fitzpatrick
c8dd39fcbc .github/workflows: use a matrix for staticcheck GOOS/GOARCHes
Change-Id: Ic4eda169729117afc4031bbefbe265195b38c19b
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-08-10 09:48:44 -07:00
Joe Tsai
539c5e44c5 util/deephash: always keep values addressable (#5328)
The logic of deephash is both simpler and easier to reason about
if values are always addressable.

In Go, the composite kinds are slices, arrays, maps, structs,
interfaces, pointers, channels, and functions,
where we define "composite" as a Go value that encapsulates
some other Go value (e.g., a map is a collection of key-value entries).

In the cases of pointers and slices, the sub-values are always addressable.

In the cases of arrays and structs, the sub-values are always addressable
if and only if the parent value is addressable.

In the case of maps and interfaces, the sub-values are never addressable.
To make them addressable, we need to copy them onto the heap.

For the purposes of deephash, we do not care about channels and functions.

For all non-composite kinds (e.g., strings and ints), they are only addressable
if obtained from one of the composite kinds that produce addressable values
(i.e., pointers, slices, addressable arrays, and addressable structs).
A non-addressible, non-composite kind can be made addressable by
allocating it on the heap, obtaining a pointer to it, and dereferencing it.

Thus, if we can ensure that values are addressable at the entry points,
and shallow copy sub-values whenever we encounter an interface or map,
then we can ensure that all values are always addressable and
assume such property throughout all the logic.

Performance:

	name                 old time/op    new time/op    delta
	Hash-24                21.5µs ± 1%    19.7µs ± 1%  -8.29%  (p=0.000 n=9+9)
	HashPacketFilter-24    2.61µs ± 1%    2.62µs ± 0%  +0.29%  (p=0.037 n=10+9)
	HashMapAcyclic-24      30.8µs ± 1%    30.9µs ± 1%    ~     (p=0.400 n=9+10)
	TailcfgNode-24         1.84µs ± 1%    1.84µs ± 2%    ~     (p=0.928 n=10+10)
	HashArray-24            324ns ± 2%     332ns ± 2%  +2.45%  (p=0.000 n=10+10)

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-08-09 22:00:02 -07:00
Brad Fitzpatrick
4ee64681ad tailcfg, control/controlclient: make Debug settings sticky in a map session [capver 37]
Fixes #4843

Change-Id: I3accfd91be474ac745cb47f5d6e866c37d5c5d2d
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-08-09 14:36:09 -07:00
Brad Fitzpatrick
8e821d7aa8 types/opt: support an explicit "unset" value for Bool
Updates #4843

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-08-09 13:34:56 -07:00
Maisem Ali
3bb57504af net/dns/resolver: add comments clarifying nil error returns
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-08-09 13:32:11 -07:00
Maisem Ali
4497bb0b81 net/dns/resolver: return SERVFAIL when no upstream resolvers set
Otherwise we just keep looping over the same thing again and again.

```
dns udp query: upstream nameservers not set
dns udp query: upstream nameservers not set
dns udp query: upstream nameservers not set
```

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-08-09 13:28:03 -07:00
Charlotte Brandhorst-Satzkorn
0f12ead567 tsconnect: pass in authkey in dev mode (#5320)
This change allows for an auth key to be specified as a url query param
for use in development mode. If an auth key is specified and valid, it
will authorize the client for use immediately.

Updates #5144

Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2022-08-09 13:07:01 -07:00
Mihai Parparita
ab159f748b cmd/tsconnect: switch UI to Preact
Reduces the amount of boilerplate to render the UI and makes it easier to
respond to state changes (e.g. machine getting authorized, netmap changing,
etc.)

Preact adds ~13K to our bundle size (5K after Brotli) thus is a neglibible
size contribution. We mitigate the delay in rendering the UI by having a static
placeholder in the HTML.

Required bumping the esbuild version to pick up evanw/esbuild#2349, which
makes it easier to support Preact's JSX code generation.

Fixes #5137
Fixes #5273

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-08-08 21:54:06 -07:00
David Crawshaw
15b8665787 tka: stable text representation of AUMHash
This makes debugging easier, you can pass an AUMHash to a printf and get
a string that is easy to debug.

Also rearrange how directories/files work in the FS store: use the first
two characters of the string representation as the prefix directory, and
use the entire AUMHash string as the file name. This is again to aid
debugging: you can `ls` a directory and line up what prints out easily
with what you get from a printf in debug code.

Signed-off-by: David Crawshaw <crawshaw@tailscale.com>
2022-08-08 11:10:56 -07:00
Maisem Ali
40ec8617ac util/must: rename Do->Get, add Do
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-08-06 09:30:10 -07:00
Brad Fitzpatrick
ec9d13bce5 hostinfo, net/netcheck: use CutPrefix
Updates #5309

Change-Id: I37e594cfd245784bf810c493de68a66d3ff20677
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-08-05 15:17:44 -07:00
Brad Fitzpatrick
01e8ef7293 util/strs: add new package for string utility funcs
Updates #5309

Change-Id: I677cc6e01050b6e10d8d6907d961b11c7a787a05
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-08-05 15:06:08 -07:00
Joe Tsai
622d80c007 util/must: new package (#5307)
The Do function assists in calling functions that must succeed.
It only interacts well with functions that return (T, err).
Signatures with more return arguments are not supported.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-08-05 12:20:50 -07:00
Maisem Ali
486cc9393c ipn/ipnlocal: fix log about local IPs when using exit nodes
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-08-05 11:45:22 -07:00
David Crawshaw
93324cc7b3 cmd/derper: add depaware.txt
Signed-off-by: David Crawshaw <crawshaw@tailscale.com>
2022-08-05 11:38:10 -07:00
Brad Fitzpatrick
18109c63b0 net/socks5: use new Go 1.19 binary.AppendByteOrder.AppendUintX
Updates #4872

Change-Id: I43db63d2ba237324bc1cd87d4261197f14cb1088
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-08-05 08:30:48 -07:00
Joe Tsai
b1fff4499f tsnet: cleanup resources upon start failure (#5301)
In a partially initialized state, we should cleanup
all prior resources when an error occurs.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-08-04 16:20:48 -07:00
Andrew Dunham
f0d6f173c9 net/netcheck: try ICMP if UDP is blocked (#5056)
Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
2022-08-04 17:10:13 -04:00
Joe Tsai
ddebd30917 tsnet: fix closing of filch buffer (#5299)
It should be safe to initialize multiple Server instances
without any resource leaks what-so-ever.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-08-04 13:22:56 -07:00
Tom DNetto
f50043f6cb tka,types/key: remove dependency for tailcfg & types/ packages on tka
Following the pattern elsewhere, we create a new tka-specific types package for the types
that need to couple between the serialized structure types, and tka.

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-08-04 12:51:58 -07:00
Maisem Ali
a9f6cd41fd all: use syncs.AtomicValue
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-08-04 11:52:16 -07:00
Maisem Ali
b75f81ec00 syncs: add generic AtomicValue
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-08-04 11:52:16 -07:00
Charlotte Brandhorst-Satzkorn
5055e00cf1 tsconnect: add flag to specify control server (#5294)
To improve the local development experience, this change allows a
control url to be passed in with the `--dev-control=` flag.

If the flag is passed in when not specifying dev, an error is returned.

If no flag is passed, the default remains the Tailscale controlled
control server set by `ipn.DefaultControlURL`.

Co-authored-by: Maisem Ali <maisem@tailscale.com>
Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2022-08-04 10:37:19 -07:00
Mihai Parparita
f371a1afd9 cmd/tsconnect: make logtail uploading work
Initialize logtail and provide an uploader that works in the
browser (we make a no-cors cross-origin request to avoid having to
open up the logcatcher servers to CORS).

Fixes #5147

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-08-04 09:10:20 -07:00
Brad Fitzpatrick
4950fe60bd syncs, all: move to using Go's new atomic types instead of ours
Fixes #5185

Change-Id: I850dd532559af78c3895e2924f8237ccc328449d
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-08-04 07:47:59 -07:00
Maisem Ali
9bb5a038e5 all: use atomic.Pointer
Also add some missing docs.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-08-03 21:42:52 -07:00
Brad Fitzpatrick
5381437664 logtail, net/portmapper, wgengine/magicsock: use fmt.Appendf
Fixes #5206

Change-Id: I490bb92e774ce7c044040537e2cd864fcf1dbe5a
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-08-03 21:35:51 -07:00
Mihai Parparita
4aa88bc2c0 cmd/tsconnect,util/precompress: move precompression to its own package
We have very similar code in corp, moving it to util/precompress allows
it to be reused.

Updates #5133

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-08-03 17:44:57 -07:00
Mihai Parparita
dfcef3382e cmd/tsconnect: add README with instructions
Outlines basic development, build and serving workflows.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-08-03 17:17:42 -07:00
Brad Fitzpatrick
9e5954c598 control/controlclient: fix crash in tests elsewhere when GetNLPublicKey is nil
4001d0bf25 caused tests in another repo to fail with a crash, calling
a nil func. This might not be the right fix, but fixes the build.

Change-Id: I67263f883c298f307abdd22bc2a30b3393f062e6
Co-authored-by: Maisem Ali <maisem@tailscale.com>
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-08-03 16:39:06 -07:00
Tom DNetto
8cfd775885 tka,types/key: implement direct node-key signatures
Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-08-03 15:42:27 -07:00
Tom DNetto
c13fab2a67 tka: add attack-scenario unit tests, defensive checks, resolve TODOs
Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-08-03 15:42:09 -07:00
Tom DNetto
4001d0bf25 assorted: plumb tka initialization & network-lock key into tailscaled
- A network-lock key is generated if it doesn't already exist, and stored in the StateStore. The public component is communicated to control during registration.
 - If TKA state exists on the filesystem, a tailnet key authority is initialized (but nothing is done with it for now).

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-08-03 14:51:47 -07:00
Tom DNetto
8d45d7e312 types/key: make NLPublic complement to NLPrivate
Forgot that I would need that in control. Oops.

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-08-03 14:51:47 -07:00
Maisem Ali
be5eadbecc tsnet: log out ephemeral nodes on Close()
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-08-03 14:27:04 -07:00
Maisem Ali
95d43c54bf cmd/{cloner,viewer}: add support for map values with pointers
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-08-03 13:02:17 -07:00
Maisem Ali
26f103473c cmd/viewer: add support for map of structs without pointers
This adds support for fields like `map[string]netaddr.IPPrefix`.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-08-03 13:02:17 -07:00
Mihai Parparita
adc5ffea99 cmd/tsconnect: make PeerAPI work
JS -> native nodes worked already, tested by exposing a fetch() method
to JS (it's Promise-based to be consistent with the native fetch() API).

Native nodes -> JS almost worked, we just needed to set the LocalBackend
on the userspace netstack.

Fixes #5130

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-08-03 10:39:47 -07:00
Brad Fitzpatrick
5f6abcfa6f all: migrate code from netaddr.FromStdAddr to Go 1.18
With caveat https://github.com/golang/go/issues/53607#issuecomment-1203466984
that then requires a new wrapper. But a simpler one at least.

Updates #5162

Change-Id: I0a5265065bfcd7f21e8dd65b2bd74cae90d76090
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-08-02 22:25:07 -07:00
Brad Fitzpatrick
7c7e23d87a control/controlclient, tailcfg: add 6 more patchable Node fields [capver 36]
Change-Id: Iae997a9a98a5dd841bc41fa91227d5a7dd476a25
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-08-02 21:14:00 -07:00
Mihai Parparita
52d769d35c cmd/tsconnect: prefetch main.wasm when serving
Avoids waterfalling of requests from the file (its load is triggered
from JavaScript).

Also has other cleanups to index.html, adding a <title> and moving the
<script> to being loaded sooner (but still not delaying page rendering
by using the defer attribute).

Fixes #5141
Fixes #5135

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-08-02 16:52:06 -07:00
Mihai Parparita
f04bc31820 cmd/tsconnect: add -fast-compression option
Changes Gzip and Brotli to optimize for speed instead of size. This
signficantly speeds up Brotli, and is useful when iterating locally
or running the build during a CI job (where we just care that it
can successfully build).

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-08-02 16:52:06 -07:00
Mihai Parparita
9a2171e4ea cmd/tsconnect: make terminal resizable
Makes the terminal container DOM node as large as the window (except for
the header) via flexbox. The xterm.js terminal is then sized to fit via
xterm-addon-fit. Once we have a computed rows/columns size, and we can
tell the SSH session of the computed size.

Required introducing an IPNSSHSession type to allow the JS to control
the SSH session once opened. That alse allows us to programatically
close it, which we do when the user closes the window with the session
still active.

I initially wanted to open the terminal in a new window instead (so that
it could be resizable independently of the main window), but xterm.js
does not appear to work well in that mode (possibly because it adds an
IntersectionObserver to pause rendering when the window is not visible,
and it ends up doing that when the parent window is hidden -- see
xtermjs/xterm.js@87dca56dee)

Fixes #5150

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-08-02 15:30:40 -07:00
Brad Fitzpatrick
8725b14056 all: migrate more code code to net/netip directly
Instead of going through the tailscale.com/net/netaddr transitional
wrappers.

Updates #5162

Change-Id: I3dafd1c2effa1a6caa9b7151ecf6edd1a3fda3dd
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-08-02 13:59:57 -07:00
Maisem Ali
eb32847d85 tailcfg: add CapabilityFileSharingTarget to identify FileTargets
This adds the inverse to CapabilityFileSharingSend so that senders can
identify who they can Taildrop to.

Updates #2101

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-08-02 13:52:10 -07:00
Mihai Parparita
9dfcdbf478 .github/workflows: put back CLI in cross-wasm GitHub action
Since we're keeping the JS support in the CLI (see https://github.com/tailscale/tailscale/pull/5265#issuecomment-1203078243),
make sure it keeps building.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-08-02 12:39:35 -07:00
Mihai Parparita
e846481731 cmd/tailscale/cli: use printf and outln consistently
Fix some fmt.Println and fmt.Printf calls that crept in since
5df7ac70d6.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-08-02 12:37:45 -07:00
Maisem Ali
02a765743e ssh/tailssh: fix deadlock in expandDelegateURL
Also rename it to expandDelegateURLLocked, previously it was trying
to acquire the mutex while holding the mutex.

Fixes #5235

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-08-02 12:25:09 -07:00
Brad Fitzpatrick
e1309e1323 all: require Go 1.19
Updates #5210

Change-Id: I2e950b4776636b4ea89b6566b60e4a87596a3a43
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-08-02 11:49:01 -07:00
Brad Fitzpatrick
fb82299f5a wgengine/magicsock: avoid RebindingUDPConn mutex in common read/write case
Change-Id: I209fac567326f2e926bace2582dbc67a8bc94c78
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-08-02 11:27:10 -07:00
Brad Fitzpatrick
116f55ff66 all: gofmt for Go 1.19
Updates #5210

Change-Id: Ib02cd5e43d0a8db60c1f09755a8ac7b140b670be
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-08-02 10:08:05 -07:00
Maisem Ali
a029989aff types/dnstype: use viewer instead of cloner
This was missed when I did the initial viewer work.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-08-02 09:58:53 -07:00
Joe Tsai
57275a4912 tsweb: add HTTPError.Header (#5251)
The Header field allows the server to specify specific headers to set.
Example use case: server returns 429 with the "Retry-After" header set.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-08-01 22:57:04 -07:00
Joe Tsai
a794963e2f tsweb: mark AccessLogRecord fields as omitempty (#5250)
If the field is the zero value, then avoid serializing the field.
This reduces verbosity in server logs.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-08-01 21:17:38 -07:00
Brad Fitzpatrick
5d0e3d379c go.mod: bump gvisor
For https://github.com/google/gvisor/pull/7850 to quiet macOS warnings.

Updates #5240

Change-Id: Iaa7abab20485c8ff40e5c9b16013aef4fd297a64
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-08-01 16:48:27 -07:00
Joe Tsai
b905db7a56 cmd/derper: remove support for logtail logging (#5248)
There aren't really any useful logs produced by derper.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-08-01 14:36:55 -07:00
Brad Fitzpatrick
357fd85ecf go.toolchain.rev: bump tailscale.go1.19 commit
for mutex slow path metrics: https://github.com/tailscale/go/pull/33

(a maybe temporary experiment)

Change-Id: Idba1ef866e2e1764728bdd869c25becccc1051b0
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-07-31 22:10:31 -07:00
Mihai Parparita
c06758c83b cmd/tsconnect: allow SSH username to be specified
Redoes the UI to be a form, with a username field and a host drop-down.

Fixes #5139

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-07-29 15:54:06 -07:00
Tom DNetto
47f91dd732 cmd/tailscale{,d}: update depaware
Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-07-29 12:16:32 -07:00
Tom DNetto
023d4e2216 tka,types/key: implement NLPrivate glue for tailnet key authority keys
Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-07-29 12:16:32 -07:00
Tom DNetto
7a74466998 shell.nix: update Go toolchain to 1.19
Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-07-29 11:25:47 -07:00
Tom DNetto
44a9b0170b tka: support processing non-primary forks, scenario-driven tests
Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-07-29 11:18:06 -07:00
Maisem Ali
8fd5d3eaf3 tstest: do not error if the there are fewer goroutines than at start
This fixes test failures like:
```
    resource.go:34: goroutine count: expected 3, got 2
```

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-07-29 09:53:01 -07:00
Tom DNetto
5e61d52f91 tka: implement API surface for generating updates
Based on the builder pattern.

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-07-29 09:36:32 -07:00
Brad Fitzpatrick
acc3b7f259 go.mod: bump inet.af/wf, tidy
This removes inet.af/netaddr from go.{mod,sum}.

Updates #5162

Change-Id: I7121e9fbb96d036cf188c51f0b53731570252d69
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-07-28 14:50:50 -07:00
Brad Fitzpatrick
f541e00db2 go.toolchain.rev: bump for VERSION file
Updates #5210

Change-Id: Ib6db8b010a6a9369a3eda8a86a49e538e376aff6
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-07-28 14:29:15 -07:00
Brad Fitzpatrick
eae003e56f ipn/ipnlocal: blend existing host SSH keys + newly-generated types as needed
If the host only has RSA, use its RSA + generate ecdsa + ed25519, etc.

Perhaps fixes https://twitter.com/colek42c/status/1550554439299244032 and
something else that was reported.

Change-Id: I88dc475c8e3d95b6f25288ff7664b8e72655fd16
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-07-28 11:42:58 -07:00
Brad Fitzpatrick
e5176f572e go.toolchain.rev: switch to Go 1.19rc2+
Switch to Go 1.19rc2 in prep for the Go 1.19 GA release on Tuesday.

(We won't be using any Go 1.19 features until then.)

Updates #5210

Change-Id: I94fa0ae8f5645fb7579429668f3970c18d1796d8
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-07-28 11:28:21 -07:00
Brad Fitzpatrick
48e73e147a logtail,logpolicy: tweak minor cosmetic things
Just reading the code again in prep for some alloc reductions.

Change-Id: I065226ea794b7ec7144c2b15942d35131c9313a8
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-07-27 21:13:46 -07:00
Mihai Parparita
ab60f28227 cmd/tsconnect: fix xterm CSS not being imported
@import rules need to come first, they are (silently) ignored otherwise.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-07-27 16:16:13 -07:00
Mihai Parparita
7c3f480767 cmd/tsconnect: lint during build step
Ensures that TypeScript checks pass before we deploy.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-07-27 16:12:22 -07:00
James Tucker
d5fb852718 build_dist.sh: add --box and --extra-small flag to produce smaller and boxed binaries
- `--box` when ./cmd/tailscaled is built with this flag, it builds a
  "toybox" style binary that includes tailscale and tailscaled.
- `--extra-small` strip the output binary and omit some dependencies
  (currently AWS integration).

Signed-off-by: James Tucker <james@tailscale.com>
2022-07-27 16:08:52 -07:00
Mihai Parparita
a3d74c4548 cmd/tsconnect: add basic panic handling
The go wasm process exiting is a sign of an unhandled panic. Also
add a explicit recover() call in the notify callback, that's where most
logic bugs are likely to happen (and they may not be fatal).

Also fixes the one panic that was encountered (nill pointer dereference
when generating the JS view of the netmap).

Fixes #5132

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-07-27 15:42:58 -07:00
Aaron Klotz
4dbdb19c26 net/tshttpproxy: fix incorrect type in Windows implementation, switch to mkwinsyscall, fix memory leak
The definition of winHTTPProxyInfo was using the wrong type (uint16 vs uint32)
for its first field. I fixed that type.

Furthermore, any UTF16 strings returned in that structure must be explicitly
freed. I added code to do this.

Finally, since this is the second time I've seen type safety errors in this code,
I switched the native API calls over to use wrappers generated by mkwinsyscall.
I know that would not have helped prevent the previous two problems, but every
bit helps IMHO.

Updates https://github.com/tailscale/tailscale/issues/4811

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2022-07-27 16:33:57 -06:00
Aaron Klotz
446d03e108 scripts: update check_license_headers.sh to skip zsyscall_windows.go
Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2022-07-27 16:19:39 -06:00
Brad Fitzpatrick
97b8c4fa1b ipn/store/awsstore: add "ts_omit_aws" build tag to reduce binary size
Drops tailscaled from 23M to 21M.

Change-Id: I731c542d03113ac94abb695e3c8fcacbc5542712
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-07-27 14:19:33 -07:00
nyghtowl
e6e1976c3a net/dns: remove systemd-resolved ping
Ping only needed to ensure system awak otherwise utilizing resolvConf to set dns mode.

Signed-off-by: nyghtowl <warrick@tailscale.com>
2022-07-27 14:15:22 -07:00
Mihai Parparita
617a2ec7cc cmd/tsconnect: add Tailwind CSS support and switch to using it
Integrates Tailwind CSS as an esbuild plugin that invokes the CLI
to process the input. It takes ~400ms, so it seems like the easiest
option (vs running a separate process for dev mode).

Existing minimal look and feel is replicated with Tailwind classes,
mostly to prove that the entire system works, including unused
class removal.

Also fixes yarn warnings about package.json not having a license
(which were showing up when invoking any scripts).

Fixes #5136
Fixes #5129

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-07-27 14:05:45 -07:00
Mihai Parparita
389629258b cmd/tsconnect: switch to TypeScript
Continues to use esbuild for development mode and building. Also
includes a `yarn lint` script that uses tsc to do full type checking.

Fixes #5138

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-07-27 13:50:34 -07:00
Brad Fitzpatrick
0a6aa75a2d cmd/tailscaled: add opt-in support for linking CLI into daemon
Doesn't help much, though.

    $ go install --tags=ts_include_cli ./cmd/tailscaled/
    $ ls -lh ~/go/bin/tailscaled
    -rwxr-xr-x 2 bradfitz bradfitz 34M Jul 27 11:00 /home/bradfitz/go/bin/tailscaled
    $ go install --tags= ./cmd/tailscaled/
    $ ls -lh ~/go/bin/tailscaled
    -rwxr-xr-x 1 bradfitz bradfitz 23M Jul 27 11:00 /home/bradfitz/go/bin/tailscaled
    $ ls -lh ~/go/bin/tailscale
    -rwxr-xr-x 1 bradfitz bradfitz 13M Jul 25 21:30 /home/bradfitz/go/bin/tailscale

Fixes #2233

Change-Id: I46bae91bb38eb47a76251c1b5c1e9e455fc234b6
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-07-27 11:15:52 -07:00
Brad Fitzpatrick
04cf46a762 util/deephash: fix unexported time.Time hashing
Updates tailscale/corp#6311

Change-Id: I33cd7e4040966261c2f2eb3d32f29936aeb7f632
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-07-27 09:28:23 -07:00
Maisem Ali
51c3d74095 types/views: add BenchmarkSliceIteration
```
goos: darwin
goarch: arm64
pkg: tailscale.com/types/views
BenchmarkSliceIteration/Len-10            340093              3212 ns/op               0 B/op          0 allocs/op
BenchmarkSliceIteration/Cached-Len-10     366727              3211 ns/op               0 B/op          0 allocs/op
BenchmarkSliceIteration/direct-10         361561              3290 ns/op               0 B/op          0 allocs/op
PASS
ok      tailscale.com/types/views       3.662s
```

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-07-26 21:25:26 -07:00
Maisem Ali
fa2fbaf3aa tailcfg: add views for SSHRule and SSHPrincipal
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-07-26 20:57:33 -07:00
Brad Fitzpatrick
7c671b0220 .github/workflows: add gofmt (goimports) check
Change-Id: Iceb3182827b9c65f28f0351e0e254abe4a95e4de
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-07-26 09:46:06 -07:00
Brad Fitzpatrick
dd3e91b678 go.mod: tidy, remove inet.af/netaddr
It was actually unused earlier, but I had a test program
in my git workdir, keeping go mod tidy from cleaning it.
(more CI needed, perhaps)

Updates #5162

Change-Id: I9047a9aaa6fde7736d6ef516dc3bb652d06fe921
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-07-25 22:08:20 -07:00
Brad Fitzpatrick
a12aad6b47 all: convert more code to use net/netip directly
perl -i -npe 's,netaddr.IPPrefixFrom,netip.PrefixFrom,' $(git grep -l -F netaddr.)
    perl -i -npe 's,netaddr.IPPortFrom,netip.AddrPortFrom,' $(git grep -l -F netaddr. )
    perl -i -npe 's,netaddr.IPPrefix,netip.Prefix,g' $(git grep -l -F netaddr. )
    perl -i -npe 's,netaddr.IPPort,netip.AddrPort,g' $(git grep -l -F netaddr. )
    perl -i -npe 's,netaddr.IP\b,netip.Addr,g' $(git grep -l -F netaddr. )
    perl -i -npe 's,netaddr.IPv6Raw\b,netip.AddrFrom16,g' $(git grep -l -F netaddr. )
    goimports -w .

Then delete some stuff from the net/netaddr shim package which is no
longer neeed.

Updates #5162

Change-Id: Ia7a86893fe21c7e3ee1ec823e8aba288d4566cd8
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-07-25 21:53:49 -07:00
Brad Fitzpatrick
6a396731eb all: use various net/netip parse funcs directly
Mechanical change with perl+goimports.

Changed {Must,}Parse{IP,IPPrefix,IPPort} to their netip variants, then
goimports -d .

Finally, removed the net/netaddr wrappers, to prevent future use.

Updates #5162

Change-Id: I59c0e38b5fbca5a935d701645789cddf3d7863ad
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-07-25 21:12:28 -07:00
Brad Fitzpatrick
730ca4203c cmd/tsshd: add a package line to appease gofmt
Change-Id: I2fbbe983186169ddf1995d2f51c7b5a6164a0904
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-07-25 20:52:04 -07:00
Mihai Parparita
7e4883b261 .github/workflows: add tsconnect static build to wasm GitHub action
Technically not the same as the wasm cross-compilation, but it's
closely connected to it.

Also includes some fixes to tool/yasm to make it actually work on
non-ARM platforms.

Fixes #5134

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-07-25 18:02:22 -07:00
Brad Fitzpatrick
7eaf5e509f net/netaddr: start migrating to net/netip via new netaddr adapter package
Updates #5162

Change-Id: Id7bdec303b25471f69d542f8ce43805328d56c12
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-07-25 16:20:43 -07:00
James Tucker
7b1a91dfd3 tool/go: accept a marker file with no line terminator
Somewhere my local configuration or program versions are producing
marker files earlier in the process that lack a line terminator. This
doesn't need to cause an exit via set -e, we can just continue the
process. $extracted matches $REV anyway, so the process works.

Signed-off-by: James Tucker <james@tailscale.com>
2022-07-25 16:06:52 -07:00
Walter Poupore
df9f3edea3 docs/k8s: add prefix to (#5167)
Signed-off-by: Walter Poupore <walterp@tailscale.com>
2022-07-25 15:10:07 -07:00
Denton Gentry
7fd03ad4b4 logpolicy: put QNAP logs buffer in /tmp
Ongoing log writing keeps the spinning disks from hibernating.
Extends earlier implementation for Synology to also handle QNAP.

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-07-25 09:45:04 -07:00
Denton Gentry
f85bb60eba ipn/ipnlocal: prevent attempting to run SSH on QNAP for now
tailscaled runs as a non-root user, SSH is not immediately working.

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-07-25 09:45:04 -07:00
Xe Iaso
904723691b cmd/gitops-pusher: things i forgot to push last PR (#5128)
Signed-off-by: Xe <xe@tailscale.com>
2022-07-25 09:09:32 -04:00
Denton Gentry
4dd799ec43 hostinfo: determine QNAP QTS version
Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-07-22 19:43:47 -07:00
Denton Gentry
d17849461c ipn/{ipnserver,ipnlocal}: support incoming Taildrop on QNAP
Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-07-22 19:43:47 -07:00
Aaron Klotz
1cae618b03 net/dns: add Windows group policy notifications to the NRPT rule manager
As discussed in previous PRs, we can register for notifications when group
policies are updated and act accordingly.

This patch changes nrptRuleDatabase to receive notifications that group policy
has changed and automatically move our NRPT rules between the local and
group policy subkeys as needed.

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2022-07-22 14:24:39 -06:00
Melanie Warrick
f17873e0f4 net/dns: handle D-Bus restarts in resolved manager (#5026)
When dbus restarts it can cause the tailscaled to crash because the nil
signal was not handled in resolved.Fixing so the nil signal leads to a
connection reset and tailscaled stays connected to systemd when dbus restarted.

Fixes #4645

Co-authored-by: James Tucker <james@tailscale.com>
Signed-off-by: nyghtowl <warrick@tailscale.com>

Co-authored-by: James Tucker <james@tailscale.com>
2022-07-22 12:49:18 -07:00
Xe Iaso
898695e312 cmd/gitops-pusher: add etag cache file for the three version problem (#5124)
This allows gitops-pusher to detect external ACL changes. I'm not
sure what to call this problem, so I've been calling it the "three
version problem" in my notes. The basic problem is that at any given
time we only have two versions of the ACL file at any given point:
the version in CONTROL and the one in the git repo. In order to
check if there has been tampering of the ACL files in the admin
panel, we need to have a _third_ version to compare against.

In this case I am not storing the old ACL entirely (though that could
be a reasonable thing to add in the future), but only its sha256sum.
This allows us to detect if the shasum in control matches the shasum
we expect, and if that expectation fails, then we can react
accordingly.

This will require additional configuration in CI, but I'm sure that
can be done.

Signed-off-by: Xe <xe@tailscale.com>
2022-07-22 15:07:38 -04:00
Brad Fitzpatrick
2024008667 types/key: add MachinePrecomputedSharedKey.Open
Follow-up to cfdb862673

Updates tailscale/corp#1709

Change-Id: I7af931a2cb55f9006e1029381663ac21d1794242
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-07-22 12:05:29 -07:00
Mihai Parparita
be8a0859a9 cmd/tsconnect: pin yarn and node
Adds a tool/yarn helper script that uses specific versions of yarn and
node, downloading them if necessary.

Modeled after tool/go (and the yarn and node Redo scripts from the
corp repo).

Also allows the path to yarn to be overidden (in case the user does not
want to use this script) and always pipes yarn output (to make debugging
and viewing of process easier).

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-07-22 11:36:49 -07:00
Xe Iaso
92357a54ec cmd/gitops-pusher: fix minor bug with ACL tests (#5123)
Signed-off-by: Xe <xe@tailscale.com>
2022-07-22 13:53:42 -04:00
Brad Fitzpatrick
ba91f57ddd ipn/ipnlocal: ignore empty SSH host key files
Change-Id: I332b0d7d01386111d0af4adf98c96c04d3d12fbb
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-07-22 10:52:04 -07:00
Brad Fitzpatrick
227c6b2a53 ipn/ipnlocal: flesh out error on ssh host key parse error
Change-Id: Iedd2d3898befa536181036b9e9dea59bc777a440
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-07-22 08:09:59 -07:00
Xe Iaso
90ccba6730 cmd/gitops-pusher: port to use ffcli (#5113)
Signed-off-by: Xe <xe@tailscale.com>
2022-07-22 09:39:24 -04:00
Logan Saso
f7a36dfeb1 api.md: added missing quote to POST DNS Searchpaths request body example
Signed-off-by: Logan Saso <logansaso@gmail.com>
2022-07-21 17:44:51 -07:00
Maisem Ali
9514ed33d2 go.mod: bump gvisor.dev/gvisor
Pick up https://github.com/google/gvisor/pull/7787

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-07-21 16:41:18 -07:00
Maisem Ali
1d33157ab9 docs/k8s: use job control in run.sh
This has the benefit of propagating SIGINT to tailscaled, which in turn
can react to the event and logout in case of an ephemeral node.

Also fix missing run.sh in Dockerfile.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-07-21 15:43:40 -07:00
Maisem Ali
3e06b9ea7a ssh/tailssh: add "ssh" to conn logs
Fixes #5089

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-07-21 12:42:31 -07:00
Maisem Ali
480fd6c797 ssh/tailssh: handle not-authenticated-yet connections in matchRule
Also make more fields in conn.info thread safe, there was previously a
data race here.

Fixes #5110

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-07-21 12:42:31 -07:00
Xe Iaso
41e60dae80 cmd/gitops-pusher: use fmt.Println for errors (#5112)
Signed-off-by: Xe <xe@tailscale.com>
2022-07-21 13:02:14 -04:00
Brad Fitzpatrick
43f3a969ca types/views: add SliceContains, View.ContainsFunc, View.IndexFunc
We were starting to write these elsewhere as little unexported copies
in misc places.

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-07-21 08:28:43 -07:00
Brad Fitzpatrick
d8cb5aae17 tailcfg, control/controlclient: add tailcfg.PeersChangedPatch [capver 33]
This adds a lighter mechanism for endpoint updates from control.

Change-Id: If169c26becb76d683e9877dc48cfb35f90cc5f24
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-07-20 15:05:56 -07:00
Mihai Parparita
b763a12331 cmd/tsconnect: allow building static resources in a different directory
When using tsconnect as a module in another repo, we cannot write to
the ./dist directory (modules directories are read-only by default -
there is a -modcacherw flag for `go get` but we can't count on it).

We add a -distdir flag that is honored by both the build and serve
commands for where to place output in.

Somewhat tedious because esbuild outputs paths relative to the working
directory, so we need to do some extra munging to make them relative
to the output directory.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-07-20 10:14:43 -07:00
Mihai Parparita
de2dcda2e0 .github/workflows: update module that we try to build in cross-wasm
We now have the actual module that we need to build, so switch to
building it directly instead of its (expected) dependencies.

Also fix a copy/paste error in a jsdeps comment.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-07-20 10:13:30 -07:00
Brad Fitzpatrick
b7f1fe7b0d tailcfg: remove old DNS fields
The control plane server doesn't send these to modern clients so we
don't need them in the tree. The server has its own serialization code
to generate legacy MapResponses when needed.

Change-Id: Idd1e5d96ddf9d4306f2da550d20b77f0c252817a
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-07-19 21:23:12 -07:00
Brad Fitzpatrick
9bd3b5b89c types/key: add ControlPrivate.Shared wrapper too
Follow-up to cfdb862673.

Change-Id: Iab610d761f1e6d88e8bcb584d9c02cafe48fc377
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-07-19 14:49:01 -07:00
Brad Fitzpatrick
cfdb862673 types/key: add naclbox shared key wrapper type + Seal method
So the control plane can stop doing precomputations on each naclbox
message.

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-07-19 14:18:12 -07:00
Mihai Parparita
6f5096fa61 cmd/tsconnect: initial scaffolding for Tailscale Connect browser client
Runs a Tailscale client in the browser (via a WebAssembly build of the
wasm package) and allows SSH access to machines. The wasm package exports
a newIPN function, which returns a simple JS object with methods like
start(), login(), logout() and ssh(). The golang.org/x/crypto/ssh
package is used for the SSH client.

Terminal emulation and QR code renedring is done via NPM packages (xterm
and qrcode respectively), thus we also need a JS toolchain that can
install and bundle them. Yarn is used for installation, and esbuild
handles loading them and bundling for production serving.

Updates #3157

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-07-19 13:43:08 -07:00
Brad Fitzpatrick
2a22ea3e83 util/deephash: generate type-specific hasher funcs
name                old time/op    new time/op    delta
Hash-8                71.1µs ± 2%    71.5µs ± 1%     ~     (p=0.114 n=9+8)
HashPacketFilter-8    8.39µs ± 1%    4.83µs ± 2%  -42.38%  (p=0.000 n=8+9)
HashMapAcyclic-8      56.2µs ± 1%    56.9µs ± 2%   +1.17%  (p=0.035 n=10+9)
TailcfgNode-8         6.49µs ± 2%    3.54µs ± 1%  -45.37%  (p=0.000 n=9+9)
HashArray-8            729ns ± 2%     566ns ± 3%  -22.30%  (p=0.000 n=10+10)

name                old alloc/op   new alloc/op   delta
Hash-8                 24.0B ± 0%     24.0B ± 0%     ~     (all equal)
HashPacketFilter-8     24.0B ± 0%     24.0B ± 0%     ~     (all equal)
HashMapAcyclic-8       0.00B          0.00B          ~     (all equal)
TailcfgNode-8          0.00B          0.00B          ~     (all equal)
HashArray-8            0.00B          0.00B          ~     (all equal)

name                old allocs/op  new allocs/op  delta
Hash-8                  1.00 ± 0%      1.00 ± 0%     ~     (all equal)
HashPacketFilter-8      1.00 ± 0%      1.00 ± 0%     ~     (all equal)
HashMapAcyclic-8        0.00           0.00          ~     (all equal)
TailcfgNode-8           0.00           0.00          ~     (all equal)
HashArray-8             0.00           0.00          ~     (all equal)

Change-Id: I34c4e786e748fe60280646d40cc63a2adb2ea6fe
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-07-19 11:33:13 -07:00
Maisem Ali
4d0461f721 ipn/ipnlocal: logout ephemeral nodes on shutdown
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-07-19 11:29:31 -07:00
Tom DNetto
393a229de9 tka: implement synchronization mechanics
This PR implements the synchronization mechanics for TKA: generating a SyncOffer, processing a SyncOffer to find an intersection,
and computing the set of AUMs that should be transmitted to effect convergence.

This is the final PR implementing core mechanics for TKA.

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-07-19 09:58:36 -07:00
Tom DNetto
165c8f898e tka: implement Authority API surface
After this, there should be one final PR to implement the Sync algorithm!

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-07-19 09:35:29 -07:00
Brad Fitzpatrick
2491fe1afe tailcfg: add missing omitempty annotation to PopBrowserURL
Change-Id: I8e752afd5bf009c17aae1b53650479b37c3232bd
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-07-19 09:25:06 -07:00
David Anderson
c1cb3efbba net/netcheck: test for OS IPv6 support as well as connectivity.
This lets us distinguish "no IPv6 because the device's ISP doesn't
offer IPv6" from "IPv6 is unavailable/disabled in the OS".

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-07-18 18:02:12 -07:00
Charlotte Brandhorst-Satzkorn
4c0feba38e derp: plumb '/derp' request context through (#5083)
This change is required to implement tracing for derp.

Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2022-07-18 15:43:03 -07:00
Denton Gentry
3c892d106c VERSION.txt: this is v1.29.0
Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-07-18 10:23:52 -07:00
Maisem Ali
bd4b27753e docs/k8s: set statedir to /tmp when not specified
This makes `tailscale cert` and Taildrop work on k8s and in ephemeral
mode.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-07-18 10:19:19 -07:00
Brad Fitzpatrick
469c30c33b ipn/localapi: define a cert dir for Synology DSM6
Fixes #4060

Change-Id: I5f145d4f56f6edb14825268e858d419c55918673
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-07-18 09:51:24 -07:00
Maisem Ali
c6648db333 cmd/tailscale/cli: make cert use localClient
This was seeminlgy missed in 87ba528ae0.

Fixes #5072

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-07-17 13:22:29 -07:00
Denton Gentry
9fcda1f0a0 cmd/tailscale/cli/web: add QNAP NAS_SID authentication
QTS 5.0 doesn't always pass a qtoken, in some circumstances
it sends a NAS_SID cookie for us to verify instead.

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-07-17 12:21:03 -07:00
Brad Fitzpatrick
0d52674a84 net/tstun: diagnose /dev/net/tun fd leak, give better failure message
Updates #5029

Change-Id: Ibee5e0c9076fe764eb5d856d5ef8b09f4d0e2921
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-07-16 14:21:56 -07:00
Brad Fitzpatrick
931f18b575 derp: add missing docs on clientInfo.Version
It's not the Tailscale version.

Change-Id: Icfbd5ff36300b2125b19cd2fa6caa22876965317
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-07-15 12:00:19 -07:00
Tom DNetto
4f1374ec9e tka: implement consensus & state computation internals
Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-07-15 10:44:43 -07:00
Maisem Ali
af412e8874 ssh/tailssh: better handling of signals and exits
We were not handling errors occurred while copying data between the subprocess and the connection.
This makes it so that we pass the appropriate signals when to the process and the connection.

This also fixes mosh.

Updates #4919

Co-authored-by: James Tucker <raggi@tailscale.com>
Co-authored-by: Brad Fitzpatrick <bradfitz@tailscale.com>
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-07-15 09:06:01 -07:00
Xe Iaso
004f0ca3e0 cmd/gitops-pusher: format HuJSON, enabling exact ACL matches (#5061)
Signed-off-by: Xe <xe@tailscale.com>
2022-07-15 11:09:44 -04:00
Xe Iaso
16c85d0dc5 cmd/gitops-pusher: support GitHub Actions error syntax (#5060)
GitHub Actions lets you annotate lines in files as errors[1]. This syntax
will only fire on syntax errors. Future improvements can extend this to
properly annotate ACL tests too.

[1]: https://docs.github.com/en/actions/using-workflows/workflow-commands-for-github-actions#setting-an-error-message

Signed-off-by: Xe <xe@tailscale.com>
2022-07-15 10:20:54 -04:00
Brad Fitzpatrick
7fb6781bda go.toolchain.rev: bump for Go 1.18.4 + runtime timer spin
See https://github.com/tailscale/go/pull/32

Updates #4760
Updates #5030?
Updates #4891?

Change-Id: I066aafddc09fade30a5f3fdee23e6bd200eda9fa
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-07-13 20:56:59 -07:00
Tom DNetto
ec4f849079 tka: implement filesystem-based tailchonk implementation
FS implements Chonk, and given the expected load characteristics (frequent use
of AUM() + ChildAUMs(), and infrequent use of Heads() + CommitVerifiedAUMs()), the
implementation avoids scanning the filesystem to service AUM() and ChildAUMs().

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-07-13 10:07:17 -07:00
Brad Fitzpatrick
505ca2750d cmd/tailscaled: fix Windows "Allow local LAN access" regression
3f686688a6 regressed the Windows beFirewallKillswitch code,
preventing the /firewall subprocess from running.

Fixes tailscale/corp#6063

Change-Id: Ibd105759e5fecfeffc54f587f8ddcd0f1cbc4dca
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-07-13 08:01:32 -07:00
David Anderson
96afd1db46 jsondb: small package to load/save JSON DBs.
Signed-off-by: David Anderson <danderson@tailscale.com>
2022-07-12 11:56:38 -07:00
Denton Gentry
755396d6fe tsweb: add Float expvar support in varz
We make assertions about stringification of 0.5. IEEE floating point and
all reasonable proprietary floating point can exactly represent 0.5.
We don't make assertions about other floating point values, too brittle
in tests.

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-07-11 21:16:46 -07:00
Tom DNetto
cca25f6107 tka: implement Chonk type & an in-memory implementation
Chonks are responsible for efficient storage of AUMs and other TKA state.

For testing/prototyping I've implemented an in-memory version, but once we
start to use this from tailscaled we'll need a file-based version.

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-07-11 10:38:29 -07:00
Mihai Parparita
e37167b3ef ipn/localapi: add API for uploading client metrics
Clients may have platform-specific metrics they would like uploaded
(e.g. extracted from MetricKit on iOS). Add a new local API endpoint
that allows metrics to be updated by a simple name/value JSON-encoded
struct.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-07-11 09:51:09 -07:00
Xe Iaso
d6b8a18b09 cmd/proxy-to-grafana: use localClient.GetCertificate (#5024)
Closes #5023

Signed-off-by: Xe <xe@tailscale.com>
2022-07-08 14:33:14 -04:00
Xe Iaso
5bb44a4a5c cmd/gitops-pusher: correctly handle ACL tests failing (#5016)
Apparently the API for running ACL tests returns a 200 if the ACL tests
fail. This is weird, but we can handle it.

Signed-off-by: Xe <xe@tailscale.com>
2022-07-08 10:53:50 -04:00
Andrew Dunham
c7993d2b88 net/dns/resolver: add fuzz/unit test for #2533 (#5018)
Signed-off-by: Andrew Dunham <andrew@du.nham.ca>
2022-07-08 09:22:50 -04:00
Tom DNetto
3709074e55 tka: implement State and applying AUMs
Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-07-07 11:25:26 -07:00
Tom DNetto
1cfd96cdc2 tka: implement AUM and Key types
This is the first in a series of PRs implementing the internals for the
Tailnet Key Authority. This PR implements the AUM and Key types, which
are used by pretty much everything else. Future PRs:

 - The State type & related machinery
 - The Tailchonk (storage) type & implementation
 - The Authority type and sync implementation

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-07-06 12:19:37 -07:00
Denton Gentry
e6572a0f08 install.sh: Add archarm and Raspbian Stretch
Fixes https://github.com/tailscale/tailscale/issues/4959
Fixes https://github.com/tailscale/tailscale/issues/4897

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-07-06 05:41:06 -07:00
Joe Tsai
fe3426b4c7 logpolicy: fix config initialization bug (#5010)
If ConfigFromFile cannot find the configuration file,
we must not initialize it with NewConfig.
Instead, we need it to fail validation so that it eventually writes
a newly constructed configuration file.
Otherwise, new tailscale instances will never be able store a persistent
log config and start with a new config file upon every bootup.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-07-05 18:27:31 -07:00
Tom DNetto
d6817d0f22 net/dns/resolver: respond with SERVFAIL if all upstreams fail
Fixes #4722

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-07-05 10:22:52 -07:00
Brad Fitzpatrick
c93fd0d22b go.mod: bump wireguard-go to set CLOEXEC on tun/netlink fds
To get:
c31a7b1ab4

Diff:
95b48cdb39..c31a7b1ab4

Fixes #4992

Change-Id: I077586fefcde923a2721712dd54548f97d010f72
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-07-03 17:11:49 -07:00
Craig Rodrigues
9584d8aa7d docs/k8s: Add env vars for tailscaled args
- TS_SOCKS5_SERVER, argument passed to tailscaled --socks5-server
- TS_OUTBOUND_HTTP_PROXY_LISTEN, argument passed to tailscaled -outbound-http-proxy-listen
- TS_TAILSCALED_EXTRA_ARGS extra arguments passed to tailscaled

Fixes #4985

Signed-off-by: Craig Rodrigues <rodrigc@crodrigues.org>
2022-07-01 14:45:51 -07:00
Jake Edgington
ea6e9099b9 fix: typo rename, ROUTES -> TS_ROUTES
Signed-off-by: Jake Edgington <jake.edgington@gmail.com>
2022-06-30 20:23:37 -07:00
Jake Edgington
72b7edbba9 fix: typo rename, KUBE_SECRET -> TS_KUBE_SECRET
Signed-off-by: Jake Edgington <jake.edgington@gmail.com>
2022-06-30 20:23:37 -07:00
Brad Fitzpatrick
6b71568eb7 util/cloudenv: add Azure support & DNS IPs
And rewrite cloud detection to try to do only zero or one metadata
discovery request for all clouds, only doing a first (or second) as
confidence increases. Work remains for Windows, but a start.

And add Cloud to tailcfg.Hostinfo, which helped with testing using
"tailcfg debug hostinfo".

Updates #4983 (Linux only)
Updates #4984

Change-Id: Ib03337089122ce0cb38c34f724ba4b4812bc614e
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-06-30 17:03:46 -07:00
Mihai Parparita
ec649e707f ipn/ipnlocal: prefer to use one CGNAT route on the Mac
Together with 06aa141632 this minimizes
the number of NEPacketTunnelNetworkSettings updates that we have to do,
and thus avoids Chrome interrupting outstanding requests due to
(perceived) network changes.

Updates #3102

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-06-30 13:18:52 -07:00
Aaron Bieber
3f4fd64311 cmd/tailscale: exit loop when timeout and pingArgs.num are met
Currently if you use '-c' and ping a host that times out, ping will
continue running indefinitely. This change exits the loop with "no
reply" when we time out, hit the value specified by '-c' and do not
have anyPong. If we have anyPong it returns nil.

Signed-off-by: Aaron Bieber <aaron@bolddaemon.com>
2022-06-30 11:52:56 -07:00
Brad Fitzpatrick
aa37aece9c ipn/ipnlocal, net/dns*, util/cloudenv: add AWS DNS support
And remove the GCP special-casing from ipn/ipnlocal; do it only in the
forwarder for *.internal.

Fixes #4980
Fixes #4981

Change-Id: I5c481e96d91f3d51d274a80fbd37c38f16dfa5cb
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-06-29 20:37:44 -07:00
Brad Fitzpatrick
88c2afd1e3 ipn/ipnlocal, net/dns*, util/cloudenv: specialize DNS config on Google Cloud
This does three things:

* If you're on GCP, it adds a *.internal DNS split route to the
  metadata server, so we never break GCP DNS names. This lets people
  have some Tailscale nodes on GCP and some not (e.g. laptops at home)
  without having to add a Tailnet-wide *.internal DNS route.
  If you already have such a route, though, it won't overwrite it.

* If the 100.100.100.100 DNS forwarder has nowhere to forward to,
  it forwards it to the GCP metadata IP, which forwards to 8.8.8.8.
  This means there are never errNoUpstreams ("upstream nameservers not set")
  errors on GCP due to e.g. mangled /etc/resolv.conf (GCP default VMs
  don't have systemd-resolved, so it's likely a DNS supremacy fight)

* makes the DNS fallback mechanism use the GCP metadata IP as a
  fallback before our hosted HTTP-based fallbacks

I created a default GCP VM from their web wizard. It has no
systemd-resolved.

I then made its /etc/resolv.conf be empty and deleted its GCP
hostnames in /etc/hosts.

I then logged in to a tailnet with no global DNS settings.

With this, tailscaled writes /etc/resolv.conf (direct mode, as no
systemd-resolved) and sets it to 100.100.100.100, which then has
regular DNS via the metadata IP and *.internal DNS via the metadata IP
as well. If the tailnet configures explicit DNS servers, those are used
instead, except for *.internal.

This also adds a new util/cloudenv package based on version/distro
where the cloud type is only detected once. We'll likely expand it in
the future for other clouds, doing variants of this change for other
popular cloud environments.

Fixes #4911

RELNOTES=Google Cloud DNS improvements

Change-Id: I19f3c2075983669b2b2c0f29a548da8de373c7cf
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-06-29 17:39:13 -07:00
Mihai Parparita
6f58497647 .github/workflows: downgrade MinGW to work around windows-race failures
Updates #4926

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-06-29 14:27:57 -07:00
Maisem Ali
88133c361e Docker: add ALPINE.txt to manage alpine versions
The goal here is to

1. make it so that the number doesn't diverge between the various places
   we had it defined
2. not define the number in corp, only in oss

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-06-29 11:47:09 -07:00
Maisem Ali
cfa484e1a2 Dockerfile: bump alpine to 3.16
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-06-29 10:29:37 -07:00
Brad Fitzpatrick
ef351ac0dd Dockerfile: fix build
The Dockerfile directions said:

But that failed with:

Step 14/15 : FROM ghcr.io/tailscale/alpine-base:3.14
Head "https://ghcr.io/v2/tailscale/alpine-base/manifests/3.14": denied: denied

So I guess the Dockerfile.base part was undocumented. But it only had
one line anyway, so move it here to avoid the intermediate layer's
published permissions problem entirely.

Also optimize the cachability a bit while here.

Change-Id: I846ad59fe7e88e6126925689fae78bfb80c279f0
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-06-29 08:18:01 -07:00
Mihai Parparita
06aa141632 wgengine/router: avoid unncessary routing configuration changes
The iOS and macOS networking extension API only exposes a single setter
for the entire routing and DNS configuration, and does not appear to
do any kind of diffing or deltas when applying changes. This results
in spurious "network changed" errors in Chrome, even when the
`OneCGNATRoute` flag from df9ce972c7 is
used (because we're setting the same configuration repeatedly).

Since we already keep track of the current routing and DNS configuration
in CallbackRouter, use that to detect if they're actually changing, and
only invoke the platform setter if it's actually necessary.

Updates #3102

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-06-28 16:59:37 -07:00
Brad Fitzpatrick
3b1f99ded1 ssh/tailssh: fix Tailscale SSH to Linux Arch machines
See https://github.com/tailscale/tailscale/issues/4924#issuecomment-1168201823

Arch uses a different login binary that makes the -h flag set the PAM
service to "remote". So if they don't have that configured, don't pass -h.

Thanks to @eddiezane for debugging!

Updates #4924

Change-Id: I8d33e0afb2dfb99517bcea2f9d5d0c6247519b3c
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-06-28 15:35:51 -07:00
kylecarbs
9280d39678 wgengine/netstack: close ipstack when netstack.Impl is closed
Fixes netstack.Impl leaking goroutines after shutdown.

Signed-off-by: kylecarbs <kyle@carberry.com>
2022-06-28 14:59:29 -07:00
Denton Gentry
d7f452c0a1 net/portmapper: send discovery packet for IGD specifically.
There appear to be devices out there which send only their
first descriptor in response to a discovery packet for
`ssdp:all`, for example the Sagemcom FAST3890V3 only sends
urn:schemas-wifialliance-org:device:WFADevice:1

Send both ssdp:all and a discovery frame for
InternetGatewayDevice specifically.

Updates https://github.com/tailscale/tailscale/issues/3557

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-06-28 03:55:17 -07:00
Denton Gentry
09eaba91ad net/portmap: add a test for Sagemcom FAST3890V3.
Updates https://github.com/tailscale/tailscale/issues/3557

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-06-28 03:55:17 -07:00
Denton Gentry
b5553c6ad2 net/portmap: run go fmt
Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-06-28 03:55:17 -07:00
Denton Gentry
de4c635e54 net/portmapper: make pcpCodeNotAuthorized log more descriptive
If PCP is present but disabled, turning it on might help
get direct connections.

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-06-28 03:55:17 -07:00
Brad Fitzpatrick
3ac8ab1791 tsnet: add Server.AuthKey field
... so callers can provide the AuthKey via mechanisms other than
environment variables which means multiple Servers can't be started
concurrently in the same process without coordination.

Change-Id: I7736ef4f59b7cc29637939e140e990613ce58e0d
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-06-27 21:57:57 -07:00
Jordan Whited
bef6e2831a cmd/tailscale: move call to cli.CleanUpArgs() from main() into cli.Run() (#4954)
Not all distributions build from package main.

Signed-off-by: Jordan Whited <jordan@tailscale.com>
2022-06-27 14:56:25 -07:00
Maisem Ali
40503ef07a ssh/tailssh: fix logging typo
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-06-27 13:23:09 -07:00
soypete
412c4c55e2 cmd/tailscale: make up respect explicitly empty --operator= value
Fixes #3808

Signed-off-by: soypete <miriah@tailscale.com>
2022-06-27 13:59:45 -06:00
Maisem Ali
c434e47f2d ssh/tailssh: always use current time for policy evaluation
Whenever the SSH policy changes we revaluate all open connections to
make sure they still have access. This check was using the wrong
timestamp and would match against expired policies, however this really
isn't a problem today as we don't have policy that would be impacted by
this check. Fixing it for future use.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-06-27 12:25:04 -07:00
Maisem Ali
a7d2024e35 ssh/tailssh: allow multiple sessions on the same conn
Fixes #4920
Fixes tailscale/corp#5633
Updates #4479

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-06-27 11:54:54 -07:00
mattn
1d04e01d1e use C:\Windows\System32\OpenSSH\ssh.exe (#4933)
cmd/tailscale: make ssh command prefer Windows ssh.exe over PATH

Signed-off-by: Yasuhiro Matsumoto <mattn.jp@gmail.com>
2022-06-25 22:26:21 -07:00
Adam Eijdenberg
9294a14a37 ssh/tailssh: limit setgroups to 16 on macOS
Fixes #4938

Signed-off-by: Adam Eijdenberg <adam@continusec.com>
2022-06-25 22:17:53 -07:00
Adam Eijdenberg
7f807fef6c ssh/tailssh: fix /usr/bin/login args on macOS
Fixes #4931

Signed-off-by: Adam Eijdenberg <adam@continusec.com>
2022-06-25 22:17:53 -07:00
Brad Fitzpatrick
35782f891d util/deephash: add canMemHash func + typeInfo property
Currently unused. (breaking up a bigger change)

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-06-25 13:09:30 -07:00
Brad Fitzpatrick
7b9a901489 util/deephash: add packet filter benchmark
(breaking up parts of another change)

This adds a PacketFilter hashing benchmark with an input that both
contains every possible field, but also is somewhat representative in
the shape of what real packet filters contain.

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-06-25 12:55:15 -07:00
James Tucker
c88bd53b1b .github/workflows: windows-race: print gcc version
Signed-off-by: James Tucker <james@tailscale.com>
2022-06-24 15:30:36 -07:00
Maisem Ali
2d65c1a950 client/tailscale: update ACLRow and ACLTest with new ACL fields
Signed-off-by: Maisem Ali <maisem@tailscale.com>
Co-authored-by: Will Norris <will@tailscale.com>
2022-06-24 12:20:08 -07:00
Aaron Klotz
4baf34cf25 net/dns: set appropriate Windows registry values to prevent it from sending DNS changes concerning our interface to AD domain controllers.
We do this unconditionally inside SetDNS such that the values are always set
before we make any other changes to DNS configurations.

It should not be harmful for the settings to remain even when other DNS
settings are cleared out (since they only affect our network interface).

See https://docs.microsoft.com/en-us/troubleshoot/windows-server/networking/configure-dns-dynamic-updates-windows-server-2003 for details about the registry value.

Fixes https://github.com/tailscale/tailscale/issues/4829

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2022-06-24 11:41:33 -06:00
Aaron Klotz
8cdfd12977 net/dns: update Windows split DNS settings to work alongside other NRPT entries set by group policy.
When there are group policy entries for the NRPT that do not belong to Tailscale,
we recognize that we need to add ourselves to group policy and use that registry
key instead of the local one. We also refresh the group policy settings as
necessary to ensure that our changes take effect immediately.

Fixes https://github.com/tailscale/tailscale/issues/4607

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2022-06-23 15:42:22 -06:00
James Tucker
76256d22d8 wgengine/router: windows: set SkipAsSource on IPv6 LL addresses
Link-local addresses on the Tailscale interface are not routable.
Ideally they would be removed, however, a concern exists that the
operating system will attempt to re-add them which would lead to
thrashing.

Setting SkipAsSource attempts to avoid production of packets using the
address as a source in any default behaviors.

Before, in powershell: `ping (hostname)` would ping the link-local
address of the Tailscale interface, and fail.
After: `ping (hostname)` now pings the link-local address on the next
highest priority metric local interface.

Fixes #4647
Signed-off-by: James Tucker <james@tailscale.com>
2022-06-22 15:26:40 -07:00
Brad Fitzpatrick
8c5c87be26 util/deephash: fix collisions between different types
Updates #4883

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-06-21 22:29:04 -07:00
Tom DNetto
4f6fa3d63a shell.nix: use 1.18 from system nixpkgs
(Now that 22.05 / 22.11 are released and presumably everyone has updated).

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-06-21 15:36:39 -07:00
Xe Iaso
dee95d0894 cmd/gitops-pusher: add new GitOps assistant (#4893)
This is for an upcoming blogpost on how to manage Tailscale ACLs using a
GitOps flow. This tool is intended to be used in CI and will allow users
to have a git repository be the ultimate source of truth for their ACL
file. This enables ACL changes to be proposed, approved and discussed
before they are applied.

Signed-off-by: Xe <xe@tailscale.com>
2022-06-21 16:04:48 -04:00
Sofiane Hamlaoui
1007983159 Adding pkg for Freebsd installation
Signed-off-by: Sofiane Hamlaoui <s0fianehaml40u1@gmail.com>
2022-06-20 11:31:10 -07:00
Sofiane Hamlaoui
51cc0e503b adding --noconfirm to pacman installation
Signed-off-by: Sofiane Hamlaoui <s0fianehaml40u1@gmail.com>
2022-06-20 11:31:10 -07:00
Brad Fitzpatrick
87a4c75fd4 control/controlclient, ipn/ipnlocal: remove Client.SetExpirySooner, fix race
Client.SetExpirySooner isn't part of the state machine. Remove it from
the Client interface.

And fix a use of LocalBackend.cc without acquiring the lock that
guards that field.

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-06-19 22:08:29 -07:00
Brad Fitzpatrick
ef0d740270 control/controlclient: remove Client.SetStatusFunc
It can't change at runtime. Make it an option.

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-06-19 21:54:39 -07:00
Brad Fitzpatrick
70a2797064 control/controlclient, ipn/ipnlocal: remove some Client methods
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-06-19 18:11:59 -07:00
Brad Fitzpatrick
a1e429f7c3 control/controlclient, types/netmap: remove unused LocalPort field
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-06-19 17:22:00 -07:00
Brad Fitzpatrick
526b0b6890 control/controlclient: start simplifying netmap fetch APIs
Step 1 of many, cleaning up the direct/auto client & restarting map
requests that leads to all the unnecessary map requests.

Updates tailscale/corp#5761

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-06-19 15:43:12 -07:00
Brad Fitzpatrick
467eb2eca0 cmd/tailscale/cli, ipn/ipnlocal: give SSH tips when off/unconfigured
Updates #3802

Change-Id: I6b9a3175f68a6daa670f912561f2c2ececc07770
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-06-17 19:37:59 -07:00
Brad Fitzpatrick
99ed54926b tailcfg: define some Node.Capabilities about SSH, its config
Updates #3802

Change-Id: Icb4ccbc6bd1c6304013bfc553d04007844a5c0bf
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-06-17 12:14:50 -07:00
Brad Fitzpatrick
13d0b8e6a4 control/controlclient, net/dnscache: use typed singleflight fork
Change-Id: I12be4c5a91ae3a812fe88d9b2d15526fdbb5a921
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-06-17 10:20:16 -07:00
Brad Fitzpatrick
59ed846277 util/singleflight: add fork of singleflight with generics
Forked from golang.org/x/sync/singleflight at
the x/sync repo's commit 67f06af15bc961c363a7260195bcd53487529a21

Updates golang/go#53427

Change-Id: Iec2b47b7777940017bb9b3db9bd7d93ba4a2e394
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-06-17 10:20:16 -07:00
Brad Fitzpatrick
757ecf7e80 util/deephash: fix map hashing when key & element have the same type
Regression from 09afb8e35b, in which the
same reflect.Value scratch value was being used as the map iterator
copy destination.

Also: make nil and empty maps hash differently, add test.

Fixes #4871

Co-authored-by: Josh Bleecher Snyder <josharian@gmail.com>
Change-Id: I67f42524bc81f694c1b7259d6682200125ea4a66
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-06-16 22:29:47 -07:00
Brad Fitzpatrick
22c544bca7 go.mod: bump go4.org/unsafe/assume-no-moving-gc for Go 1.19beta1
Otherwise we crash at startup with Go 1.19beta1.

Updates #4872

Change-Id: I371df4146735f7e066efd2edd48c1a305906c13d
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-06-16 20:40:22 -07:00
Brad Fitzpatrick
f31588786f util/deephash: don't track cycles on non-recursive types
name              old time/op    new time/op    delta
Hash-8              67.3µs ±20%    76.5µs ±16%     ~     (p=0.143 n=10+10)
HashMapAcyclic-8    63.0µs ± 2%    56.3µs ± 1%  -10.65%  (p=0.000 n=10+8)
TailcfgNode-8       9.18µs ± 2%    6.52µs ± 3%  -28.96%  (p=0.000 n=9+10)
HashArray-8          732ns ± 3%     709ns ± 1%   -3.21%  (p=0.000 n=10+10)

name              old alloc/op   new alloc/op   delta
Hash-8               24.0B ± 0%     24.0B ± 0%     ~     (all equal)
HashMapAcyclic-8     0.00B          0.00B          ~     (all equal)
TailcfgNode-8        0.00B          0.00B          ~     (all equal)
HashArray-8          0.00B          0.00B          ~     (all equal)

name              old allocs/op  new allocs/op  delta
Hash-8                1.00 ± 0%      1.00 ± 0%     ~     (all equal)
HashMapAcyclic-8      0.00           0.00          ~     (all equal)
TailcfgNode-8         0.00           0.00          ~     (all equal)
HashArray-8           0.00           0.00          ~     (all equal)

Change-Id: I28642050d837dff66b2db54b2b0e6d272a930be8
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-06-16 18:39:10 -07:00
Brad Fitzpatrick
36ea837736 util/deephash: fix map hashing to actually hash elements
Fixes #4868

Change-Id: I574fd139cb7f7033dd93527344e6aa0e625477c7
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-06-16 11:32:12 -07:00
Brad Fitzpatrick
4005134263 tailcfg: clarify some of the MapRequest variants
Change-Id: Ia09bd69856e372c3a6b64cda7ddb34029b32a11b
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-06-14 13:08:55 -07:00
Joe Tsai
0f05b2c13f tsnet: use tailscaled as prefix for state file names (#4816)
Use the "tailscaled" prefix instead of "tsnet" for state file names:
1. It is consistent with the pre-existing {{Dir}}/tailscaled.state file.
2. It makes the file layout of `tsnet` and `tailscaled` identical,
   so that they are compatible with each other.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-06-09 11:46:43 -07:00
Denton Gentry
1392a93445 socks5: add a simple test
Start up a backend service, put a SOCKS5 server in front
of it, and verify that we can get data from the backend via
SOCKS5.

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-06-09 10:41:06 -07:00
Denton Gentry
7fffddce8e net/portmapper: enable for iOS
In the 1.27 unstable releases we set the min-version to iOS15,
which means we have 50 MBytes of RAM in the Network Extension.
https://tailscale.com/blog/go-linker/

Include the UPnP/NAT-PMP/PCP portmapper support now that there
is memory for it.

Fixes https://github.com/tailscale/tailscale/issues/2495
Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-06-09 10:40:25 -07:00
Mihai Parparita
2990c2b1cf control/controlhttp: use secure WebSockets protocol by default
Forcing the insecure protocol (and perserving the port number) is only
desired for localhost testing, in prod we need to use wss:// to avoid
mixed-content errors.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-06-08 15:29:21 -07:00
Tom DNetto
32c6823cf5 tsweb: implement interceptor for error page presentation
Updates https://github.com/tailscale/corp/issues/5605

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-06-08 15:21:16 -07:00
Mihai Parparita
b788a5ba7e tailcfg: add HostinfoView version of TailscaleSSHEnabled
Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-06-08 12:08:14 -07:00
Praneet Loke
d8c05fc1b2 Update a Taildrop error message (#4818)
ipn/ipnlocal: update error message on Taildrop send while not connected

Signed-off-by: Praneet <1466314+praneetloke@users.noreply.github.com>
2022-06-08 09:11:50 -07:00
Brad Fitzpatrick
d3643fa151 cmd/tailscale: add 'debug ts2021' Noise connectivity subcommand
Updates #3488

Change-Id: I9272e68f66c4cf36fb98dd1248a74d3817447690
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-06-08 09:07:05 -07:00
Joe Tsai
96f73b3894 logtail: do not panic in PrivateID.PublicID (#4815)
It is not idiomatic for Go code to panic for situations that
can be normal. For example, if a server receives PrivateID
from a client, it is normal for the server to call
PrivateID.PublicID to validate that the PublicID matches.
However, doing so would panic prior to this change.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-06-07 17:25:05 -07:00
Melanie Warrick
3a182d5dd6 ipn/ipnstate: add ExitNodeStatus to share the exit node if it is in use, the IP, ID and whether its online. (#4761)
-
Updates #4619

Signed-off-by: nyghtowl <warrick@tailscale.com>
2022-06-07 12:31:10 -07:00
Mihai Parparita
6246fa32f0 wasm: add test for disallowed JS/WASM dependencies
Ensures that binary size gains like the ones from #4802 and #4813
don't regress.

Updates #3517

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-06-07 12:19:11 -07:00
Mihai Parparita
c41837842b wasm: drop pprof dependency
We can use the browser tools to profile, pprof adds 200K to the binary size.

Updates #3157

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-06-07 12:16:16 -07:00
Ross Zurowski
bb67999808 tailcfg: add TailscaleSSHEnabled helper check (#4812)
This commit adds a helper to check if Tailscale SSH is enabled. We're
currently checking the SSH_HostKeys field in a few places, but later
plan to add an explicit bool. This helper makes the check and any future
changes easier.

Signed-off-by: Ross Zurowski <ross@rosszurowski.com>
2022-06-07 14:50:08 -04:00
Will Norris
09363064b5 tsnet: use proper log ID
refactor logpolicy config loading to make it easier to reuse from
outside the package.  Within tsnet, setup a basic logtail config.

Signed-off-by: Will Norris <will@tailscale.com>
2022-06-07 10:09:21 -07:00
Mihai Parparita
edc90ebc61 net/wsconn: remove homegrown wrapper for turning a websocket.Conn into a net.Conn
The one from the nhooyr/websocket package seems to work equally well.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-06-07 09:28:56 -07:00
Denton Gentry
cfb5bd0559 VERSION.txt: this is v1.27.0
Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-06-06 16:11:18 -07:00
Brad Fitzpatrick
db83926121 go.toolchain.rev: bump Go to 1.18.3 (+ Tailscale patches)
See 04d67b90d8

Diff:

bb6009ec7c..04d67b90d8

Change-Id: Ic0abd3058f3696c3f8007e1004ab4bf377c5323c
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-06-06 15:46:28 -07:00
Mihai Parparita
27a1ad6a70 wasm: exclude code that's not used on iOS for Wasm too
It has similar size constraints. Saves ~1.9MB from the Wasm build.

Updates #3157

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-06-06 13:52:52 -07:00
Brad Fitzpatrick
4007601f73 cmd/controlclient: wire up PingRequest peerapi pings too
Updates tailscale/corp#754

Change-Id: I61ac3fc44783b54bd02455bcb0baf19159b7a9d2
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-06-06 13:41:34 -07:00
Maisem Ali
3b55bf9306 build_docker.sh: add run.sh as an entrypoint to the docker image
Fixes #4071

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-06-07 00:45:49 +05:00
Maisem Ali
bf2fa7b184 go.mod: pin github.com/tailscale/mkctr (try #2)
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-06-07 00:44:21 +05:00
Brad Fitzpatrick
0d972678e7 cmd/tailscale/cli: disable 'tailscale ssh' on sandboxed macOS
Updates #3802
Updates #4518
Fixes #4628

Change-Id: I194d2cc30fc8e38b66d4910787efbce14317b0ff
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-06-06 08:54:38 -07:00
Brad Fitzpatrick
0df3b76c25 tsweb: fix Port80Handler redirect to https with FQDN unset
Fixes the current http://pkgs.tailscale.com/ redirect to https:///
as that server doesn't configure the Port80Handler.FQDN field.

Change-Id: Iff56e6127a46c306ca97738d91b217bcab32a582
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-06-05 13:01:30 -07:00
Denton Gentry
c6ac82e3a6 hostinfo,distro: Identify Western Digital MyCloud devices.
root@WDMyCloud HD_a2 # ./tailscale debug hostinfo
{
  "IPNVersion": "1.25.0-dev20220605-t7fea52e02",
  "OS": "linux",
  "OSVersion": "5.22.113",
  "Desktop": false,
  "DeviceModel": "WD My Cloud Gen2: Marvell Armada 375",
  "Hostname": "WDMyCloud",
  "GoArch": "arm"
}

Updates https://github.com/tailscale/tailscale/issues/4622

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-06-05 08:22:42 -07:00
Denton Gentry
0687195bee logpolicy: put Synology logs buffer in /tmp
Ongoing log writing keeps the spinning disks from hibernating.
Fixes https://github.com/tailscale/tailscale/issues/3551

Tested on DSM6 and DSM7.

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-06-04 22:06:14 -07:00
Brad Fitzpatrick
fbc079d82d ipn/ipnlocal: prevent attempting to run SSH on Synology for now
On DSM7 as a non-root user it'll run into problems.

And we haven't tested on DSM6, even though it might work, but I doubt
it.

Updates #3802
Updates tailscale/corp#5468

Change-Id: I75729042e4788f03f9eb82057482a44b319f04f3
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-06-03 13:50:33 -07:00
Brad Fitzpatrick
2bac8b6013 Revert "cmd/tailscale/cli: disallow --ssh on Synology"
This reverts commit 03e3e6abcd
in favor of #4785.

Change-Id: Ied65914106917c4cb8d15d6ad5e093a6299d1d48
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-06-03 13:49:42 -07:00
Maisem Ali
03e3e6abcd cmd/tailscale/cli: disallow --ssh on Synology
Updates tailscale/corp#5468
Updates #3802

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-06-04 01:39:33 +05:00
Brad Fitzpatrick
a9b4bf1535 ipn/ipnserver, cmd/tailscaled: fix peerapi on Windows
We weren't wiring up netstack.Impl to the LocalBackend in some cases
on Windows. This fixes Windows 7 when run as a service.

Updates #4750 (fixes after pull in to corp repo)

Change-Id: I9ce51b797710f2bedfa90545776b7628c7528e99
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-06-03 12:24:47 -07:00
Jordan Whited
43f9c25fd2 cmd/tailscale: surface authentication errors in status.Health (#4748)
Fixes #3713

Signed-off-by: Jordan Whited <jordan@tailscale.com>
2022-06-03 10:52:07 -07:00
Charlotte Brandhorst-Satzkorn
c980bf01be words: The lists continue to drag-on. (#4780)
For Zaku and Pretzel.

Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2022-06-03 10:55:17 -04:00
Mihai Parparita
a9f32656f5 control/controlhttp: allow client and server to communicate over WebSockets
We can't do Noise-over-HTTP in Wasm/JS (because we don't have bidirectional
communication), but we should be able to do it over WebSockets. Reuses
derp WebSocket support that allows us to turn a WebSocket connection
into a net.Conn.

Updates #3157

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-06-02 21:20:54 -07:00
Maisem Ali
80157f3f37 net/dns/resolver: add support for <IPv4>.via-<site-id>
Currently we only support "via-<site-id>.<IPv4>", however that does not
work with Google Chrome which parses `http://via-1.10.0.0.1` as a search
string and not as a URL. This commit introduces "<IPv4>.via-<site-id>"
(`http://10.0.0.1.via-1`) which is parsed correctly by Chrome.

Updates #3616

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-06-02 23:20:37 +05:00
Brad Fitzpatrick
69b535c01f wgengine/netstack: replace a 1500 with a const + doc
Per post-submit code review feedback of 1336fb740b from @maisem.

Change-Id: Ic5c16306cbdee1029518448642304981f77ea1fd
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-06-02 08:24:35 -07:00
Brad Fitzpatrick
e428bba7a3 ssh/tailssh: add metrics
Updates #3802

Change-Id: Ic9a4b8c51cff6dfe148a1c78bc0e5074195b7f80
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-06-02 08:18:53 -07:00
Maisem Ali
67325d334e cmd/tailscale/cli: add lose-ssh risk
This makes it so that the user is notified that the action
they are about to take may result in them getting disconnected from
the machine. It then waits for 5s for the user to maybe Ctrl+C out of
it.

It also introduces a `--accept-risk=lose-ssh` flag for automation, which
allows the caller to pre-acknowledge the risk.

The two actions that cause this are:
- updating `--ssh` from `true` to `false`
- running `tailscale down`

Updates #3802

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-06-02 13:14:43 +05:00
Brad Fitzpatrick
1336fb740b wgengine/netstack: make netstack MTU be 1280 also
Updates #3878

Change-Id: I1850085b32c8a40d85607b4ad433622c97d96a8d
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-06-01 12:16:41 -07:00
Maisem Ali
81487169f0 build_docker.sh: pin github.com/tailscale/mkctr
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-06-01 19:55:06 +05:00
Tobias Klauser
3a926348a4 hostinfo: use ByteSliceToString from golang.org/x/sys/unix
Use unix.ByteSliceToString in osVersionFreebsd and osVersionLinux to
convert the Utsname.Release []byte field to string.

Signed-off-by: Tobias Klauser <tklauser@distanz.ch>
2022-06-01 07:43:44 -07:00
Tobias Klauser
2a61261a5a hostinfo: use Uname from golang.org/x/sys/unix in osVersionLinux
As already done in osVersionFreebsd. This will allow to use the Utsname
fields as []byte for easier conversion to string.

Signed-off-by: Tobias Klauser <tklauser@distanz.ch>
2022-06-01 07:43:44 -07:00
Maisem Ali
928530a112 ipn/ipnlocal: shutdown sshServer on tailscale down
Also lazify SSHServer initialization to allow restarting the server on a
subsequent `tailscale up`

Updates #3802

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-05-30 15:01:22 +05:00
Brad Fitzpatrick
4d85cf586b cmd/tailscale, ipn/ipnlocal: add "peerapi" ping type
For debugging when stuff like #4750 isn't working.

RELNOTE=tailscale ping -peerapi

Change-Id: I9c52c90fb046e3ab7d2b121387073319fbf27b99
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-05-28 13:47:12 -07:00
Maisem Ali
575aacb1e2 ssh/tailssh: terminate sessions on stdout copy failures
Currently, killing a SCP copy with a Ctrl+C leaves the session hanging
even though the stdout copy goroutine fails with an io.EOF. Taking a
step back, when we are unable to send any more data back to the client
we should just terminate the session as the client will stop getting any
response from the server anyways.

Updates #3802

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-05-28 21:30:54 +05:00
Maisem Ali
7cd8c3e839 ssh/tailssh: terminate sessions when tailscaled shutsdown
Ideally we would re-establish these sessions when tailscaled comes back
up, however we do not do that yet so this is better than leaking the
sessions.

Updates #3802

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-05-28 21:30:54 +05:00
Maisem Ali
760740905e ssh/tailssh: only use login with TTY sessions
Otherwise, the shell exits immediately causing applications like mosh
and VSCode to fail.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-05-28 21:03:40 +05:00
Brad Fitzpatrick
02e580c1d2 logtail: use http.NewRequestWithContext
Saves some allocs. Not hot, but because we can now.

And a const instead of a var.

Change-Id: Ieb2b64534ed38051c36b2c0aa2e82739d9d0e015
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-05-27 16:33:43 -07:00
Tom
2903d42921 wgengine/router: delete hardcoded link-local address on Windows (#4740)
Fixes #4647

It seems that Windows creates a link-local address for the TUN driver, seemingly
based on the (fixed) adapter GUID. This results in a fixed MAC address, which
for some reason doesn't handle loopback correctly. Given the derived link-local
address is preferred for lookups (thanks LLMNR), traffic which addresses the
current node by hostname uses this broken address and never works.

To address this, we remove the broken link-local address from the wintun adapter.

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-05-27 14:42:55 -07:00
Aaron Klotz
b005b79236 net/dns, paths, util/winutil: change net/dns/windowsManager NRPT management to support more than 50 domains.
AFAICT this isn't documented on MSDN, but based on the issue referenced below,
NRPT rules are not working when a rule specifies > 50 domains.

This patch modifies our NRPT rule generator to split the list of domains
into chunks as necessary, and write a separate rule for each chunk.

For compatibility reasons, we continue to use the hard-coded rule ID, but
as additional rules are required, we generate new GUIDs. Those GUIDs are
stored under the Tailscale registry path so that we know which rules are ours.

I made some changes to winutils to add additional helper functions in support
of both the code and its test: I added additional registry accessors, and also
moved some token accessors from paths to util/winutil.

Fixes https://github.com/tailscale/coral/issues/63

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2022-05-27 14:56:09 -06:00
Joel Cressy
c16271fb46 ipn/localapi: implement LoginInteractive via localapi
Updates: #4738

Signed-off-by: Joel Cressy <joel@jtcressy.net>
2022-05-27 06:34:27 -07:00
Denton Gentry
0f95eaa8bb scripts/installer: fix elementaryOS
c2b907c965 moved UBUNTU_VERSION out
of the ubuntu case and into linuxmint, but linuxmint wasn't the
only Ubuntu-based system which needed it. Restore UBUNTU_VERSION
handling in the ubuntu case.

Break elementaryOS out into its own handling so we can get the
version number handling correct for keyring support.
Tested on an elementaryOS 6.1 VM.

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-05-27 06:21:15 -07:00
James Tucker
3f686688a6 cmd/tailscaled: fix state path for windows svc
Signed-off-by: James Tucker <james@tailscale.com>
2022-05-26 17:59:50 -07:00
Aaron Klotz
c163b2a3f1 util/winutil, util/winutil/vss: remove winrestore and vss as they are unnecessary.
I wrote this code way back at the beginning of my tenure at Tailscale when we
had concerns about needing to restore deleted machine keys from backups.

We never ended up using this functionality, and the code is now getting in the
way, so we might as well remove it.

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2022-05-26 12:13:36 -06:00
Tom
fc5839864b wgengine/netstack: handle multiple magicDNS queries per UDP socket (#4708)
Fixes: #4686

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-05-20 13:30:11 -07:00
Brad Fitzpatrick
c81be7b899 control/controlclient: avoid Noise protocol for js/wasm for now
Updates #3157

Change-Id: I04accc09783a68257d28cadde5818bf0724a8013
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-05-20 12:09:09 -07:00
Denton Gentry
36af49ae7f install.sh: add RHEL9.
Fixes https://github.com/tailscale/tailscale/issues/4718

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-05-20 09:49:39 -07:00
Mihai Parparita
bded712e58 .github/workflows: fix duplicated build target in Wasm action
Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-05-20 09:31:14 -07:00
Mihai Parparita
7cfc6130e5 .github/workflows: add cross-builder for Wasm
For now just checks that we can build cmd/tailscale/cli, will be
broadened once we can actually build more things.

Updates #3157

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-05-19 20:57:31 -07:00
Mihai Parparita
eda647cb47 cmd/tailscale/cli: fix ssh CLI command breaking the Wasm build
Adds a stub for syscall.Exec when GOOS=js. We also had a separate branch
for Windows, might as well use the same mechanism there too.

For #3157

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-05-19 20:49:34 -07:00
Brad Fitzpatrick
cc91a05686 ipn/ipnserver: fix build on js/wasm
Broken by 3dedcd1640 but we don't have CI coverage yet.

Updates #3157

Change-Id: Ie8e95ebd36264887fdeed16fc9f25a857d48124b
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-05-19 15:01:27 -07:00
Mihai Parparita
3222bce02d logtail: add instance metadata to the entry logtail
Allows instances that are running with the same machine ID (due to
cloning) to be distinguished.

Also adds sequence numbers to detect duplicates.

For tailscale/corp#5244

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-05-18 13:57:14 -07:00
Tom
acfe5bd33b net/dns{., resolver}: time out DNS queries after 10 seconds (#4690)
Fixes https://github.com/tailscale/corp/issues/5198

The upstream forwarder will block indefinitely on `udpconn.ReadFrom` if no
reply is recieved, due to the lack of deadline on the connection object.

There still isn't a deadline on the connection object, but the automatic closing
of the context on deadline expiry will close the connection via `closeOnCtxDone`,
unblocking the read and resulting in a normal teardown.

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-05-18 10:40:04 -07:00
Tom
ec4c49a338 types/key: make NodePublic implement Shardable (#4698)
Needed for an experiment in Control.

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-05-17 10:37:25 -07:00
Denton Gentry
53f6c3f9f2 api.md: document preauthorized and tags fields
Updates https://github.com/tailscale/tailscale/issues/2120
Updates https://github.com/tailscale/tailscale/issues/4571
Updates https://github.com/tailscale/tailscale/issues/1369

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-05-17 09:25:13 -07:00
Brad Fitzpatrick
48d43134d7 cmd/tsshd: delete, leaving only forwarding docs
Updates #3802

Change-Id: I89d4d3d68d64af9bc7288a149b4b34f61884f5f4
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-05-16 11:52:44 -07:00
Denton Gentry
afb3f62b01 scripts/installer.sh: add Xen Enterprise
Tested on a VM running Xen Enterprise 8.2.1.
https://xcp-ng.org/
Fixes https://github.com/tailscale/tailscale/issues/4655

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-05-16 08:37:39 -07:00
Brad Fitzpatrick
da601c23e1 ipn/ipnlocal: add missing place where we set the SSH atomic
This fixes the "tailscale up --authkey=... --ssh" path (or any "up"
path that used Start instead of EditPrefs) which wasn't setting the
bit.

Updates #3802

Change-Id: Ifca532ec58296fedcedb5582312dfee884367ed7
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-05-14 12:47:28 -07:00
David Anderson
e1c1d47991 tsweb: memoize the string forms of HTTP response codes.
Saves 1-2 allocs per HTTP request after warmup, thanks to
avoiding strconv and fmt.

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-05-13 14:25:17 -07:00
Tom
9343967317 wgengine/filter: preallocate some hot slices in MatchesFromFilterRules (#4672)
Profiling identified this as a fairly hot path for growing a slice.

Given this is only used in control & when a new packet filter is received, this shouldnt be hot in the client.
2022-05-13 13:56:53 -07:00
David Anderson
c48513b2be tsweb: support recording unabridged HTTP status codes as well.
Signed-off-by: David Anderson <danderson@tailscale.com>
2022-05-13 13:50:23 -07:00
Mihai Parparita
561f7be434 wgengine/magicsock: remove unused metric
We don't increment the metricRecvData anywhere, just the per-protocol
ones.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-05-13 11:15:56 -07:00
Mihai Parparita
dd5548771e util/clientmetric: add gauge_ name prefix when uploading names
The prefix is a signal to tsweb to treat this as a gauge metric when
generating the Prometheus version.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-05-12 09:52:56 -07:00
Mihai Parparita
86069874c9 net/tstun, wgengine: use correct type for counter metrics
We were marking them as gauges, but they are only ever incremented,
thus counter is more appropriate.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-05-12 09:30:50 -07:00
James Tucker
87b44aa311 go.mod: bump golang.org/x/sys for CVE-2022-29526
Signed-off-by: James Tucker <james@tailscale.com>
2022-05-10 17:57:51 -07:00
James Tucker
4bb7440094 cmd/tailscaled: use --statedir as documented
Enables the behavior described in the statepath flag, where if only
statedir is passed, then state is statedir/tailscaled.state.

Signed-off-by: James Tucker <james@tailscale.com>
2022-05-10 15:13:13 -07:00
Maisem Ali
6dae9e47f9 types/views: remove alloc in hot path
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-05-10 11:20:00 -07:00
Brad Fitzpatrick
4c75605e23 go.toolchain.rev: bump Tailscale Go toolchain
For bb6009ec7c

(The cherry-picked fix for golang/go#51776)

Change-Id: Ib4a67c0f82256c62989fbba2cc9c15b728313ebd
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-05-10 05:31:13 -07:00
Maisem Ali
395cb588b6 types/views: make SliceOf/MapOf panic if they see a pointer
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-05-09 19:49:31 -07:00
Maisem Ali
d04afc697c cmd/viewer,types/views: add support for views of maps
Updates #4635

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-05-09 19:49:31 -07:00
Maisem Ali
5cd56fe8d5 ssh/tailssh: exec into login when launching a shell
This has the added benefit of displaying the MOTD and reducing our
dependency on the DBus interface.

Fixes #4627
Updates #3802

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-05-09 19:17:52 -07:00
Maisem Ali
a253057fc3 ssh/tailssh: refactor incubator flags
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-05-09 19:17:52 -07:00
Joe Tsai
741ae9956e tstest/integration/vms: use hujson.Standardize instead of hujson.Unmarshal (#4520)
The hujson package transition to just being a pure AST
parser and formatter for HuJSON and not an unmarshaler.

Thus, parse HuJSON as such, convert it to JSON,
and then use the standard JSON unmarshaler.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-05-06 14:16:10 -07:00
Maisem Ali
9f3ad40707 tailcfg: use cmd/viewer instead of cmd/cloner.
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-05-06 10:58:10 -07:00
Maisem Ali
fd99c54e10 tailcfg,all: change structs to []*dnstype.Resolver
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-05-06 10:58:10 -07:00
Maisem Ali
679415f3a8 tailcfg: move views into tailcfg_view.go
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-05-06 10:58:10 -07:00
Maisem Ali
c4e9739251 cmd/viewer: add codegen tool for Views
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-05-06 10:58:10 -07:00
Maisem Ali
e409e59a54 cmd/cloner,util/codegen: refactor cloner internals to allow reuse
Also run go generate again for Copyright updates.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-05-06 10:58:10 -07:00
Mihai Parparita
025867fd07 util/clientmetric: switch to TestHooks struct for test-only functions (#4632)
Followup to 7966aed1e0 to pick up
review feedback that was accidentally left out.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-05-06 10:08:57 -07:00
Mihai Parparita
7966aed1e0 util/clientmetric: add test hooks and ResetLastDelta function
Necessary to force flushing of client metrics more aggressively in
dev/test mode.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-05-06 09:52:48 -07:00
Brad Fitzpatrick
35111061e9 wgengine/netstack, ipn/ipnlocal: serve http://100.100.100.100/
For future stuff.

Change-Id: I64615b8b2ab50b57e4eef1ca66fa72e3458cb4a9
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-05-06 07:51:28 -07:00
Tom
d1d6ab068e net/dns, wgengine: implement DNS over TCP (#4598)
* net/dns, wgengine: implement DNS over TCP

Signed-off-by: Tom DNetto <tom@tailscale.com>

* wgengine/netstack: intercept only relevant port/protocols to quad-100

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-05-05 16:42:45 -07:00
Brad Fitzpatrick
c4f06ef7be client/tailscale: fix ExpandSNIName on non-default LocalClient
It was using a mix.

Found by @maisem.

Change-Id: Ieb79d78608474ac13c2f44e0f3d8997a5665eb13
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-05-05 12:22:38 -07:00
Brad Fitzpatrick
46cb9d98a3 api.md: update GET tailnet key detail docs to show preauthorized, tags
Fixes #4571

Change-Id: If81471d0d8cb2f659736991ad8612aed2efc174e
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-05-05 12:09:28 -07:00
Brad Fitzpatrick
c1445155ef ssh/tailssh: handle Control-C during hold-and-delegate prompt
Fixes #4549

Change-Id: Iafc61af5e08cd03564d39cf667e940b2417714cc
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-05-05 11:47:08 -07:00
James Tucker
f9e86e64b7 *: use WireGuard where logged, printed or named
Signed-off-by: James Tucker <james@tailscale.com>
2022-05-04 13:36:05 -07:00
Brad Fitzpatrick
2d1849a7b9 tsweb: remove JSONHandlerFunc
It's unused and we've decided it's not what we want.

Change-Id: I425a0104e8869630b498a0adfd0f455876d6f92b
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-05-04 11:52:07 -07:00
Charlotte Brandhorst-Satzkorn
7ee3068f9d words: after a Series of discussions, Bees should be included (#4606)
There has been a lot of talk about Bees at Tailscale recently, and
naturally, with it being Tailscale, we thought to ourselves:

Do Bees have a tail and/or scales?

Tailscale has a long track record of scientific rigor around the
validity of the inclusions on the tails and scales list, and this time
will be no exception.

Our research has found that Bees, in particular the Honey Bee, produces
wax scales on their abdomens and thus should be included. As for tails;

'Stabby-tails' - Tailscale Employee, 2022

No further justification needed, it will be included.

This change includes Bee in both tails.txt and scales.txt.

Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2022-05-04 09:20:23 -04:00
Brad Fitzpatrick
3e1f2d01f7 ipn/ipnlocal: move Ping method from IPN bus to LocalBackend (HTTP)
Change-Id: I61759f1dae8d9d446353db54c8b1e13bfffb3287
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-05-03 15:59:19 -07:00
Maisem Ali
c60cbca371 control/controlclient: store netinfo and hostinfo separately
Currently, when SetNetInfo is called it sets the value on
hostinfo.NetInfo. However, when SetHostInfo is called it overwrites the
hostinfo field which may mean it also clears out the NetInfo it had just
received.
This commit stores NetInfo separately and combines it into Hostinfo as
needed so that control is always notified of the latest values.

Also, remove unused copies of Hostinfo from ipn.Status and
controlclient.Auto.

Updates #tailscale/corp#4824 (maybe fixes)

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-05-03 15:33:01 -07:00
James Tucker
ae483d3446 wgengine, net/packet, cmd/tailscale: add ICMP echo
Updates tailscale/corp#754

Signed-off-by: James Tucker <james@tailscale.com>
2022-05-03 13:03:45 -07:00
Brad Fitzpatrick
66f9292835 client/tailscale: update Client API a bit
Change-Id: I81aa29a8b042a247eac1941038f5d90259569941
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-05-03 11:30:57 -07:00
Brad Fitzpatrick
512573598a tailcfg: remove some documented DebugFlags that no longer exist
Update tailscale/corp#5007

Change-Id: I3ce5b1c4cd367bae769a5f5a301925a2dac1b3a6
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-05-03 08:28:41 -07:00
Tom DNetto
2a0b5c21d2 net/dns/{., resolver}, wgengine: fix goroutine leak on shutdown
Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-05-02 10:42:06 -07:00
Tom DNetto
7f45734663 assorted: documentation and readability fixes
This were intended to be pushed to #4408, but in my excitement I
forgot to git push :/ better late than never.

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-04-30 18:42:19 -07:00
Tom DNetto
9e77660931 net/tstun,wgengine/{.,netstack}: handle UDP magicDNS traffic in netstack
This change wires netstack with a hook for traffic coming from the host
into the tun, allowing interception and handling of traffic to quad-100.

With this hook wired, magicDNS queries over UDP are now handled within
netstack. The existing logic in wgengine to handle magicDNS remains for now,
but its hook operates after the netstack hook so the netstack implementation
takes precedence. This is done in case we need to support platforms with
netstack longer than expected.

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-04-30 10:18:59 -07:00
Tom DNetto
dc71d3559f net/tstun,wgengine: split PreFilterOut into multiple hooks
A subsequent commit implements handling of magicDNS traffic via netstack.
Implementing this requires a hook for traffic originating from the host and
hitting the tun, so we make another hook to support this.

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-04-30 10:18:59 -07:00
Tom DNetto
9dee6adfab cmd/tailscaled,ipn/ipnlocal,wgengine/...: pass dns.Manager into netstack
Needed for a following commit which moves magicDNS handling into
netstack.

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-04-30 10:18:59 -07:00
Tom DNetto
5b85f848dd net/dns,net/dns/resolver: refactor channels/magicDNS out of Resolver
Moves magicDNS-specific handling out of Resolver & into dns.Manager. This
greatly simplifies the Resolver to solely issuing queries and returning
responses, without channels.

Enforcement of max number of in-flight magicDNS queries, assembly of
synthetic UDP datagrams, and integration with wgengine for
recieving/responding to magicDNS traffic is now entirely in Manager.
This path is being kept around, but ultimately aims to be deleted and
replaced with a netstack-based path.

This commit is part of a series to implement magicDNS using netstack.

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-04-30 10:18:59 -07:00
Brad Fitzpatrick
a54671529b client/tailscale: move API client for the control admin API
This was work done Nov-Dec 2020 by @c22wen and @chungdaniel.

This is just moving it to another repo.

Co-Authored-By: Christina Wen <37028905+c22wen@users.noreply.github.com>
Co-Authored-By: Christina Wen <christina@tailscale.com>
Co-Authored-By: Daniel Chung <chungdaniel@users.noreply.github.com>
Co-Authored-By: Daniel Chung <daniel@tailscale.com>

Change-Id: I6da3b05b972b54771f796b5be82de5aa463635ca
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-30 09:05:26 -07:00
Brad Fitzpatrick
e3619b890c client/tailscale: rename tailscale.go -> localclient.go
In prep for other stuff.

Change-Id: I82c24946d062d668cab48ca6749776b6ae7025ac
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-29 19:50:40 -07:00
Maisem Ali
3012a2e1ca ssh/tailssh,ipn/ipnlocal: terminate any active sessions on up --ssh=false
Currently the ssh session isn't terminated cleanly, instead the packets
are just are no longer routed to the in-proc SSH server. This makes it
so that clients get a disconnection when the `RunSSH` pref changes to
`false`.

Updates #3802

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-04-29 16:08:27 -07:00
Mihai Parparita
2ec371fe8b ipn: remove FakeExpireAfter Backend function
No callers remain (last one was removed with
tailscale/corp@1c095ae08f), and it's
pretty esoteric.

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-04-29 15:34:53 -07:00
Aaron Klotz
d915e0054c cmd/tailscaled: change Windows service shutdown and add optional event logging
Once a stop request is received and the service updates its status to `svc.StopPending`,
it should continue running *until the shutdown sequence is complete*, and then
return out of `(*ipnService).Execute`, which automatically sends a `svc.Stopped`
notification to Windows.

To make this happen, I changed the loop so that it runs until `doneCh` is
closed, and then returns. I also removed a spurious `svc.StopPending` notification
that the Windows Service Control Manager might be interpreting as a request for
more time to shut down.

Finally, I added some optional logging that sends a record of service notifications
to the Windows event log, allowing us to more easily correlate with any Service
Control Manager errors that are sent to the same log.

Change-Id: I5b596122e5e89c4c655fe747a612a52cb4e8f1e0
Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2022-04-29 15:13:11 -07:00
Mihai Parparita
316523cc1e ipn: remove enforceDefaults option from PrefsFromBytes
The Mac client was using it, but it had the effect of the `RouteAll`
("Use Tailscale subnets") pref always being enabled at startup,
regardless of the persisted value.

enforceDefaults was added to handle cases from ~2 years ago where
we ended up with persisted `"RouteAll": false` values in the keychain,
but that should no longer be a concern. New users will get the default
of it being enabled via `NewPrefs`.

There will be a corresponding Mac client change to stop passing in
enforceDefaults.

For #3962

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-04-29 14:08:26 -07:00
Brad Fitzpatrick
87ba528ae0 client/tailscale: move/copy all package funcs to new LocalClient type
Remove all global variables, and clean up tsnet and cmd/tailscale's usage.

This is in prep for using this package for the web API too (it has the
best package name).

RELNOTE=tailscale.com/client/tailscale package refactored w/ LocalClient type

Change-Id: Iba9f162fff0c520a09d1d4bd8862f5c5acc9d7cd
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-29 13:57:52 -07:00
Brad Fitzpatrick
373176ea54 util/codegen: format generated code with goimports, not gofmt
goimports is a superset of gofmt that also groups imports.
(the goimports tool also adds/removes imports as needed, but that
part is disabled here)

Change-Id: Iacf0408dfd9497f4ed3da4fa50e165359ce38498
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-29 13:35:45 -07:00
Brad Fitzpatrick
6bed781259 all: gofmt all
Well, goimports actually (which adds the normal import grouping order we do)

Change-Id: I0ce1b1c03185f3741aad67c14a7ec91a838de389
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-29 13:06:04 -07:00
Brad Fitzpatrick
deb56f276e Revert "api: document preauthorized auth keys"
This reverts commit dd6472d4e8.

Reason: it appears I was just really really wrong or confused.

We added it to the old internal API used by the website instead,
not to the "v2" API.

Updates #2120
Updates #4571

Change-Id: I744a72b9193aafa7b526fd760add52148a377e83
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-29 08:47:18 -07:00
Mihai Parparita
cfe68d0a86 safesocket: log warning when running sandboxed Mac binary as root
It won't work, provide a clue in the error output.

Fixes #3063

Signed-off-by: Mihai Parparita <mihai@tailscale.com>
2022-04-28 16:22:19 -07:00
Brad Fitzpatrick
6f5b91c94c go.mod: tidy
Change-Id: If3b5fe42e7dd7858dcce02a3a24a5e59736815a2
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-28 14:32:43 -07:00
Brad Fitzpatrick
2336c73d4d go.mod: tidy
Change-Id: If3b5fe42e7dd7858dcce02a3a24a5e59736815a2
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-28 14:29:53 -07:00
James Tucker
96fec4b969 net/tshttpproxy: synology: pick proxy by scheme
This updates the fix from #4562 to pick the proxy based on the request
scheme.

Updates #4395, #2605, #4562
Signed-off-by: James Tucker <james@tailscale.com>
2022-04-28 11:56:37 -07:00
Maisem Ali
eff6a404a6 net/tshttpproxy: use http as the scheme for proxies
Currently we try to use `https://` when we see `https_host`, however
that doesn't work and results in errors like `Received error: fetch
control key: Get "https://controlplane.tailscale.com/key?v=32":
proxyconnect tcp: tls: first record does not look like a TLS handshake`

This indiciates that we are trying to do a HTTPS request to a HTTP
server. Googling suggests that the standard is to use `http` regardless
of `https` or `http` proxy

Updates #4395, #2605

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-04-28 10:45:33 -07:00
Walter Poupore
71d401cc4e api.md: remove descriptions from TOC (#4561) 2022-04-28 09:36:26 -07:00
Brad Fitzpatrick
1237000efe control/controlhttp: don't assume port 80 upgrade response will work
Just because we get an HTTP upgrade response over port 80, don't
assume we'll be able to do bi-di Noise over it. There might be a MITM
corp proxy or anti-virus/firewall interfering. Do a bit more work to
validate the connection before proceeding to give up on the TLS port
443 dial.

Updates #4557 (probably fixes)

Change-Id: I0e1bcc195af21ad3d360ffe79daead730dfd86f1
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-28 09:14:41 -07:00
Brad Fitzpatrick
488e63979e api.md: document new ACL validate mode
Updates tailscale/corp#4932

Change-Id: Ie176ee79595c3b56d3376f1d81a441f9272e6ed4
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-27 15:58:37 -07:00
Maisem Ali
5a1ef1bbb9 net/tsdial: add SystemDial as a wrapper on netns.Dial
The connections returned from SystemDial are automatically closed when
there is a major link change.

Also plumb through the dialer to the noise client so that connections
are auto-reset when moving from cellular to WiFi etc.

Updates #3363

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-04-27 12:02:36 -07:00
Brad Fitzpatrick
e38d3dfc76 control/controlhttp: start port 443 fallback sooner if 80's stuck
Fixes #4544

Change-Id: I39877e71915ad48c6668351c45cd8e33e2f5dbae
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-27 10:34:53 -07:00
Maisem Ali
637cc1b5fc ipn/ipnlocal/peerapi: add endpoint to list local interfaces
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-04-27 06:44:58 -07:00
James Tucker
1aa75b1c9e wgengine/netstack: always set TCP keepalive
Setting keepalive ensures that idle connections will eventually be
closed. In userspace mode, any application configured TCP keepalive is
effectively swallowed by the host kernel, and is not easy to detect.
Failure to close connections when a peer tailscaled goes offline or
restarts may result in an otherwise indefinite connection for any
protocol endpoint that does not initiate new traffic.

This patch does not take any new opinion on a sensible default for the
keepalive timers, though as noted in the TODO, doing so likely deserves
further consideration.

Update #4522

Signed-off-by: James Tucker <james@tailscale.com>
2022-04-26 19:29:08 -07:00
Brad Fitzpatrick
adcb7e59d2 control/controlclient: fix log print with always-empty key
In debugging #4541, I noticed this log print was always empty.
The value printed was always zero at this point.

Updates #4541

Change-Id: I0eef60c32717c293c1c853879446be65d9b2cef6
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-26 19:27:20 -07:00
Brad Fitzpatrick
c88506caa6 ipn/ipnlocal: add Wake-on-LAN function to peerapi
No CLI support yet. Just the curl'able version if you know the peerapi
port. (like via a TSMP ping)

Updates #306

Change-Id: I0662ba6530f7ab58d0ddb24e3664167fcd1c4bcf
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-26 15:20:59 -07:00
Brad Fitzpatrick
3f7cc3563f ipn: always treat login.tailscale.com as controlplane.tailscale.com
Like 888e50e1, but more aggressive.

Updates #4538 (likely fixes)
Updates #3488

Change-Id: I3924eee9110e47bdba926ce12954253bf2413040
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-26 15:16:32 -07:00
Brad Fitzpatrick
c6c752cf64 net/tshttpproxy: fix typo
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-26 08:14:50 -07:00
Brad Fitzpatrick
50eb8c5add cmd/tailscale: mostly fix 'tailscale ssh' on macOS (sandbox)
Still a little wonky, though. See the tcsetattr error and inability to
hit Ctrl-D, for instance:

    bradfitz@laptop ~ % tailscale.app ssh foo@bar
    tcsetattr: Operation not permitted
    # Authentication checked with Tailscale SSH.
    # Time since last authentication: 1h13m22s
    foo@bar:~$ ^D
    ^D
    ^D

Updates #4518
Updates #4529

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-26 07:40:42 -07:00
Brad Fitzpatrick
48e5f4ff88 cmd/tailscale/cli: add 'debug stat' subcommand
For debugging what's visible inside the macOS sandbox.

But could also be useful for giving users portable commands
during debugging without worrying about which OS they're on.

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-26 07:30:08 -07:00
Brad Fitzpatrick
21413392cf safesocket: fix CLI on standalone mac GUI build
Tested three macOS Tailscale daemons:

- App Store (Network Extension)
- Standalone (macsys)
- tailscaled

And two types of local IPC each:

- IPN
- HTTP

And two CLI modes:

- sandboxed (running the GUI binary as the CLI; normal way)
- open source CLI hitting GUI (with #4525)

Bonus: simplifies the code.

Fixes tailscale/corp#4559

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-25 21:47:00 -07:00
Brad Fitzpatrick
3601b43530 ipn: add IPCVersion override func
I've done this a handful of times in the past and again today.
Time to make it a supported thing for the future.

Used while debugging tailscale/corp#4559 (macsys CLI issues)

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-25 20:51:05 -07:00
James Tucker
928d1fddd2 cmd/tailscale: s/-authkey/-auth-key/ in help text
Signed-off-by: James Tucker <james@tailscale.com>
2022-04-25 17:30:50 -07:00
Tom DNetto
5fb8e01a8b net/dns/resolver: add metric for number of truncated dns packets
Updates #2067

This should help us determine if more robust control of edns parameters
+ implementing answer truncation is warranted, given its likely complexity.

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-04-25 13:05:28 -07:00
Maisem Ali
80ba161c40 wgengine/monitor: do not ignore changes to pdp_ip*
One current theory (among other things) on battery consumption is that
magicsock is resorting to using the IPv6 over LTE even on WiFi.
One thing that could explain this is that we do not get link change updates
for the LTE modem as we ignore them in this list.
This commit makes us not ignore changes to `pdp_ip` as a test.

Updates #3363

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-04-25 12:17:00 -07:00
Maisem Ali
1a19aed410 ipn/ipnlocal: do not initialize peer api listeners when shutting down
Updates tailscale/corp#4824

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-04-25 11:08:03 -07:00
Brad Fitzpatrick
e97209c6bf net/dns: add tailscaled-on-macOS DNS OSConfigurator
This populates DNS suffixes ("ts.net", etc) in /etc/resolver/* files
to point to 100.100.100.100 so MagicDNS works.

It also sets search domains.

Updates #4276

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-23 20:43:41 -07:00
Maisem Ali
bbca2c78cb tsnet: fix mem.Store check for normal nodes
There was a typo in the check it was doing `!ok` instead of `ok`, this
restructures it a bit to read better.

Fixes #4506

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-04-22 23:52:16 -07:00
Denton Gentry
d819bb3bb0 VERSION.txt: This is 1.25.0
Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-04-22 13:26:24 -07:00
Maisem Ali
2265587d38 wgengine/{,magicsock}: add metrics for rebinds and restuns
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-04-22 11:55:46 -07:00
Tom DNetto
78fededaa5 net/dns/resolver: support magic resolution of via-<siteid>.<ip4> domains
Updates #3616

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-04-22 09:21:35 -07:00
Brad Fitzpatrick
910ae68e0b util/mak: move tailssh's mapSet into a new package for reuse elsewhere
Change-Id: Idfe95db82275fd2be6ca88f245830731a0d5aecf
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-21 21:20:10 -07:00
James Tucker
c2eff20008 ssh/tailssh: avoid user ssh configuration in tests
Signed-off-by: James Tucker <james@tailscale.com>
2022-04-21 19:17:34 -07:00
James Tucker
700bd37730 tshttpproxy: support synology proxy configuration
Fixes #4395
Fixes #2605

Signed-off-by: James Tucker <james@tailscale.com>
2022-04-21 18:39:00 -07:00
Maisem Ali
90b5f6286c cmd/tailscale: use double quotes in the ssh subcommands
Single-quote escaping is insufficient apparently.

Updates #3802

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-04-21 17:43:04 -07:00
Maisem Ali
db70774685 cmd/tailscale/cli: do not use syscall.Exec from macOS sandbox
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-04-21 17:07:18 -07:00
Tom DNetto
37c94c07cd shell.nix: update go toolchain
Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-04-21 15:47:34 -07:00
David Anderson
a364bf2b62 ssh/tailssh: various typo fixes, clarifications.
Signed-off-by: David Anderson <danderson@tailscale.com>
2022-04-21 15:04:13 -07:00
Brad Fitzpatrick
c994eba763 ssh/tailssh: simplify matchRule with Reject rules
Updates #3802

Change-Id: I59fe111eef5ac8abbcbcec922e293712a65a4830
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-21 15:04:02 -07:00
Maisem Ali
31094d557b ssh/tailssh: chmod the auth socket to be only user accessible
Updates #3802

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-04-21 14:49:22 -07:00
Maisem Ali
337c77964b ssh/tailssh: set groups and gid in the incubated process
Updates #3802

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-04-21 14:48:34 -07:00
Brad Fitzpatrick
8ac4d52b59 ssh/tailssh: filter accepted environment variables
Noted by @danderson

Updates #3802

Change-Id: Iac70717ed57f11726209ac1ea93ddc6696605f94
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-21 14:44:46 -07:00
Brad Fitzpatrick
89832c1a95 tailcfg: fix typo in SessionDuration field name
Noted by @danderson.

Updates #3802

Change-Id: Ide15f3f28e30f6abb5c94d7dcd218bd9482752a0
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-21 14:19:58 -07:00
Maisem Ali
695f8a1d7e ssh/tailssh: add support for sftp
Updates #3802

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-04-21 10:52:22 -07:00
Brad Fitzpatrick
53588f632d Revert "wgengine/router,util/kmod: load & log xt_mark"
This reverts commit 8d6793fd70.

Reason: breaks Android build (cgo/pthreads addition)

We can try again next cycle.

Change-Id: I5e7e1730a8bf399a8acfce546a6d22e11fb835d5
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-21 09:53:23 -07:00
Tom DNetto
df26c63793 net/dns/resolver, net/tsaddr: fix reverse lookups in 4to6 IP range
Fixes #4439

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-04-21 09:37:21 -07:00
James Tucker
8d6793fd70 wgengine/router,util/kmod: load & log xt_mark
Attempt to load the xt_mark kernel module when it is not present. If the
load fails, log error information.

It may be tempting to promote this failure to an error once it has been
in use for some time, so as to avoid reaching an error with the iptables
invocation, however, there are conditions under which the two stages may
disagree - this change adds more useful breadcrumbs.

Example new output from tailscaled running under my WSL2:

```
router: ensure module xt_mark: "/usr/sbin/modprobe xt_mark" failed: exit status 1; modprobe: FATAL: Module xt_mark not found in directory /lib/modules/5.10.43.3-microsoft-standard-WSL2
```

Background:

There are two places to lookup modules, one is `/proc/modules` "old",
the other is `/sys/module/` "new".

There was query_modules(2) in linux <2.6, alas, it is gone.

In a docker container in the default configuration, you would get
/proc/modules and /sys/module/ both populated. lsmod may work file,
modprobe will fail with EPERM at `finit_module()` for an unpriviliged
container.

In a priviliged container the load may *succeed*, if some conditions are
met. This condition should be avoided, but the code landing in this
change does not attempt to avoid this scenario as it is both difficult
to detect, and has a very uncertain impact.

In an nspawn container `/proc/modules` is populated, but `/sys/module`
does not exist. Modern `lsmod` versions will fail to gather most module
information, without sysfs being populated with module information.

In WSL2 modules are likely missing, as the in-use kernel typically is
not provided by the distribution filesystem, and WSL does not mount in a
module filesystem of its own. Notably the WSL2 kernel supports iptables
marks without listing the xt_mark module in /sys/module, and
/proc/modules is empty.

On a recent kernel, we can ask the capabilities system about SYS_MODULE,
that will help to disambiguate between the non-privileged container case
and just being root. On older kernels these calls may fail.

Update #4329

Signed-off-by: James Tucker <james@tailscale.com>
2022-04-20 22:21:35 -07:00
Brad Fitzpatrick
f7cb6630e7 tailcfg: document SSHPrincipal.PubKeys URL expansions
From f74ee80abe which lacked docs.

Updates #3802

Change-Id: Ia7df05a486ae383cc6d9aca9dfe487b04e243ad5
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-20 20:12:37 -07:00
Brad Fitzpatrick
5b4154342e ssh/tailssh: fix double SSH-2.0- prefix in greeting banner
gliderlabs/ssh was already adding the "SSH-2.0-" prefix.

Updates #3802

Change-Id: I19a1cd9308371a2898e7883cf26e94c9b54bab29
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-20 20:08:39 -07:00
Brad Fitzpatrick
7a097ccc83 ipn/ipnlocal: close peerapi listeners on LocalBackend.Shutdown
For tests.

Now that we can always listen (whereas we used to fail prior to
a2c330c496), some goroutine leak
checks were failing in tests in another repo after that change.

Change-Id: Id95a4b71167eca61962a48616d79741b9991e0bc
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-20 19:25:42 -07:00
Maisem Ali
2b8b887d55 ssh/tailssh: send banner messages during auth, move more to conn
(VSCode Live Share between Brad & Maisem!)

Updates #3802

Change-Id: Id8edca4481b0811debfdf56d4ccb1a46f71dd6d3
Co-Authored-By: Brad Fitzpatrick <bradfitz@tailscale.com>
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-04-20 18:34:11 -07:00
Denton Gentry
13f75b9667 scripts/install: add Alma Linux.
Tested using an Alma Linux 8.5 VM.
Updates https://github.com/tailscale/tailscale/issues/2915

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-04-20 17:43:49 -07:00
Denton Gentry
c2b907c965 scripts/installer: support LinuxMint Debian.
The primary distribution for LinuxMint is based on Ubuntu,
but there is an alternate Debian-based distribution called
LMDE. Both variations identify themselves as "linuxmint"

We added UBUNTU_VERSION to the Ubuntu handling for linuxmint,
the only distribution so far found to do this. Instead, split
linuxmint out into its own case and use either UBUNTU_VERSION
or DEBIAN_VERSION, whichever is present.

Tested on an LMDE 5 (elsie) VM.

Updates https://github.com/tailscale/tailscale/issues/2915

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-04-20 17:43:49 -07:00
Denton Gentry
61868f281e scripts/installer: call emerge with --ask=n
Fixes https://github.com/tailscale/tailscale/issues/4354

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-04-20 17:43:49 -07:00
Denton Gentry
db7da6622a scripts/installer: add ParrotOS support
Support ParrotSec https://parrotsec.org/
Tested using a Parrot 5.0 VM.

Updates https://github.com/tailscale/tailscale/issues/2915

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-04-20 17:43:49 -07:00
Brad Fitzpatrick
d413850bd7 cmd/tailscale: add "debug via" subcommand to do CIDR math for via ranges
$ tailscale debug via 0xb 10.2.0.0/16
fd7a:115c:a1e0:b1a:0:b:a02:0/112
$ tailscale debug via fd7a:115c:a1e0:b1a:0:b:a02:0/112
site 11 (0xb), 10.2.0.0/16

Previously: 3ae701f0eb

This adds a little debug tool to do CIDR math to make converting between
those ranges easier for now.

Updates #3616

Change-Id: I98302e95d17765bfaced3ecbb71cbd43e84bff46
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-20 14:47:48 -07:00
Brad Fitzpatrick
f74ee80abe ssh/tailssh: support expansions in public key fetch URL too
Updates #3802

Change-Id: I5aa98bdab14fd1c1c00ba63b93f8d7e670f72437
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-20 14:04:50 -07:00
Maisem Ali
14d077fc3a ssh/tailssh: terminate ssh auth early if no policy can match
Also bump github.com/tailscale/golang-x-crypto/ssh

Updates #3802

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-04-20 13:44:04 -07:00
Brad Fitzpatrick
a2c330c496 ipn/ipnlocal: use the fake peerapi listener as fallback if netstack available
The previous commit (1b89662eff) this for Android, but we can also use
this on any platform if we we would otherwise fail.

Change-Id: I4cd78b40e9e77fca5cc8e717dd48ac173101bed4
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-20 13:41:44 -07:00
Maisem Ali
136f30fc92 wgengine/monitor: split the unexpected stringification log line
It unfortuantely gets truncated because it's too long, split it into 3
different log lines to circumvent truncation.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-04-20 12:32:15 -07:00
Maisem Ali
8e40bfc6ea wgengine/monitor: ignore OS-specific uninteresting interfaces
Currently we ignore these interfaces in the darwin osMon but then would consider it
interesting when checking if anything had changed.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-04-20 12:32:15 -07:00
Brad Fitzpatrick
1b89662eff ipn/ipnlocal: make peerapi listener on Android avoid the kernel
We intercept the peerapi port in netstack anyway, so there's no reason
the linux kernel on Android needs to know about it. It's only getting
in the way and causing problems for reasons we don't fully understand.
But we don't even need to understand it because it's not relevant
anymore.

Instead, provide a dummy net.Listener that just sits and blocks to
pacify the rest of the code that assumes it can be stuck in a
Listener.Accept call and call Listener.Close and Listener.Addr.

We'll likely do this for all platforms in the future, if/when we also
link in netstack on iOS.

Updates #4449
Updates #4293
Updates #3986

Change-Id: Ic2d3fe2f3cee60fc527356a3368830f17aeb75ae
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-20 12:31:12 -07:00
Brad Fitzpatrick
cf9b9a7fec tstest/iosdeps: add test for forbidden iOS dependencies
Fixes #4463

Change-Id: I8305710e8a075263ae9a88a29624b19032d5beeb
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-20 12:30:23 -07:00
Brad Fitzpatrick
8b81254992 ipn/ipnlocal: reject tailscale up --ssh if disabled on tailnet
Updates #3802

Change-Id: I3f1e839391fe9b28270f506f4bb8d8e3d36716f5
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-20 11:38:27 -07:00
Brad Fitzpatrick
0ce67ccda6 wgengine/router: make supportsV6NAT check catch more cases
Updates #4459

Change-Id: Ic27621569d2739298e652769d10e38608c6012be
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-20 10:28:33 -07:00
Xe Iaso
fc2f628d4c cmd/nginx-auth: maintainer scripts and tailnet checking (#4460)
* cmd/nginx-auth: add maintainer scripts

Signed-off-by: Xe <xe@tailscale.com>

* cmd/nginx-auth: add Expected-Tailnet header and documentation

Signed-off-by: Xe <xe@tailscale.com>
2022-04-20 13:06:05 -04:00
Blake Mizerany
33fa43252e cmd/proxy-to-grafana: prevent premature termination
This commit changes proxy-to-grafana to report errors while polling for
tailscaled status instead of terminating at the first sign of an error.
This allows tailscale some time to come up before the proxy decides to
give up.

Signed-off-by: Blake Mizerany <blake.mizerany@gmail.com>
2022-04-19 13:31:36 -07:00
Tom DNetto
c8f4dfc8c0 derp/derphttp,net/netcheck: improve netcheck behavior under MITM proxies
In cases where tailscale is operating behind a MITM proxy, we need to consider
that a lot more of the internals of our HTTP requests are visible and may be
used as part of authorization checks. As such, we need to 'behave' as closely
as possible to ideal.

 - Some proxies do authorization or consistency checks based the on Host header
   or HTTP URI, instead of just the IP/hostname/SNI. As such, we need to
   construct a `*http.Request` with a valid URI everytime HTTP is going to be
   used on the wire, even if its over TLS.
   Aside from the singular instance in net/netcheck, I couldn't find anywhere
   else a http.Request was constructed incorrectly.

 - Some proxies may deny requests, typically by returning a 403 status code. We
   should not consider these requests as a valid latency check, so netcheck
   semantics have been updated to consider >299 status codes as a failed probe.

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-04-19 12:47:57 -07:00
Brad Fitzpatrick
cc575fe4d6 net/dns: schedule DoH upgrade explicitly, fix Resolver.Addr confusion
Two changes in one:

* make DoH upgrades an explicitly scheduled send earlier, when we come
  up with the resolvers-and-delay send plan. Previously we were
  getting e.g.  four Google DNS IPs and then spreading them out in
  time (for back when we only did UDP) but then later we added DoH
  upgrading at the UDP packet layer, which resulted in sometimes
  multiple DoH queries to the same provider running (each doing happy
  eyeballs dialing to 4x IPs themselves) for each of the 4 source IPs.
  Instead, take those 4 Google/Cloudflare IPs and schedule 5 things:
  first the DoH query (which can use all 4 IPs), and then each of the
  4 IPs as UDP later.

* clean up the dnstype.Resolver.Addr confusion; half the code was
  using it as an IP string (as documented) as half was using it as
  an IP:port (from some prior type we used), primarily for tests.
  Instead, document it was being primarily an IP string but also
  accepting an IP:port for tests, then add an accessor method on it
  to get the IPPort and use that consistently everywhere.

Change-Id: Ifdd72b9e45433a5b9c029194d50db2b9f9217b53
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-19 12:00:22 -07:00
Brad Fitzpatrick
e3a4952527 net/dns/resolver: count errors when racing DNS queries, fail earlier
If all N queries failed, we waited until context timeout (in 5
seconds) to return.

This makes (*forwarder).forward fail fast when the network's
unavailable.

Change-Id: Ibbb3efea7ed34acd3f3b29b5fee00ba8c7492569
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-19 11:07:31 -07:00
Brad Fitzpatrick
d9efbd97cb net/dns: remove an unused function
Change-Id: I7c920c76223ffac37954ef2a18754afc52177598
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-19 10:53:54 -07:00
Brad Fitzpatrick
c13be0c509 tailcfg: clarify how SSHPolicy.Rules are evaluated between auth phases
Updates #3802

Change-Id: I321183a8a2b065a40dca8dd95ca90cd822a17ff8
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-18 22:03:52 -07:00
Maisem Ali
91a187bf87 ssh/tailssh: make checkStillValid also consider username changes
Currently if the policy changes and the session is logged in with local
user "u1" and the new policy says they can only login with "u2" now, the
user doesn't get kicked out because they had requested
`rando@<ssh-host>` and the defaulting had made that go to `u1`.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-04-18 16:34:06 -07:00
Maisem Ali
a04eebf59f ipn/ipnlocal: also use SSHPolicies when updating filterHash
Updates #3802

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-04-18 16:34:06 -07:00
Joe Tsai
d201d217df go.toolchain.rev: update to go1.18.1 (#4438)
Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-04-18 14:42:58 -07:00
Tom DNetto
24cd26534f hostinfo, tailcfg: add desktop detection on Linux to hostinfo
From the machines tab its hard to differenciate desktop Linux installs from
server Linux installs. Transmitting this information should make this
determination a lot easier.

Due to the reality that tailscaled is likely a system process, the standard
checks based on XDG_SESSION_TYPE or DISPLAY environment variables are not
possible (those variables won't be set). Instead, we look for listening
unix sockets that are typical of desktop installs.

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-04-18 14:22:15 -07:00
Brad Fitzpatrick
9f1dd716e8 tailcfg, logtail: provide Debug bit to disable logtail
For people running self-hosted control planes who want a global
opt-out knob instead of running their own logcatcher.

Change-Id: I7f996c09f45850ff77b58bfd5a535e197971725a
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-18 13:53:13 -07:00
Brad Fitzpatrick
ecea6cb994 net/dns/resolver: make DoH dialer use existing dnscache happy eyeball dialer
Simplify the ability to reason about the DoH dialing code by reusing the
dnscache's dialer we already have.

Also, reduce the scope of the "ip" variable we don't want to close over.

This necessarily adds a new field to dnscache.Resolver:
SingleHostStaticResult, for when the caller already knows the IPs to be
returned.

Change-Id: I9f2aef7926f649137a5a3e63eebad6a3fffa48c0
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-18 13:18:39 -07:00
Brad Fitzpatrick
e96dd00652 ipn/ipnlocal: add capability for debugging peers over peerapi
The default is still users can debug their own nodes. But like
cd916b728b did, this adds support for admins to grant additional
capabilities with the new tailcfg.CapabilityDebugPeer cap.

Updates #4217

Change-Id: Ifce3d9a1f8e8845797970a4f97b393194663d35f
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-18 10:21:42 -07:00
Maisem Ali
945879fa38 cmd/tailscale: [ssh] enable StrictHostKeyChecking mode
Updates #3802

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-04-18 10:11:36 -07:00
Brad Fitzpatrick
8f5e5bff1e cmd/tailscale, etc: make "tailscale up --ssh" fail fast when unavailable
Fail on unsupported platforms (must be Linux or macOS tailscaled with
WIP env) or when disabled by admin (with TS_DISABLE_SSH_SERVER=1)

Updates #3802

Change-Id: I5ba191ed0d8ba4ddabe9b8fc1c6a0ead8754b286
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-18 09:45:46 -07:00
Brad Fitzpatrick
f0e2272e04 cmd/tailscale: unhide 'up --ssh' behind WIP env var
Updates #3802

Change-Id: I99c550c2e4450640b0ee6ab060f178dde1360553
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-18 07:55:16 -07:00
Brad Fitzpatrick
93221b4535 ssh/tailssh: cache public keys fetched from URLs
Updates #3802

Change-Id: I96715bae02bce6ea19f16b1736d1bbcd7bcf3534
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-18 07:46:38 -07:00
Maisem Ali
3ffd88a84a wgengine/monitor: do not set timeJumped on iOS/Android
In `(*Mon).Start` we don't run a timer to update `(*Mon).lastWall` on iOS and
Android as their sleep patterns are bespoke. However, in the debounce
goroutine we would notice that the the wall clock hadn't been updated
since the last event would assume that a time jump had occurred. This would
result in non-events being considered as major-change events.

This commit makes it so that `(*Mon).timeJumped` is never set to `true`
on iOS and Android.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-04-17 23:46:17 -07:00
Brad Fitzpatrick
ade7bd8745 ssh/tailssh: close sessions on policy change if no longer allowed
Updates #3802

Change-Id: I98503c2505b77ac9d0cc792614fcdb691761a70c
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-17 15:29:44 -07:00
Brad Fitzpatrick
4ec83fbad6 ipn/ipnlocal: only call updateFilter with mutex held
And rename to updateFilterLocked to prevent future mistakes.

Fixes #4427

Change-Id: I4d37b90027d5ff872a339ce8180f5723704848dc
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-17 15:29:24 -07:00
Brad Fitzpatrick
cd916b728b ipn/ipnlocal: add start of inter-user Taildrop
Controlled by server-sent capability policy.

To be initially used for SSH servers to record sessions to other
nodes. Not yet productized into something user-accessible. (Notably,
the list of Taildrop targets from the sender side isn't augmented
yet.) This purely permits expanding the set of expands a node will
accept a drop from.

Updates #3802
Updates #4217

Change-Id: Id7a5bccd686490f8ef2cdc7dae7c07c440dc0085
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-17 10:07:07 -07:00
Brad Fitzpatrick
f4f76eb275 net/dnsfallback: update from 'go generate'
Change-Id: I93e0e6d9a4a471953c1ffef07f32605c5724aed8
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-17 10:06:09 -07:00
Brad Fitzpatrick
16f3520089 all: add arbitrary capability support
Updates #4217

RELNOTE=start of WhoIsResponse capability support

Change-Id: I6522998a911fe49e2f003077dad6164c017eed9b
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-17 09:01:53 -07:00
James Tucker
c591c91653 tailcfg, control/controlclient: TSMP & disco pings
tailcfg.PingResponse formalizes the TSMP & disco response message, and
controlclient is wired to send POST responses containing
tailcfg.PingResponse for TSMP and disco PingRequests.

Updates tailscale/corp#754

Signed-off-by: James Tucker <james@tailscale.com>
2022-04-15 22:36:51 -07:00
James Tucker
67192a2323 go.mod: bump u-root
We only use the termios subpackage, so we're unaffected by
CVE-2020-7665, but the bump will let dependabot return to slumber.

Fixes https://github.com/tailscale/tailscale/security/dependabot/2

Signed-off-by: James Tucker <james@tailscale.com>
2022-04-15 14:13:22 -07:00
Brad Fitzpatrick
8ee044ea4a ssh/tailssh: make the SSH server a singleton, register with LocalBackend
Remove the weird netstack -> tailssh dependency and instead have tailssh
register itself with ipnlocal when linked.

This makes tailssh.server a singleton, so we can have a global map of
all sessions.

Updates #3802

Change-Id: Iad5caec3a26a33011796878ab66b8e7b49339f29
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-15 13:45:39 -07:00
Brad Fitzpatrick
da14e024a8 tailcfg, ssh/tailssh: optionally support SSH public keys in wire policy
And clean up logging.

Updates #3802

Change-Id: I756dc2d579a16757537142283d791f1d0319f4f0
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-15 13:36:57 -07:00
Brad Fitzpatrick
df9ce972c7 tailcfg, ipn/ipnlocal: add debug flag to enable one-big-CGNAT/10 route
To experiment with avoiding Chrome ERR_NETWORK_CHANGED errors on route
changes.

Updates #3102

Change-Id: I339da14c684fdac45ac261566aa21bf2198672ff
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-14 14:47:42 -07:00
phirework
52d32c94d8 net/dns/publicdns: add missing call to sync.Once.Do (#4410)
Signed-off-by: Jenny Zhang <jz@tailscale.com>
2022-04-14 17:45:58 -04:00
phirework
83c734a6e0 net/dns, util/publicdns: extract public DNS mapping into own package (#4405)
This extracts DOH mapping of known public DNS providers in
forwarder.go into its own package, to be consumed by other repos

Signed-off-by: Jenny Zhang <jz@tailscale.com>
2022-04-14 17:15:54 -04:00
James Tucker
8de7f9bff7 tailscaled: no longer tune gcpercent
Usage of userspace-networking is increasing, and the aggressive GC
tuning causes a significant reduction in performance in that mode.

Signed-off-by: James Tucker <james@tailscale.com>
2022-04-14 11:41:45 -07:00
Xe Iaso
4f1d6c53cb cmd/nginx-auth: create new Tailscale NGINX auth service (#4400)
This conforms to the NGINX subrequest result authentication protocol[1]
using the NGINX module `ngx_http_auth_request_module`. This is based on
the example that @peterkeen provided on Twitter[2], but with several
changes to make things more tightly locked down:

* This listens over a UNIX socket instead of a TCP socket to prevent
  leakage to the network
* This uses systemd socket activation so that systemd owns the socket
  and can then lock down the service to the bare minimum required to do
  its job without having to worry about dropping permissions
* This provides additional information in HTTP response headers that can
  be useful for integrating with various services
* This has a script to automagically create debian and redhat packages
  for easier distribution

This will be written about on the Tailscale blog. There is more
information in README.md.

[1]: https://docs.nginx.com/nginx/admin-guide/security-controls/configuring-subrequest-authentication/
[2]: https://github.com/peterkeen/tailscale/blob/main/cmd/nginx-auth-proxy/nginx-auth-proxy.go

Signed-off-by: Xe Iaso <xe@tailscale.com>
2022-04-14 11:55:35 -04:00
Maisem Ali
50b4b8b2c6 ipn/ipnlocal: make peerIPs return a sorted slice
Currently peerIPs doesn't do any sorting of the routes it returns. This
is typically fine, however imagine the case of an HA subnet router
failover. When a route R moves from peer A to peer B, the output of
peerIPs changes. This in turn causes all the deephash check inside
wgengine to fail as the hashed value of [R1, R2] is different than
the hashed value of [R2, R1]. When the hash check failes, it causes
wgengine to reconfigure all routes in the OS. This is especially
problematic for macOS and iOS where we use the NetworkExtension.

This commit makes it that the peerIPs are always sorted when returned,
thus making the hash be consistent as long as the list of routes remains
static.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-04-13 16:30:17 -07:00
Brad Fitzpatrick
a49d8d5200 Revert ".github/workflows: work around golang/go#51629"
This reverts commit 2a412ac9ee.

Updates #4194

Change-Id: I0098b66b71d20bea301ca79058c1cdd201237dd0
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-13 14:27:01 -07:00
Brad Fitzpatrick
09c5c9eb83 go.mod: bump x/tools for go/packages generics fix
Updates #4194

Change-Id: Ia992ffb14210d5ad53f8f98d12b80d64080998e6
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-13 14:27:01 -07:00
Tom DNetto
dec68166e4 tstest/integration/vms: smoke test derphttp through mitm proxies
Updates #4377

Very smoky/high-level test to ensure that derphttp internals play well
with an agressive (stare + bump) meddler-in-the-middle proxy.

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-04-12 13:24:29 -07:00
Ilya Mateyko
2748750aa2 ipn/ipnstate: make status page more mobile-friendly
Signed-off-by: Ilya Mateyko <me@astrophena.name>
2022-04-12 12:33:31 -07:00
Maisem Ali
c87ed52ad4 cmd/tailscale: add id-token subcommand
RELNOTE=Initial support for getting OIDC ID Tokens

Updates tailscale/corp#4347

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-04-12 12:04:04 -07:00
Brad Fitzpatrick
3ae701f0eb net/tsaddr, wgengine/netstack: add IPv6 range that forwards to site-relative IPv4
This defines a new magic IPv6 prefix, fd7a:115c:a1e0:b1a::/64, a
subset of our existing /48, where the final 32 bits are an IPv4
address, and the middle 32 bits are a user-chosen "site ID". (which
must currently be 0000:00xx; the top 3 bytes must be zero for now)

e.g., I can say my home LAN's "site ID" is "0000:00bb" and then
advertise its 10.2.0.0/16 IPv4 range via IPv6, like:

    tailscale up --advertise-routes=fd7a:115c:a1e0:b1a::bb:10.2.0.0/112

(112 being /128 minuse the /96 v6 prefix length)

Then people in my tailnet can:

     $ curl '[fd7a:115c:a1e0:b1a::bb:10.2.0.230]'
     <!DOCTYPE html PUBLIC "-//W3C//DTD XHTML 1.0 Transitional//EN" ....

Updates #3616, etc

RELNOTE=initial support for TS IPv6 addresses to route v4 "via" specific nodes

Change-Id: I9b49b6ad10410a24b5866b9fbc69d3cae1f600ef
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-04-11 17:26:07 -07:00
David Eger
f992749b98 cmd/tailscale: Add file get --loop flag.
To "automatically receive taildrop files to my Downloads directory,"
user currently has to run 'tailscale file get' in a loop.  Make
it easy to do this without shell.

Updates: #2312

Signed-off-by: David Eger <david.eger@gmail.com>
2022-04-11 17:23:08 -07:00
James Tucker
f4aad61e67 wgengine/monitor: ignore duplicate RTM_NEWADDRs
Ignoring the events at this layer is the simpler path for right now, a
broader change should follow to suppress irrelevant change events in a
higher layer so as to avoid related problems with other monitoring paths
on other platforms.  This approach may also carry a small risk that it
applies an at-most-once invariant low in the chain that could be assumed
otherwise higher in the code.

I adjusted the newAddrMessage type to include interface index rather
than a label, as labels are not always supplied, and in particular on my
test hosts they were consistently missing for ipv6 address messages.

I adjusted the newAddrMessage.Addr field to be populated from
Attributes.Address rather than Attributes.Local, as again for ipv6
.Local was always empty, and with ipv4 the .Address and .Local contained
the same contents in each of my test environments.

Update #4282

Signed-off-by: James Tucker <james@tailscale.com>
2022-04-11 14:35:19 -07:00
James Tucker
2f69c383a5 wgengine/monitor: add envknob TS_DEBUG_NETLINK
While I trust the test behavior, I also want to assert the behavior in a
reproduction environment, this envknob gives me the log information I
need to do so.

Update #4282

Signed-off-by: James Tucker <james@tailscale.com>
2022-04-11 14:35:19 -07:00
Tom DNetto
8f6d8cf979 tstest/integration/vms: test on stable nixos (21.11)
I would like to do some more customized integration tests in the future,
(specifically, bringing up a mitm proxy and testing tailscaled through that)
so hoping to bring back the nixos wiring to support that.

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-04-11 12:54:56 -07:00
James Tucker
8226f1482c go.mod: bump rtnetlink for address label encoding (#4386)
This will enable me to land tests for the upcoming monitor change in
PR #4385.

Update #4385
Update #4282

Signed-off-by: James Tucker <james@tailscale.com>
2022-04-08 14:17:53 -07:00
Tom DNetto
f923ce6f87 shell.nix: use tailscale-go for compilation
This change builds a derivation for tailscale-go and makes it available in the
users development environment. This is consistent with the shell.nix in corp/.

Once go1.18 is in a stable Nixpkgs release we can avoid relying on derivations
from nixpkgs head. For now, this works well, and the fetched derivations are
cached in the Nix store according to the usual rules.

Fixes #4231

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-04-08 14:10:50 -07:00
Tom
24bdcbe5c7 net/dns, net/dns/resolver, wgengine: refactor DNS request path (#4364)
* net/dns, net/dns/resolver, wgengine: refactor DNS request path

Previously, method calls into the DNS manager/resolver types handled DNS
requests rather than DNS packets. This is fine for UDP as one packet
corresponds to one request or response, however will not suit an
implementation that supports DNS over TCP.

To support PRs implementing this in the future, wgengine delegates
all handling/construction of packets to the magic DNS endpoint, to
the DNS types themselves. Handling IP packets at this level enables
future support for both UDP and TCP.

Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-04-08 12:17:31 -07:00
Tom DNetto
3b3d1b9350 tstest/integration/vms: consistently use two dashes for command-line switches
Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-04-08 09:54:22 -07:00
Xiaochao Dong (@damnever)
7d97800d52 cmd/tailscale: make web mode preserve URL scheme in Synology redirect
Signed-off-by: Xiaochao Dong (@damnever) <the.xcdong@gmail.com>
2022-04-08 06:18:13 -07:00
James Tucker
2550acfd9d go.mod: bump netstack for clone reset fix (#4379)
In tracking down issue #4144 and reading through the netstack code in
detail, I discovered that the packet buf Clone path did not reset the
packetbuf it was getting from the sync.Pool. The fix was sent upstream
https://github.com/google/gvisor/pull/7385, and this bump pulls that in.
At this time there is no known path that this fixes, however at the time
of upstream submission this reset at least one field that could lead to
incorrect packet routing if exercised, a situation that could therefore
lead to an information leak.

Signed-off-by: James Tucker <james@tailscale.com>
2022-04-07 19:03:18 -07:00
David Anderson
f570372b4d control/controlbase: don't enforce a max protocol version at handshake time.
Doing so makes development unpleasant, because we have to first break the
client by bumping to a version the control server rejects, then upgrade
the control server to make it accept the new version.

This strict rejection at handshake time is only necessary if we want to
blocklist some vulnerable protocol versions in the future. So, switch
to a default-permissive stance: until we have such a version that we
have to eagerly block early, we'll accept whatever version the client
presents, and leave it to the user of controlbase.Conn to make decisions
based on that version.

Noise still enforces that the client and server *agree* on what protocol
version is being used, and the control server still has the option to
finish the handshake and then hang up with an in-noise error, rather
than abort at the handshake level.

Updates #3488

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-04-07 17:55:29 -07:00
James Tucker
c6ac29bcc4 wgengine/netstack: disable refsvfs2 leak tracking (#4378)
In addition an envknob (TS_DEBUG_NETSTACK_LEAK_MODE) now provides access
to set leak tracking to more useful values.

Fixes #4309

Signed-off-by: James Tucker <james@tailscale.com>
2022-04-07 17:21:45 -07:00
Tom DNetto
858ab80172 tstest/integration/vms: fix docs, qemu-img invocation
Signed-off-by: Tom DNetto <tom@tailscale.com>
2022-04-07 15:40:14 -07:00
Xe Iaso
55161b3d92 cmd/mkpkg: use package flag (#4373)
Also removes getopt

Signed-off-by: Xe <xe@tailscale.com>
2022-04-07 16:38:33 -04:00
David Anderson
02ad987e24 control/controlbase: make the protocol version number selectable.
This is so that we can plumb our client capability version through
the protocol as the Noise version. The capability version increments
more frequently than strictly required (the Noise version only needs
to change when cryptographically-significant changes are made to
the protocol, whereas the capability version also indicates changes
in non-cryptographically-significant parts of the protocol), but this
gives us a safe pre-auth way to determine if the client supports
future protocol features, while still relying on Noise's strong
assurance that the client and server have agreed on the same version.

Currently, the server executes the same protocol regardless of the
version number, and just presents the version to the caller so they
can do capability-based things in the upper RPC protocol. In future,
we may add a ratchet to disallow obsolete protocols, or vary the
Noise handshake behavior based on requested version.

Updates #3488

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-04-07 13:25:28 -07:00
Xe Iaso
be861797b4 cmd/mkpkg: add name argument (#4372)
* shell.nix: rename goimports to gotools

Signed-off-by: Xe <xe@tailscale.com>

* cmd/mkpkg: allow specifying description and name in flag args

Signed-off-by: Xe <xe@tailscale.com>
2022-04-07 16:05:04 -04:00
Ramya Nagarajan
e014b4d970 api: update acl/validate data format (#4366)
Expected input is JSON formatted []policy.ACLTest

Signed-off-by: Ramya Nagarajan <ramya@tailscale.com>
2022-04-07 10:33:52 -07:00
Matt Layher
c79c72c4fc go.mod: github.com/mdlayher/sdnotify@v1.0.0
Signed-off-by: Matt Layher <mdlayher@gmail.com>
2022-04-06 19:25:50 -07:00
Tom
6be7931eb4 net/dns/resolver: return symbolic PTR records for TS service IPs (#4361)
Fixes #1233

Signed-off-by: Tom DNetto <tom@tailscale.com>

Co-authored-by: Tom DNetto <tom@tailscale.com>
2022-04-06 15:56:21 -07:00
oliverpool
0b273e1857 cmd/tailscale: drop special exit code 125 for gokrazy
No needed since gokrazy doesn't restart successful processes anymore: https://github.com/gokrazy/gokrazy/pull/127

Signed-off-by: Olivier Charvin <git@olivier.pfad.fr>
2022-04-06 06:21:44 -07:00
Maisem Ali
3603a18710 ipn/localapi: add endpoint to request id token
Updates tailscale/corp#4347

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-04-05 14:48:45 -07:00
Maisem Ali
035e8ab00e tailcfg: add Token{Request,Response} types
Updates tailscale/corp#4347

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-04-05 14:48:45 -07:00
Joe Tsai
01adcfa688 tailcfg: add omitempty to all fields of Hostinfo (#4360)
This reduces the noise when marshaling only a subset of this type.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-04-05 13:25:14 -07:00
Maisem Ali
ac2033d98c go.mod: bump staticcheck (#4359)
Updates #4194

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-04-05 12:24:33 -07:00
Maisem Ali
9f604f2bd3 derp: add (*Server).IsClientConnectedForTest func. (#4331)
This allows tests to verfiy that a DERP connection was actually
established.

Related to #4326
Updates tailscale/corp#2579

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-03-30 10:50:50 -07:00
Brad Fitzpatrick
3d180c0376 go.mod, ssh/tailssh, tempfork/gliderlabs: bump x/crypto/ssh fork for NoClientAuthCallback
Prep for evaluating SSHPolicy earlier to decide whether certs are
required, which requires knowing the target SSH user.

Updates #3802

Change-Id: I2753ec8069e7f19c9121300d0fb0813c1c627c36
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-29 18:17:34 -07:00
Maisem Ali
f4686a76a1 envknob: use the correct key when logging (#4319) 2022-03-29 14:04:12 -07:00
Maisem Ali
309ddef852 net/netutil: add CheckIPForwardingLinux (#4301)
Combine the code between `LocalBackend.CheckIPForwarding` and
`controlclient.ipForwardingBroken`.

Fixes #4300

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-03-28 10:24:11 -07:00
David Anderson
7c7f37342f prober: used keyed initializer for LimitedReader.
Reported by go vet.

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-03-26 21:45:27 -07:00
Maisem Ali
909f40da84 util/groupmember: remove redundant code (#4298)
Now that we have 30faf968b1
this is no longer needed.

Fixes #3001

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-03-26 21:45:06 -07:00
Brad Fitzpatrick
e4d8d5e78b net/packet, wgengine/netstack: remove workaround for old gvisor ECN bug
Fixes #2642

Change-Id: Ic02251d24a4109679645d1c8336e0f961d0cce13
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-26 21:24:24 -07:00
Brad Fitzpatrick
5a44f9f5b5 tempfork: temporarily fork gliderlabs/ssh and x/crypto/ssh
While we rearrange/upstream things.

gliderlabs/ssh is forked into tempfork from our prior fork
at be8b7add40

x/crypto/ssh OTOH is forked at
https://github.com/tailscale/golang-x-crypto because it was gnarlier
to vendor with various internal packages, etc.
Its git history shows where it starts (2c7772ba30643b7a2026cbea938420dce7c6384d).

Updates #3802

Change-Id: I546e5cdf831cfc030a6c42557c0ad2c58766c65f
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-26 21:07:01 -07:00
Maisem Ali
6fecc16c3b ipn/ipnlocal: do not process old status messages received out of order
When `setWgengineStatus` is invoked concurrently from multiple
goroutines, it is possible that the call invoked with a newer status is
processed before a call with an older status. e.g. a status that has
endpoints might be followed by a status without endpoints. This causes
unnecessary work in the engine and can result in packet loss.

This patch adds an `AsOf time.Time` field to the status to specifiy when the
status was calculated, which later allows `setWgengineStatus` to ignore
any status messages it receives that are older than the one it has
already processed.

Updates tailscale/corp#2579

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-03-26 20:23:50 -07:00
Brad Fitzpatrick
753f1bfad4 cmd/tailscale: write fewer known_hosts, resolve ssh host to FQDN early
Updates #3802

Change-Id: Ic44fa2e6661a9c046e725c04fa6b8213d3d4d2b2
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-25 15:17:27 -07:00
Brad Fitzpatrick
df93158aac cmd/tailscale: generate known_hosts file for 'tailscale ssh'
Updates #3802

Change-Id: I7a0052392f000ee44fc8e719f6666756aab91f3d
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-25 14:10:48 -07:00
Brad Fitzpatrick
cceacda5eb ipn/ipnstate: put SSH Host Keys in ipnstate.PeerStatus
Updates #3802

Change-Id: I47ba3b4545b25988f375bd867aecd98bb0da8d79
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-25 12:14:39 -07:00
Maisem Ali
42ee4c917d go.toolchain.rev: pick up httptest race fix
tailscale/go@5ce3ec4d89

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-03-25 09:53:10 -07:00
Brad Fitzpatrick
a0e345dba4 tsnet: set Hostinfo.Package to "tsnet" on use
Fixes #4256

Change-Id: I11276596c3724bead1e0aa1f2e57ba75cef3b6be
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-25 09:26:02 -07:00
Maisem Ali
b2f269d5b7 net/dnsfallback: do not attempt lookups of IPs.
Currently if the passed in host is an IP, Lookup still attempts to
resolve it with a dns server. This makes it just return the IP directly.

Updates tailscale/corp#4475

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-03-24 22:43:01 -07:00
Maisem Ali
b45bb577a0 net/dnscache: do not call LookupIPFallback if the context was canceled.
When the context is canceled, dc.dialOne returns an error from line 345.
This causes the defer on line 312 to try to resolve the host again, which
triggers a dns lookup of "127.0.0.1" from derp.

Updates tailscale/corp#4475

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-03-24 22:43:01 -07:00
Brad Fitzpatrick
8294915780 cmd/tailscale/cli: add start of 'ssh' subcommand
Updates #3802

Change-Id: Iabc07c00c7e4f43944cfe7daec8d2b66ac002289
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-24 21:43:42 -07:00
Brad Fitzpatrick
06fcf3b225 cmd/tailscale: make status --peers=false work earlier + in JSON mode
And return an error if you use non-flag arguments.

Change-Id: I0dd6c357eb5cabd0f17020f21ba86406aea21681
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-24 14:02:22 -07:00
Brad Fitzpatrick
5df12b9059 client/tailscale, cmd/tailscale, localapi: add 'tailscale nc' (actually)
Adds missing file from fc12cbfcd3.

GitHub was having issues earlier and it was all green because the
checks never actually ran, but the DCO non-Actions check at least did,
so "green" and I merged, not realizing it hadn't really run anything.

Updates #3802

Change-Id: I29f605eebe5336f1f3ca28ebb78b092dd99d9fd8
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-24 11:36:34 -07:00
Brad Fitzpatrick
fc12cbfcd3 client/tailscale, cmd/tailscale, localapi: add 'tailscale nc'
This adds a "tailscale nc" command that acts a bit like "nc", but
dials out via tailscaled via localapi.

This is a step towards a "tailscale ssh", as we'll use "tailscale nc"
as a ProxyCommand for in some cases (notably in userspace mode).

But this is also just useful for debugging & scripting.

Updates #3802

RELNOTE=tailscale nc

Change-Id: Ia5c37af2d51dd0259d5833d80264d3ad5f68446a
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-24 10:28:53 -07:00
Brad Fitzpatrick
b647977b33 net/netutil: move some net utils from control/controlhttp to netutil
In prep for reuse elsewhere.

Change-Id: I1b804edf76ac66b9108e6f434e77eab7a7472d69
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-24 09:56:10 -07:00
Brad Fitzpatrick
d2f3ec8a63 envknob, ipn/ipnlocal: add SSH admin kill switch
Updates #3802

Change-Id: I6127907446d1a6be1b097d9ba3b534f2b8eb707f
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-23 15:40:30 -07:00
Josh Bleecher Snyder
77b4fe0afa all: remove "no 1.18 support" failures
We have worked around the issue in DERP,
so the vanilla Go 1.18 toolchain now works.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-03-23 13:04:48 -07:00
Brad Fitzpatrick
98984c1a9a cmd/proxy-to-grafana: fix package doc code snippet
Markdown isn't supported.

Change-Id: I8d9bb92260c164dc277afbce624f64fc2faf5125
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-23 12:43:41 -07:00
Nick O'Neill
5fa502b5dc cmd/proxy-to-grafana: use grafana's authproxy to log in tailnet users (#4208)
Signed-off-by: Nick O'Neill <nick@tailscale.com>
2022-03-23 11:33:53 -07:00
Brad Fitzpatrick
4fc38888d2 go.mod: bump x/crypto for SSH change
(for golang/go#51808)

Updates #3802

Change-Id: Ifbd483c0144b4c86da69143b23b2a06da7672c92
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-23 10:22:16 -07:00
Brad Fitzpatrick
8144c6d87d tsnet: fail with nice message with go1.18 on darwin
Like we did in ead16b24ec for tailscaled.

Updates #4258
Due to golang/go#51759

Change-Id: I6effcea7c5f2ec264b9711f4c316f8fca09490f1
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-22 20:43:09 -07:00
Brad Fitzpatrick
0861923c21 ssh/tailssh, tailcfg: add more HoldAndDelegate expansions, document
Updates #3802

Change-Id: I447f06b49e2a917bffe36881d0634c9195085512
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-22 17:56:45 -07:00
dependabot[bot]
a121b9f263 .github: Bump actions/checkout from 2 to 3
Bumps [actions/checkout](https://github.com/actions/checkout) from 2 to 3.
- [Release notes](https://github.com/actions/checkout/releases)
- [Changelog](https://github.com/actions/checkout/blob/main/CHANGELOG.md)
- [Commits](https://github.com/actions/checkout/compare/v2...v3)

---
updated-dependencies:
- dependency-name: actions/checkout
  dependency-type: direct:production
  update-type: version-update:semver-major
...

Signed-off-by: dependabot[bot] <support@github.com>
2022-03-22 16:07:00 -07:00
Brad Fitzpatrick
091ea4a4a5 ssh/tailssh: support placeholders in SSHAction.HoldAndDelegate URL
Updates #3802

Change-Id: I60f9827409d14fd4f4824d102ba11db49bf0d365
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-22 16:02:40 -07:00
dependabot[bot]
257d75beb1 .github: Bump actions/setup-go from 2.1.5 to 3
Bumps [actions/setup-go](https://github.com/actions/setup-go) from 2.1.5 to 3.
- [Release notes](https://github.com/actions/setup-go/releases)
- [Commits](https://github.com/actions/setup-go/compare/v2.1.5...v3)

---
updated-dependencies:
- dependency-name: actions/setup-go
  dependency-type: direct:production
  update-type: version-update:semver-major
...

Signed-off-by: dependabot[bot] <support@github.com>
2022-03-22 15:58:46 -07:00
dependabot[bot]
f2b0faf91e .github: Bump actions/upload-artifact from 2.3.1 to 3
Bumps [actions/upload-artifact](https://github.com/actions/upload-artifact) from 2.3.1 to 3.
- [Release notes](https://github.com/actions/upload-artifact/releases)
- [Commits](https://github.com/actions/upload-artifact/compare/v2.3.1...v3)

---
updated-dependencies:
- dependency-name: actions/upload-artifact
  dependency-type: direct:production
  update-type: version-update:semver-major
...

Signed-off-by: dependabot[bot] <support@github.com>
2022-03-22 15:57:32 -07:00
dependabot[bot]
7fbb6a76ad .github: Bump actions/cache from 2 to 3
Bumps [actions/cache](https://github.com/actions/cache) from 2 to 3.
- [Release notes](https://github.com/actions/cache/releases)
- [Commits](https://github.com/actions/cache/compare/v2...v3)

---
updated-dependencies:
- dependency-name: actions/cache
  dependency-type: direct:production
  update-type: version-update:semver-major
...

Signed-off-by: dependabot[bot] <support@github.com>
2022-03-22 15:55:50 -07:00
Dave Anderson
0968b2d55a prober: support adding key/value labels to probes. (#4250)
prober: add labels to Probe instances.

This allows especially dynamically-registered probes to have a bunch
more dimensions along which they can be sliced in Prometheus.

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-03-22 13:45:11 -07:00
Brad Fitzpatrick
f3b13604b3 control/controlclient, ipn/ipnlocal, tailcfg: add MapResponse.PopBrowserURL
Updates #3802

Change-Id: I89481fc5782a0cc8084354706f8f28d94f197325
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-22 09:37:00 -07:00
Brad Fitzpatrick
3ea6ddbb5f control/controlbase: use less memory when idle (remove rxState.buf)
Uses 4KB less per Conn.

Fixes #4113

Change-Id: I38d25b1cf5ecf45423404a330b7ecab79a9fb176
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-21 17:47:50 -07:00
James Tucker
445c04c938 wgengine: inject packetbuffers rather than bytes (#4220)
Plumb the outbound injection path to allow passing netstack
PacketBuffers down to the tun Read, where they are decref'd to enable
buffer re-use. This removes one packet alloc & copy, and reduces GC
pressure by pooling outbound injected packets.

Fixes #2741
Signed-off-by: James Tucker <james@tailscale.com>
2022-03-21 14:58:43 -07:00
David Anderson
a09c30aac2 prober: refactor probe state into a Probe struct.
Signed-off-by: David Anderson <danderson@tailscale.com>
2022-03-21 13:45:08 -07:00
David Anderson
94aaec5c66 prober: rename Probe to ProbeFunc.
Making way for a future Probe struct to encapsulate per-probe state.

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-03-21 13:45:08 -07:00
David Anderson
7b4960316b tsweb: add PrometheusVar, for vars that want to output varz themselves.
This enables the infrequent use of more complex Prometheus types, such as
timeseries with high/irregular label cardinality, without needing to
discover and implement generic abstracted type like LabelMap for each one.

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-03-21 12:33:18 -07:00
Brad Fitzpatrick
f6642e0ece Makefile: add tidy target
Change-Id: I6cd3a6837f9ddfd283f57378465dcefa4d0ada47
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-21 11:06:13 -07:00
James Tucker
73314009d0 go.mod: bump netstack (#4222)
Primarily this is for f375784d83852b1e3ff20cc9de0648b3c0cf8525 and the
related commits that provide buffer pooling for the endpoint code paths
we use.

Signed-off-by: James Tucker <james@tailscale.com>
2022-03-21 11:01:40 -07:00
Brad Fitzpatrick
f7e976db55 tailcfg, ssh/tailssh: make SSHUser value '=' map ssh-user to same local-user
Updates #3802

Change-Id: Icde60d4150ca15c25d615a4effb3d3c236f020a8
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-21 10:49:37 -07:00
Brad Fitzpatrick
21445b56a5 control/controlbase: use less memory when idle (remove txState.buf)
Uses 4KB less per Conn.

Updates #4113

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-20 16:35:43 -07:00
Brad Fitzpatrick
bfb4a4d9e9 tsnet: fix format string/argument mismatch in log output
Change-Id: Ia7291ea47a289baec6cc6013d63d2f248ae57d9e
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-19 20:24:33 -07:00
David Anderson
19f61607b6 prober: run all probes once on initial registration.
Turns out, it's annoying to have to wait the entire interval
before getting any monitorable data, especially for very long
interval probes like hourly/daily checks.

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-03-19 18:54:33 -07:00
David Anderson
e41a3b983c prober: library to build healthchecking probers.
Signed-off-by: David Anderson <danderson@tailscale.com>
2022-03-19 18:38:32 -07:00
Brad Fitzpatrick
f2041c9088 all: use strings.Cut even more
Change-Id: I943ce72c6f339589235bddbe10d07799c4e37979
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-19 13:02:38 -07:00
Brad Fitzpatrick
f30473211b ssh/tailssh: start of implementing optional session recording
To asciinema cast format.

Updates #3802

Change-Id: Ifd3ea31922cd2c99068369cb1650e21f2545b0e1
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-19 12:59:51 -07:00
Josh Bleecher Snyder
32fd42430b all: use cibuild.On
Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-03-18 15:19:26 -07:00
Maisem Ali
b775df0b57 ssh/tailssh_test: skip TestSSH/stdin in CI
Updates #4051

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-03-18 10:57:12 -07:00
Maisem Ali
309c0a13a5 tsweb: add FQDN to Port80Handler to allow HTTPS redirects
When the request comes in say over http://mon, the current
implementation would rewrite it https://mon which causes the cert
validation to fail. This PR keeps the existing behavior intact but also
allows passing in a FQDN to the handler to reroute to the correct
hostname.

Related to https://github.com/tailscale/tailscale/pull/4208#pullrequestreview-913832340

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-03-18 10:16:08 -07:00
Maisem Ali
7f3d0992aa Makefile: use ./tool/go everywhere
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-03-18 10:13:18 -07:00
Aaron Klotz
6e91f872af net/tshttpproxy: ensure we pass the correct flags to WinHttpOpen on Win7 and Win8.0
The best flag to use on Win7 and Win8.0 is deprecated in Win8.1, so we resolve
the flag depending on OS version info.

Fixes https://github.com/tailscale/tailscale/issues/4201

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2022-03-18 11:05:02 -06:00
Brad Fitzpatrick
1db46919ab cmd/tailscaled: make build fail nicely on older Go versions
Due to a bug in Go (golang/go#51778), cmd/go doesn't warn about your
Go version being older than the go.mod's declared Go version in that
case that package loading fails before the build starts, such as when
you use packages that are only in the current version of Go, like our
use of net/netip.

This change works around that Go bug by adding build tags and a
pre-Go1.18-only file that will cause Go 1.17 and earlier to fail like:

    $ ~/sdk/go1.17/bin/go install ./cmd/tailscaled
    # tailscale.com/cmd/tailscaled
    ./required_version.go:11:2: undefined: you_need_Go_1_18_to_compile_Tailscale
    note: module requires Go 1.18

Change-Id: I39f5820de646703e19dde448dd86a7022252f75c
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-18 08:25:51 -07:00
David Anderson
2a412ac9ee .github/workflows: work around golang/go#51629
Incidentally, simplify the go generate CI workflow, by
marking the dnsfallback update non-hermetic (so CI will
skip it) rather than manually filter it out of `go list`.

Updates #4194

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-03-17 17:22:17 -07:00
Brad Fitzpatrick
18818763d1 derp: set Basic Constraints on metacert
See https://github.com/golang/go/issues/51759#issuecomment-1071147836

Once we deploy this, tailscaled should work again for macOS users with
Go 1.18.

Updates golang/go#51759

Change-Id: I869b6ddc556a2de885e96ccf9f335dfc8f6f6a7e
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-17 15:38:21 -07:00
Simon Deziel
eaf5591953 scripts: install gnupg only when apt-key is needed
apt-key depends on gnupg but apt-key itself if not used
on modern systems (APT_KEY_TYPE=keyring).

Signed-off-by: Simon Deziel <simon@sdeziel.info>
2022-03-17 15:11:25 -07:00
Maisem Ali
bd073b8dd6 types/views: rename Generic to Unwrap
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-03-17 14:41:57 -07:00
Maisem Ali
1e12a29806 ssh/tailssh_test: Skip the env test in CI
Updates #4051

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-03-17 14:34:49 -07:00
Josh Bleecher Snyder
0868329936 all: use any instead of interface{}
My favorite part of generics.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-03-17 11:35:09 -07:00
Josh Bleecher Snyder
5f176f24db go.mod: upgrade to the latest wireguard-go
This pulls in a handful of fixes and an update to Go 1.18.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-03-17 10:59:39 -07:00
Brad Fitzpatrick
2708544018 tsnet: add some usability polish, remove WIP env var restriction
Change-Id: Id9ec1713c65cdd597d20b03e21e11cd60b54bb6a
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-17 10:59:21 -07:00
Josh Bleecher Snyder
997b19545b syncs: use TryLock and TryRLock instead of unsafe
The docs say:

Note that while correct uses of TryLock do exist, they are rare,
and use of TryLock is often a sign of a deeper problem in a particular use of mutexes.

Rare code! Or bad code! Who can tell!

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-03-17 10:57:41 -07:00
Brad Fitzpatrick
ead16b24ec cmd/tailscaled: fail early with nice error on macOS with go1.18
Due to golang/go#51759

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-17 10:41:50 -07:00
Josh Bleecher Snyder
9d4ffd135f go.toolchain.rev: pick up crypto/x509 crash fix
68c97fb924

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-03-17 10:37:15 -07:00
Maisem Ali
6b9d938c1a types/views: add generic Slice[T] and remove StringSlice
Also make IPPrefixSliceOf use Slice[netaddr.IPPrefix] as it also
provides additional functions besides the standard ones provided by
Slice[T].

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-03-16 22:13:16 -07:00
Denton Gentry
d8953bf2ba cmd/derpprobe: don't alert for smaller failures.
There is a Cosmic Background level of DERP Unreachability,
with individual nodes or regions becoming unreachable briefly
and returning a short time later. This is due to hosting provider
outages or just the Internet sloshing about.

Returning a 500 error pages a human. Being awoken at 3am for
a transient error is annoying.

For relatively small levels of badness don't page a human,
just post to Slack. If the outage impacts a significant fraction
of the DERP fleet, then page a human.

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-03-16 18:22:22 -07:00
Josh Bleecher Snyder
84a2dc3a7e go.toolchain.rev: update to slightly less forked Go 1.18
Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-03-16 16:10:29 -07:00
Josh Bleecher Snyder
8c2cb4b431 go.mod: update to latest certstore
It includes a fix to allow us to use Go 1.18.
We can now remove our Tailscale-only build tags.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-03-16 16:10:29 -07:00
Brad Fitzpatrick
61ee72940c all: use Go 1.18's strings.Cut
More remain.

Change-Id: I6ec562cc1f687600758deae1c9d7dbd0d04004cb
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-16 14:53:59 -07:00
Brad Fitzpatrick
1f22507c06 version: use Go 1.18's git stamping as default implementation
No more manual version bumps!

Fixes #81

Change-Id: I3a9e544a7248f0b83bcbacbaabbc4dabc435e62d
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-16 14:53:51 -07:00
Josh Bleecher Snyder
c2c97f8f38 go.toolchain.rev: remove second entry
No idea how that happened.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-03-16 12:55:26 -07:00
Josh Bleecher Snyder
26021b07ec control/controlclient: only build certstore-related code with the Tailscale Go toolchain
The certstore code is impacted by golang/go#51726.
The Tailscale Go toolchain fork contains a temporary workaround,
so it can compile it. Once the upstream toolchain can compile certstore,
presumably in Go 1.18.1, we can revert this change.

Note that depaware runs with the upstream toolchain.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-03-16 12:45:28 -07:00
Josh Bleecher Snyder
0ef74f37a5 net/dns/resolver: remove closure allocation explanation
As of Go 1.18, the register ABI list includes arm64, amd64,
ppc64, and ppc64le. This is a large enough percentage of the
architectures that it's not worth explaining.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-03-16 12:45:28 -07:00
Josh Bleecher Snyder
9482576bb1 ipn/ipnserver: use strings.Cut
We now require Go 1.18.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-03-16 12:45:28 -07:00
Josh Bleecher Snyder
97a01b7b17 util/deephash: remove Tailscale toolchain compatibility shim
The future is now.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-03-16 12:45:28 -07:00
Josh Bleecher Snyder
1b57b0380d wgengine/magicsock: remove final alloc from ReceiveFrom
And now that we don't have to play escape analysis and inlining games,
simplify the code.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-03-16 12:45:28 -07:00
Josh Bleecher Snyder
463728a885 util/netconv: add package to convert between netip and netaddr types
Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-03-16 12:45:28 -07:00
Josh Bleecher Snyder
5cb9999be3 go.toolchain.rev: upgrade to our Go 1.18 fork
Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-03-16 12:45:28 -07:00
Josh Bleecher Snyder
927fc36123 go.toolchain.branch: upgrade to Go 1.18
Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-03-16 12:45:28 -07:00
Josh Bleecher Snyder
71b535fc94 go.mod: require Go 1.18
Also, update depaware for Go 1.18's dependency tree.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-03-16 12:45:28 -07:00
Josh Bleecher Snyder
f695f0b178 go.mod: update golang.org/x/tools and honnef.co/go/tools
This is required for staticcheck to process code
using Go 1.18.

This puts us on a random commit on the bleeding edge
of staticcheck, which isn't great, but there don't
appear to have been any releases yet that support 1.18.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-03-16 12:45:28 -07:00
Josh Bleecher Snyder
f143ff89b7 README.md: update current Go release
Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-03-16 12:45:28 -07:00
Josh Bleecher Snyder
d77b4c1344 Dockerfile: require Go 1.18
Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-03-16 12:45:28 -07:00
Josh Bleecher Snyder
4b1e02057a .github/workflows: request Go 1.18
Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-03-16 12:45:28 -07:00
Josh Bleecher Snyder
08cf54f386 wgengine/magicsock: fix goMajorVersion for 1.18 ts release
The version string changed slightly. Adapt.
And always check the current Go version to prevent future
accidental regressions. I would have missed this one had
I not explicitly manually checked it.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-03-16 12:45:28 -07:00
David Eger
5be42c0af1 cmd/tailscale: add file get options for dealing with existing files
A new flag --conflict=(skip|overwrite|rename) lets users specify
what to do when receiving files that match a same-named file in
the target directory.

Updates #3548

Signed-off-by: David Eger <david.eger@gmail.com>
2022-03-16 12:05:41 -07:00
Maisem Ali
07f48a7bfe wgengine: handle nil netmaps when assigning isSubnetRouter.
Fixes tailscale/coral#51

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-03-16 10:51:12 -07:00
James Tucker
858286d97f github/windows: improve caching in -race builder (#4172)
Signed-off-by: James Tucker <james@tailscale.com>
Co-authored-by: James Tucker <james@tailscale.com>
2022-03-15 10:04:02 -07:00
Brad Fitzpatrick
5f529d1359 logtail: add Logger.PrivateID accessor
For the control plane to use.

Change-Id: I0f02321fc4fa3a41c3ece3b51eee729ea9770905
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-14 20:59:04 -07:00
James Tucker
36b148c2d2 github/windows: improve cache performance (#4171)
- Remove the expanded module files, as Go can likely expand the zips
  faster than tar can expand the extra copies.
- Add the go-build cache.
- Remove the extra restore key to avoid extra cache lookups on miss.

Signed-off-by: James Tucker <james@tailscale.com>
Co-authored-by: James Tucker <james@tailscale.com>
2022-03-14 17:10:13 -07:00
Maisem Ali
45a7f6689c tailcfg: add field to allow LocalPortForwarding in SSHAction
Updates #3802, #4129

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-03-14 13:39:42 -07:00
Maisem Ali
98b45ef12c ssh/tailssh: add support for agent forwarding.
Updates #3802

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-03-14 13:38:53 -07:00
Brad Fitzpatrick
6e86bbcb06 ssh/tailssh: add a new sshSession type to clean up existing+future code
Updates #3802

Change-Id: I7054dca387f5e5aee1185937ecf41b77a5a07f1a
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
Co-authored-by: Maisem Ali <maisem@tailscale.com>
2022-03-14 12:01:49 -07:00
Maisem Ali
462e75666b ssh/tailssh: start sending the server version
Updates #3802

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-03-12 19:40:51 -08:00
Maisem Ali
bf3559171f ssh/tailssh: set DBUS_SESSION_BUS_ADDRESS and SSH_TTY variables
Updates #3802

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-03-12 19:40:51 -08:00
Maisem Ali
6d61b7906e ssh/tailssh: handle terminal opcodes
Updates #3802 #4146

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-03-12 17:57:07 -08:00
Maisem Ali
da6ce27416 go.mod: move from github.com/gliderlabs/ssh to github.com/tailscale/ssh
Updates #4146

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-03-12 17:57:07 -08:00
Brad Fitzpatrick
012098ec32 ssh/tailssh: fix terminal corruption (temporary hack)
Maisem figured out the real problem but will take several commits
(e.g. tailscale/ssh#2) in different repos to get it fixed
properly. This is an interim hack.

Details of real fix:
https://github.com/tailscale/tailscale/issues/4146#issuecomment-1065952947

Updates #4146
Updates #3802

Change-Id: I7b7dc5713baa3e5de75b87b69e7179a6e7549b0b
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-12 14:19:45 -08:00
Brad Fitzpatrick
ba1adf6c24 ssh/tailssh: make pty termios options match OpenSSH
Still not sure the exact rules of how/when/who's supposed to set
these, but this works for now on making them match. Baby steps.
Will research more and adjust later.

Updates #4146 (but not enough to fix it, something's still wrong)
Updates #3802

Change-Id: I496d8cd7e31d45fe9ede88fc8894f35dc096de67
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-11 12:16:10 -08:00
Brad Fitzpatrick
1dd5cf62a5 ssh/tailssh: start login shell, fix arg passing, width/height mismatch
Updates #3802

Change-Id: I137d7a79195ee86d5dd7c8999f2797fc3cb57cec
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-10 20:11:41 -08:00
Brad Fitzpatrick
efc48b0578 ssh/tailssh, ipnlocal, controlclient: fetch next SSHAction from network
Updates #3802

Change-Id: I08e98805ab86d6bbabb6c365ed4526f54742fd8e
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-10 13:41:08 -08:00
Brad Fitzpatrick
6b11004a2a control/controlclient: proactively close TLS connection after /key fetch
When using Noise.

Updates #3488

Change-Id: I1049963763075a15b72fd8065dcf44a9cf37975f
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-10 13:26:18 -08:00
Aaron Klotz
f8a4df66de cmd/tailscale/cli, ipn: move exit node IP parsing and validation from cli into prefs.
We need to be able to provide the ability for the GUI clients to resolve and set
the exit node IP from an untrusted string, thus enabling the ability to specify
that information via enterprise policy.

This patch moves the relevant code out of the handler for `tailscale up`,
into a method on `Prefs` that may then be called by GUI clients.

We also update tests accordingly.

Updates https://github.com/tailscale/corp/issues/4239

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2022-03-10 10:51:05 -07:00
Maisem Ali
888e50e1f6 ipn/ipnlocal: migrate all platforms to controlplane.tailscale.com
Updates #3488

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-03-09 21:14:06 -08:00
Nick O'Neill
1625e87526 control/controlclient, localapi: shorten expiry time via localapi (#4112)
Signed-off-by: Nick O'Neill <nick@tailscale.com>
2022-03-09 14:42:42 -08:00
Maisem Ali
2bcc047d4f tailcfg: bump capVer for Noise
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-03-09 14:41:24 -08:00
Joonas Kuorilehto
c1b3500a05 cmd/tailscale: allow use of flags in gokrazy
Enable use of command line arguments with tailscale cli on gokrazy. Before
this change using arguments like "up" would cause tailscale cli to be
repeatedly restarted by gokrazy process supervisor.

We never want to have gokrazy restart tailscale cli, even if user would
manually start the process.

Expected usage is that user creates files:

flags/tailscale.com/cmd/tailscale/flags.txt:

    up

flags/tailscale.com/cmd/tailscaled/flags.txt:

    --statedir=/perm/tailscaled/
    --tun=userspace-networking

Then tailscale prints URL for user to log in with browser.

Alternatively it should be possible to use up with auth key to allow
unattended gokrazy installs.

Signed-off-by: Joonas Kuorilehto <joneskoo@derbian.fi>
2022-03-09 12:30:32 -08:00
Maisem Ali
2c89b3a601 control/controlbase: make Conn.Write return consumed bytes
Currently `Write` returns the number of ciphertext bytes written.
According to the docs for io.Writer, Write should return the amount
of bytes consumed from the input.
```
// Write writes len(p) bytes from p to the underlying data stream.
// It returns the number of bytes written from p (0 <= n <= len(p))
// and any error encountered that caused the write to stop early.
// Write must return a non-nil error if it returns n < len(p).
// Write must not modify the slice data, even temporarily.
Write(p []byte) (n int, err error)
```

Fixes #4126

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-03-09 11:42:11 -08:00
Maisem Ali
e82a74553b control/controlclient: make MapRequests go over noise.
Updates #3488

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-03-09 11:32:11 -08:00
Maisem Ali
56bf2ce642 ssh/tailssh: handle local port forwarding
Updates #3802

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-03-09 11:31:04 -08:00
Maisem Ali
598c7a22e7 ssh/tailssh: use lu.Username not lu.Name.
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-03-08 22:39:03 -08:00
Maisem Ali
06c147d848 ssh/tailssh: create login sessions for new connections
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-03-08 21:47:19 -08:00
Maisem Ali
ba2c0c3145 control/controlclient: call direct.Close after map requests are complete
This was causing a flake in another repo.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-03-08 21:17:35 -08:00
Brad Fitzpatrick
61cdcf4082 net/interfaces: add FreeBSD default route lookup (portmapping, etc)
Updates #4101 (probably fixes)

Change-Id: I2b75ee3ced276fb7b211f17c382621cf1ef882fa
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-08 13:02:02 -08:00
Maisem Ali
2fb087891b net/socks5: always close client connections after serving
Customer reported an issue where the connections were not closing, and
would instead just stay open. This commit makes it so that we close out
the connection regardless of what error we see. I've verified locally
that it fixes the issue, we should add a test for this.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-03-08 12:52:20 -08:00
Maisem Ali
91a8cdc84b control/controlclient: make Auto.Shutdown call Direct.Close
Updates #3488

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-03-08 11:57:41 -08:00
Maisem Ali
0f37317664 control/controlclient: make RegisterRequest go over Noise
Updates #3488

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-03-08 11:57:41 -08:00
Brad Fitzpatrick
c4f6df47e5 control/controlclient: fix Noise HTTP/2 regression from earlier commit
Fix regression from 21069124db caught by tests in another repo.

The HTTP/2 Transport that was being returned had a ConnPool that never
dialed.

Updates #3488

Change-Id: I3184d6393813448ae143d37ece14eb732334c05f
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-08 09:50:36 -08:00
Brad Fitzpatrick
21069124db control/controlclient: fix the Noise HTTP/2 timeout config
We want to close the connection after a minute of inactivity,
not heartbeat once a minute to keep it alive forever.

Updates #3488

Change-Id: I4b5275e8d1f2528e13de2d54808773c70537db91
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-08 08:48:28 -08:00
Brad Fitzpatrick
740e3c006c cmd/derper: add --stun-port flag
And flesh out docs on the --http-port flag.

Change-Id: If9d42665f67409082081cb9a25ad74e98869337b
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-08 07:19:33 -08:00
Maisem Ali
0588ca5d8b control/controlclient: make SetDNS attempt to go over Noise first
Updates #3488

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-03-07 16:27:13 -08:00
Maisem Ali
da1821197a tailcfg: add SetDNSResponse
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-03-07 16:27:13 -08:00
Maisem Ali
0f31a0fc76 control/controlclient: add Noise client
Updates #3488

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-03-07 15:43:19 -08:00
Brad Fitzpatrick
26f27a620a wgengine/router: delete legacy netfilter rule cleanup [Linux]
This was just cleanup for an ancient version of Tailscale. Any such machines
have upgraded since then.

Change-Id: Iadcde05b37c2b867f92e02ec5d2b18bf2b8f653a
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-07 14:39:04 -08:00
Maisem Ali
249758df90 control/controlclient: start fetching the server noise key
Updates #3488

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-03-07 11:29:27 -08:00
Brad Fitzpatrick
d5f8f38ac6 tailcfg: rename map request version to "capability version"
And add a CapabilityVersion type, primarily for documentation.

This makes MapRequest.Version, RegisterRequest.Version, and
SetDNSRequest.Version all use the same version, which will avoid
confusing in the future if Register or SetDNS ever changed their
semantics on Version change. (Currently they're both always 1)

This will requre a control server change to allow a
SetDNSRequest.Version value other than 1 to be deployed first.

Change-Id: I073042a216e0d745f52ee2dbc45cf336b9f84b7c
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-06 14:29:08 -08:00
Brad Fitzpatrick
105dfa1efa tailcfg: add OverTLSPublicKeyResponse for the new response from /key
Updates #3488

Change-Id: I8729cb3fb7f6dda1a874f8ae2d9570311ed158db
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-06 13:51:32 -08:00
Robert Fritzsche
0e62a7d1a2 tstime/mono: fix Before function comment
Signed-off-by: Robert Fritzsche <r.fritzsche@gridx.de>
2022-03-05 15:05:57 -08:00
Maisem Ali
c85694fac4 types/views: add ContainsExitRoutes to IPPrefixSlice
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-03-04 09:08:42 -08:00
Brad Fitzpatrick
b493ef5b71 net/tsaddr: add func ContainsExitRoutes
Change-Id: I772441a406083e2fe0f9374b2b23d89aac18928f
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-04 08:56:06 -08:00
Josh Bleecher Snyder
7ddf2e2fea go.toolchain.rev: bump to Go 1.17.8
Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-03-03 14:51:16 -08:00
Brad Fitzpatrick
f18bb6397b cmd/tailscale: tell gokrazy to not manage the CLI as a daemon
In the future we'll probably want to run the "tailscale web"
server instead, but for now stop the infinite restart loop.

See https://gokrazy.org/userguide/process-interface/ for details.

Updates #1866

Change-Id: I4133a5fdb859b848813972620495865727fe397a
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-01 20:35:18 -08:00
Brad Fitzpatrick
db85384f9c cmd/tailscaled: default to userspace-networking mode on gokrazy, set paths
One of the current few steps to run Tailscale on gokrazy is to
specify the --tun=userspace-networking flag:

    https://gokrazy.org/userguide/install/tailscale/

Instead, make it the default for now. Later we can change the
default to kernel mode if available and fall back to userspace
mode like Synology, once #391 is done.

Likewise, set default paths for Gokrazy, as its filesystem hierarchy
is not the Linux standard one. Instead, use the conventional paths as
documented at https://gokrazy.org/userguide/install/tailscale/.

Updates #1866

RELNOTE=default to userspace-networking mode on gokrazy

Change-Id: I3766159a294738597b4b30629d2860312dbb7609
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-01 20:34:45 -08:00
Brad Fitzpatrick
c9a5dadce8 ssh/tailssh: skip flaky test on CI for now
Updates #4051

Change-Id: I94f2165dd248eba9ca3f782c907a13bd6dde4a5e
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-01 19:57:07 -08:00
Brad Fitzpatrick
58a6c9b2b8 version, hostinfo: recognize gokrazy as a distro
Now:

/tmp/breakglass3929186798 # /user/tailscale debug hostinfo
{
  "IPNVersion": "1.23.0-date.20220107",
  "OS": "linux",
  "OSVersion": "Gokrazy; kernel=5.16.11",
  "DeviceModel": "Raspberry Pi 4 Model B Rev 1.2",
  "Hostname": "gokrazy",
  "GoArch": "arm64"
}

Also, cache the distro lookup. It doesn't change while the program is
running:

name   old time/op    new time/op    delta
Get-6    5.21µs ± 5%    0.00µs ± 3%   -99.91%  (p=0.008 n=5+5)

name   old alloc/op   new alloc/op   delta
Get-6      792B ± 0%        0B       -100.00%  (p=0.008 n=5+5)

name   old allocs/op  new allocs/op  delta
Get-6      8.00 ± 0%      0.00       -100.00%  (p=0.008 n=5+5)

Updates #1866

Change-Id: Ifb9a63b94287010d3f4c8bfeb6b78119e8a9b203
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-03-01 19:37:20 -08:00
Brad Fitzpatrick
6a2e94cbeb tstime/rate: deflake TestLongRunningQPS even more
Previous de-flakings:
* 8cf1af8a07 for #3733
* 30458c71c8 for #2727

Fixes #4044

Change-Id: I506cf1ff37bb224f5a9929f1998901e60b24535d
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-28 20:22:16 -08:00
Brad Fitzpatrick
55095df644 net/interfaces: get Linux default route from netlink as fallback
If it's in a non-standard table, as it is on Unifi UDM Pro, apparently.

Updates #4038 (probably fixes, but don't have hardware to verify)

Change-Id: I2cb9a098d8bb07d1a97a6045b686aca31763a937
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-28 19:57:34 -08:00
Maisem Ali
518f6cee63 ipn/store: [TestNewStore] do not use an empty file
Otherwise it would log warnings about an empty file.
```
    stores.go:138: store.NewFileStore("/tmp/3777352782"): file empty; treating it like a missing file [warning]
```

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-02-28 18:26:24 -08:00
Maisem Ali
497324ddf6 ipn/store: add common package for instantiating ipn.StateStores
Also move KubeStore and MemStore into their own package.

RELNOTE: tsnet now supports providing a custom ipn.StateStore.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-02-28 13:23:33 -08:00
Dmytro Shynkevych
d9a7205be5 net/tstun: set link speed to SPEED_UNKNOWN
Fixes #3933.

Signed-off-by: Dmytro Shynkevych <dm.shynk@gmail.com>
2022-02-27 23:11:35 -08:00
Brad Fitzpatrick
5d085a6f41 controlhttp: add some docs, change Dial's path from /switch to /ts2021
When I deployed server-side changes, I put the upgrade handler at /ts2021
instead of /switch. We could move the server to /switch, but ts2021 seems
more specific and better, but I don't feel strongly.

Updates #3488

Change-Id: Ifbf8ea60a815fd2fa1bfbe1b7af1ac2a27218354
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-26 12:44:29 -08:00
Brad Fitzpatrick
4b50977422 ssh/tailssh: add more SSH tests, blend in env from ssh session
Updates #3802

Change-Id: I568c661cacbb0524afcd8be9577457ddba611f19
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-24 16:02:01 -08:00
Brad Fitzpatrick
4686224e5a cmd/tailscaled: add a no-op test for profiling init-time memory allocs
Turns out we're pretty good already at init-time work in tailscaled.
The regexp/syntax shows up but it's hard to get rid of that; zstd even
uses regexp. *shrug*

Change-Id: I856aca056dcb7489f5fc22ef07f55f34ddf19bd6
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-24 14:58:12 -08:00
Brad Fitzpatrick
4cbdc84d27 cmd/tailscaled/childproc: add be-child registration mechanism
For ssh and maybe windows service babysitter later.

Updates #3802

Change-Id: I7492b98df98971b3fb72d148ba92c2276cca491f
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-24 14:20:20 -08:00
Brad Fitzpatrick
6e4f3614cf ssh/tailssh: add start of real ssh tests
Updates #3802

Change-Id: I9aea4250062d3a06ca7a5e71a81d31c27a988615
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-24 14:13:12 -08:00
Brad Fitzpatrick
c9eca9451a ssh: make it build on darwin
For local dev testing initially. Product-wise, it'll probably only be
workable on the two unsandboxed builds.

Updates #3802

Change-Id: Ic352f966e7fb29aff897217d79b383131bf3f92b
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-24 13:00:45 -08:00
Brad Fitzpatrick
c4a6d9fa5d ipn/ipnlocal: generate tailscaled-owned SSH keys as needed
Updates #3802

Change-Id: Ie1bc9ae3f3639603b88b4e19b7eb12bea528ff77
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-24 12:15:57 -08:00
Brad Fitzpatrick
cce6aad6c0 ssh/tailssh: fix non-interactive commands as non-root user
Updates #3802

Change-Id: I89a3f14420b8782bc407b1939dce54a1d24636da
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-24 12:13:16 -08:00
Brad Fitzpatrick
e2ed06c53c ssh/tailssh: break a method into half in prep for testing
And add a private context type in the process.

Updates #3802

Change-Id: I257187f4cfb0f2248d95b81c1dfe0911ef203b60
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-24 09:59:00 -08:00
Brad Fitzpatrick
1b5bb2e81d ssh/tailssh: rename sshContext to sshConnInfo
So it's not confused for a context.Context and we can add contexts
later and not look like we have two.

Updates #3802

Change-Id: Icf229ae2c020d173f3cbf09a13ccd03a60cbb85e
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-24 09:06:21 -08:00
Denton Gentry
8175504584 VERSION.txt: This is 1.23.
Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-02-23 15:51:28 -08:00
Brad Fitzpatrick
3c2cd854be ssh/tailssh: flesh out env, support non-pty commands
Updates #3802

Change-Id: I7022460117542a5424919144828bf571c7c19ec0
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-23 15:00:41 -08:00
Brad Fitzpatrick
7d897229d9 net/dns: ignore permission errors on Synology DSM7 for now
Updates #4017

Change-Id: Ia7fd4df47588c010dea8e63d88f397cc8eb748e5
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-23 10:13:53 -08:00
Brad Fitzpatrick
29279b34fa cmd/tailscale: make configure-host on Synology also add CAP_NET_RAW
Updates #4012

Change-Id: Ic45b5709a73b4f1cd466823e177b52d1d20ba84e
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-23 07:56:38 -08:00
Maisem Ali
38c59c0ad2 tsnet: fix typo in Ephemeral
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-02-22 15:35:24 -08:00
Brad Fitzpatrick
bb94561c96 net/netutil: fix regression where peerapi would get closed after 1st req
I introduced a bug in 8fe503057d when unifying oneConnListener
implementations.

The NewOneConnListenerFrom API was easy to misuse (its Close method
closes the underlying Listener), and we did (via http.Serve, which
closes the listener after use, which meant we were close the peerapi's
listener, even though we only wanted its Addr)

Instead, combine those two constructors into one and pass in the Addr
explicitly, without delegating through to any Listener.

Change-Id: I061d7e5f842e0cada416e7b2dd62100d4f987125
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-22 13:52:18 -08:00
Aaron Klotz
e31d68d64e hostinfo: use the sentinel value set by the MSI installer to detect MSI package type
The MSI installer sets a special sentinel value that we can use to detect it.

I also removed the code that bails out when the installation path is not
`Program Files`, as both the NSIS and MSI installers permit the user to install
to a different path.

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2022-02-22 12:48:20 -07:00
Brad Fitzpatrick
4fee321004 hostinfo: move packageType out to platform-specific files
Change-Id: I3236b3d4e2376dd7e2482c2562817b1b6f44872e
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-22 10:23:13 -08:00
Maisem Ali
c7a8f0992d ipn/ipnlocal: use views for Peer.PrimaryRoutes and Peer.Tags
RELNOTE=`tailscale status --json` now shows Tags and PrimaryRoutes

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-02-22 10:09:02 -08:00
Maisem Ali
9cbb0913be ipn/{ipnlocal,ipnstate}: add Tags and PrimaryRoutes to PeerStatus
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-02-21 20:06:48 -08:00
David Anderson
0fc1479633 go.mod: update github.com/mdlayher/netlink to 1.6.0
This unbreaks some downstream users of tailscale who end up
with build errors from importing a v0 indirect dependency.

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-02-21 14:31:03 -08:00
Brad Fitzpatrick
e921e1b02d cmd/tailscale: add "tailscale debug hostinfo" subcommand
Change-Id: Ifa09364d42e0516fdf80feddaf33c95880228049
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-20 08:06:37 -08:00
Brad Fitzpatrick
300d897fd7 hostinfo: detect NSIS vs MSI package type on Windows
Change-Id: I624a4cb04803e483553eb53c952060393029c435
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-20 07:58:49 -08:00
Brad Fitzpatrick
d19a63ddf6 ipn/localapi: treat ACME "invalid" state as terminal, log more
Fixes #3975

Change-Id: Idb2cc8d4730e140939898c7dcc15c2014acca142
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-19 16:22:58 -08:00
Brad Fitzpatrick
de72a1f9fc ipn/ipnserver: let TS_PERMIT_CERT_UID contain a username too, not just uid
Don't make users map their system's "caddy" (or whatever) system user
to its userid. We can do that. Support either a uid or a username.

RELNOTE=TS_PERMIT_CERT_UID can contain a uid or username

Change-Id: I7451b537a5e118b818addf1353882291d5f0d07f
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-19 16:22:43 -08:00
Brad Fitzpatrick
03caa95bf2 ssh/tailssh: get login shell when running as non-root
And also reject attempts to use other users.

Updates #3802

Change-Id: Iddc85f6ea2dba17d12be66a50408d24c1f92833e
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-18 19:22:11 -08:00
Brad Fitzpatrick
e1e20f6d39 ssh/tailssh: evaluate tailcfg.SSHPolicy on incoming connections
Updates #3802
Fixes #3960

Change-Id: Ieda2007d462ddce6c217b958167417ae9755774e
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-18 18:07:39 -08:00
Josh Bleecher Snyder
66f5aa6814 types/logger: add more reserved top level field names
Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-02-18 15:21:35 -08:00
Maisem Ali
f9a50779e2 cmd/tailscaled: add -state=mem: to support creation of an ephemeral node.
RELNOTE=`tailscaled --state=mem:` registers as an ephemeral node and
does not store state to disk.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-02-18 13:40:39 -08:00
Josh Bleecher Snyder
823d970d60 control/controlclient: use structured logging for MapResponse.ControlTime
Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-02-18 13:05:42 -08:00
Brad Fitzpatrick
84138450a4 types/logger, logtail: add mechanism to do structured JSON logs
e.g. the change to ipnlocal in this commit ultimately logs out:

{"logtail":{"client_time":"2022-02-17T20:40:30.511381153-08:00","server_time":"2022-02-18T04:40:31.057771504Z"},"type":"Hostinfo","val":{"GoArch":"amd64","Hostname":"tsdev","IPNVersion":"1.21.0-date.20220107","OS":"linux","OSVersion":"Debian 11.2 (bullseye); kernel=5.10.0-10-amd64"},"v":1}

Change-Id: I668646b19aeae4a2fed05170d7b279456829c844
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-18 12:42:06 -08:00
Josh Bleecher Snyder
8c3c5e80b7 tailcfg: make MapResponse.ControlTime a pointer
Otherwise omitempty doesn't work.

This is wire-compatible with a non-pointer type, so switching
is safe, now and in the future.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-02-18 10:37:27 -08:00
Brad Fitzpatrick
bb93e29d5c tailcfg, ipn/ipnlocal: add Hostinfo.SSH_HostKeys, send when SSH enabled
(The name SSH_HostKeys is bad but SSHHostKeys is worse.)

Updates #3802

Change-Id: I2a889019c9e8b065b668dd58140db4fcab868a91
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-17 15:46:57 -08:00
Josh Bleecher Snyder
4609096271 tailcfg: fix stale docs for MapResponse.KeepAlive
Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-02-17 15:15:43 -08:00
Brad Fitzpatrick
dd6472d4e8 api: document preauthorized auth keys
Fixes #2120

Change-Id: If6a803680b544df1f70449c26fd0f5e15940226b
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-17 14:27:39 -08:00
Brad Fitzpatrick
fbff1555fc ipnlocal, tailssh: start moving host key stuff into the right spot
Make tailssh ask LocalBackend for the SSH hostkeys, as we'll need to
distribute them to peers.

For now only the hacky use-same-as-actual-host mode is implemented.

Updates #3802

Change-Id: I819dcb25c14e42e6692c441186c1dc744441592b
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-17 14:01:50 -08:00
Josh Bleecher Snyder
94409db7e2 cmd/tailscale: rewrite --authkey to --auth-key
That way humans don't have to remember which is correct.

RELNOTE=--auth-key is the new --authkey, but --authkey still works

Updates tailscale/corp#3486

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-02-17 10:00:46 -08:00
Xe Iaso
a45f8accdb scripts/installer: add Ubuntu 22.04 LTS Jammy Jellyfish (#3955)
Signed-off-by: Xe Iaso <xe@tailscale.com>
2022-02-17 09:52:35 -05:00
Josh Bleecher Snyder
8cf6d0a17b tailcfg: add MapResponse.ControlTime field
And log it when provided in map responses.

The test uses the date on which I joined Tailscale. :)

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-02-16 20:18:03 -08:00
Maisem Ali
72d8672ef7 tailcfg: make Node.Hostinfo a HostinfoView
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-02-16 12:55:57 -08:00
Maisem Ali
53998e26a6 tailcfg: introduce HostinfoView
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-02-16 12:55:57 -08:00
Brad Fitzpatrick
2ff481ff10 net/dns: add health check for particular broken-ish Linux DNS config
Updates #3937 (need to write docs before closing)

Change-Id: I1df7244cfbb0303481e2621ee750d21358bd67c6
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-16 10:40:04 -08:00
Brad Fitzpatrick
57115e923e tailcfg: add start of SSH policy to be sent from control plane to nodes
Updates #3802

Change-Id: Iec58f35d445aaa267d0f7e7e2f30c049c1df4c0e
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-15 16:05:42 -08:00
Josh Bleecher Snyder
b486448ab9 go.toolchain.rev: bump to Go 1.17.7
Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-02-15 13:29:17 -08:00
Brad Fitzpatrick
1b87e025e9 ssh/tailssh: move SSH code from wgengine/netstack to this new package
Still largely incomplete, but in a better home now.

Updates #3802

Change-Id: I46c5ffdeb12e306879af801b06266839157bc624
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-15 12:21:01 -08:00
Ross Zurowski
6d02a48d8d ipn: add TailnetStatus field to tailscale status --json (#3865)
We need to capture some tailnet-related information for some Docker
features we're building. This exposes the tailnet name and MagicDNS
information via `tailscale status --json`.

Fixes tailscale/corp#3670

Signed-off-by: Ross Zurowski <ross@rosszurowski.com>
2022-02-15 12:36:01 -05:00
Brad Fitzpatrick
c988bd6ed1 net/dns/resolvconffile: unify three /etc/resolv.conf parsers into new package
Change-Id: I2120893ca802d12f1bd0407d49077d3672627d33
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-14 20:55:57 -08:00
Josh Bleecher Snyder
1dc4151f8b logtail: add MustParsePublicID
Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-02-14 16:00:17 -08:00
Brad Fitzpatrick
8d6cf14456 net/dnscache: don't do bootstrap DNS lookup after most failed dials
If we've already connected to a certain name's IP in the past, don't
assume the problem was DNS related. That just puts unnecessarily load
on our bootstrap DNS servers during regular restarts of Tailscale
infrastructure components.

Also, if we do do a bootstrap DNS lookup and it gives the same IP(s)
that we already tried, don't try them again.

Change-Id: I743e8991a7f957381b8e4c1508b8e9d0df1782fe
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-14 14:28:08 -08:00
Xe Iaso
b4947be0c8 scripts/installer: automagically run apt update (#3939)
When running this script against a totally fresh out of the box Debian
11 image, sometimes it will fail to run because it doesn't have a
package list cached. This patch adds an `apt-get update` to ensure that
the local package cache is up to date.

Signed-off-by: Xe Iaso <xe@tailscale.com>
2022-02-14 15:55:46 -05:00
Brad Fitzpatrick
01e8a152f7 ipn/ipnlocal: log most of Hostinfo once non-verbose at start-up
Our previous Hostinfo logging was all as a side effect of telling
control. And it got marked as verbose (as it was)

This adds a one-time Hostinfo logging that's not verbose, early in
start-up.

Change-Id: I1896222b207457b9bb12ffa7cf361761fa4d3b3a
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-14 12:33:35 -08:00
Charlotte Brandhorst-Satzkorn
2448c000b3 words: more hamsters, less hampsters (#3938)
Spell hamster correctly, and add the name of a teeny tiny type of
hamster, the Roborovski dwarf hamster.

Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@tailscale.com>
2022-02-14 15:15:30 -05:00
Brad Fitzpatrick
903988b392 net/dnscache: refactor from func-y closure-y state to types & methods
No behavior changes (intended, at least).

This is in prep for future changes to this package, which would get
too complicated in the current style.

Change-Id: Ic260f8e34ae2f64f34819d4a56e38bee8d8ac5ce
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-14 10:47:48 -08:00
Brad Fitzpatrick
8267ea0f80 net/tstun: remove TODO that's done
This TODO was both added and fixed in 506c727e3.

As I recall, I wasn't originally going to do it because it seemed
annoying, so I wrote the TODO, but then I felt bad about it and just
did it, but forgot to remove the TODO.

Change-Id: I8f3514809ad69b447c62bfeb0a703678c1aec9a3
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-13 20:59:47 -08:00
Brad Fitzpatrick
8fe503057d net/netutil: unify two oneConnListeners into a new package
I was about to add a third copy, so unify them now instead.

Change-Id: I3b93896aa1249b1250a6b1df4829d57717f2311a
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-13 14:57:27 -08:00
Brad Fitzpatrick
5d9ab502f3 logtail: don't strip verbose level on upload
For analysis of log spam.

Bandwidth is ~unchanged from had we not stripped the "[vN] " from
text; it just gets restructed intot he new "v":N, field.  I guess it
adds one byte.

Updates #1548

Change-Id: Ie00a4e0d511066a33d10dc38d765d92b0b044697
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-13 11:30:37 -08:00
Brad Fitzpatrick
a19c110dd3 envknob: track, log env knobs in use
Fixes #3921

Change-Id: I8186053b5c09c43f0358b4e7fdd131361a6d8f2e
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-12 21:56:10 -08:00
Brad Fitzpatrick
2db6cd1025 ipn/ipnlocal, wgengine/magicsock, logpolicy: quiet more logs
Updates #1548

Change-Id: Ied169f872e93be2857890211f2e018307d4aeadc
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-12 16:42:29 -08:00
Brad Fitzpatrick
be9d564c29 envknob: remove some stutter from error messages
The strconv errors already stringified with the same.

Change-Id: I6938c5653e9aafa6d9028d45fc26e39eb9ccbaea
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-12 16:36:15 -08:00
Brad Fitzpatrick
3a94ece30c control/controlclient: remove dummy endpoint in endpoint stripping mode
The TODO is done. Magicsock doesn't require any endpoints to create an
*endpoint now.  Verified both in code and empirically: I can use the
env knob and access everything.

Change-Id: I4fe7ed5b11c5c5e94b21ef3d77be149daeab998a
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-12 16:36:04 -08:00
Brad Fitzpatrick
86a902b201 all: adjust some log verbosity
Updates #1548

Change-Id: Ia55f1b5dc7dfea09a08c90324226fb92cd10fa00
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-12 08:51:16 -08:00
Adrian Dewhurst
adda2d2a51 control/controlclient: select newer certificate
If multiple certificates match when selecting a certificate, use the one
issued the most recently (as determined by the NotBefore timestamp).
This also adds some tests for the function that performs that
comparison.

Updates tailscale/coral#6

Signed-off-by: Adrian Dewhurst <adrian@tailscale.com>
2022-02-11 23:00:22 -05:00
Brad Fitzpatrick
a80cef0c13 cmd/derper: fix regression from bootstrap DNS optimization
The commit b9c92b90db earlier today
caused a regression of serving an empty map always, as it was
JSON marshalling an atomic.Value instead of the DNS entries map
it just built.

Change-Id: I9da3eeca132c6324462dedeaa7d002908557384b
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-11 15:28:38 -08:00
Josh Bleecher Snyder
84046d6f7c Revert "cmd/derper: stop setting content header in handleBootstrapDNS"
Didn't help enough. We are setting another header anyway. Restore it.

This reverts commit 60abeb027b.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-02-11 14:15:28 -08:00
Josh Bleecher Snyder
ec62217f52 cmd/derper: close connections once bootstrap DNS has been served
Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-02-11 14:08:43 -08:00
Brad Fitzpatrick
21358cf2f5 net/dns: slightly optimize dbusPing for non-dbus case [Linux]
Avoid some work when D-Bus isn't running.

Change-Id: I6f89bb75fdb24c13f61be9b400610772756db1ef
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-11 14:00:54 -08:00
Brad Fitzpatrick
37e7a387ff net/dns: remove some unused code for detecting systemd-resolved [Linux]
Change-Id: I19c5fd2cdacfb9e5b688ccd9b4336ae4edffc445
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-11 14:00:54 -08:00
Brad Fitzpatrick
15599323a1 net/dns: fix systemd-resolved detection race at boot
If systemd-resolved is enabled but not running (or not yet running,
such as early boot) and resolv.conf is old/dangling, we weren't
detecting systemd-resolved.

This moves its ping earlier, which will trigger it to start up and
write its file.

Updates #3362 (likely fixes)
Updates #3531 (likely fixes)

Change-Id: I6392944ac59f600571c43b8f7a677df224f2beed
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-11 14:00:54 -08:00
Josh Bleecher Snyder
60abeb027b cmd/derper: stop setting content header in handleBootstrapDNS
No one really cares. Its cost outweighs its usefulness.

name                   old time/op    new time/op    delta
HandleBootstrapDNS-10     105ns ± 4%      65ns ± 2%   -37.68%  (p=0.000 n=15+14)

name                   old alloc/op   new alloc/op   delta
HandleBootstrapDNS-10      416B ± 0%        0B       -100.00%  (p=0.000 n=15+15)

name                   old allocs/op  new allocs/op  delta
HandleBootstrapDNS-10      3.00 ± 0%      0.00       -100.00%  (p=0.000 n=15+15)

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-02-11 12:43:19 -08:00
Josh Bleecher Snyder
b9c92b90db cmd/derper: optimize handleBootstrapDNS
Do json formatting once, rather than on every request.

Use an atomic.Value.

name                   old time/op    new time/op    delta
HandleBootstrapDNS-10    6.35µs ± 0%    0.10µs ± 4%  -98.35%  (p=0.000 n=14+15)

name                   old alloc/op   new alloc/op   delta
HandleBootstrapDNS-10    3.20kB ± 0%    0.42kB ± 0%  -86.99%  (p=0.000 n=12+15)

name                   old allocs/op  new allocs/op  delta
HandleBootstrapDNS-10      41.0 ± 0%       3.0 ± 0%  -92.68%  (p=0.000 n=15+15)

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-02-11 12:43:19 -08:00
Josh Bleecher Snyder
e206a3663f cmd/derper: add BenchmarkHandleBootstrapDNS
Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-02-11 12:43:19 -08:00
Joe Tsai
0173a50bf0 cmd/derper: add a rate limiter for accepting new connection (#3908)
A large influx of new connections can bring down DERP
since it spins off a new goroutine for each connection,
where each routine may do significant amount of work
(e.g., allocating memory and crunching numbers for TLS crypto).
The momentary spike can cause the process to OOM.

This commit sets the groundwork for limiting connections,
but leaves the limit at infinite by default.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-02-11 12:02:38 -08:00
Denton Gentry
dbea8217ac net/dns: add NetworkManager regression test
Use the exact /etc/resolv.conf file from a user report.
Updates https://github.com/tailscale/tailscale/issues/3531

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-02-10 15:01:49 -08:00
Aaron Klotz
82cd98609f util/winutil: migrate corp's winutil into OSS.
It makes the most sense to have all our utility functions reside in one place.
There was nothing in corp that could not reasonably live in OSS.

I also updated `StartProcessAsChild` to no longer depend on `futureexec`,
thus reducing the amount of code that needed migration. I tested this change
with `tswin` and it is working correctly.

I have a follow-up PR to remove the corresponding code from corp.

The migrated code was mostly written by @alexbrainman.
Sourced from corp revision 03e90cfcc4dd7b8bc9b25eb13a26ec3a24ae0ef9

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2022-02-10 15:22:55 -07:00
Jay Stapleton
39d173e5fc add -y flag for xbps to allow installation on void
Signed-off-by: Jay Stapleton <jay@tailscale.com>
2022-02-10 16:05:17 -05:00
Jay Stapleton
c8551c8a67 add -y flag for xbps to allow installation on void 2022-02-10 16:05:17 -05:00
Aaron Klotz
3a74f2d2d7 cmd/tailscaled, util/winutil: add accessor functions for Windows system policies.
This patch adds new functions to be used when accessing system policies,
and revises callers to use the new functions. They first attempt the new
registry path for policies, and if that fails, attempt to fall back to the
legacy path.

We keep non-policy variants of these functions because we should be able to
retain the ability to read settings from locations that are not exposed to
sysadmins for group policy edits.

The remaining changes will be done in corp.

Updates https://github.com/tailscale/tailscale/issues/3584

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2022-02-09 14:58:51 -07:00
Brad Fitzpatrick
24c9dbd129 tsweb: fix JSONHandlerFunc regression where HTTP status was lost on gzip
Change-Id: Ia7add6cf7e8b46bb6dd45bd3c0371ea79402fb45
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-09 12:17:14 -08:00
Xe Iaso
62db629227 words: add ferret to tails.txt (#3897)
In honor of this post[1] inspiring me to remember that ferrets exist and
have tails.

[1]: https://tech.davidfield.co.uk/what-is-tailscale/

Signed-off-by: Xe <xe@tailscale.com>
2022-02-09 14:40:15 -05:00
Brad Fitzpatrick
3c481d6b18 cmd/tailscale: add "tailscale configure-host" to prep a Synology machine at boot
Updates #3761

Change-Id: Ib5ab9a4808ade074f48d3abee22c57d7670f9e21
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-08 09:26:26 -08:00
Brad Fitzpatrick
b3d268c5a1 control/controlclient: turn off Go's implicit compression
We don't use it anyway, so be explicit that we're not using it.

Change-Id: Iec953271ef0169a2e227811932f5b65b479624af
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-07 13:55:42 -08:00
Brad Fitzpatrick
df8f02db3f tsweb: add gzip support to JSONHandlerFunc
Change-Id: I337e05f92f744bfc7e9d6fb8e67c87c191ba4da8
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-07 10:31:25 -08:00
Denton Gentry
16652ae52c installer.sh: accommodate linuxmint versioning.
Recent linuxmint releases now use VERSION_CODENAME for
a linuxmint release (like "uma") and set UBUNTU_CODENAME to
the Ubuntu release they branched from.

Tested in a linuxmint 20.2 VM.

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-02-07 07:06:00 -08:00
Sonia Appasamy
aaba49ca10 api.md: add docs for device tags and keys endpoints
Signed-off-by: Sonia Appasamy <sonia@tailscale.com>
2022-02-04 16:20:46 -05:00
Maisem Ali
e64cecac8e chirp: remove regex dependency
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-02-03 11:24:17 -08:00
Brad Fitzpatrick
2a67beaacf net/interfaces: bound Linux /proc/net/route parsing
tailscaled was using 100% CPU on a machine with ~1M lines, 100MB+
of /proc/net/route data.

Two problems: in likelyHomeRouterIPLinux, we didn't stop reading the
file once we found the default route (which is on the first non-header
line when present). Which meant it was finding the answer and then
parsing 100MB over 1M lines unnecessarily. Second was that if the
default route isn't present, it'd read to the end of the file looking
for it. If it's not in the first 1,000 lines, it ain't coming, or at
least isn't worth having. (it's only used for discovering a potential
UPnP/PMP/PCP server, which is very unlikely to be present in the
environment of a machine with a ton of routes)

Change-Id: I2c4a291ab7f26aedc13885d79237b8f05c2fd8e4
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-03 09:31:25 -08:00
Brad Fitzpatrick
0626cf4183 util/winutil: fix build
It was broken on Windows:

Error: util\winutil\winutil_windows.go:15:7: regBase redeclared in this block
Error:                                       D:\a\tailscale\tailscale\util\winutil\winutil_notwindows.go:7:17: previous declaration
Error: util\winutil\winutil_windows.go:29:6: getRegString redeclared in this block
Error:                                       D:\a\tailscale\tailscale\util\winutil\winutil_notwindows.go:9:40: previous declaration
Error: util\winutil\winutil_windows.go:47:6: getRegInteger redeclared in this block
Error:                                       D:\a\tailscale\tailscale\util\winutil\winutil_notwindows.go:11:48: previous declaration
Error: util\winutil\winutil_windows.go:77:6: isSIDValidPrincipal redeclared in this block
Error:                                       D:\a\tailscale\tailscale\util\winutil\winutil_notwindows.go:13:38: previous declaration

Change-Id: Ib1ce4b647f5711547840c736b933a6c42bf09583
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-02 16:45:29 -08:00
Aaron Klotz
d7962e3bcf ipn/ipnserver, util/winutil: update workaround for os/user.LookupId failures on Windows to reject SIDs from deleted/invalid security principals.
Our current workaround made the user check too lax, thus allowing deleted
users. This patch adds a helper function to winutil that checks that the
uid's SID represents a valid Windows security principal.

Now if `lookupUserFromID` determines that the SID is invalid, we simply
propagate the error.

Updates https://github.com/tailscale/tailscale/issues/869

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2022-02-02 15:01:28 -07:00
Brad Fitzpatrick
6eed2811b2 wgengine/netstack: start supporting different SSH users
Updates #3802

Change-Id: I44de6897e36b1362cd74c9b10c9cbfeb9abc3dbc
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-02-02 13:58:31 -08:00
Maisem Ali
e3dccfd7ff chirp: handle multiline responses from BIRD
Also add tests to verify the parsing logic.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-02-02 13:48:07 -08:00
Brad Fitzpatrick
fa612c28cf cmd/derper: make --stun default to on, flesh out flag docs
Change-Id: I49e80c61ab19e78e4c8b4bc9012bb70cfe3bfa75
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-31 17:42:45 -08:00
Aaron Bieber
e5cd765e00 net/dns/resolvd: properly handle not having "search" entries
This prevents adding an empty "search" line when no search domains are set.

Signed-off-by: Aaron Bieber <aaron@bolddaemon.com>
2022-01-31 15:11:28 -08:00
Brad Fitzpatrick
bd90781b34 ipn/ipnlocal, wgengine/netstack: use netstack for peerapi server
We're finding a bunch of host operating systems/firewalls interact poorly
with peerapi. We either get ICMP errors from the host or users need to run
commands to allow the peerapi port:

https://github.com/tailscale/tailscale/issues/3842#issuecomment-1025133727

... even though the peerapi should be an internal implementation detail.

Rather than fight the host OS & firewalls, this change handles the
server side of peerapi entirely in netstack (except on iOS), so it
never makes its way to the host OS where it might be messed with. Two
main downsides are:

1) netstack isn't as fast, but we don't really need speed for peerapi.
   And actually, with fewer trips to/from the kernel, we might
   actually make up for some of the netstack performance loss by
   staying in userspace.

2) tcpdump / Wireshark etc packet captures will no longer see the peerapi
   traffic. Oh well. Crawshaw's been wanting to add packet capture server
   support to tailscaled, so we'll probably do that sooner now.

A future change might also then use peerapi for the client-side
(except on iOS).

Updates #3842 (probably fixes, as well as many exit node issues I bet)

Change-Id: Ibc25edbb895dc083d1f07bd3cab614134705aa39
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-31 14:20:08 -08:00
Josh Bleecher Snyder
e45d51b060 logtail: add a few new methods to PublicID
These are for use in our internal systems.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-01-31 14:14:10 -08:00
Brad Fitzpatrick
730aa1c89c derp/derphttp, wgengine/magicsock: prefer IPv6 to DERPs when IPv6 works
Fixes #3838

Change-Id: Ie47a2a30c7e8e431512824798d2355006d72fb6a
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-29 15:55:54 -08:00
David Anderson
f5ec916214 cmd/derper: disable TLS 1.0 and 1.1.
Updates tailscale/corp#3568

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-01-28 01:13:30 +00:00
Brad Fitzpatrick
69392411d9 .github/workflows: add some iOS CI coverage
Updates #3812

Change-Id: Ia779c6a2e9a0fd02418bf5479fdb76d4c80c55a4
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-27 15:57:49 -08:00
Brad Fitzpatrick
02bdc654d5 cmd/tailscale: fix up --reset, again
Also fix a somewhat related printing bug in the process where
some paths would print "Success." inconsistently even
when there otherwise was no output (in the EditPrefs path)

Fixes #3830
Updates #3702 (which broke it once while trying to fix it)

Change-Id: Ic51e14526ad75be61ba00084670aa6a98221daa5
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-27 15:54:33 -08:00
Brad Fitzpatrick
70d71ba1e7 cmd/derpprobe: check derper TLS certs too
Change-Id: If8c48e012b294570ebbb1a46bacdc58fafbfbcc5
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-27 10:09:04 -08:00
Brad Fitzpatrick
1af26222b6 go.mod: bump netstack, switch to upstream netstack
Now that Go 1.17 has module graph pruning
(https://go.dev/doc/go1.17#go-command), we should be able to use
upstream netstack without breaking our private repo's build
that then depends on the tailscale.com Go module.

This is that experiment.

Updates #1518 (the original bug to break out netstack to own module)
Updates #2642 (this updates netstack, but doesn't remove workaround)

Change-Id: I27a252c74a517053462e5250db09f379de8ac8ff
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-26 11:30:03 -08:00
Brad Fitzpatrick
857cd6c0d7 ipn/ipnstate: add TailnetName to status
RELNOTE=tailscale status --json | jq .TailnetName

Fixes tailscale/corp#3665

Change-Id: I85de027ba2781eb31ee1e0c5ab913b0dfa5b4c86
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-26 10:08:39 -08:00
Xe Iaso
ae525a7394 scripts/installer: add Centos Stream 9 support (#3818)
Blocked on package server support being deployed

Signed-off-by: Xe <xe@tailscale.com>
2022-01-26 10:49:32 -05:00
David Anderson
7a18fe3dca wgengine/magicsock: make debugUseDerpRoute an opt.Bool.
Can still be constant, just needs the extra methods.

Fixes #3812

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-01-25 17:25:08 -08:00
David Anderson
c2059d5b8a words: fallout from mudpuppy-gate.
Salamanders also have no scales. I checked the interweb, and there
doesn't seem to be any subspecies that would let us claim that
*some* salamanders are scaley.

But they are tailey, for sure.

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-01-26 01:05:49 +00:00
Brad Fitzpatrick
ca774c3249 ipn/ipnserver: add TS_PERMIT_CERT_UID envknob to give webservers cert access
So you can run Caddy etc as a non-root user and let it have access to
get certs.

Updates caddyserver/caddy#4541

Change-Id: Iecc5922274530e2b00ba107d4b536580f374109b
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-25 12:12:41 -08:00
David Anderson
508f332bb2 cmd/derper: export TLS vars with derper_ prefix, not stun_
Updates tailscale/corp#3568

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-01-25 18:57:30 +00:00
davideger
f31546809f cmd/tailscale: propagate tailscaled 403s as AccessDeniedErrors
So Linux/etc CLI users get helpful advice to run tailscale
with --operator=$USER when they try to 'tailscale file {cp,get}'
but are mysteriously forbidden.

Signed-off-by: David Eger <eger@google.com>
Signed-off-by: David Eger <david.eger@gmail.com>
2022-01-25 09:58:21 -08:00
Brad Fitzpatrick
f3c0023add wgengine/netstack: add an SSH server experiment
Disabled by default.

To use, run tailscaled with:

    TS_SSH_ALLOW_LOGIN=you@bar.com

And enable with:

    $ TAILSCALE_USE_WIP_CODE=true tailscale up --ssh=true

Then ssh [any-user]@[your-tailscale-ip] for a root bash shell.
(both the "root" and "bash" part are temporary)

Updates #3802

Change-Id: I268f8c3c95c8eed5f3231d712a5dc89615a406f0
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-24 19:14:13 -08:00
Brad Fitzpatrick
41fd4eab5c envknob: add new package for all the strconv.ParseBool(os.Getenv(..))
A new package can also later record/report which knobs are checked and
set. It also makes the code cleaner & easier to grep for env knobs.

Change-Id: Id8a123ab7539f1fadbd27e0cbeac79c2e4f09751
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-24 11:51:23 -08:00
Brad Fitzpatrick
6feb8f4c51 net/dns: log why resolved does not look like it's on use [Linux]
Updates #3742
Updates #3531

Change-Id: I9fc7fa0f4bcab1cf8001ba92408c660a5b25f105
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-24 09:14:53 -08:00
David Anderson
ff3442d92d cmd/derper: record TLS versions used for requests.
Surveying the fleet prior to turning off old/unused/insecure
TLS versions.

Updates tailscale/corp#3615

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-01-22 02:35:55 +00:00
Maisem Ali
0ada42684b Makefile: update make spk target to use the new go spk builder
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-01-21 12:27:00 -08:00
David Anderson
7ba874d7f1 words: correct inexcusable oversight re: mudpuppies.
Mudpuppies are salamanders, and as such have tails but no scales.
The management apologizes for the error.

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-01-20 21:12:09 +00:00
Brad Fitzpatrick
92dfaf53bb cmd/tailscaled: include Go runtime metrics in /debug/metrics
Fixes #3772

Change-Id: I237ea23268664d99e83d27890146018b04474556
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-20 09:49:54 -08:00
Aaron Bieber
411c6c316c net/dns/resolvd: store nameservers
Currently only search domains are stored. This was an oversight
(under?) on my part.

As things are now, when MagicDNS is on and "Override local DNS" is
off, the dns forwarder has to timeout before names resolve. This
introduces a pretty annoying lang that makes everything feel
extremely slow. You will also see an error: "upstream nameservers
not set".

I tested with "Override local DNS" on and off. In both situations
things seem to function as expected (and quickly).

Signed-off-by: Aaron Bieber <aaron@bolddaemon.com>
2022-01-19 21:17:31 -08:00
Brad Fitzpatrick
c64af5e676 wgengine/netstack: clear TCP ECN bits before giving to gvisor
Updates #2642

Change-Id: Ic219442a2656dd9dc99ae1dd91e907fd3d924987
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-19 20:09:24 -08:00
Josh Bleecher Snyder
de4696da10 wgengine/magicsock: fix deadlock on shutdown
This fixes a deadlock on shutdown.
One goroutine is waiting to send on c.derpRecvCh before unlocking c.mu.
The other goroutine is waiting to lock c.mu before receiving from c.derpRecvCh.

#3736 has a more detailed explanation of the sequence of events.

Fixes #3736

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-01-19 14:39:28 -08:00
Brad Fitzpatrick
390490e7b1 net/packet: fix typo in comment
Change-Id: Ia666609fde18db44bf38d4e656f490fc372ac3b6
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-19 12:59:13 -08:00
Joe Tsai
3e50a265be go.toolchain.rev: pick up new bufio.Writer API for Go1.18 (#3768)
25fe91a25c

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2022-01-19 12:40:56 -08:00
Brad Fitzpatrick
185825df11 wgengine/netstack: add a missing refcount decrement after packet injection
Fixes #3762
Updates #3745 (probably fixes?)

Change-Id: I1d3f0590fd5b8adfbc9110bc45ff717bb9e79aae
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-19 12:28:43 -08:00
Brad Fitzpatrick
790e41645b wgengine/netstack: add an Impl.Close method for tests
Change-Id: Idbb3fd6d749d3e4effdf96de77a1106584822fef
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-19 12:28:43 -08:00
Brad Fitzpatrick
166fe3fb12 wgengine/netstack: add missing error logging in a RST case
Updates #2642

Change-Id: I9f2f8fd28fc980208b0739eb9caf9db7b0977c09
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-18 14:15:32 -08:00
Brad Fitzpatrick
6be48dfcc6 wgengine/netstack: fix netstack ping timeout on darwin
-W is milliseconds on darwin, not seconds, and empirically it's
milliseconds after a 1 second base.

Change-Id: I2520619e6699d9c505d9645ce4dfee4973555227
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-18 08:00:30 -08:00
David Anderson
96f008cf87 control/controlhttp: package to get a controlbase.Conn over HTTP(S).
Updates #3488

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-01-17 23:52:27 +00:00
David Anderson
d5a7eabcd0 control/controlbase: enable asynchronous client handshaking.
With this change, the client can obtain the initial handshake message
separately from the rest of the handshake, for embedding into another
protocol. This enables things like RTT reduction by stuffing the
handshake initiation message into an HTTP header.

Similarly, the server API optionally accepts a pre-read Noise initiation
message, in addition to reading the message directly off a net.Conn.

Updates #3488

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-01-17 23:52:27 +00:00
David Anderson
6cd180746f control/controlbase: rename from control/noise.
Updates #3488

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-01-17 23:52:27 +00:00
Jay Stapleton
02461ea459 Update installer.sh 2022-01-17 11:37:05 -05:00
Josh Bleecher Snyder
8cf1af8a07 tstime/rate: deflake TestLongRunningQPS
This test set the bar too high.
Just a couple of missed timers was enough to fail.
Change the test to more of a sanity check.
While we're here, run it for just 1s instead of 5s.

Prior to this change, on a 13" M1 MPB, with

stress -p 512 ./rate.test -test.run=QPS

I saw 90%+ failures.

After this change, I'm at 30k runs with no failures yet.

Fixes #3733

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-01-13 16:48:29 -08:00
David Anderson
463b3e8f62 net/dnscache: use tls.Conn.HandshakeContext.
Go 1.17 added a HandshakeContext func to take care of timeouts during
TLS handshaking, so switch from our homegrown goroutine implementation
to the standard way.

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-01-13 23:01:29 +00:00
David Anderson
a9da6b73a8 net/dnscache: don't cancel the TLS context before writing to the result channel.
Cancelling the context makes the timeout goroutine race with the write that
reports a successful TLS handshake, so you can end up with a successful TLS
handshake that mysteriously reports that it timed out after ~0s in flight.

The context is always canceled and cleaned up as the function exits, which
happens mere microseconds later, so just let function exit clean up and
thereby avoid races.

Signed-off-by: David Anderson <danderson@tailscale.com>
2022-01-13 23:01:29 +00:00
Josh Bleecher Snyder
9fe5ece833 logtail: cap the buffer size in encodeText
This started as an attempt to placate GitHub's code scanner,
but it's also probably generally a good idea.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-01-13 14:37:27 -08:00
Brad Fitzpatrick
5404a0557b wgengine/magicsock: remove a per-DERP-packet map lookup in common case
Updates #150

Change-Id: Iffb6eccbe7ca97af97d29be63b7e37d487b3ba28
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-13 14:13:45 -08:00
Brad Fitzpatrick
5a317d312d wgengine/magicsock: enable DERP Return Path Optimization (DRPO)
Turning this on at the beginning of the 1.21.x dev cycle, for 1.22.

Updates #150

Change-Id: I1de567cfe0be3df5227087de196ab88e60c9eb56
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-13 14:12:09 -08:00
Brad Fitzpatrick
c6c39930cc wgengine/magicsock: fix lock ordering deadlock with derphttp
Fixes #3726

Change-Id: I32631a44dcc1da3ae47764728ec11ace1c78190d
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-13 13:47:51 -08:00
Josh Bleecher Snyder
a076aaecc6 cmd/tailscale: use html/template for synoTokenRedirect
The GitHub code scanner flagged this as a security vulnerability.
I don't believe it was, but I couldn't convince myself of it 100%.
Err on the safe side and use html/template to generate the HTML,
with all necessary escaping.

Fixes tailscale/corp#2698

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-01-13 13:32:45 -08:00
Denton Gentry
27da7fd5cb VERSION.txt: This is 1.21.
Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2022-01-12 17:38:49 -08:00
Brad Fitzpatrick
a7da236d3d tailcfg: no-op bump of MapRequest.Version
So 1.18 and 1.20 don't have the same.

Change-Id: Ib2cac7c11eb37d9a0c2fcb66630f1cae619a97f4
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-12 15:20:52 -08:00
Brad Fitzpatrick
a93937abc3 wgengine/netstack: make userspace ping work when tailscaled has CAP_NET_RAW
Updates #3710

Change-Id: Ief56c7ac20f5f09a2f940a1906b9efbf1b0d6932
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-12 14:23:39 -08:00
Maisem Ali
26d4ccb816 scripts/installer.sh: add support to use the unstable track.
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-01-12 13:41:11 -08:00
Maisem Ali
9e8a432146 cmd/tailscale/cli/web: fix typo where the html template data was being
replaced instead of being appended to.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-01-12 12:41:37 -08:00
Brad Fitzpatrick
24a04d07d1 net/dns/resolver: handle tabs as whitespace when ExitDNS parses resolv.conf
On Synology, the /etc/resolv.conf has tabs in it, which this
resolv.conf parser (we have two, sigh) didn't handle.

Updates #3710

Change-Id: I86f8e09ad1867ee32fa211e85c382a27191418ea
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-12 12:38:48 -08:00
Brad Fitzpatrick
51bc9a6d9d net/netns: remove a useless probe of the "ip" command
We stopped using it in 1.18.

Change-Id: If5adf1d99275286a89e2a05f0bce5193d9f6e5e3
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-11 17:47:06 -08:00
Brad Fitzpatrick
e6626366a2 cmd/tailscale: let 'tailscale up --reset' do a pref edit
The --reset shouldn't imply that a Backend.Start is necessary.  With
this, it can do a Backend.EditPrefs instead, which then doesn't do all
the heavy work that Start does. Also, Start on Windows behaves
slightly differently than Linux etc in some cases because of tailscaled
running in client mode on Windows (where the GUI supplies the prefs).

Fixes #3702

Change-Id: I75c9f08d5e0052bf623074030a3a7fcaa677abf6
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-11 12:59:36 -08:00
Brad Fitzpatrick
8df3fa4638 net/dns: make WSL network configuration opt-in for now
Tailscale seems to be breaking WSL configurations lately.  Until we
understand what changed, turn off Tailscale's involvement by default
and make it opt-in.

Updates #2815

Change-Id: I9977801f8debec7d489d97761f74000a4a33f71b
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-11 10:10:21 -08:00
Brad Fitzpatrick
66f6efa8cb scripts: install gnupg deb, pass --yes to apt-get
Fixes #3685
Fixes #3528
Fixes #3649

Change-Id: Ie029fca6cf3d07a77d228e9591ec1c1c828e68af
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-11 09:44:59 -08:00
Aaron Bieber
189f359609 net/dns: teach OpenBSD's manager to talk to resolvd(8). (#2789)
OpenBSD 6.9 and up has a daemon which handles nameserver configuration. This PR
teaches the OpenBSD dns manager to check if resolvd is being used. If it is, it
will use the route(8) command to tell resolvd to add the Tailscale dns entries
to resolv.conf

Signed-off-by: Aaron Bieber <aaron@bolddaemon.com>
2022-01-11 08:45:50 -08:00
Brad Fitzpatrick
b8ad90c2bf cmd/derper: in manual cert mode, don't discard error from VerifyHostname
Updates #3701

Change-Id: If8ca5104bd8221c99cc390ca49ee3401aff09b62
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-11 08:40:42 -08:00
dependabot[bot]
b1b0fd119b .github: Bump actions/setup-go from 2.1.4 to 2.1.5
Bumps [actions/setup-go](https://github.com/actions/setup-go) from 2.1.4 to 2.1.5.
- [Release notes](https://github.com/actions/setup-go/releases)
- [Commits](https://github.com/actions/setup-go/compare/v2.1.4...v2.1.5)

---
updated-dependencies:
- dependency-name: actions/setup-go
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>
2022-01-10 16:39:26 -08:00
Josh Bleecher Snyder
1dc1c8b709 .github/workflows: upgrade to setup-go@v2
The rest of our workflows use v2.1.4.
For reasons I do not understand, we must set GOPATH here.
Maybe the GitHub Action builds come with GOPATH already set?

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-01-10 16:19:06 -08:00
Josh Bleecher Snyder
408522ddad go.toolchain.rev: add update script
Also go.toolchain.branch.

Both migrated from the corp repo.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2022-01-10 14:55:04 -08:00
Brad Fitzpatrick
1ffc21ad71 go.toolchain.rev: update to Go 1.17.6
Co-authored-by: Josh Bleecher Snyder <josh@tailscale.com>
Change-Id: I572b2b36aa8acb53ea7fde638aa89a7510c84915
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-10 13:22:18 -08:00
dependabot[bot]
dee0833b27 .github: Bump actions/upload-artifact from 2.2.4 to 2.3.1
Bumps [actions/upload-artifact](https://github.com/actions/upload-artifact) from 2.2.4 to 2.3.1.
- [Release notes](https://github.com/actions/upload-artifact/releases)
- [Commits](https://github.com/actions/upload-artifact/compare/v2.2.4...v2.3.1)

---
updated-dependencies:
- dependency-name: actions/upload-artifact
  dependency-type: direct:production
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <support@github.com>
2022-01-10 12:58:41 -08:00
Brad Fitzpatrick
b03170b901 ipn/ipnserver: provide means of setting debug env vars on Windows
Fixes #3688

Change-Id: I2f88ca32bf764e2b084fe544d821c43b6a20ffa5
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-10 10:48:18 -08:00
Brad Fitzpatrick
c5243562d7 version: bump date
Change-Id: Ib314eccff199fc0854553216762737ce6af19586
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-07 12:40:23 -08:00
Brad Fitzpatrick
1a4e8da084 wgengine/netstack: fake pings through netstack on Android too
Every OS ping binary is slightly different. Adjust for Android's.

Updates #1738

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-07 10:05:32 -08:00
Maisem Ali
138662e248 Dockerfile.base: update to alpine:3.15
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-01-07 07:33:25 -08:00
Brad Fitzpatrick
1b426cc232 wgengine/netstack: add env knob to turn on netstack debug logs
Except for the super verbose packet-level dumps. Keep those disabled
by default with a const.

Updates #2642

Change-Id: Ia9eae1677e8b3fe6f457a59e44896a335d95d547
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-06 16:59:35 -08:00
Brad Fitzpatrick
8d0ed1c9ba net/dns/resolver: on Android, make ExitDNS use net package for DNS
Like Windows.

Updates #1738

Change-Id: I9f26bc58ce7e760c749786fbe5d9952c99eeb91c
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-06 16:17:24 -08:00
Brad Fitzpatrick
e68d87eb44 ipn: rename SetRunExitNode to SetAdvertiseExitNode
From Maisem's code review feedback where he mashed the merge
button by mistake.

Change-Id: I55abce036a6c25dc391250514983125dda10126c
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-06 16:17:03 -08:00
Brad Fitzpatrick
2cfc96aa90 ipn: add methods on Prefs to get/set exit node being advertised
This code was copied in a few places (Windows, Android), so unify it
and add tests.

Change-Id: Id0510c0f5974761365a2045279d1fb498feca11e
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-06 16:14:14 -08:00
Brad Fitzpatrick
addda5b96f wgengine/magicsock: fix watchdog timeout on Close when IPv6 not available
The blockForeverConn was only using its sync.Cond one side. Looks like it
was just forgotten.

Fixes #3671

Change-Id: I4ed0191982cdd0bfd451f133139428a4fa48238c
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-06 13:24:59 -08:00
Brad Fitzpatrick
64c2657448 cmd/printdep: add flag to print out Go toolchain tarball URL
Updates #3669

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-06 08:44:17 -08:00
Brad Fitzpatrick
3690bfecb0 ipn/ipnlocal: fix cert fetching on macOS GUI platforms
And clarify the directory they get written to when under the sandbox.

Fixes #3667

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-06 07:59:20 -08:00
Brad Fitzpatrick
28bf53f502 wgengine/magicsock: reduce disco ping heartbeat aggressiveness a bit
Bigger changes coming later, but this should improve things a bit in
the meantime.

Rationale:

* 2 minutes -> 45 seconds: 2 minutes was overkill and never considered
  phones/battery at the time. It was totally arbitrary. 45 seconds is
  also arbitrary but is less than 2 minutes.

* heartbeat from 2 seconds to 3 seconds: in practice this meant two
  packets per second (2 pings and 2 pongs every 2 seconds) because the
  other side was also pinging us every 2 seconds on their own.
  That's just overkill. (see #540 too)

So in the worst case before: when we sent a single packet (say: a DNS
packet), we ended up sending 61 packets over 2 minutes: the 1 DNS
query and then then 60 disco pings (2 minutes / 2 seconds) & received
the same (1 DNS response + 60 pongs).  Now it's 15. In 1.22 we plan to
remove this whole timer-based heartbeat mechanism entirely.

The 5 seconds to 6.5 seconds change is just stretching out that
interval so you can still miss two heartbeats (other 3 + 3 seconds
would be greater than 5 seconds). This means that if your peer moves
without telling you, you can have a path out for 6.5 seconds
now instead of 5 seconds before disco finds a new one. That will also
improve in 1.22 when we start doing UDP+DERP at the same time
when confidence starts to go down on a UDP path.

Updates #3363

Change-Id: Ic2314bbdaf42edcdd7103014b775db9cf4facb47
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-05 14:05:16 -08:00
Brad Fitzpatrick
c8b63a409e cmd/hello: also redirect https://hello.ipn.dev to hello.ts.net
I apparently only did HTTP before, not HTTPS.

Updates tailscale/corp#1327

Change-Id: I7d5265a0a25fcab5b142c8c3f21a0920f6cae39f
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-04 19:45:02 -08:00
Brad Fitzpatrick
a201b89e4a wgengine/magicsock: reconnect to DERP when its definition changes
Change-Id: I7c560feb9e4a6e155a35ec764a68354f19f694e4
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-04 15:19:21 -08:00
Brad Fitzpatrick
506c727e30 ipnlocal, net/{dns,tsaddr,tstun}, wgengine: support MagicDNS on IPv6
Fixes #3660

RELNOTE=MagicDNS now works over IPv6 when CGNAT IPv4 is disabled.

Change-Id: I001e983df5feeb65289abe5012dedd177b841b45
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-04 14:37:22 -08:00
Brad Fitzpatrick
e2d9c99e5b cmd/hello: migrate to hello.ts.net as the hostname
But still support hello.ipn.dev for a bit.

Updates tailscale/corp#1327

Change-Id: Iab59cca0b260d69858af16f4e42677e54f9fe54a
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-04 09:50:47 -08:00
Maisem Ali
01a9906bf8 tool/go: add wrapper to download and use go.toolchain.rev go version.
Also update build_dist.sh and build_docker.sh to use the wrapper.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-01-04 09:45:29 -08:00
Brad Fitzpatrick
2aeb93003f derp: add metrics to server got pings, sent pongs
Updates #3652

Change-Id: I1d350bcaee39ea36b0c71912028624d18fb541b4
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-03 14:04:20 -08:00
Brad Fitzpatrick
2513d2d728 net/{neterror,dns/resolver}: move PacketWasTruncated to neterror from DNS code
And delete the unused code in net/dns/resolver/neterr_*.go.

Change-Id: Ibe62c486bacce2733eb9968c96a98cbbdb2758bd
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-03 14:03:30 -08:00
Maisem Ali
dd45bba76b tsnet: add Start method to allow connecting to the tailnet without
requiring a call to Dial/Listen.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-01-03 11:56:54 -08:00
Brad Fitzpatrick
ebdd25920e go.toolchain.rev: add Go toolchain rev, tool to print it out
Updates tailscale/corp#3385

Change-Id: Ia0e285a0ae836744539c97ff6eff207588159688
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2022-01-03 11:56:27 -08:00
Maisem Ali
431329e47c build_docker.sh: add env overrides
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2022-01-03 10:59:55 -08:00
Brad Fitzpatrick
7d9b1de3aa netcheck,portmapper,magicsock: ignore some UDP write errors on Linux
Treat UDP send EPERM errors as a lost UDP packet, not something super
fatal. That's just the Linux firewall preventing it from going out.

And add a leaf package net/neterror for that (and future) policy that
all three packages can share, with tests.

Updates #3619

Change-Id: Ibdb838c43ee9efe70f4f25f7fc7fdf4607ba9c1d
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-31 08:27:21 -08:00
Brad Fitzpatrick
2c94e3c4ad wgengine/magicsock: don't unconditionally close DERP connections on rebind
Only if the source address isn't on the currently active interface or
a ping of the DERP server fails.

Updates #3619

Change-Id: I6bf06503cff4d781f518b437c8744ac29577acc8
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-29 13:21:05 -08:00
Brad Fitzpatrick
04c2c5bd80 net/interfaces: define DefaultRouteInterface and State.DefaultRouteInterface
It was pretty ill-defined before and mostly for logging. But I wanted
to start depending on it, so define what it is and make Windows match
the other operating systems, without losing the log output we had
before. (and add tests for that)

Change-Id: I0fbbba1cfc67a265d09dd6cb738b73f0f6005247
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-29 12:13:15 -08:00
Brad Fitzpatrick
96cab21383 cmd/tailscale: add debug restun, rebind subcommands
In the hidden debug menu.

Change-Id: I20213f1f4e2290d36f9ff561bac0cc767400d5fd
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-28 21:26:45 -08:00
Brad Fitzpatrick
63d9c7b9b3 derp: add Client.LocalAddr method
So magicsock can later ask a DERP connection whether its source IP
would've changed if it reconnected.

Updates #3619

Change-Id: Ibc8810340c511d6786b60c78c1a61c09f5800e40
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-28 15:13:53 -08:00
Brad Fitzpatrick
b09000ad5d ipn/localapi: add debug handler to Rebind, ReSTUN magicsock
And more later probably.

Updates #3619

Change-Id: Ia4cba34a7c0dcce4d2eddec8aae17f32b51c207f
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-28 15:13:44 -08:00
Brad Fitzpatrick
eb26c081b1 net/dns: bound time we wait on restarting systemd-resolved in another place
Fixes #3629
Updates #3537

Change-Id: I5d4b6acfcfdf0e3efcf6eb49c5e6cf4521e4baed
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-28 11:09:07 -08:00
Maisem Ali
44937b59e7 tsnet: add Dial method to allow dialing out to the tailnet.
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2021-12-28 10:19:36 -08:00
Brad Fitzpatrick
535b925d1b derp/derphttp: add Client.Ping, SendPing methods
Continuing work in 434af15a04, to make it possible for magicsock to
probe whether a DERP server is still there.

Updates #3619

Change-Id: I366a77c27e93b876734e64f445b85ef01eb590f2
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-28 09:52:10 -08:00
Brad Fitzpatrick
434af15a04 derp: support client->server ping (and server->client pong)
In prep for a future change to have client ping derp connections
when their state is questionable, rather than aggressively tearing
them down and doing a heavy reconnect when their state is unknown.

We already support ping/pong in the other direction (servers probing
clients) so we already had the two frame types, but I'd never finished
this direction.

Updates #3619

Change-Id: I024b815d9db1bc57c20f82f80f95fb55fc9e2fcc
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-27 14:49:50 -08:00
Brad Fitzpatrick
bc537adb1a tailcfg: add Hostinfo.HowUnequal method
Change-Id: I80ee49c2ab581feccc4aa6ab47bc3c8392d9989d
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-23 09:04:53 -08:00
Brad Fitzpatrick
0aa4c6f147 net/dns/resolver: add debug HTML handler to see what DNS traffic was forwarded
Change-Id: I6b790e92dcc608515ac8b178f2271adc9fd98f78
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-21 14:32:36 -08:00
Brad Fitzpatrick
ae319b4636 wgengine/magicsock: add HTML debug handler to see magicsock state
Change-Id: Ibc46f4e9651e1c86ec6f5d139f5e9bdc7a488415
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-21 14:26:52 -08:00
Brad Fitzpatrick
c7f5bc0f69 wgengine/magicsock: add metrics for sent disco messages
We only tracked the transport type (UDP vs DERP), not what they were.

Change-Id: Ia4430c1c53afd4634e2d9893d96751a885d77955
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-20 09:39:38 -08:00
Brad Fitzpatrick
81bc812402 Dockerfile: remove long-obsolete -tags=xversion
That build tag hasn't been used since 5088af68cf
(June 2nd, 2021, for 1.10.0)

Change-Id: Ib6093a975505339872a0dc663fff9fc09c13bbc0
2021-12-19 18:15:09 -08:00
Brad Fitzpatrick
0848b36dd2 net/dns/resolver: add metrics to PTR lookup misses
Updates tailscale/corp#3326

Change-Id: I58077d889a3b58ef0633267c92ffb265686ce152
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-19 09:50:16 -08:00
Brad Fitzpatrick
39f22a357d net/dns/resolver: send NXDOMAIN to iOS DNS-SD/Bonjour queries
Don't just ignore them. See if this makes them calm down.

Updates #3363

Change-Id: Id1d66308e26660d26719b2538b577522a1e36b63
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-18 19:24:19 -08:00
Brad Fitzpatrick
394c9de02b net/dns/resolver: add nameFromQuery benchmark
To convince me it's not as alloc-y as it looks.

Change-Id: I503a0cc267268a23d2973dfde9833c420be4e868
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-18 19:03:45 -08:00
Brad Fitzpatrick
c7052154d5 net/dns/resolver: fix the subject in a func comment
Change-Id: I519268c20dbd2c2da92da565839d3c1c84612dcc
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-18 15:11:01 -08:00
Brad Fitzpatrick
3dedcd1640 logpolicy, ipn/ipnserver: connect to logtail via tailscaled when needed
This is for use by the Windows GUI client to log via when an
exit node is in use, so the logs don't go out via the exit node and
instead go directly, like tailscaled's. The dialer tried to do that
in the unprivileged GUI by binding to a specific interface, but the
"Internet Kill Switch" installed by tailscaled for exit nodes
precludes that from working and instead the GUI fails to dial out.
So, go through tailscaled (with a CONNECT request) instead.

Fixes tailscale/corp#3169

Change-Id: I17a8efdc1d4b8fed53a29d1c19995592b651b215
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-17 14:40:26 -08:00
Brad Fitzpatrick
5a9914a92f wgengine/netstack: don't remove 255.255.255.255/32 from netstack
The intent of the updateIPs code is to add & remove IP addresses
to netstack based on what we get from the netmap.

But netstack itself adds 255.255.255.255/32 apparently and we always
fight it (and it adds it back?). So stop fighting it.

Updates #2642 (maybe fixes? maybe.)

Change-Id: I37cb23f8e3f07a42a1a55a585689ca51c2be7c60
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-16 14:15:07 -08:00
Joe Tsai
66164b9307 api: document API endpoint to manipulate keys (#3544)
The new /keys endpoint allows you to list API and machine auth keys.
You can also create machine auth key.
It currently does not support creating another API key.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2021-12-16 13:50:14 -08:00
Brad Fitzpatrick
40e2b312b6 ipn/ipnserver, logpolicy: move Windows disk logging up earlier
This moves the Windows-only initialization of the filelogger into
logpolicy. Previously we only did it when babysitting the tailscaled
subprocess, but this meant that log messages from the service itself
never made it to disk. Examples that weren't logged to disk:

* logtail unable to dial out,
* DNS flush messages from the service
* svc.ChangeRequest messages (#3581)

This is basically the same fix as #3571 but staying in the Logf type,
and avoiding build-tagged file (which wasn't quite a goal, but
happened and seemed nice)

Fixes #3570

Co-authored-by: Aaron Klotz <aaron@tailscale.com>
Change-Id: Iacd80c4720b7218365ec80ae143339d030842702
2021-12-16 12:33:04 -08:00
Brad Fitzpatrick
689426d6bc cmd/tailscaled: log Windows service change requests
And add a little comment.

Change-Id: If0bedf8aefd8d528149548fba829e7a9a8b2e114
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-16 12:24:05 -08:00
Josh Bleecher Snyder
add6dc8ccc ipn/ipnlocal: make TestShrinkDefaultRoute hermetic
Make shrinkDefaultRoute a pure function.
Instead of calling interfaceRoutes, accept that information as parameters.
Hard-code those parameters in TestShrinkDefaultRoute.

Fixes #3580

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-12-16 11:31:20 -08:00
Jay Stapleton
894693f352 scripts/installer.sh fix APT_SYSTEMCTL_START error
fix error: 'sh: 411: APT_SYSTEMCTL_START: parameter not set' on certain debian distributions

Signed-off-by: Jay Stapleton <jay@tailscale.com>
2021-12-16 13:55:11 -05:00
Josh Bleecher Snyder
4512e213d5 cmd/tailscale: improve ping error message when logged out
Refactor out the pretty status printing code from status, use it in ping.

Fixes #3549

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-12-16 10:46:18 -08:00
Brad Fitzpatrick
8f43ddf1a2 ipn/ipnlocal, health: populate self node's Online bit in tailscale status
One option was to just hide "offline" in the text output, but that
doesn't fix the JSON output.

The next option was to lie and say it's online in the JSON (which then
fixes the "offline" in the text output).

But instead, this sets the self node's "Online" to whether we're in an
active map poll.

Fixes #3564

Change-Id: I9b379989bd14655198959e37eec39bb570fb814a
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-16 10:14:08 -08:00
Josh Bleecher Snyder
681d4897cc tstest/integration: remove t param in testNode methods
testNodes have a reference to a testing.TB via their env.
Use it instead of making the caller pass theirs.
We did this in some methods but not others; finish the job.
This simplifies the call sites.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-12-15 18:06:14 -08:00
Josh Bleecher Snyder
93ae11105d ipn/ipnlocal: clear magicsock's netmap on logout
magicsock was hanging onto its netmap on logout,
which caused tailscale status to display partial
information about a bunch of zombie peers.
After logout, there should be no peers.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-12-15 17:00:08 -08:00
Josh Bleecher Snyder
84a1106fa7 tstest/integration: make -verbose-tailscaled pass -verbose=2 to tailscaled
If you're using -verbose-tailscaled, you're doing in-the-weeds debugging,
so you probably want the verbose output.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-12-15 17:00:08 -08:00
Brad Fitzpatrick
aac974a5e5 ipn/ipnlocal: deflake (mostly) TestStateMachine
I'm sick of this flaking. Even if this isn't the right fix, it
stops the alert fatigue.

Updates #3020

Change-Id: I4001c127d78f1056302f7741adec34210a72ee61
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-15 13:41:06 -08:00
Brad Fitzpatrick
6590fc3a94 wgengine/netstack: remove some logging on forwarding connections
Change-Id: Ib1165b918cd5da38583f8e7d4be8cda54af3c81d
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-15 11:38:25 -08:00
Brad Fitzpatrick
486059589b all: gofmt -w -s (simplify) tests
And it updates the build tag style on a couple files.

Change-Id: I84478d822c8de3f84b56fa1176c99d2ea5083237
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-15 08:43:41 -08:00
Brad Fitzpatrick
59f4f33f60 cmd/tailscaled: fix windows logtail integration
I broke it in 1.17.x sometime while rewiring some logs stuff,
mostly in 0653efb092 (but with a handful
of logs-related changes around that time)

Fixes tailscale/corp#3265

Change-Id: Icb5c07412dc6d55f1d9244c5d0b51dceca6a7e34
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-14 15:03:37 -08:00
Maya Kaczorowski
ac8e69b713 Merge pull request #3330 from tailscale/mayakacz-patch-2
README.md: update platforms
2021-12-13 17:25:02 -08:00
Maya Kaczorowski
0f3b55c299 README.md: update platforms
Update platform support. This matches content in https://tailscale.com/kb/1062/reviewer-guide/#which-platforms-does-it-run-on

Signed-off-by: Maya Kaczorowski <15946341+mayakacz@users.noreply.github.com>
2021-12-13 17:11:07 -08:00
Josh Bleecher Snyder
4691e012a9 tstest/integration: build binaries only once
The existing code relied on the Go build cache to avoid
needless work when obtaining the tailscale binaries.

For non-obvious reasons, the binaries were getting re-linked
every time, which added 600ms or so on my machine to every test.

Instead, build the binaries exactly once, on demand.
This reduces the time to run 'go test -count=5' from 34s to 10s
on my machine.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-12-13 14:38:08 -08:00
Denton Gentry
e133bb570b install.sh: add linuxmint, kali, several more.
After apt install, Kali Linux had not enabled nor started
the tailscaled systemd service. Add a quirks mode to enable
and start it after apt install for debian platforms.

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2021-12-13 11:38:29 -08:00
Brad Fitzpatrick
adc97e9c4d cmd/tailscale: make --accept-routes default true on Windows, macOS GUI
One of the most annoying parts of using the Tailscale CLI on Windows
and the macOS GUI is that Tailscale's GUIs default to running with
"Route All" (accept all non-exitnode subnet routes) but the CLI--being
originally for Linux--uses the Linux default, which is to not accept
subnets.

Which means if a Windows user does, e.g.:

    tailscale up --advertise-exit-node
Or:
    tailscale up --shields-up

... then it'd warn about reverting the --accept-routes option, which the user
never explicitly used.

Instead, make the CLI's default match the platform/GUI's default.

Change-Id: I15c804b3d9b0266e9ca8651e0c09da0f96c9ef8d
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-13 10:33:20 -08:00
Maisem Ali
d24a8f7b5a wgengine/router{windows}: return the output from the firewallTweaker
on error.

While debugging a customer issue where the firewallTweaker was failing
the only message we have is `router: firewall: error adding
Tailscale-Process rule: exit status 1` which is not really helpful.
This will help diagnose firewall tweaking failures.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2021-12-13 10:07:32 -08:00
David Crawshaw
8dbda1a722 scripts/installer.sh: press Y on RHEL
For #3540

Signed-off-by: David Crawshaw <crawshaw@tailscale.com>
2021-12-13 09:48:41 -08:00
Brad Fitzpatrick
cced414c7d net/dns/resolver: add Windows ExitDNS service support, using net package
Updates #1713
Updates #835

Change-Id: Ia71e96d0632c2d617b401695ad68301b07c1c2ec
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-10 20:47:17 -08:00
Brad Fitzpatrick
cab5c46481 net/dns: bound how long we block looking for, restarting systemd-resolved
Fixes #3537

Change-Id: Iba6a3cde75983490d4072b5341f48dbfa2f997c0
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-10 09:58:14 -08:00
Josh Bleecher Snyder
63cd581c3f safesocket: add ConnectionStrategy, provide control over fallbacks
fee2d9fad added support for cmd/tailscale to connect to IPNExtension.
It came in two parts: If no socket was provided, dial IPNExtension first,
and also, if dialing the socket failed, fall back to IPNExtension.

The second half of that support caused the integration tests to fail
when run on a machine that was also running IPNExtension.
The integration tests want to wait until the tailscaled instances
that they spun up are listening. They do that by dialing the new
instance. But when that dial failed, it was falling back to IPNExtension,
so it appeared (incorrectly) that tailscaled was running.
Hilarity predictably ensued.

If a user (or a test) explicitly provides a socket to dial,
it is a reasonable assumption that they have a specific tailscaled
in mind and don't want to fall back to IPNExtension.
It is certainly true of the integration tests.

Instead of adding a bool to Connect, split out the notion of a
connection strategy. For now, the implementation remains the same,
but with the details hidden a bit. Later, we can improve that.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-12-09 15:46:38 -08:00
Josh Bleecher Snyder
a5235e165c tstest/integration: fix running with -verbose-tailscale
Without this fix, any run with -verbose-tailscale fails.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-12-09 15:46:38 -08:00
Josh Bleecher Snyder
c8829b742b all: minor code cleanup
Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-12-09 15:46:38 -08:00
Brad Fitzpatrick
39ffa16853 net/dnscache, net/tsdial: add DNS caching to tsdial UserDial
This is enough to handle the DNS queries as generated by Go's
net package (which our HTTP/SOCKS client uses), and the responses
generated by the ExitDNS DoH server.

This isn't yet suitable for putting on 100.100.100.100 where a number
of different DNS clients would hit it, as this doesn't yet do
EDNS0. It might work, but it's untested and likely incomplete.

Likewise, this doesn't handle anything about truncation, as the
exchanges are entirely in memory between Go or DoH. That would also
need to be handled later, if/when it's hooked up to 100.100.100.100.

Updates #3507

Change-Id: I1736b0ad31eea85ea853b310c52c5e6bf65c6e2a
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-09 11:34:21 -08:00
Brad Fitzpatrick
b59e7669c1 wgengine/netstack: in netstack/hybrid mode, fake ICMP using ping command
Change-Id: I42cb4b9b326337f4090d9cea532230e36944b6cb
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-09 09:30:10 -08:00
Brad Fitzpatrick
21741e111b net/packet: add ICMP6Header, like ICMP4Header
So we can generate IPv6 ping replies.

Change-Id: I79a9a38d8aa242e5dfca4cd15dfaffaea6cb1aee
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-09 09:30:10 -08:00
Brad Fitzpatrick
7b9c7bc42b ipn/ipnstate: remove old deprecated TailAddr IPv4-only field
It's been a bunch of releases now since the TailscaleIPs slice
replacement was added.

Change-Id: I3bd80e1466b3d9e4a4ac5bedba8b4d3d3e430a03
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-09 09:28:23 -08:00
Brad Fitzpatrick
affc4530a2 net/packet: don't make IP6Header.marshalPseudo assume UDP
It will be used for ICMPv6 next, so pass in the proto.

Also, use the ipproto constants rather than hardcoding the mysterious
number.

Change-Id: I57b68bdd2d39fff75f82affe955aff9245de246b
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-08 21:15:46 -08:00
Brad Fitzpatrick
485bcdc951 net/packet: fix doc copy/paste-o
Change-Id: I0aca490b3ccb0c124192afb362a10b19a15a3e2b
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-08 21:12:43 -08:00
Denton Gentry
878a20df29 net/dns: add GetBaseConfig to CallbackRouter.
Allow users of CallbackRouter to supply a GetBaseConfig
implementation. This is expected to be used on Android,
which currently lacks both a) platform support for
Split-DNS and b) a way to retrieve the current DNS
servers.

iOS/macOS also use the CallbackRouter but have platform
support for SplitDNS, so don't need getBaseConfig.

Updates https://github.com/tailscale/tailscale/issues/2116
Updates https://github.com/tailscale/tailscale/issues/988

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2021-12-08 16:49:11 -08:00
Brad Fitzpatrick
a28d280b95 cmd/tailscaled: move start-up failure logging to one place
The caller of func run said:

    // No need to log; the func already did

But that wasn't true. Some return paths didn't log.

So instead, return rich errors and have func main do the logging,
so we can't miss anything in the future.

Prior to this, safesocket.Listen for instance was causing tailscaled
to os.Exit(1) on failure without any clue as to why.

Change-Id: I9d71cc4d73d0fed4aa1b1902cae199f584f25793
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-08 15:13:39 -08:00
David Anderson
9f867ad2c5 .github/dependabot.yml: disable eager updates for Go.
Given our development cycle, we'll instead do big-bang updates
after every release, to give time for all the updates to soak in
unstable.

This does _not_ disable dependabot security-critical PRs.

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-12-08 10:37:03 -08:00
Brad Fitzpatrick
c0701b130d ipn/ipnstate, cmd/tailscale: add Online bool to tailscale status & --json
Fixes #3533

Change-Id: I2f6f0d712cf3f987fba1c15be74cdb5c8d565f04
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-08 09:34:15 -08:00
Arnaud Dezandee
656809e4ee cmd/derper: allow http port configuration
Signed-off-by: Arnaud Dezandee <dezandee.arnaud@gmail.com>
2021-12-08 08:58:30 -08:00
root
e34ba3223c version/distro: report TrueNAS Scale as "truenas"
TrueNAS Scale is based on Debian Linux

Signed-off-by: Todd Neal <todd@tneal.org>
2021-12-07 21:04:58 -08:00
Todd Neal
c18dc57861 ipn/{ipnserver,ipnlocal}: support incoming Taildrop on TrueNAS
Signed-off-by: Todd Neal <todd@tneal.org>
2021-12-07 21:04:58 -08:00
Denton Gentry
ffb16cdffb cmd/tailscale: add --json for up
Print JSON to stdout containing everything needed for
authentication.

{
  "AuthURL": "https://login.tailscale.com/a/0123456789",
  "QR": "data:image/png;base64,iV...QmCC",
  "BackendState": "NeedsLogin"
}
{
  "BackendState": "Running"
}

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2021-12-06 21:17:15 -08:00
Brad Fitzpatrick
d3d503d997 ipn/ipnlocal: add HTTP/2 h2c server support to peerapi on non-mobile platforms
To make ExitDNS cheaper.

Might not finish client-side support in December before 1.20, but at
least server support can start rolling out ahead of clients being
ready for it.

Tested with curl against peerapi.

Updates #1713

Change-Id: I676fed5fb1aef67e78c542a3bc93bddd04dd11fe
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-06 16:39:14 -08:00
Brad Fitzpatrick
abc00e9c8d ipn/{ipnserver,ipnlocal}: support incoming Taildrop on Synology
If the user has a "Taildrop" shared folder on startup and
the "tailscale" system user has read/write access to it,
then the user can "tailscale file cp" to their NAS.

Updates #2179 (would be fixes, but not super ideal/easy yet)

Change-Id: I68e59a99064b302abeb6d8cc84f7d2a09f764990
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-06 16:36:24 -08:00
David Anderson
190b7a4cca go.mod: mass update with go get -u.
Gets ahead of dependabot slightly, but the updates are minor.

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-12-06 13:00:37 -08:00
dependabot[bot]
0d8ef1ff35 go.mod: bump github.com/aws/aws-sdk-go-v2/service/ssm
Bumps [github.com/aws/aws-sdk-go-v2/service/ssm](https://github.com/aws/aws-sdk-go-v2) from 1.17.0 to 1.17.1.
- [Release notes](https://github.com/aws/aws-sdk-go-v2/releases)
- [Changelog](https://github.com/aws/aws-sdk-go-v2/blob/main/CHANGELOG.md)
- [Commits](https://github.com/aws/aws-sdk-go-v2/compare/service/s3/v1.17.0...service/ssm/v1.17.1)

---
updated-dependencies:
- dependency-name: github.com/aws/aws-sdk-go-v2/service/ssm
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>
2021-12-06 11:27:21 -08:00
dependabot[bot]
329751c48e go.mod: bump golang.org/x/tools from 0.1.7 to 0.1.8
Bumps [golang.org/x/tools](https://github.com/golang/tools) from 0.1.7 to 0.1.8.
- [Release notes](https://github.com/golang/tools/releases)
- [Commits](https://github.com/golang/tools/compare/v0.1.7...v0.1.8)

---
updated-dependencies:
- dependency-name: golang.org/x/tools
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>
2021-12-06 11:20:43 -08:00
dependabot[bot]
9ddef8cdbf go.mod: bump github.com/mdlayher/netlink from 1.4.1 to 1.4.2
Bumps [github.com/mdlayher/netlink](https://github.com/mdlayher/netlink) from 1.4.1 to 1.4.2.
- [Release notes](https://github.com/mdlayher/netlink/releases)
- [Changelog](https://github.com/mdlayher/netlink/blob/main/CHANGELOG.md)
- [Commits](https://github.com/mdlayher/netlink/compare/v1.4.1...v1.4.2)

---
updated-dependencies:
- dependency-name: github.com/mdlayher/netlink
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>
2021-12-06 11:05:15 -08:00
dependabot[bot]
9140f193bc go.mod: bump github.com/aws/aws-sdk-go-v2/feature/s3/manager
Bumps [github.com/aws/aws-sdk-go-v2/feature/s3/manager](https://github.com/aws/aws-sdk-go-v2) from 1.7.3 to 1.7.4.
- [Release notes](https://github.com/aws/aws-sdk-go-v2/releases)
- [Changelog](https://github.com/aws/aws-sdk-go-v2/blob/main/CHANGELOG.md)
- [Commits](https://github.com/aws/aws-sdk-go-v2/compare/service/fsx/v1.7.3...feature/s3/manager/v1.7.4)

---
updated-dependencies:
- dependency-name: github.com/aws/aws-sdk-go-v2/feature/s3/manager
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>
2021-12-06 11:02:21 -08:00
dependabot[bot]
05c1be3e47 .github: Bump actions/upload-artifact from 1 to 2.2.4
Bumps [actions/upload-artifact](https://github.com/actions/upload-artifact) from 1 to 2.2.4.
- [Release notes](https://github.com/actions/upload-artifact/releases)
- [Commits](https://github.com/actions/upload-artifact/compare/v1...v2.2.4)

---
updated-dependencies:
- dependency-name: actions/upload-artifact
  dependency-type: direct:production
  update-type: version-update:semver-major
...

Signed-off-by: dependabot[bot] <support@github.com>
2021-12-06 11:01:40 -08:00
David Anderson
e6e63c2305 .github/dependabot.yml: make dependabot send all the updates right now.
So we can mass-process updates once now, then turn it off.

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-12-06 10:57:33 -08:00
Brad Fitzpatrick
c0984f88dc Makefile: add spk and pushspk targets for iterative Synology development
Change-Id: I97319d14917aa2b00ff72a7b73b3db79ea8392b7
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-06 09:52:06 -08:00
Todd Neal
eeccbccd08 support running in a FreeBSD jail
Since devd apparently can't be made to work in a FreeBSD jail
fall back to polling.

Fixes tailscale#2858

Signed-off-by: Todd Neal <todd@tneal.org>
2021-12-05 21:42:52 -08:00
Brad Fitzpatrick
69de3bf7bf wgengine/filter: let unknown IPProto match if IP okay & match allows all ports
RELNOTE=yes

Change-Id: I96eaf3cf550cee7bb6cdb4ad81fc761e280a1b2a
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-05 10:44:18 -08:00
Josh Bleecher Snyder
1813c2a162 .: add .gitattributes entry to use Go hunk-header driver
Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-12-03 17:56:02 -08:00
Maisem Ali
0a9932f3b2 build_docker.sh: prefix version strings with v
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2021-12-03 13:55:09 -08:00
Brad Fitzpatrick
9c5c9d0a50 ipn/ipnlocal, net/tsdial: make SOCKS/HTTP dials use ExitDNS
And simplify, unexport some tsdial/netstack stuff in the the process.

Fixes #3475

Change-Id: I186a5a5cbd8958e25c075b4676f7f6e70f3ff76e
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-03 13:39:37 -08:00
Brad Fitzpatrick
9f6249b26d ipn/policy: treat DNS service as interesting so it's not filtered out
The control plane is currently still eating it.

Updates #1713

Change-Id: I66a0698599d6794ab1302f9585bf29e38553c884
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-03 12:55:54 -08:00
Josh Bleecher Snyder
de635ac0a8 cmd/tailscale: print more detail in connection failure error message
Before:

failed to connect to local tailscaled (which appears to be running). Got error: Get "http://local-tailscaled.sock/localapi/v0/status": EOF

After:

failed to connect to local tailscaled (which appears to be running as IPNExtension, pid 2118). Got error: Get "http://local-tailscaled.sock/localapi/v0/status": EOF

This was useful just now, as it made it clear that tailscaled I thought
I was connecting to might not in fact be running; there was
a second tailscaled running that made the error message slightly misleading.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-12-03 12:46:50 -08:00
Brad Fitzpatrick
003089820d cmd/tailscale: fix setting revert checker's finding an exit node
It was using the wrong prefs (intended vs current) to map the current
exit node ID to an IP.

Fixes #3480

Change-Id: I9f117d99a84edddb4cd1cb0df44a2f486abde6c2
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-02 21:19:48 -08:00
Brad Fitzpatrick
03a323de4e cmd/tailscale: don't allow setting exit node to known invalid value
Fixes #3081

Change-Id: I34c378dfd51ee013c21962dbe79c49b1ba06c0c5
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-02 14:34:33 -08:00
Brad Fitzpatrick
a8f60cf6e8 cmd/tailscale: clarify which prefless flags don't need revert protection
Fixes #3482

Change-Id: Icb51476b0d78d3758cb04df3b565e372b8289a46
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-02 14:07:00 -08:00
Brad Fitzpatrick
f91481075d cmd/tailscale: let --exit-node= take a machine name in addition to IP
If you're online, let tailscale up --exit-node=NAME map NAME to its IP.

We don't store the exit node name server-side in prefs, avoiding
the concern raised earlier.

Fixes #3062

Change-Id: Ieea5ceec1a30befc67e9d6b8a530b3cb047b6b40
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-02 14:02:55 -08:00
Brad Fitzpatrick
adc5997592 net/tsdial: give netstack a Dialer, start refactoring name resolution
This starts to refactor tsdial.Dialer's name resolution to have
different stages: in-memory MagicDNS vs system resolution. A future
change will plug in ExitDNS resolution.

This also plumbs a Dialer into netstack and unexports the dnsMap
internals.

And it removes some of the async AddNetworkMapCallback usage and
replaces it with synchronous updates of the Dialer's netmap
from LocalBackend, since the LocalBackend has the Dialer too.

Updates #3475

Change-Id: Idcb7b1169878c74f0522f5151031ccbc49fe4cb4
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-02 11:33:13 -08:00
Josh Bleecher Snyder
768baafcb5 tstest/integration: use t.Cleanup
Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-12-02 11:11:11 -08:00
Brad Fitzpatrick
43983a4a3b ipn/ipnlocal: run peerapi even if Taildrop storage not configured
Change-Id: I77f9ecbe4617d01d13aa1127fa59c83f2aa3e1b8
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-01 16:45:09 -08:00
David Anderson
44d0c1ab06 ipn/ipnlocal: resolve exit node IP to ID at EditPrefs time.
Without this, enabling an exit node immediately blackholes all traffic,
but doesn't correctly let it flow to the exit node until the next netmap
update.

Fixes #3447

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-12-01 15:50:32 -08:00
Brad Fitzpatrick
8775c646be net/tsdial: make dialing to peerapi work in netstack mode
With this, I'm able to send a Taildrop file (using "tailscale file cp")
from a Linux machine running --tun=userspace-networking.

Updates #2179

Change-Id: I4e7a4fb0fbda393e4fb483adb06b74054a02cfd0
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-01 14:16:34 -08:00
Brad Fitzpatrick
ad3d6e31f0 net/tsdial: move macOS/iOS peerapi sockopt logic from LocalBackend
Change-Id: I812cae027c40c70cdc701427b1a1850cd9bcd60c
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-01 12:55:31 -08:00
Josh Bleecher Snyder
25eab78573 control/noise: clean up resources in TestNoReuse
Close the server and client.
Without this, we leak system threads.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-12-01 12:50:21 -08:00
Brad Fitzpatrick
c7fb26acdb net/tsdial: also plumb TUN name and monitor into tsdial.Dialer
In prep for moving stuff out of LocalBackend.

Change-Id: I9725aa9c3ebc7275f8c40e040b326483c0340127
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-01 10:36:55 -08:00
Brad Fitzpatrick
c37af58ea4 net/tsdial: move more weirdo dialing into new tsdial package, plumb
Not done yet, but this move more of the outbound dial special casing
from random packages into tsdial, which aspires to be the one unified
place for all outbound dialing shenanigans.

Then this plumbs it all around, so everybody is ultimately
holding on to the same dialer.

As of this commit, macOS/iOS using an exit node should be able to
reach to the exit node's DoH DNS proxy over peerapi, doing the sockopt
to stay within the Network Extension.

A number of steps remain, including but limited to:

* move a bunch more random dialing stuff

* make netstack-mode tailscaled be able to use exit node's DNS proxy,
  teaching tsdial's resolver to use it when an exit node is in use.

Updates #1713

Change-Id: I1e8ee378f125421c2b816f47bc2c6d913ddcd2f5
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-01 10:36:55 -08:00
Brad Fitzpatrick
bf1d69f25b wgengine/monitor: fix docs on Mon.InterfaceState
The behavior was changed in March (in 7f174e84e6)
but that change forgot to update these docs.

Change-Id: I79c0301692c1d13a4a26641cc5144baf48ec1360
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-12-01 10:36:06 -08:00
Josh Bleecher Snyder
2075c39fd7 net/portmapper: deflake TestPCPIntegration
Logging in goroutines after the test completed
caused data races and panics. Prevent that.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-12-01 10:13:27 -08:00
Artyom Pervukhin
49a9e62d58 Replace AWS SDK v1 dependency with v2
This change drops AWS SDKv1 dependency, leaving only SDK v2 in use.

Closes #3461

Signed-off-by: Artyom Pervukhin <github@artyom.dev>
2021-12-01 07:51:22 -08:00
Danny Hermes
56c72d9cde godoc fix: StatusWithPeers -> StatusWithoutPeers
Signed-off-by: Danny Hermes <daniel.j.hermes@gmail.com>
2021-11-30 23:17:06 -08:00
Brad Fitzpatrick
d5405c66b7 net/tsdial: start of new package to unify all outbound dialing complexity
For now this just deletes the net/socks5/tssocks implementation (and
the DNSMap stuff from wgengine/netstack) and moves it into net/tsdial.

Then initialize a Dialer early in tailscaled, currently only use for the
outbound and SOCKS5 proxies. It will be plumbed more later. Notably, it
needs to get down into the DNS forwarder for exit node DNS forwading
in netstack mode. But it will also absorb all the peerapi setsockopt
and netns Dial and tlsdial complexity too.

Updates #1713

Change-Id: Ibc6d56ae21a22655b2fa1002d8fc3f2b2ae8b6df
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-30 17:21:49 -08:00
Brad Fitzpatrick
3ae6f898cf ipn/ipnlocal, net/dns/resolver: use exit node's DoH proxy when available
Updates #1713

Change-Id: I3695a40ec12d2b4e6dac41cf4559daca6dddd68e
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-30 17:01:09 -08:00
Brad Fitzpatrick
16abd7e07c ipn/ipnlocal: fix Content-Length in DoH DNS proxy response
Updates #1713

Change-Id: I912d90383b751ad97b32bcec55e8fedbcf4d3db8
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-30 17:01:09 -08:00
Brad Fitzpatrick
2a95ee4680 cmd/tailscale, ipn/ipnstate: note which nodes are exit nodes in status
Fixes #3446

Change-Id: Ib41d588e7fa434c02d134fa449f85b0e15083683
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-30 16:59:23 -08:00
Josh Bleecher Snyder
deb2f5e793 types/logger: add Context and related helpers
We often need both a log function and a context.
We can do this by adding the log function as a context value.
This commit adds helper glue to make that easy.
It is designed to allow incremental adoption.

Updates tailscale/corp#3138

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-11-30 15:18:21 -08:00
Aaron Klotz
f93cf6fa03 net/dns: fix checking for wrapped error when attempting to read wsl.conf for Windows WSL2
Fixes https://github.com/tailscale/tailscale/issues/3437

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2021-11-30 15:36:39 -07:00
Josh Bleecher Snyder
b800663779 tstest/integration: stop leaking zstd.Decoders
Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-11-30 14:08:05 -08:00
David Anderson
124363e0ca net/dns: detect and decode UTF-16 from wsl.exe earlier.
Fixes #3170

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-11-30 13:10:18 -08:00
Josh Bleecher Snyder
e16cb523aa net/nettest: deflake TestPipeTimeout
The block-write and block-read tests are both flaky,
because each assumes it can get a normal read/write
completed within 10ms. This isn’t always true.

We can’t increase the timeouts, because that slows down the test.
However, we don’t need to issue a regular read/write for this test.
The immediately preceding tests already test this code,
using a far more generous timeout.

Remove the extraneous read/write.

This drops the failure rate from 1 per 20,000 to undetectable
on my machine.

While we’re here, fix a typo in a debug print statement.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-11-30 12:21:59 -08:00
Josh Bleecher Snyder
a8cc519c70 net/portmapper: improve handling of UPnP parse errors
Without the continue, we might overwrite our current meta
with a zero meta.

Log the error, so that we can check for anything unexpected.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-11-30 12:13:15 -08:00
Josh Bleecher Snyder
fddf43f3d1 net/portmapper: fill out PCP/PMP client metrics
Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-11-30 12:13:15 -08:00
Josh Bleecher Snyder
9787ec6f4a net/portmapper: add UPnP client metrics
Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-11-30 12:13:15 -08:00
Josh Bleecher Snyder
40f11c50a1 net/portmapper: make PCP/PMP result codes stringers
Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-11-30 12:13:15 -08:00
Josh Bleecher Snyder
38d90fa330 net/portmapper: add clientmetrics for PCP/PMP responses
Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-11-30 12:13:15 -08:00
Josh Bleecher Snyder
999814e9e1 net/portmapper: handle pcp ADDRESS_MISMATCH response
These show up a fair amount in our logs.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-11-30 12:13:15 -08:00
Brad Fitzpatrick
bb91cfeae7 net/socks5/tssocks, wgengine: permit SOCKS through subnet routers/exit nodes
Fixes #1970

Change-Id: Ibef45e8796e1d9625716d72539c96d1dbf7b1f76
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-30 11:54:14 -08:00
Brad Fitzpatrick
3181bbb8e4 cmd/tailscale: make file cp send files via tailscaled localapi
So Taildrop sends work even if the local tailscaled is running in
netstack mode, as it often is on Synology, etc.

Updates #2179 (which is primarily about receiving, but both important)

Change-Id: I9bd1afdc8d25717e0ab6802c7cf2f5e0bd89a3b2
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-30 11:47:27 -08:00
David Crawshaw
46a9782322 .github/dependabot.yml: slow down the stream of unusable PRs
Signed-off-by: David Crawshaw <crawshaw@tailscale.com>
2021-11-30 09:27:14 -08:00
dependabot[bot]
d89c61b812 go.mod: bump github.com/aws/aws-sdk-go-v2/service/ssm
Bumps [github.com/aws/aws-sdk-go-v2/service/ssm](https://github.com/aws/aws-sdk-go-v2) from 1.16.0 to 1.17.0.
- [Release notes](https://github.com/aws/aws-sdk-go-v2/releases)
- [Changelog](https://github.com/aws/aws-sdk-go-v2/blob/main/CHANGELOG.md)
- [Commits](https://github.com/aws/aws-sdk-go-v2/compare/service/s3/v1.16.0...service/s3/v1.17.0)

---
updated-dependencies:
- dependency-name: github.com/aws/aws-sdk-go-v2/service/ssm
  dependency-type: direct:production
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <support@github.com>
2021-11-30 08:01:44 -08:00
dependabot[bot]
341e1af873 go.mod: bump github.com/aws/aws-sdk-go-v2/config from 1.10.2 to 1.10.3
Bumps [github.com/aws/aws-sdk-go-v2/config](https://github.com/aws/aws-sdk-go-v2) from 1.10.2 to 1.10.3.
- [Release notes](https://github.com/aws/aws-sdk-go-v2/releases)
- [Changelog](https://github.com/aws/aws-sdk-go-v2/blob/main/CHANGELOG.md)
- [Commits](https://github.com/aws/aws-sdk-go-v2/compare/config/v1.10.2...config/v1.10.3)

---
updated-dependencies:
- dependency-name: github.com/aws/aws-sdk-go-v2/config
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>
2021-11-30 05:48:56 -08:00
Brad Fitzpatrick
b811a316bc tailcfg, ipn/ipnlocal: advertise a Service when exit node DNS proxy available
Updates #1713

Change-Id: I20c8e2ad1062d82ef17363414e372133f4c7181e
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-29 21:57:06 -08:00
David Anderson
6e584ffa33 cmd/tailscaled: allow running the SOCKS5 and HTTP proxies on the same port.
Fixes #3248

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-11-29 16:49:48 -08:00
David Anderson
a54d13294f net/proxymux: add a listener mux that can run SOCKS and HTTP on a single socket.
Updates #3248

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-11-29 16:49:48 -08:00
Brad Fitzpatrick
135580a5a8 tailcfg, ipn/ipnlocal, net/dns: forward exit node DNS on Unix to system DNS
Updates #1713

Change-Id: I4c073fec0992d9e01a9a4ce97087d5af0efdc68d
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-29 15:25:41 -08:00
Josh Bleecher Snyder
d9c21936c3 control/controlclient: stop logging about goal.url invariant
This isn't the ideal solution, but it's good enough for now.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-11-29 14:00:53 -08:00
David Crawshaw
1e8b4e770a update github.com/aws/aws-sdk-go-v2
Replaces #3464, #3365, #3366 with a PR that includes the depaware fix.

Signed-off-by: David Crawshaw <crawshaw@tailscale.com>
2021-11-29 12:10:28 -08:00
Brad Fitzpatrick
105c545366 cmd/tailscale/cli: don't complain about --accept-routes true->false on Synology
Fixes #3176

Change-Id: I844883e741dccfa5e7771c853180e9f65fb7f7a4
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-29 11:21:38 -08:00
Brad Fitzpatrick
c2efe46f72 ipn/ipnlocal: restrict exit node DoH server based on ACL'ed packet filter
Don't be a DoH DNS server to peers unless the Tailnet admin has permitted
that peer autogroup:internet access.

Updates #1713

Change-Id: Iec69360d8e4d24d5187c26904b6a75c1dabc8979
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-29 09:56:59 -08:00
Brad Fitzpatrick
ff9727c9ff wgengine/filter: fix, test NewAllowAllForTest
I probably broke it when SCTP support was added but nothing apparently
ever used NewAllowAllForTest so it wasn't noticed when it broke.

Change-Id: Ib5a405be233d53cb7fcc61d493ae7aa2d1d590a2
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-29 09:56:59 -08:00
Thomas Weiß
f8cef1ba08 ipn/store/aws: support using sub-paths in parameters
Fixes #3431

Signed-off-by: Thomas Weiß <panos@unbunt.org>
2021-11-29 07:48:01 -08:00
Thomas Weiß
6dc6ea9b37 cmd/tailscaled: log error on state store init failure
Signed-off-by: Thomas Weiß <panos@unbunt.org>
2021-11-29 07:48:01 -08:00
Brad Fitzpatrick
78b0bd2957 net/dns/resolver: add clientmetrics for DNS
Fixes tailscale/corp#1811

Change-Id: I864d11e0332a177e8c5ff403591bff6fec548f5a
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-26 17:57:48 -08:00
David Anderson
097602b3ca ipn/ipnlocal: warn more precisely about IP forwarding issues on linux.
If IP forwarding is disabled globally, but enabled per-interface on all interfaces,
don't complain. If only some interfaces have forwarding enabled, warn that some
subnet routing/exit node traffic may not work.

Fixes #1586

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-11-26 11:03:10 -08:00
David Anderson
db800ddeac cmd/derper: set Content-Security-Policy on DERPs.
It's a basic "deny everything" policy, since DERP's HTTP
server is very uninteresting from a browser POV. But it
stops every security scanner under the sun from reporting
"dangerously configured" HTTP servers.

Updates tailscale/corp#3119

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-11-26 11:00:44 -08:00
David Anderson
33c541ae30 ipn/ipnlocal: populate self status from netmap in ipnlocal, not magicsock.
Fixes #1933

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-11-26 10:56:42 -08:00
Denton Gentry
e121c2f724 logpolicy: export NewLogtailTransport for Android
Android doesn't use logpolicy and currently has enough
unique stuff about its logging that makes it difficult to
do so. For example, its logsDir comes from Gio.

Export NewLogtailTransport to let Android use it.

Updates https://github.com/tailscale/tailscale/issues/3046

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2021-11-26 07:45:13 -08:00
Brad Fitzpatrick
25525b7754 net/dns/resolver, ipn/ipnlocal: wire up peerapi DoH server to DNS forwarder
Updates #1713

Change-Id: Ia4ed9d8c9cef0e70aa6d30f2852eaab80f5f695a
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-23 18:59:36 -08:00
Maya Kaczorowski
9bb91cb977 Merge pull request #3214 from tailscale/mayakacz-patch-1
.github: feature request template change
2021-11-23 19:09:51 -05:00
Maya Kaczorowski
259163dfe1 Update feature_request.yml
Signed-off-by: Maya Kaczorowski <15946341+mayakacz@users.noreply.github.com>
2021-11-23 18:52:52 -05:00
Denton Gentry
f56a7559ce scripts/installer.sh: add more Linux variants.
Updates https://github.com/tailscale/tailscale/issues/2915

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2021-11-23 15:12:29 -08:00
Josh Bleecher Snyder
d10cefdb9b net/dns: require space after nameserver/search parsing resolv.conf
Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-11-23 15:11:46 -08:00
Josh Bleecher Snyder
9f00510833 net/dns: handle comments in resolv.conf
Currently, comments in resolv.conf cause our parser to fail,
with error messages like:

ParseIP("192.168.0.100 # comment"): unexpected character (at " # comment")

Fix that.

Noticed while looking through logs.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-11-23 15:11:46 -08:00
Josh Bleecher Snyder
955aa188b3 ipn/ipnlocal: fix logging
We were missing an argument here.
Also, switch to %q, in case anything weird
is happening with these strings.

Updates tailscale/corp#461

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-11-23 13:36:59 -08:00
Josh Bleecher Snyder
73beaaf360 net/tstun: rate limit "self disco out packet" logging
When this happens, it is incredibly noisy in the logs.
It accounts for about a third of all remaining
"unexpected" log lines from a recent investigation.

It's not clear that we know how to fix this,
we have a functioning workaround,
and we now have a (cheap and efficient) metric for this
that we can use for measurements.

So reduce the logging to approximately once per minute.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-11-23 12:52:52 -08:00
Josh Bleecher Snyder
b0d543f7a1 cmd/tailscale: add ip -1 flag
This limits the output to a single IP address.

RELNOTE=tailscale ip now has a -1 flag (TODO: update docs to use it)

Fixes #1921

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-11-23 12:05:32 -08:00
Josh Bleecher Snyder
73beaf59fb cmd/tailscale: improve ip subcommand docs
Streamline the prose.
Clarify what peer may be.
Improve an error message.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-11-23 12:05:32 -08:00
Joonas Loppi
a3b709f0c4 tsshd: fix double exit with different exit codes
Signed-off-by: Joonas Loppi <joonas@joonas.fi>
2021-11-23 09:19:59 -08:00
Brad Fitzpatrick
283ae702c1 ipn/ipnlocal: start adding DoH DNS server to peerapi when exit node
Updates #1713

Change-Id: I8d9c488f779e7acc811a9bc18166a2726198a429
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-23 08:21:41 -08:00
dependabot[bot]
6fd6fe11f2 go.mod: bump honnef.co/go/tools from 0.2.1 to 0.2.2
Bumps [honnef.co/go/tools](https://github.com/dominikh/go-tools) from 0.2.1 to 0.2.2.
- [Release notes](https://github.com/dominikh/go-tools/releases)
- [Commits](https://github.com/dominikh/go-tools/compare/v0.2.1...v0.2.2)

---
updated-dependencies:
- dependency-name: honnef.co/go/tools
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>
2021-11-22 22:01:32 -08:00
Josh Bleecher Snyder
027b46d0c1 ipn/ipnstate: clarify PeerStatusLite.LastHandshake
And document the other fields, as long as we're here.

Updates #1182

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-11-22 22:01:20 -08:00
Brad Fitzpatrick
0de1b74fbb util/clientmetric: add tests omitted from earlier commit
These were supposed to be part of
3b541c833e but I guess I forgot to "git
add" them. Whoops.

Updates #3307

Change-Id: I8c768a61ec7102a01799e81dc502a22399b9e9f0
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-22 21:49:28 -08:00
Josh Bleecher Snyder
ad5e04249b wgengine/monitor: ignore adding/removing uninteresting IPs
One of the most common "unexpected" log lines is:

"network state changed, but stringification didn't"

One way that this can occur is if an interesting interface
(non-Tailscale, has interesting IP address)
gains or loses an uninteresting IP address (link local or loopback).

The fact that the interface is interesting is enough for EqualFiltered
to inspect it. The fact that an IP address changed is enough for
EqualFiltered to declare that the interfaces are not equal.

But the State.String method reasonably declines to print any
uninteresting IP addresses. As a result, the network state appears
to have changed, but the stringification did not.

The String method is correct; nothing interesting happened.

This change fixes this by adding an IP address filter to EqualFiltered
in addition to the interface filter. This lets the network monitor
ignore the addition/removal of uninteresting IP addresses.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-11-22 16:33:15 -08:00
Josh Bleecher Snyder
60510a6ae7 .github/workflows: check that repo is clean after build and test
Linux-only for now, to avoid having to figure out why
powershell doesn't like my shell scripting. (Not that I blame it.)
That'll be enough to catch most regressions.

Fixes #1083

Co-authored-by: Aaron Klotz <aaron@tailscale.com>
Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-11-22 15:28:59 -08:00
Denton Gentry
1ea270375a hostinfo: report when running in Docker Desktop.
Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2021-11-22 13:45:54 -08:00
Josh Bleecher Snyder
ca1b3fe235 net/tshttpproxy: use correct size for Windows BOOL argument
The Windows BOOL type is an int32. We were using a bool,
which is a one byte wide. This could be responsible for the
ERROR_INVALID_PARAMETER errors we were seeing for calls to
WinHttpGetProxyForUrl.

We manually checked all other existing Windows syscalls
for similar mistakes and did not find any.

Updates #879

Co-authored-by: Aaron Klotz <aaron@tailscale.com>
Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-11-22 12:24:24 -08:00
David Anderson
9a217ec841 cmd/derper: increase HSTS cache lifetime to 2 years.
Fixes #3373.

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-11-22 11:59:01 -08:00
Maisem Ali
9feb483ad3 build_docker.sh: use github.com/tailscale/mkctr instead of docker
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2021-11-22 11:39:30 -08:00
Aaron Klotz
7d8feb2784 hostinfo: change Windows implementation to directly query version information using API and registry
We replace the cmd.exe invocation with RtlGetNtVersionNumbers for the first
three fields. On Windows 10+, we query for the fourth field which is available
via the registry.

The fourth field is not really documented anywhere; Firefox has been querying
it successfully since Windows 10 was released, so we can be pretty confident in
its longevity at this point.

Fixes https://github.com/tailscale/tailscale/issues/1478

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2021-11-22 12:26:42 -07:00
Josh Bleecher Snyder
1a629a4715 net/portmapper: mark fewer PMP probe failures as unexpected
There are lots of lines in the logs of the form:

portmapper: unexpected PMP probe response: {OpCode:128 ResultCode:3
SecondsSinceEpoch:NNN MappingValidSeconds:0 InternalPort:0
ExternalPort:0 PublicAddr:0.0.0.0}

ResultCode 3 here means a network failure, e.g. the NAT box itself has
not obtained a DHCP lease. This is not an indication that something
is wrong in the Tailscale client, so use different wording here
to reflect that. Keep logging, so that we can analyze and debug
the reasons that PMP probes fail.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-11-22 11:13:15 -08:00
Brad Fitzpatrick
e8db43e8fa wgengine/router: demote TestDebugListRules fail to skip
Updates #3360

Change-Id: Ic5c98ea03f3171c13ab9293a0ae74d17fd04d149
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-22 11:04:45 -08:00
David Anderson
937e96f43d cmd/derper: enable HSTS when serving over HTTPS.
Starting with a short lifetime, to verify nothing breaks.

Updates #3373

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-11-22 09:57:34 -08:00
dependabot[bot]
f76a8d93da go.mod: bump github.com/godbus/dbus/v5 from 5.0.5 to 5.0.6
Bumps [github.com/godbus/dbus/v5](https://github.com/godbus/dbus) from 5.0.5 to 5.0.6.
- [Release notes](https://github.com/godbus/dbus/releases)
- [Commits](https://github.com/godbus/dbus/compare/v5.0.5...v5.0.6)

---
updated-dependencies:
- dependency-name: github.com/godbus/dbus/v5
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>
2021-11-22 08:40:09 -08:00
Brad Fitzpatrick
2ea765e5d8 go.mod: bump inet.af/netstack
Updates #2642 (I'd hoped, but doesn't seem to fix it)

Change-Id: Id54af7c90a1206bc7018215957e20e954782b911
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-21 09:18:31 -08:00
AdamKorcz
def659d1ec Fuzzing: Add CIFuzz
Signed-off-by: AdamKorcz <adam@adalogics.com>
2021-11-19 13:06:20 -08:00
Brad Fitzpatrick
946dfec98a wgengine/router: fix checkIPRuleSupportsV6 to actually use IPv6
Updates #3358 (should fix it)
Updates #391

Change-Id: Ia62437dfa81247b0b5994d554cf279c3d540e4e7
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-19 11:37:05 -08:00
Brad Fitzpatrick
9259377a7f wgengine/router: don't assume Linux was built with IP_MULTIPLE_TABLES
Updates #3351
Updates #391

Change-Id: I7e66b686e05f3c970846513679cc62556ebe322a
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-19 11:19:03 -08:00
David Anderson
88b8a09d37 net/dns: make constants for the various DBus strings.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-11-19 11:09:32 -08:00
David Anderson
6c82cebe57 health: add a health state for net/dns.OSConfigurator.
Lets the systemd-resolved OSConfigurator report health changes
for out of band config resyncs.

Updates #3327

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-11-19 11:09:32 -08:00
David Anderson
4ef3fed100 net/dns: resync config to systemd-resolved when it restarts.
Fixes #3327

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-11-19 11:09:32 -08:00
David Anderson
cf9169e4be net/dns: remove unused Config struct element.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-11-19 11:09:32 -08:00
Brad Fitzpatrick
0350cf0438 wgengine{,/router}: annotate some more errors
Updates #3351

Change-Id: I8b4f957d2051b3e29401bb449dbadbdada3a7c46
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-19 10:46:01 -08:00
Brad Fitzpatrick
5294125e7a cmd/tailscaled: disambiguate some startup failure error messages
Updates #3351

Change-Id: I0afead4a084623567f56b19187574fa97b295b2a
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-19 08:58:29 -08:00
Josh Bleecher Snyder
758c37b83d net/netns: thread logf into control functions
So that darwin can log there without panicking during tests.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-11-18 15:09:51 -08:00
Josh Bleecher Snyder
85184a58ed wgengine/wgcfg: recover from mismatched PublicKey/Endpoints
In rare circumstances (tailscale/corp#3016), the PublicKey
and Endpoints can diverge.

This by itself doesn't cause any harm, but our early exit
in response did, because it prevented us from recovering from it.

Remove the early exit.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-11-18 14:28:41 -08:00
Denton Gentry
9fc4e876e3 VERSION.txt: this is v1.19.0
Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2021-11-18 12:12:48 -08:00
Brad Fitzpatrick
8ec44d0d5f wgengine/magicsock: remove some log spam
Fixes tailscale/corp#3070

Change-Id: Ie50031800ec8669e0596ad6d59d1e329a5c88516
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-18 11:01:51 -08:00
Brad Fitzpatrick
61d0435ed9 wgengine/monitor: reduce Windows log spam
Fixes #3345

Change-Id: Icde9c92f88f98bb3b030d39b0424a7d389bceb88
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-18 10:57:27 -08:00
Brad Fitzpatrick
0653efb092 cmd/tailscaled: remove a redundant date prefix on Windows logs
Change-Id: I28e122d4384697f51a748d67829409276c00b11e
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-18 10:23:41 -08:00
Brad Fitzpatrick
49a3fcae78 log/filelogger: make filelogger remove redundant date before adding a date
At some point since filelogger was added on Windows, the log hierarchy
above it changed such that a log.Printf writes to filelogger and includes
the log package's own date. But then filelogger adds another.

Rather than debug everything above and risk removing the prefix when
run by tailscaled, instead just remove the log package's prefix
very late right before we go to add the filelogger's own.

Change-Id: I9db518f42c603ef83017f74827270f124fdf5c14
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-18 10:23:41 -08:00
Brad Fitzpatrick
4a59a2781a ipn/ipnlocal: export client metrics over peerapi to owner
Updates #3307

Change-Id: I41b1f3c16af5f385575e8d6cea70ae8386504dd8
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-18 08:04:00 -08:00
Brad Fitzpatrick
d24ed3f68e wgengine/router: add debug knob to resort to Linux "ip" command usage
Tailscale 1.18 uses netlink instead of the "ip" command to program the
Linux kernel.

The old way was kept primarily for tests, but this also adds a
TS_DEBUG_USE_IP_COMMAND environment knob to force the old way
temporarily for debugging anybody who might have problems with the
new way in 1.18.

Updates #391

Change-Id: I0236fbfda6c9c05dcb3554fcc27ec0c86456efd9
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-18 08:01:22 -08:00
Josh Bleecher Snyder
b3d6704aa3 wgengine/magicsock: fix data race on endpoint.discoKey
endpoint.discoKey is protected by endpoint.mu.
endpoint.sendDiscoMessage was reading it without holding the lock.
This showed up in a CI failure and is readily reproducible locally.

The fix is in two parts.

First, for Conn.enqueueCallMeMaybe, eliminate the one-line helper method endpoint.sendDiscoMessage; call Conn.sendDiscoMessage directly.
This makes it more natural to read endpoint.discoKey in a context
in which endpoint.mu is already held.

Second, for endpoint.sendDiscoPing, explicitly pass the disco key
as an argument. Again, this makes it easier to read endpoint.discoKey
in a context in which endpoint.mu is already held.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-11-17 17:49:33 -08:00
Brad Fitzpatrick
cf06f9df37 net/tstun, wgengine: add packet-level and drop metrics
Primarily tstun work, but some MagicDNS stuff spread into wgengine.

No wireguard reconfig metrics (yet).

Updates #3307

Change-Id: Ide768848d7b7d0591e558f118b553013d1ec94ad
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-17 16:18:52 -08:00
Brad Fitzpatrick
ec036b3561 logpolicy: use bootstrap DNS for logtail dialer
Fixes #3332

Change-Id: Ie45efb448e5508c3ece48dd1d8d7e9a39e2e9dc1
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-17 14:37:43 -08:00
Brad Fitzpatrick
7901289578 wgengine/magicsock: add a stress test
And add a peerMap validate method that checks its internal invariants.

Updates tailscale/corp#3016

Change-Id: I23708e68ed44d81986d9e2be82029d4555547592
Co-authored-by: Brad Fitzpatrick <bradfitz@tailscale.com>
Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-11-17 14:37:28 -08:00
Josh Bleecher Snyder
5a60781919 wgengine/magicsock: increase TestDiscokeyChange connection timeout
I believe that this should eliminate the flakiness.
If GitHub CI manages to be even slower that can be believed
(and I can believe a lot at this point),
then we should roll this back and make some more invasive changes.

Updates #654
Fixes #3247 (I hope)

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-11-17 14:13:58 -08:00
Brad Fitzpatrick
5b5f032c9a util/clientmetric: optimize memory layout for finding updates
Updates #3307

Change-Id: I2840b190583467cc3f00688b96ce3d170df46a46
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-17 12:30:49 -08:00
Josh Bleecher Snyder
773af7292b wgengine/magicsock: simplify peerMap.upsertEndpoint
We can do the "maybe delete" check unilaterally:
In the case of an insert, both oldDiscoKey
and ep.discoKey will be the zero value.

And since we don't use pi again, we can skip
giving it a name, which makes scoping clearer.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-11-16 15:15:49 -08:00
Josh Bleecher Snyder
9da22dac3d wgengine/magicsock: fix bug in peerMap.upsertEndpoint
Found by inspection by David Crawshaw while
investigating tailscale/corp#3016.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-11-16 15:15:49 -08:00
Josh Bleecher Snyder
16870cb754 wgengine/magicsock: fix typo in comment
Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-11-16 15:15:49 -08:00
Brad Fitzpatrick
36b1df1241 cmd/tailscale/cli: add --watch flag to "debug metrics" subcommand
This adds a new --watch flag that prints out a block of metric changes
every second, if anything changed.

Example output:

magicsock_disco_recv_ping    +1 => 254
magicsock_disco_recv_pong    +1 => 218
magicsock_disco_recv_udp     +2 => 472
magicsock_disco_send_udp     +2 => 536
magicsock_disco_sent_udp     +2 => 536
magicsock_recv_data_ipv6     +1 => 82
magicsock_send_data          +1 => 86
magicsock_send_udp           +3 => 620

magicsock_recv_data_ipv6    +1 => 83
magicsock_send_data         +1 => 87
magicsock_send_udp          +1 => 621

magicsock_disco_recv_ping    +1 => 255
magicsock_disco_recv_pong    +1 => 219
magicsock_disco_recv_udp     +2 => 474
magicsock_disco_send_udp     +2 => 538
magicsock_disco_sent_udp     +2 => 538
magicsock_recv_data_ipv6     +1 => 84
magicsock_send_data          +1 => 88
magicsock_send_udp           +3 => 624

magicsock_recv_data_ipv6    +1 => 85
magicsock_send_data         +1 => 89
magicsock_send_udp          +1 => 625

controlclient_map_response_map          +1 => 207
controlclient_map_response_map_delta    +1 => 204
controlclient_map_response_message      +1 => 275
magicsock_disco_recv_ping               +3 => 258
magicsock_disco_recv_pong               +2 => 221
magicsock_disco_recv_udp                +5 => 479
magicsock_disco_send_derp               +1 => 6
magicsock_disco_send_udp                +7 => 545
magicsock_disco_sent_derp               +1 => 6
magicsock_disco_sent_udp                +7 => 545
magicsock_recv_data_ipv6                +1 => 86
magicsock_send_data                     +1 => 90
magicsock_send_derp                     +1 => 12
magicsock_send_derp_queued              +1 => 12
magicsock_send_udp                      +8 => 633

Updates #3307

Change-Id: I5ac2511e3ad24fa1e6ea958c3946fecebe4f79a7
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-16 13:48:21 -08:00
David Anderson
41da7620af go.mod: update wireguard-go to pick up roaming toggle
wgengine/wgcfg: introduce wgcfg.NewDevice helper to disable roaming
at all call sites (one real plus several tests).

Fixes tailscale/corp#3016.

Signed-off-by: David Anderson <danderson@tailscale.com>
Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-11-16 13:15:04 -08:00
Brad Fitzpatrick
400ed799e6 net/dns: work around old systemd-resolved setLinkDomain length limit
Don't set all the *.arpa. reverse DNS lookup domains if systemd-resolved
is old and can't handle them.

Fixes #3188

Change-Id: I283f8ce174daa8f0a972ac7bfafb6ff393dde41d
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-16 12:54:21 -08:00
Brian Fallik
9fa6cdf7bf fix minor typo
Signed-off-by: Brian Fallik <bfallik@gmail.com>
2021-11-16 11:03:43 -08:00
Brad Fitzpatrick
24ea365d48 netcheck, controlclient, magicsock: add more metrics
Updates #3307

Change-Id: Ibb33425764a75bde49230632f1b472f923551126
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-16 10:48:19 -08:00
Brad Fitzpatrick
3b541c833e util/clientmetric, logtail: log metric changes
Updates #3307

Change-Id: I1399ebd786f6ff7defe6e11c0eb651144c071574
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-16 08:06:31 -08:00
Brad Fitzpatrick
68917fdb5d cmd/tailscale/cli: add "debug metrics" subcommand
To let users inspect the tailscaled metrics easily.

Updates #3307

Change-Id: I922126ca0626659948c57de74c6ef62f40ef5f5f
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-15 15:13:25 -08:00
Brad Fitzpatrick
945290cc3f cmd/tailscale/cli: migrate hidden debug subcommand to use subcomands
It was a mess of flags. Use subcommands under "debug" instead.

And document loudly that it's not a stable interface.

Change-Id: Idcc58f6a6cff51f72cb5565aa977ac0cc30c3a03
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-15 15:03:58 -08:00
Brad Fitzpatrick
57b039c51d util/clientmetrics: add new package to add metrics to the client
And annotate magicsock as a start.

And add localapi and debug handlers with the Prometheus-format
exporter.

Updates #3307

Change-Id: I47c5d535fe54424741df143d052760387248f8d3
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-15 13:46:05 -08:00
David Anderson
c5d572f371 net/dns: correctly handle NetworkManager-managed DNS that points to resolved.
Fixes #3304

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-11-15 12:21:25 -08:00
Brad Fitzpatrick
f7da8c77bd tstest/integration/testcontrol: fix data race
Fix race from 1ec99e99f4

Fixes #3289

Change-Id: I58158d3f82339ac171fb14827c5f158d602327f4
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-11 08:25:16 -08:00
David Anderson
5b94f67956 control/noise: make Conn.readNLocked less surprising.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-11-10 12:13:54 -08:00
David Anderson
a34350ffda control/noise: factor out nonce checking and incrementing into a type.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-11-10 12:13:54 -08:00
David Anderson
d3acd35a90 control/noise: make message headers match the specification.
Only the initiation message should carry a protocol version, all
others are just type+len.

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-11-10 12:13:54 -08:00
David Anderson
a63c4ab378 control/noise: don't panic when handling ciphertext.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-11-10 12:13:54 -08:00
David Anderson
4004b22fe5 control/noise: stop using poly1305 package constants.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-11-10 12:13:54 -08:00
David Anderson
293431aaea control/noise: use key.Machine{Public,Private} as appropriate.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-11-10 12:13:54 -08:00
David Anderson
edb33d65c3 control/noise: don't cache mixer, just rebuild a BLAKE2s each time.
This should optimize out fine, and readability is preferable to performance
here.

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-11-10 12:13:54 -08:00
David Anderson
7e9e72887c control/noise: add singleUseCHP, use it to simplify nonce/key tracking in handshake.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-11-10 12:13:54 -08:00
David Anderson
cf90392174 control/noise: review fixups
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-11-10 12:13:54 -08:00
David Anderson
0b392dbaf7 control/noise: adjust implementation to match revised spec.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-11-10 12:13:54 -08:00
David Anderson
89a68a4c22 control/noise: include the protocol version in the Noise prologue.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-11-10 12:13:54 -08:00
David Anderson
5e005a658f control/noise: fix typo in docstring.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-11-10 12:13:54 -08:00
David Anderson
eabca699ec control/noise: remove allocations in the encrypt and decrypt paths.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-11-10 12:13:54 -08:00
David Anderson
da7544bcc5 control/noise: implement the base transport for the 2021 control protocol.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-11-10 12:13:54 -08:00
Brad Fitzpatrick
3e1daab704 hostinfo, control/controlclient: tell control when Ubuntu has disabled Tailscale's sources
Fixes #3177
Updates #2500

Change-Id: Iff2a8e27ec7d36a1c210263d6218f20ebed37924
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-10 09:56:58 -08:00
Brad Fitzpatrick
d2ef73ed82 control/controlclient: rename a variable to not shadow a package name
Change-Id: I1bcb577cb2c47e936d545ad57f308e57399de323
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-10 08:11:29 -08:00
Maisem Ali
d6dde5a1ac ipn/ipnlocal: handle key extensions after key has already expired
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2021-11-08 18:15:09 -08:00
Maisem Ali
eccc2ac6ee net/interfaces/windows: update Tailscale interface detection logic to
account for new wintun naming.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2021-11-08 07:44:33 -08:00
Brad Fitzpatrick
ad63fc0510 control/controlclient: make js/wasm work with Go 1.18+
Updates #3157

Change-Id: I2d67e582842ab3638d720bb5db4701b878ad4473
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-07 13:49:55 -08:00
Brad Fitzpatrick
87137405e5 ipn/ipnserver: grant js/wasm all localapi permissions
Updates #3157

Change-Id: I3b63762583a4d655eac33ce3dfda37a1f5135a57
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-07 12:13:15 -08:00
Brad Fitzpatrick
40e13c316c paths: add missing js/wasm stub
Change-Id: Iae4838f5fa1dc0cd491d5a3ac906fd3cdacb173c
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-07 12:13:15 -08:00
Brad Fitzpatrick
0edd2d1cd5 safesocket: add js/wasm implementation with in-memory net.Conn
Updates #3157

Change-Id: Ia35b1e259011fb86f8c4e01f62146f9fd4c9b7c6
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-07 12:13:14 -08:00
Brad Fitzpatrick
01bd789c26 ipn/ipnserver: add Server.LocalBackend accessor
Was done as part of e6fbc0cd54 for ssh
work, but wasn't committed yet. Including it here both to minimize the
ssh diff size, and because I need it for a separate change.

Change-Id: If6eb54a2ca7150ace96488ed14582c2c05ca3422
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-07 11:31:52 -08:00
Michael Stapelberg
b3abdc381d tsnet: set varRoot state directory field
This makes tsnet work on https://gokrazy.org! 🎉

Signed-off-by: Michael Stapelberg <michael@stapelberg.de>
2021-11-07 10:56:23 -08:00
Brad Fitzpatrick
e6fbc0cd54 cmd/tailscaled, ipn/ipnserver: refactor ipnserver
More work towards removing the massive ipnserver.Run and ipnserver.Options
and making composable pieces.

Work remains. (The getEngine retry loop on Windows complicates things.)
For now some duplicate code exists. Once the Windows side is fixed
to either not need the retry loop or to move the retry loop into a
custom wgengine.Engine wrapper, then we can unify tailscaled_windows.go
too.

Change-Id: If84d16e3cd15b54ead3c3bb301f27ae78d055f80
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-05 15:00:02 -07:00
Brad Fitzpatrick
5f36ab8a90 tstest/integration: go generate
Change-Id: I49d19007a16261e447240e149deac24c15c93fce
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-05 14:43:51 -07:00
Brad Fitzpatrick
2b082959db safesocket: add WindowsLocalPort const
Remove all the 41112 references.

Change-Id: I2d7ed330d457e3bb91b7e6416cfb2667611e50c4
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-05 14:05:13 -07:00
Denton Gentry
1ec99e99f4 tstest: extend node key expiration integration test.
Can produce the problem in #2515, preparing to test a fix.
Marked as t.Skip() until we have a fix.

Updates https://github.com/tailscale/tailscale/issues/2515

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2021-11-04 11:46:42 -07:00
dependabot[bot]
12148dcf48 go.mod: bump github.com/frankban/quicktest from 1.13.1 to 1.14.0
Bumps [github.com/frankban/quicktest](https://github.com/frankban/quicktest) from 1.13.1 to 1.14.0.
- [Release notes](https://github.com/frankban/quicktest/releases)
- [Commits](https://github.com/frankban/quicktest/compare/v1.13.1...v1.14.0)

---
updated-dependencies:
- dependency-name: github.com/frankban/quicktest
  dependency-type: direct:production
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <support@github.com>
2021-11-04 09:39:31 -07:00
Brad Fitzpatrick
337757a819 ipn/ipnlocal, control/controlclient: don't propagate all map errors to UI
Fixes regression from 81cabf48ec which made
all map errors be sent to the frontend UI.

Fixes #3230

Change-Id: I7f142c801c7d15e268a24ddf901c3e6348b6729c
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-03 17:56:54 -07:00
David Anderson
0532eb30db all: replace tailcfg.DiscoKey with key.DiscoPublic.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-11-03 14:00:16 -07:00
Mangirdas
f771327f0c Add multiarch image make target
Updates #3112

Signed-off-by: Mangirdas <mangirdas@judeikis.lt>
2021-11-03 13:13:20 -07:00
Brad Fitzpatrick
649f7556e8 cmd/tailscaled, ipn: add tailscaled --statedir flag for var directory
Fixes #2932

Change-Id: I1aa2b323ad542386d140f8336bcc4dcbb8310bd0
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-03 13:12:38 -07:00
Brad Fitzpatrick
c7bff35fee ipn/ipnlocal: add owner-only debug handler to get process env
For debugging Synology. Like the existing goroutines handler, in that
it's owner-only.

Change-Id: I852f0626be8e1c0b6794c1e062111d14adc3e6ac
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-03 13:12:32 -07:00
Brad Fitzpatrick
6d82a18916 tstest/integration: don't include stdlib deps in go generate output
Causes too much churn for zero benefit.

Change-Id: I838f8cdb5723f122f11dd4bbce5e9c07755c3cd9
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-03 11:59:59 -07:00
Josh Bleecher Snyder
c467ed0b62 wgengine/wgcfg: always close io.Pipe
In DeviceConfig, we did not close r after calling FromUAPI.
If FromUAPI returned early due to an error, then it might
not have read all the data that IpcGetOperation wanted to write.
As a result, IpcGetOperation could hang, as in #3220.

We were also closing the wrong end of the pipe after IpcSetOperation
in ReconfigDevice.

To ensure that we get all available information to diagnose
such a situation, include all errors anytime something goes wrong.

This should fix the immediate crashing problem in #3220.
We'll then need to figure out why IpcGetOperation was failing.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-11-02 17:50:15 -07:00
Josh Bleecher Snyder
3fd5f4380f util/multierr: new package
github.com/go-multierror/multierror served us well.
But we need a few feature from it (implement Is),
and it's not worth maintaining a fork of such a small module.

Instead, I did a clean room implementation inspired by its API.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-11-02 17:50:15 -07:00
David Anderson
17b5782b3a types/key: delete legacy NodeKey type.
Fixes #3206

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-11-02 14:14:32 -07:00
David Anderson
7e6a1ef4f1 tailcfg: use key.NodePublic in wire protocol types.
Updates #3206.

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-11-02 09:11:43 -07:00
David Anderson
7e8d5ed6f3 ipn: use key.NodePublic instead of tailcfg.NodeKey
Updates #3206

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-11-01 20:32:10 -07:00
David Anderson
c17250cee2 ipn/ipnstate: use key.NodePublic instead of tailcfg.NodeKey.
Updates #3206

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-11-01 20:32:10 -07:00
David Anderson
c3d7115e63 wgengine: use key.NodePublic instead of tailcfg.NodeKey.
Updates #3206

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-11-01 18:28:45 -07:00
David Anderson
72ace0acba wgengine/magicsock: use key.NodePublic instead of tailcfg.NodeKey.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-11-01 18:03:48 -07:00
David Anderson
d6e7cec6a7 types/netmap: use key.NodePublic instead of tailcfg.NodeKey.
Update #3206

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-11-01 17:07:40 -07:00
Brad Fitzpatrick
408b0923a6 wgengine/router: remove last non-test "ip" command usage on Linux
Updates #391

Change-Id: Ic2c3f8460b1e4b8d34b936a1725705fcc1effbae
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-01 15:52:24 -07:00
Brad Fitzpatrick
ff1954cfd9 wgengine/router: use netlink for ip rules on Linux
Using temporary netlink fork in github.com/tailscale/netlink until we
get the necessary changes upstream in either vishvananda/netlink
or jsimonetti/rtnetlink.

Updates #391

Change-Id: I6e1de96cf0750ccba53dabff670aca0c56dffb7c
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-01 15:40:36 -07:00
Brad Fitzpatrick
5dc5bd8d20 cmd/tailscaled, wgengine/netstack: always wire up netstack
Even if not in use. We plan to use it for more stuff later.

(not for iOS or macOS-GUIs yet; only tailscaled)

Change-Id: Idaef719d2a009be6a39f158fd8f57f8cca68e0ee
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-01 14:11:30 -07:00
Brad Fitzpatrick
ff597e773e tailcfg, control/controlclient: add method to exit client from control plane
Change-Id: Ic28ef283ba63396b68fab86bfb0a8ee8f432474c
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-01 11:59:04 -07:00
Brad Fitzpatrick
0303ec44c3 go.mod: bump netstack for mipsle fix
Fixes #3233

Change-Id: I18d1af886402774ce0ecc77dae3bc71eb8ba5c9d
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-01 11:23:05 -07:00
Brad Fitzpatrick
c18b9d58aa tstest/archtest: add GOARCH-specific tests, run via qemu-user
Updates #3233

Change-Id: Ia224c90490d41e50a1d547eeea709b0d9171c1f9
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-11-01 11:17:43 -07:00
Xe
b02eb1d5c5 scripts/installer: handle fedora (#3235)
We missed a switch case.

Signed-off-by: Christine Dodrill <xe@tailscale.com>
2021-11-01 12:29:48 -04:00
oocococo
3a2b0fc36c cmd/derper: support custom TLS port when in manual mode (#3231)
Fixes #3232

Change-Id: I8dae5c01f9dfdfd6d45e34e4ca3534b642ae5c8e
Signed-off-by: oocococo <mercurial.lx@gmail.com>
2021-10-31 18:31:49 -07:00
David Anderson
8d14bc32d1 tstest/integration: use key.NodePublic instead of tailcfg.NodeKey.
Updates #3206

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-29 17:49:16 -07:00
David Anderson
84c3a09a8d types/key: export constants for key size, not a method.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-29 17:39:04 -07:00
David Anderson
6422789ea0 disco: use key.NodePublic instead of tailcfg.NodeKey.
Updates #3206

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-29 17:39:04 -07:00
David Anderson
0fcc88873b tailcfg: remove NodeKeyFromNodePublic.
Updates #3206

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-29 16:35:32 -07:00
David Anderson
c0ae1d2563 tailcfg: update go generate, which apparently normalizes type aliases.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-29 16:24:38 -07:00
David Anderson
418adae379 various: use NodePublic.AsNodeKey() instead of tailcfg.NodeKeyFromNodePublic()
Updates #3206

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-29 16:19:27 -07:00
David Anderson
ff16e58d23 tailcfg: move NodeKey type to types/key.
This leaves behind a type alias and associated constructor, to allow
for gradual switchover.

Updates #3206.

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-29 16:04:45 -07:00
David Anderson
15d329b4fa tailcfg: add marshaling round-tripping test.
Temporary until #3206 goes away, but having changed the marshal/unmarshal
implementation I got nervous about the new one doing the correct thing.
Thankfully, the test says it does.

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-29 15:21:41 -07:00
David Anderson
27e83402a8 cmd/tailscaled: fix depaware. 2021-10-29 15:07:13 -07:00
David Anderson
b43362852c types/key: delete legacy undifferentiated key types.
Updates #3206

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-29 15:01:12 -07:00
David Anderson
eeb97fd89f various: remove remaining uses of key.NewPrivate.
Updates #3206

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-29 15:01:12 -07:00
David Anderson
ccd36cb5b1 wgengine: remove use of legacy key parsing helper.
Updates #3206

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-29 14:57:32 -07:00
David Anderson
743293d473 types/key: remove node key AsPublic/AsPrivate compat shims.
Updates #3206.

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-29 14:48:36 -07:00
David Anderson
2486d7cb9b tailcfg: remove use of legacy key parsing helper.
Updates #3206.

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-29 14:48:07 -07:00
David Anderson
ef241f782e wgengine/magicsock: remove uses of tailcfg.DiscoKey.
Updates #3206

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-29 14:31:44 -07:00
David Anderson
073a3ec416 types/key: correct ShortString representation of DiscoPublic.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-29 14:31:44 -07:00
Brad Fitzpatrick
cb87b7aa5b version: only prefix VERSION.txt to version if not link-stamped
(Fix to 31e4f60047)

The 31e4f60047 change accidentally
made it always prepend the VERSION.txt, even when it was already
link-stamped properly.

Updates #81

Change-Id: I6cdcff096c25d92d566ad3ac1de5771c7384daea
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-29 14:05:03 -07:00
David Anderson
06dccea416 types/key: fix license header on disco files.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-29 13:45:49 -07:00
David Anderson
05cc2f510b types/key: new types for disco keys.
Needed for #3206 to remove final uses of key.{Public,Private}.

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-29 13:44:02 -07:00
Maisem Ali
05e55f4a0b logtail/filch: limit buffer file size to 50MB
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2021-10-29 13:31:30 -07:00
David Anderson
55b6753c11 wgengine/magicsock: remove use of key.{Public,Private}.
Updates #3206

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-29 13:20:13 -07:00
Brad Fitzpatrick
429632d32c ipn/ipnlocal: treat js/wasm interative logins as ephemeral for now
At least until js/wasm starts using browser LocalStorage or something.
But for the foreseeable future, any login from a browser should
be considered ephemeral as the tab can close at any time and lose
the wireguard key, never to be seen again.

Updates #3157

Change-Id: I6c410d86dc7f9f233c3edd623313d9dee2085aac
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-29 11:57:12 -07:00
David Anderson
c1d009b9e9 ipn/ipnstate: use key.NodePublic instead of the generic key.Public.
Updates #3206.

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-29 10:00:59 -07:00
David Anderson
ebae0d95d0 Revert "Revert "tailcfg: remove reference to types/key.Public.""
Updates #3206

This reverts commit ef14663934.
2021-10-29 09:38:44 -07:00
David Anderson
ef14663934 Revert "tailcfg: remove reference to types/key.Public."
Breaks corp unit tests.

Updates #3206

This reverts commit 94f6257fde.
2021-10-28 19:00:29 -07:00
David Anderson
94f6257fde tailcfg: remove reference to types/key.Public.
Updates #3206

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-28 16:16:38 -07:00
David Anderson
1f06f77dcb derp: remove package shadowing of types/key.
Updates #3206

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-28 16:13:28 -07:00
David Anderson
37c150aee1 derp: use new node key type.
Update #3206

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-28 16:02:11 -07:00
David Anderson
15376f975b types/wgkey: delete, no longer used.
Updates #3206

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-28 14:53:38 -07:00
Brad Fitzpatrick
19189d7018 wgengine/router: add a addrFamily type [linux]
In prep for more netlink-ification.

Change-Id: I7c34a04001988107dc2583597aa4f26ddb887e91
2021-10-28 14:52:29 -07:00
David Anderson
c41fe182f0 cmd/tailscaled: update depaware.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-28 14:28:59 -07:00
David Anderson
4d38194c21 control/controlclient: stop using wgkey.
Updates #3206

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-28 14:22:51 -07:00
David Anderson
e03fda7ae6 wgengine/magicsock: remove test uses of wgkey.
Updates #3206

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-28 14:17:25 -07:00
Brad Fitzpatrick
7c40a5d440 wgengine/router: refactor in prep for Linux netlink-ification
Pull out the list of policy routing rules to a data structure
now shared between the add & delete paths, but to also be shared
by the netlink paths in a future change.

Updates #391

Change-Id: I119ab1c246f141d639006c808b61c585c3d67924
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-28 13:56:46 -07:00
Brad Fitzpatrick
ada8cd99af control/controlclient: add a LoginEphemeral LoginFlags bit
Change-Id: Ib9029ea0c49aa2ee1b6aac6e464ab1f16aef92e8
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-28 13:21:35 -07:00
Josh Bleecher Snyder
94fb42d4b2 all: use testingutil.MinAllocsPerRun
There are a few remaining uses of testing.AllocsPerRun:
Two in which we only log the number of allocations,
and one in which dynamically calculate the allocations
target based on a different AllocsPerRun run.

This also allows us to tighten the "no allocs"
test in wgengine/filter.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-10-28 12:48:37 -07:00
Josh Bleecher Snyder
1df865a580 wgengine/magicsock: allow even fewer allocs per UDP receive
We improved things again for Go 1.18. Lock that in.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-10-28 12:48:37 -07:00
Josh Bleecher Snyder
c1d377078d wgengine/magicsock: use testingutil.MinAllocsPerRun
This speeds up and deflakes the test.

Fixes #2826 (again)

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-10-28 12:48:37 -07:00
Josh Bleecher Snyder
4bb2c6980d util/testingutil: new package with MinAllocsPerRun
testing.AllocsPerRun measures the total allocations performed
by the entire program while repeatedly executing a function f.
If some unrelated part of the rest of the program happens to
allocate a lot during that period, you end up with a test failure.

Ideally, the rest of the program would be silent while
testing.AllocsPerRun executes.

Realistically, that is often unachievable.

AllocsPerRun attempts to mitigate this by setting GOMAXPROCS to 1,
but that doesn't prevent other code from running;
it only makes it less likely.

You can also mitigate this by passing a large iteration count to
AllocsPerRun, but that is unreliable and needlessly expensive.

Unlike most of package testing, AllocsPerRun doesn't use any
toolchain magic, so we can just write a replacement.

One wild idea is to change how we count mallocs.
Instead of using runtime.MemStats, turn on memory profiling with a
memprofilerate of 1. Discard all samples from the profile whose stack
does not contain testing.AllocsPerRun. Count the remaining samples to
determine the number of mallocs.

That's fun, but overkill.

Instead, this change adds a simple API that attempts to get f to
run at least once with a target number of allocations.
This is useful when you know that f should allocate consistently.
We can then assume that any iterations with too many allocations
are probably due to one-time costs or background noise.

This suits most uses of AllocsPerRun.

Ratcheting tests tend to be significantly less flaky,
because they are biased towards success.
They can also be faster, because they can exit early,
once success has been reached.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-10-28 12:48:37 -07:00
Josh Bleecher Snyder
640de1921f depaware: update
To fix build broken by c9bf773312.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-10-28 12:35:14 -07:00
Brad Fitzpatrick
aad46bd9ff wgengine/router: stop cleaning up old dev rules on Linux
Anybody using that one old, unreleased version of Tailscale from over
a year ago should've rebooted their machine by now to get various
non-Tailscale security updates. :)

Change-Id: If9e043cb008b20fcd6ddfd03756b3b23a9d7aeb5
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-28 12:29:54 -07:00
David Anderson
c9bf773312 wgengine/magicsock: replace use of wgkey with new node key type.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-28 11:21:52 -07:00
Brad Fitzpatrick
d36c0d3566 wgengine/router: add debug test to enumerate rules
No non-test changes.

Updates #391

Change-Id: Ia88610c08e07a119d002e58250463cb4659b9f54
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-28 11:12:16 -07:00
David Anderson
6e5175373e types/netmap: use new node key type.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-28 10:44:34 -07:00
David Anderson
96ad68c5d6 ipn: remove mention of wgkey in comment.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-28 10:40:44 -07:00
David Anderson
bab2d92c42 tailcfg: remove use of wgkey.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-28 10:39:56 -07:00
David Anderson
3164c7410e wgengine/wgcfg: remove unused helper function.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-28 10:38:13 -07:00
David Anderson
0c546a28ba types/persist: use new node key type.
Updates #3206

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-28 10:29:43 -07:00
Denton Gentry
5302e4be96 net/portmapper: only print PCP/PMP if VerboseLogs
Make UPnP, NAT-PMP, and PCP packet reception logs be [v1] so
they will never appear on stdout and instead only go to logtail.

```
$ tailscale netcheck
2021/10/15 22:50:31 portmap: Got PMP response; IP: w.x.y.z, epoch: 1012707
2021/10/15 22:50:31 portmap: Got PCP response: epoch: 1012707

Report:
        * UDP: true
        * IPv4: yes, w.x.y.z:1511
        * IPv6: no
        * MappingVariesByDestIP: true
        * HairPinning: false
        * PortMapping: NAT-PMP, PCP
        * Nearest DERP: San Francisco
        * DERP latency:
                - sfo: 5.9ms   (San Francisco)
                - sea: 24ms    (Seattle)
                - dfw: 45ms    (Dallas)
                - ord: 53.7ms  (Chicago)
                - nyc: 74.1ms  (New York City)
                - tok: 111.1ms (Tokyo)
                - lhr: 139.4ms (London)
                - syd: 152.7ms (Sydney)
                - fra: 153.1ms (Frankfurt)
                - sin: 182.1ms (Singapore)
                - sao: 190.1ms (S_o Paulo)
                - blr: 218.6ms (Bangalore)
```

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2021-10-28 10:18:51 -07:00
Brad Fitzpatrick
dc2fbf5877 wgengine/router: start using netlink instead of 'ip' on Linux
Converts up, down, add/del addresses, add/del routes.

Not yet done: rules.

Updates #391

Change-Id: I02554ca07046d18f838e04a626ba99bbd35266fb
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-28 10:16:26 -07:00
Brad Fitzpatrick
7b87c04861 tailcfg: add RegisterRequest.Ephemeral to request new ephemeral node
So js/wasm clients can log in for a bit using regular Gmail/GitHub auth
without using an ephemeral key but still have their node cleaned up
when they're done.

Updates #3157

Change-Id: I49e3d14e9d355a9b8bff0ea810b0016bfe8d47f2
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-28 10:05:36 -07:00
Michael Stapelberg
3ad11f6b8c Dockerfile: build/run instructions need a /, not :
The image is pulled using tailscale/tailscale:latest, and can be run using tailscale/tailscale

Signed-off-by: Michael Stapelberg <michael@stapelberg.de>
2021-10-28 09:51:50 -07:00
Brad Fitzpatrick
31e4f60047 version: embed VERSION.txt in unstamped version
Temporary measure until we switch to Go 1.18.

    $ go run ./cmd/tailscale version
    1.17.0-date.20211022
      go version: go1.17

Updates #81

Change-Id: Ic82ebffa5f46789089e5fb9810b3f29e36a47f1a
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-28 09:48:24 -07:00
David Anderson
a9c78910bd wgengine/wgcfg: convert to use new node key type.
Updates #3206

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-28 09:39:23 -07:00
David Anderson
a47158e14d cmd/derper: use new node key type.
Updates #3206

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-28 09:39:23 -07:00
David Anderson
bc89a796ec types/key: add a dedicated type for node keys.
Complete with converters to all the other types that represent a
node key today, so the new type can gradually subsume old ones.

Updates #3206

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-28 09:16:39 -07:00
Brad Fitzpatrick
22dbaa0894 ipn/ipnserver: add New, Server.Server
Change-Id: I1dc85a5131b9a628d7fc780fde7103492cd3f1f8
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-28 09:01:01 -07:00
Brad Fitzpatrick
d381bc2b6c ipn/ipnserver: move the unserved connection logic to a Listener
So future refactors can only deal with a net.Listener and
be unconcerned with their caller's (Windows-specific) struggles.

Change-Id: I0af588b9a769ab65c59b0bd21f8a0c99abfa1784
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-28 09:01:01 -07:00
Brad Fitzpatrick
c23a378f63 ipn/ipnserver: start refactoring ipnserver.Run into smaller pieces
I'll keep ipnserver.Run for compatibility, but it'll be a wrapper
around several smaller pieces. (more testable too)

For now, start untangling some things in preparation.

Plan is to have to have a constructor for the just-exported
ipnserver.Server type that takes a LocalBackend and can
accept (in a new method) on a provided listener.

Change-Id: Ide73aadaac1a82605c97a2af1321d0d8f60b2a8c
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-28 09:01:01 -07:00
Brad Fitzpatrick
e4d2ef2b67 go.sum: tidy
Change-Id: I198755a3a94d89d838ff817573fbdd198412b2f3
2021-10-27 21:36:49 -07:00
Josh Bleecher Snyder
cf8fcc1254 syncs: mark as safe for Go 1.18
Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-10-27 18:10:09 -07:00
Brad Fitzpatrick
869999955d ipn/ipnserver: export server type as Server
It's all opaque, there's no constructor, and no exported
methods, so it's useless at this point, but this is one
small refactoring step.

Change-Id: Id961e8880cf0c84f1a0a989eefff48ecb3735add
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-27 15:48:28 -07:00
Josh Bleecher Snyder
f27950e97f go.mod: upgrade netaddr, netstack
For Go 1.18 support.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-10-27 15:47:15 -07:00
David Anderson
060ba86baa net/portmapper: ignore IGD SSDP responses from !defaultgw
Now that we multicast the SSDP query, we can get IGD offers from
devices other than the current device's default gateway. We don't want
to accidentally bind ourselves to those.

Updates #3197

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-27 15:34:27 -07:00
Brad Fitzpatrick
675f9cd199 cmd/tailscale/cli: add, use log.Fatalf indirection for js/wasm
Updates #3157

Change-Id: I97a4962a44bd36313ff68388e3de0d852a8fa869
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-27 15:19:52 -07:00
David Anderson
4a65b07e34 net/portmapper: also send UPnP SSDP query to the SSDP multicast address.
Fixes #3197

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-27 15:02:03 -07:00
Brad Fitzpatrick
5df7ac70d6 cmd/tailscale/cli: add Stdout, Stderr and output through them
So js/wasm can override where those go, without implementing
an *os.File pipe pair, etc.

Updates #3157

Change-Id: I14ba954d9f2349ff15b58796d95ecb1367e8ba3a
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-27 14:53:46 -07:00
Brad Fitzpatrick
2ce5fc7b0a safesocket: fail early on js/wasm
Updates #3157

Change-Id: Ib78efb3b1ba34ca4fb34296033b95327188774a7
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-27 14:53:28 -07:00
Brad Fitzpatrick
3b5ada1fd8 cmd/tailscale/cli: use errors.Is to check ff's wrapped flag errors
And also check from its Parse method.

Change-Id: I18754920575254cb6858a16b7954e74aa16483a1
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-27 14:06:22 -07:00
Brad Fitzpatrick
75de4e9cc2 cmd/tailscale/cli: don't ExitOnError on js/wasm
An os.Exit brings down the whole wasm module.

Updates #3157

Change-Id: I3daa97fd854715b901f3dbb04b57d841576b60b1
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-27 13:59:12 -07:00
Brad Fitzpatrick
b0b0a80318 net/netcheck: implement netcheck for js/wasm clients
And the derper change to add a CORS endpoint for latency measurement.

And a little magicsock change to cut down some log spam on js/wasm.

Updates #3157

Change-Id: I5fd9e6f5098c815116ddc8ac90cbcd0602098a48
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-27 09:59:31 -07:00
Brad Fitzpatrick
eebe7afad7 derp/derphttp: only log about a weird upgrade if any was specified
Otherwise random browser requests to /derp cause log spam.

Change-Id: I7bdf991d2106f0323868e651156c788a877a90d5
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-27 09:41:25 -07:00
Maisem Ali
81cabf48ec control/controlclient,tailcfg: propagate registration errors to the frontend
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2021-10-27 06:57:26 -07:00
Denton Gentry
139a6c4c9c net/dns: detect when resolvconf points to systemd-resolved.
There are /etc/resolv.conf files out there where resolvconf wrote
the file but pointed to systemd-resolved as the nameserver.
We're better off handling those as systemd-resolved.

> # Dynamic resolv.conf(5) file for glibc resolver(3) generated by resolvconf(8)
> #     DO NOT EDIT THIS FILE BY HAND -- YOUR CHANGES WILL BE OVERWRITTEN
> # 127.0.0.53 is the systemd-resolved stub resolver.
> # run "systemd-resolve --status" to see details about the actual nameservers.

Fixes https://github.com/tailscale/tailscale/issues/3026
Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2021-10-26 18:00:31 -07:00
David Anderson
a320d70614 net/dns: fall back to copy+delete/truncate if moving to/from /etc/resolv.conf fails.
In some containers, /etc/resolv.conf is a bind-mount from outside the container.
This prevents renaming to or from /etc/resolv.conf, because it's on a different
filesystem from linux's perspective. It also prevents removing /etc/resolv.conf,
because doing so would break the bind-mount.

If we find ourselves within this environment, fall back to using copy+delete when
renaming to /etc/resolv.conf, and copy+truncate when renaming from /etc/resolv.conf.

Fixes #3000

Co-authored-by: Denton Gentry <dgentry@tailscale.com>
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-26 09:03:37 -07:00
David Anderson
04d24d3a38 net/dns: move directManager function below directManager's definition.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-26 09:03:37 -07:00
David Anderson
422ea4980f net/dns: remove a tiny wrapper function that isn't contributing anything.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-26 09:03:37 -07:00
Maisem Ali
10745c099a tailcfg: add Node.Tags
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2021-10-25 22:04:45 -07:00
Maisem Ali
85fa1b0d61 wgengine: fail NewUserspaceEngine if wireguard device doesn't come up
Just something I ran across while debugging an unrelated failure. This
is not in response to any bug/issue.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2021-10-25 12:34:14 -07:00
Maya Kaczorowski
59a906df47 Merge pull request #3179 from tailscale/bugreport
.github: Add Synology as an OS
2021-10-25 09:59:39 -07:00
Denton Gentry
c1293b3858 .github: Add Synology as an OS
Sufficiently different from Linux to split it out separately.

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2021-10-24 06:01:29 -07:00
Brad Fitzpatrick
505f844a43 cmd/derper, derp/derphttp: add websocket support
Updates #3157

Change-Id: I337a919a3b350bc7bd9af567b49c4d5d6616abdd
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-22 12:51:30 -07:00
David Crawshaw
0b62f26349 magicsock: remove test data race
Speculative, I haven't been able to replicate it locally.

Fixes #3156

Signed-off-by: David Crawshaw <crawshaw@tailscale.com>
2021-10-22 11:19:07 -07:00
Brad Fitzpatrick
09e692e318 health: don't look for UDP goroutines in js/wasm health check
Updates #3157

Change-Id: I43d97e6876eeb2d1936fc567835134568bb8615c
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-22 09:12:00 -07:00
Brad Fitzpatrick
ed3fb197ad wgengine/magicsock: fix/disable a few misc things to get js/wasm working
Updates #3157

Change-Id: Ie9e3a772bb9878584080bb257b32150492e26eaf
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-22 09:09:37 -07:00
Brad Fitzpatrick
a8e2cceefd net/netcheck: hard-code preferred DERP region 900 on js/wasm for now
See TODO in code.

Updates #3157

Change-Id: I3a14dd2cf51d3c21336bb357af5abc362a079ff4
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-22 09:08:15 -07:00
Brad Fitzpatrick
c209278a9b go.mod: bump wireguard-go to pick up upstreamed js/wasm build fixes
Updates #3157

Change-Id: I727cb5f77110c87850061aa3b9f03c15dbda70d3
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-21 10:37:07 -07:00
Brad Fitzpatrick
9b101bd6af net/tstun: don't compile the code New constructor on js/wasm
Updates #3157

Change-Id: I81603edf3e69e6f1517b0074eef6b648f2981c50
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-21 10:36:30 -07:00
David Anderson
c60806b557 scripts/installer.sh: use .asc suffix for armored debian gpg key URL.
Fixes #2512

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-20 18:58:50 -07:00
Maxim Merzhanov
9f954628e5 net/dns: ignore UnknownMethod error in SetLinkDefaultRoute for resolved manager
Signed-off-by: Maxim Merzhanov <maksimmerzh@gmail.com>
2021-10-20 16:31:24 -07:00
Brad Fitzpatrick
e25afc6656 wgengine/magicsock: don't try to determine endpoints on js/wasm
Avoid netcheck, LocalAddr, etc.

Updates #3157

Change-Id: Ibc875c787c0e101b8076e64833f4fcc809372815
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-20 12:57:45 -07:00
David Anderson
8e3b8dbb50 scripts/installer.sh: Correct support for Oracle Linux.
Co-Authored-By: Jonathan Hult <jhult@mythics.com>
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-20 12:47:38 -07:00
Brad Fitzpatrick
6cb2705833 wgengine/magicsock: don't run UDP listeners on js/wasm
Be DERP-only for now. (WebRTC can come later :))

Updates #3157

Change-Id: I56ebb3d914e37e8f4ab651306fd705b817ca381c
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-20 12:23:22 -07:00
Brad Fitzpatrick
8efc306e4f net/interfaces: assume the network's up on js/wasm
Updates #3157

Change-Id: If4acd33598ad5e8ef7fb5960964c9ac32bc8f68b
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-20 12:23:22 -07:00
Brad Fitzpatrick
9310713bfb all: fix some js/wasm compilation issues
Change-Id: I05a3a4835e225a1e413ec3540a7c7e4a2d477084
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-20 10:06:16 -07:00
Maisem Ali
0bf515e780 cmd/tailscale: changes to --advertise-tags should wait for possible
reauth.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2021-10-20 10:31:40 -04:00
David Anderson
1b4e007425 scripts/installer.sh: use expr for regex matches.
=~ doesn't work in posix shell, only in bash, and we don't use bash.

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-19 19:33:52 -07:00
David Anderson
7ce9c7ce84 scripts/installer.sh: use the appropriate apt key wrangling for the distro.
Updates #1937

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-19 19:15:07 -07:00
David Anderson
118fe105f5 scripts/installer.sh: add a few more supported distro versions.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-19 19:15:07 -07:00
Brad Fitzpatrick
c30fa5903d wgengine/magicsock: remove peerMap.byDiscoKey map
No longer used.

Updates #3088

Change-Id: I0ced3f87baa4053d3838d3c4a828ed0293923825
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-19 12:22:11 -07:00
David Crawshaw
3552d86525 wgengine/magicsock: turn down timeouts in tests
Before:

	--- PASS: TestActiveDiscovery (11.78s)
	    --- PASS: TestActiveDiscovery/facing_easy_firewalls (5.89s)
	    --- PASS: TestActiveDiscovery/facing_nats (5.89s)
	    --- PASS: TestActiveDiscovery/simple_internet (0.89s)

After:

	--- PASS: TestActiveDiscovery (1.98s)
	    --- PASS: TestActiveDiscovery/facing_easy_firewalls (0.99s)
	    --- PASS: TestActiveDiscovery/facing_nats (0.99s)
	    --- PASS: TestActiveDiscovery/simple_internet (0.89s)

Signed-off-by: David Crawshaw <crawshaw@tailscale.com>
2021-10-19 09:22:50 -07:00
dependabot[bot]
eaa0aef934 go.mod: bump github.com/creack/pty from 1.1.16 to 1.1.17
Bumps [github.com/creack/pty](https://github.com/creack/pty) from 1.1.16 to 1.1.17.
- [Release notes](https://github.com/creack/pty/releases)
- [Commits](https://github.com/creack/pty/compare/v1.1.16...v1.1.17)

---
updated-dependencies:
- dependency-name: github.com/creack/pty
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>
2021-10-18 15:34:09 -07:00
David Anderson
b956139b0c wgengine/magicsock: track IP<>node mappings without relying on discokeys.
Updates #3088.

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-18 14:58:21 -07:00
Brad Fitzpatrick
7a243ae5b1 wgengine/magicsock: finish TODO to speed up peerMap.forEachEndpointWithDiscoKey
Now that peerMap tracks the set of nodes for a DiscoKey.

Updates #3088

Change-Id: I927bf2bdfd2b8126475f6b6acc44bc799fcb489f
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-18 14:50:28 -07:00
Aaron Klotz
c6ea282b3f utils/winutil utils/winutil/vss: add utility function for extracting data from Windows System Restore Point backups.
utils/winutil/vss contains just enough COM wrapping to query the Volume Shadow Copy service for snapshots.
WalkSnapshotsForLegacyStateDir is the friendlier interface that adds awareness of our actual use case,
mapping the snapshots and locating our legacy state directory.

Updates #3011

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2021-10-18 15:48:42 -06:00
Aaron Klotz
6425f497b1 ipn/ipnserver paths: add paths.LegacyStateFilePath
Moving this information into a centralized place so that it is accessible to
code in subsequent commits.

Updates #3011

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2021-10-18 15:48:42 -06:00
Brad Fitzpatrick
11fdb14c53 wgengine/magicsock: don't check always-non-nil endpoint for nil-ness
Continuation of 2aa5df7ac1, remove nil
check because it can never be nil. (It previously was able to be nil.)

Change-Id: I59cd9ad611dbdcbfba680ed9b22e841b00c9d5e6
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-18 14:37:59 -07:00
David Anderson
e7eb46bced wgengine/magicsock: add an explicit else branch to peerMap update.
Clarifies that the replace+delete of peerinfo data is only when peerInfo
already exists.

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-18 13:05:52 -07:00
David Anderson
1c56643136 disco: amplify comment that disco ping's NodeKey shouldn't be trusted by itself.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-18 13:05:52 -07:00
Robert
cb030a0bb4 docs/k8s: add example about setting up a subnet router
Signed-off-by: Robert <rspier@pobox.com>
Co-authored-by: Maisem Ali <3953239+maisem@users.noreply.github.com>
2021-10-18 14:54:00 -04:00
Maisem Ali
53199738fb wgengine: don't try to delete legacy netfilter rules on synology.
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2021-10-18 14:51:25 -04:00
David Anderson
2aa5df7ac1 wgengine/magicsock: document and enforce that peerInfo.ep is non-nil.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-18 10:49:24 -07:00
David Anderson
521b44e653 wgengine/magicsock: move discoKey fields to the mutex-protected section.
Fixes #3106

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-18 10:49:24 -07:00
Maisem Ali
27799a1a96 wgengine: only use AmbientCaps on DSM7+
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2021-10-18 13:39:51 -04:00
Brad Fitzpatrick
a6d02dc122 wgengine/magicsock: track which NodeKey each DiscoKey was last for
This adds new fields (currently unused) to discoInfo to track what the
last verified (unambiguous) NodeKey a DiscoKey last mapped to, and
when.

Then on CallMeMaybe, Pong and on most Pings, we update the mapping
from DiscoKey to the current NodeKey for that DiscoKey.

Updates #3088

Change-Id: Idc4261972084dec71cf8ec7f9861fb9178eb0a4d
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-18 09:55:02 -07:00
Brad Fitzpatrick
c759fcc7d3 wgengine/magicsock: fix data race with sync.Pool in error+logging path
Fixes #3122

Change-Id: Ib52e84f9bd5813d6cf2e80ce5b2296912a48e064
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-17 17:27:57 -07:00
Brad Fitzpatrick
75a7779b42 disco, wgengine/magicsock: send self node key in disco pings
This lets clients quickly (sub-millisecond within a local LAN) map
from an ambiguous disco key to a node key without waiting for a
CallMeMaybe (over relatively high latency DERP).

Updates #3088

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-17 10:24:07 -07:00
Joe Tsai
9af27ba829 cmd/cloner: mangle "go:generate" in cloner.go
The "go generate" command blindly looks for "//go:generate" anywhere
in the file regardless of whether it is truly a comment.
Prevent this false positive in cloner.go by mangling the string
to look less like "//go:generate".

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2021-10-16 17:53:43 -07:00
Denton Gentry
def650b3e8 wgengine/magicsock: don't Rebind after STUN error if closed.
https://github.com/tailscale/tailscale/pull/3014 added a
rebind on STUN failure, which means there can now be a
tailscale.com/wgengine/magicsock.(*RebindingUDPConn).ReadFromNetaddr
in progress at the end of the test waiting for a STUN
response which will never arrive.

This causes a test flake due to the resource leak in those
cases where the Conn decided to rebind. For whatever reason,
it mostly flakes with Windows.

If the Conn is closed, don't Rebind after a send error.

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2021-10-16 17:22:13 -07:00
Brad Fitzpatrick
f55c2bccf5 wgengine/magicsock: don't call setAddrToDiscoLocked on DERP ping
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-16 07:43:48 -07:00
Brad Fitzpatrick
569f70abfd wgengine/magicsock: finish some renamings of discoEndpoint to endpoint
Renames only; continuation of earlier 8049063d35

These kept confusing me while working on #3088

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-15 22:26:07 -07:00
Brad Fitzpatrick
695df497ba wgengine/magicsock: delete peerMap.endpointForDiscoKey, remove remaining caller
The one remaining caller of peerMap.endpointForDiscoKey was making the
improper assumption that there's exactly 1 node with a given DiscoKey
in the network. That was the cause of #3088.

Now that all the other callers have been updated to not use
endpointForDiscoKey, there's no need to try to keep maintaining that
prone-to-misuse index.

Updates #3088

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-15 22:19:27 -07:00
Brad Fitzpatrick
04fd94acd6 wgengine/magicsock: remove endpointForDiscoKey call from handleDiscoMessage
A DiscoKey maps 1:n to endpoints. When we get a disco pong, we don't
necessarily know which endpoint sent it to us. Ask them all. There
will only usually be 1 (and in rare circumstances 2). So it's easier
to ask all two rather than building new maps from the random ping TxID
to its endpoint.

Updates #3088

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-15 21:59:15 -07:00
Brad Fitzpatrick
151b4415ca wgengine/magicsock: remove endpoint parameter from handlePingLocked
We can reply to a ping without knowing which exact node it's from.  As
long as it's in our netmap, it's safe to reply. If there's more than
one node with that discokey, it doesn't matter who we're relpying to.

Updates #3088

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-15 21:44:52 -07:00
Brad Fitzpatrick
d86081f353 wgengine/magicsock: add new discoInfo type for DiscoKey state, move some fields
As more prep for removing the false assumption that you're able to
map from DiscoKey to a single peer, move the lastPingFrom and lastPingTime
fields from the endpoint type to a new discoInfo type, effectively upgrading
the old sharedDiscoKey map (which only held a *[32]byte nacl precomputed key
as its value) to discoInfo which then includes that naclbox key.

Then start plumbing it into handlePing in prep for removing the need
for handlePing to take an endpoint parameter.

Updates #3088

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-15 20:48:44 -07:00
Brad Fitzpatrick
e5779f019e wgengine/magicsock: move temporary endpoint lookup later, add TODO to remove
Updates #3088

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-15 19:22:30 -07:00
Brad Fitzpatrick
36a07089ee wgengine/magicsock: remove redundant/wrong sharedDiscoKey delete
The pass just after in this method handles cleaning up sharedDiscoKey.
No need to do it wrong (assuming DiscoKey => 1 node) earlier.

Updates #3088

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-15 16:57:59 -07:00
Brad Fitzpatrick
3e80806804 wgengine/magicsock: pass src NodeKey to handleDiscoMessage for DERP disco msgs
And then use it to avoid another lookup-by-DiscoKey.

Updates #3088
2021-10-15 16:52:42 -07:00
Brad Fitzpatrick
82fa15fa3b wgengine/magicsock: start removing endpointForDiscoKey
It's not valid to assume that a discokey is globally unique.

This removes the first two of the four callers.

Updates #3088

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-15 16:44:02 -07:00
Maisem Ali
7817ab6b20 net/dns/resolver: set maxDoHInFlight to 1000 on iOS 15+.
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2021-10-14 23:29:23 -04:00
Maisem Ali
2662a1c98c hostinfo: add EnvType for Kubernetes
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2021-10-14 23:02:26 -04:00
Felipe Cruz Martinez
47ace13ac8 Fix k8s README
Use the correct KUBE_SECRET value
2021-10-14 19:12:48 -04:00
Maisem Ali
c6d3f622e9 ipn/ipnlocal: use netaddr.IPSetBuilder when constructing list of interface IPPrefixes.
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2021-10-14 18:53:54 -04:00
Maisem Ali
e538d47bd5 docs/k8s: update run.sh to use the correct socket path
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2021-10-14 18:09:12 -04:00
Brad Fitzpatrick
4a3e2842d9 net/interfaces: add List, GetList
And start moving funcs to methods on List.

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-14 15:06:12 -07:00
Brad Fitzpatrick
14f9c75293 wgengine/router: ignore Linux ip route error adding dup route
Updates #3060
Updates #391

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-14 14:00:45 -07:00
Brad Fitzpatrick
ddf3394b40 ipn/ipnlocal: don't try to block localhost traffic when using exit nodes
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-14 14:00:45 -07:00
David Crawshaw
77696579f5 net/dns/resolver: drop dropping log
Signed-off-by: David Crawshaw <crawshaw@tailscale.com>
2021-10-14 13:58:24 -07:00
Brad Fitzpatrick
7742caef0a .github/workflows: always ignore go:generate dnsfallback check
Keep the now-redundant github.ref branch check for
the future, in case we want to change the policy for main vs
release-branch again later. Save somebody the YAML debugging
time.
2021-10-14 13:57:02 -07:00
Joe Tsai
2fa004a2a0 cmd/cloner: emit go:generate pragmas (#3082)
Emit a go:generate pragma with the full set of flags passed to cloner.
This allows the user to simply run "go generate" at the location
of the generate file to reproduce the file.

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2021-10-14 12:25:55 -07:00
Brad Fitzpatrick
676fb458c3 net/dns/resolver: make hasRDNSBonjourPrefix match shorter queries too
Fixes tailscale/corp#2886
Updates tailscale/corp#2820
Updates #2442

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-13 15:49:45 -07:00
Maisem Ali
a6c3de72d6 docs/k8s: use ghcr.io for base image
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2021-10-13 17:55:14 -04:00
Brad Fitzpatrick
751c42c097 ipn: fix formatting of ExitNodeIP in MaskedPrefs
%#v on a netaddr.IP showed the netaddr.IP innards.

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-13 14:52:50 -07:00
Maisem Ali
9ab8492694 docker: install ip6tables
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2021-10-13 17:34:23 -04:00
Maisem Ali
45d4adcb63 docs/k8s: use tailscale/tailscale as base image
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2021-10-13 15:34:44 -04:00
Maisem Ali
061dab5d61 docker: only add tailscale and tailscaled binaries
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2021-10-13 14:43:29 -04:00
Maisem Ali
2c403cbb31 docs/k8s: add instructions on how to run as a sidecar or a proxy.
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2021-10-13 13:26:53 -04:00
nicksherron
f01ff18b6f all: fix spelling mistakes
Signed-off-by: nicksherron <nsherron90@gmail.com>
2021-10-12 21:23:14 -07:00
Maya Kaczorowski
9795fca946 .github: change issue checkboxes to dropdown 2021-10-12 20:58:33 -07:00
Maya Kaczorowski
7dbb1b51fe .github: change issue checkboxes to dropdown
Signed-off-by: Maya Kaczorowski <15946341+mayakacz@users.noreply.github.com>
2021-10-12 20:49:26 -07:00
Maisem Ali
c121fa81c4 tsnet: add TLS and LetsEncrypt example.
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2021-10-12 15:31:18 -07:00
Aaron Klotz
1991a1ac6a net/tstun: update tun_windows for wintun 0.14 API revisions, update wireguard-go dependency to 82d2aa87aa623cb5143a41c3345da4fb875ad85d
Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2021-10-12 16:07:46 -06:00
Maxime VISONNEAU
4528f448d6 ipn/store/aws, cmd/tailscaled: add AWS SSM ipn.StateStore implementation
From https://github.com/tailscale/tailscale/pull/1919 with
edits by bradfitz@.

This change introduces a new storage provider for the state file. It
allows users to leverage AWS SSM parameter store natively within
tailscaled, like:

    $ tailscaled --state=arn:aws:ssm:eu-west-1:123456789:parameter/foo

Known limitations:
- it is not currently possible to specific a custom KMS key ID

RELNOTE=tailscaled on Linux supports using AWS SSM for state

Edits-By: Brad Fitzpatrick <bradfitz@tailscale.com>
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
Signed-off-by: Maxime VISONNEAU <maxime.visonneau@gmail.com>
2021-10-12 13:51:13 -07:00
Maya Kaczorowski
1b20d1ce54 Dockerfile, build_docker: change Docker warning 2021-10-12 13:21:51 -07:00
apenwarr
5b06c50669 Bug report template: remove empty 'title' field.
Mysteriously, GitHub can't parse it if it's an empty string rather than
just missing.

Signed-off-by: Avery Pennarun <apenwarr@tailscale.com>
2021-10-13 04:38:28 +09:00
Maya Kaczorowski
525f15bf81 Dockerfile, build_docker: change Docker warning
Signed-off-by: Maya Kaczorowski <15946341+mayakacz@users.noreply.github.com>
2021-10-12 12:27:39 -07:00
Avery Pennarun
9c3ae750da Bug template: remove "[Bug]: " prefix for the common case.
Also shorten "[FR]:" to "FR:" to save precious subject line space.

I don't mind a prefix to distinguish feature requests, but the majority
of cases are bugs. Let's preserve as many chars as possible for the
specific topic when looking at subject lines in gmail.

(Now, if only it wouldn't include [tailscale/tailscale] on every
message...)

Signed-off-by: Avery Pennarun <apenwarr@tailscale.com>
2021-10-13 04:14:59 +09:00
Smitty
b382161fe5 tsdns: don't forward transient DNS errors
When a DNS server claims to be unable or unwilling to handle a request,
instead of passing that refusal along to the client, just treat it as
any other error trying to connect to the DNS server. This prevents DNS
requests from failing based on if a server can respond with a transient
error before another server is able to give an actual response. DNS
requests only failing *sometimes* is really hard to find the cause of
(#1033).

Signed-off-by: Smitty <me@smitop.com>
2021-10-12 09:35:25 -04:00
Brad Fitzpatrick
92215065eb cmd/derpprobe: fix fmt bug
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-11 20:27:31 -07:00
Brad Fitzpatrick
13ef8e3c06 cmd/derpprobe: also do UDP STUN probing
Updates #3049

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-11 20:25:14 -07:00
Brad Fitzpatrick
a2e1e5d909 go.mod: bump go-ole for windows/arm64 support
Updates #2606

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-11 08:48:25 -07:00
Denton Gentry
5d6198adee netcheck: don't log ErrGatewayRange
"skipping portmap; gateway range likely lacks support" is really
spammy on cloud systems, and not very useful in debugging.

Fixes https://github.com/tailscale/tailscale/issues/3034

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2021-10-10 10:47:03 -07:00
Denton Gentry
d883747d8b net/dns/resolver: don't forward DNS-SD on all platforms
We added the initial handling only for macOS and iOS.
With 1.16.0 now released, suppress forwarding DNS-SD
on all platforms to test it through the 1.17.x cycle.

Updates #2442

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2021-10-08 17:14:59 -07:00
Maya Kaczorowski
e5dddb2b99 .github: fix checkboxes in bug report 2021-10-08 09:37:15 -07:00
Maya Kaczorowski
3b0ee07713 .github: fix checkboxes in bug report
Signed-off-by: Maya Kaczorowski <15946341+mayakacz@users.noreply.github.com>
2021-10-08 09:27:36 -07:00
Maya Kaczorowski
af04726c18 .github: change templates to yml 2021-10-08 09:17:26 -07:00
Maya Kaczorowski
d7a2828fed .github: change templates to yml
Signed-off-by: Maya Kaczorowski <15946341+mayakacz@users.noreply.github.com>
2021-10-08 09:05:03 -07:00
Maya Kaczorowski
1f506d2351 .github: update issue templates 2021-10-07 17:46:53 -07:00
Maya Kaczorowski
8bdb2c3adc .github: update issue templates
Signed-off-by: Maya Kaczorowski <15946341+mayakacz@users.noreply.github.com>
2021-10-07 17:26:23 -07:00
Denton Gentry
3675fafec6 VERSION.txt: new unstable v1.17.0
Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2021-10-07 13:07:04 -07:00
Brad Fitzpatrick
297d1b7cb6 net/dns/resolver: don't forward DNS-SD queries
Updates #2442
Fixes tailscale/corp#2820

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-07 12:38:55 -07:00
Brad Fitzpatrick
47044f3af7 net/dns/resolver: fix log prefix
The passed in logf already has a "dns: " prefix so they were
doubled up.
2021-10-07 12:19:41 -07:00
Brad Fitzpatrick
7634af5c6f all: gofmt
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-07 12:18:31 -07:00
Avery Pennarun
0d4a0bf60e magicsock: if STUN failed to send before, rebind before STUNning again.
On iOS (and possibly other platforms), sometimes our UDP socket would
get stuck in a state where it was bound to an invalid interface (or no
interface) after a network reconfiguration. We can detect this by
actually checking the error codes from sending our STUN packets.

If we completely fail to send any STUN packets, we know something is
very broken. So on the next STUN attempt, let's rebind the UDP socket
to try to correct any problems.

This fixes a problem where iOS would sometimes get stuck using DERP
instead of direct connections until the backend was restarted.

Fixes #2994

Signed-off-by: Avery Pennarun <apenwarr@tailscale.com>
2021-10-08 02:17:09 +09:00
Maisem Ali
52be1c0c78 tsnet: run the LocalAPI handler
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2021-10-07 10:01:03 -07:00
David Anderson
830f641c6b wgengine/magicsock: update discokeys on netmap change.
Fixes #3008.

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-10-06 14:52:47 -07:00
Brad Fitzpatrick
2d11503cff cmd/tailscale: add up --qr to show QR code
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-06 11:13:31 -07:00
Brad Fitzpatrick
2501a694cb net/interfaces: add RegisterInterfaceGetter for Android
Updates #2293

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-06 10:43:12 -07:00
Aaron Klotz
df7899759d cmd/tailscaled: set the correct flag for receiving Windows session change events
This feature wasn't working until I realized that we also need to opt into
the events. MSDN wasn't so generous as to make this easy to deduce.

Updates #2956

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2021-10-06 10:23:55 -06:00
David Crawshaw
cc9cf97cbe cli: web advertise exit node button
A couple of gnarly assumptions in this code, as always with the async
message thing.

UI button is based on the DNS settings in the admin panel.

Co-authored-by: Maisem Ali <maisem@tailscale.com>
Signed-off-by: David Crawshaw <crawshaw@tailscale.com>
2021-10-06 07:35:43 -07:00
Brad Fitzpatrick
0410f1a35a util/groupmember: adjust build tags for osusergo
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-05 15:38:57 -07:00
Brad Fitzpatrick
2a0d3f72c5 util/groupmember: fix typo of package's name in its package doc
And canonicalize a func comment while I'm here.

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-05 15:21:18 -07:00
Brad Fitzpatrick
cb4a2c00d1 ipn: remove unused Prefs.OSVersion and Prefs.DeviceModel
iOS and Android no longer use these. They both now (as of today)
use the hostinfo.SetFoo setters instead.

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-05 15:18:32 -07:00
Brad Fitzpatrick
67e5fabdbd hostinfo, ipn/ipnlocal: add SetPackage, remove ipnlocal hacks
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-05 15:02:35 -07:00
Brad Fitzpatrick
81269fad28 hostinfo: add SetOSVersion like SetDeviceModel, deprecate ipn.Prefs way
Turns out the iOS client has been only sending the OS version it first
started at. This whole hostinfo-via-prefs mechanism was never a good idea.
Start removing it.

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-05 13:29:06 -07:00
Brad Fitzpatrick
98b3fa78aa cmd/tailscale: let certs/keys be written to stdout, warn about macOS sandbox
Fixes https://twitter.com/SeanHood/status/1443668378468720647

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-04 12:12:09 -07:00
Brad Fitzpatrick
2d464cecd1 cmd/tailscale: make netcheck work when logged out
Fixes #2993

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-04 11:42:51 -07:00
Brad Fitzpatrick
58e1475ec7 hostinfo: look up Synology hardware a more specific way
Fixes #2991

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-04 10:28:28 -07:00
Brad Fitzpatrick
a71fb6428d version: new month, new date bump 2021-10-04 08:56:41 -07:00
Brad Fitzpatrick
22a1a5d7cf ipn/ipnlocal: for IPv6-only nodes, publish IPv6 MagicDNS records of peers
See https://github.com/tailscale/tailscale/issues/2970#issuecomment-931885268

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-04 08:54:23 -07:00
David Crawshaw
45f51d4fa6 types/opt: implement Bool.Scan
Signed-off-by: David Crawshaw <crawshaw@tailscale.com>
2021-10-03 15:24:13 -07:00
Brad Fitzpatrick
6d43cbc325 ipn/ipnlocal: make sure mobile clients don't use the old control server URL
The new frontends are better for battery.

Updates #2442
Updates tailscale/corp#2750

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-03 14:11:12 -07:00
Nathan Dias
babd163aac bencher: add config to suppress failures on benchmark regressions.
This config update will let tailscale use bencher without worrying about the bencher check appearing as failed due to a benchmark regressing.

Updates #2938

Signed-off-by: Nathan Dias <nathan@orijtech.com>
2021-10-01 16:16:02 -07:00
Brad Fitzpatrick
09c2462ae5 net/tlsdial: add forgotten test file for go mod tidy
I forgot to include this file in the earlier
7cf8ec8108 commit.

This exists purely to keep "go mod tidy" happy.

Updates #1609

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-01 10:30:01 -07:00
Brad Fitzpatrick
f62e6d83a9 cmd/tailscale: make cert subcommand give hints on access denied
Lot of people have been hitting this.

Now it says:

    $ tailscale cert tsdev.corp.ts.net
    Access denied: cert access denied

    Use 'sudo tailscale cert' or 'tailscale up --operator=$USER' to not require root.

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-01 10:27:48 -07:00
Brad Fitzpatrick
7cf8ec8108 net/tlsdial: bake in LetsEncrypt's ISRG Root X1 root
We still try the host's x509 roots first, but if that fails (like if
the host is old), we fall back to using LetsEncrypt's root and
retrying with that.

tlsdial was used in the three main places: logs, control, DERP. But it
was missing in dnsfallback. So added it there too, so we can run fine
now on a machine with no DNS config and no root CAs configured.

Also, move SSLKEYLOGFILE support out of DERP. tlsdial is the logical place
for that support.

Fixes #1609

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-10-01 08:30:07 -07:00
Brad Fitzpatrick
b10a55e4ed cmd/tailscale/cli: fix typo in cert usage 2021-09-30 21:23:18 -07:00
Filippo Valsorda
d7ce2be5f4 net/dns/resolver: add unsecured Quad9 resolvers
DNSSEC is an availability issue, as recently demonstrated by the
Slack issue, with limited security advantage. DoH on the other hand
is a critical security upgrade. This change adds DoH support for the
non-DNSSEC endpoints of Quad9.

https://www.quad9.net/service/service-addresses-and-features#unsec
Signed-off-by: Filippo Valsorda <hi@filippo.io>
2021-09-30 18:08:19 -07:00
Brad Fitzpatrick
891e7986cc cmd/tailscale: make cert give hints on usage failure
Like mentioning which cert domain(s) are valid.
2021-09-29 14:35:00 -07:00
Brad Fitzpatrick
080381c79f net/tstun: block looped disco traffic, take 17
It was in the wrong filter direction before, per CPU profiles
we now have.

Updates #1526 (maybe fixes? time will tell)

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-29 14:17:40 -07:00
Brad Fitzpatrick
3618e8d8ac cmd/tailscaled: rename outbound HTTP proxy flag
The old name invited confusion:

* is this the HTTP proxy to use ourselves? (no, that's
  via an environment variable, per proxy conventions)
* is this for LetsEncrypt https-to-localhost-http
  proxying? (no, that'll come later)

So rename to super verbose --outbound-http-proxy-listen
before the 1.16.0 release to make it clear what it is.
It listens (serves) and it's for outbound, not inbound.

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-29 11:25:09 -07:00
Brad Fitzpatrick
b822b5c798 cmd/tailscale: let up --authkey be of form file:/path/to/secret
Fixes #2958

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-29 09:27:17 -07:00
Aaron Klotz
e016eaf410 cmd/tailscaled: conditionally flush Windows DNS cache on SessionChange
For the service, all we need to do is handle the `svc.SessionChange` command.
Upon receipt of a `windows.WTS_SESSION_UNLOCK` event, we fire off a goroutine to flush the DNS cache.
(Windows expects responses to service requests to be quick, so we don't want to do that synchronously.)

This is gated on an integral registry value named `FlushDNSOnSessionUnlock`,
whose value we obtain during service initialization.

(See [this link](https://docs.microsoft.com/en-us/windows/win32/api/winsvc/nc-winsvc-lphandler_function_ex) for information re: handling `SERVICE_CONTROL_SESSIONCHANGE`.)

Fixes #2956

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2021-09-29 09:43:22 -06:00
Aaron Klotz
3386a86fe5 util/winutil: add GetRegInteger
This helper allows us to retrieve `DWORD` and `QWORD` values from the Tailscale key in the Windows registry.

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2021-09-29 09:43:22 -06:00
dependabot[bot]
5809386525 go.mod: bump golang.zx2c4.com/wireguard/windows from 0.4.9 to 0.4.10
Bumps golang.zx2c4.com/wireguard/windows from 0.4.9 to 0.4.10.

---
updated-dependencies:
- dependency-name: golang.zx2c4.com/wireguard/windows
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>
2021-09-29 08:16:35 -07:00
dependabot[bot]
0fa1da2d1b go.mod: bump golang.org/x/tools from 0.1.6 to 0.1.7
Bumps [golang.org/x/tools](https://github.com/golang/tools) from 0.1.6 to 0.1.7.
- [Release notes](https://github.com/golang/tools/releases)
- [Commits](https://github.com/golang/tools/compare/v0.1.6...v0.1.7)

---
updated-dependencies:
- dependency-name: golang.org/x/tools
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>
2021-09-29 07:47:38 -07:00
Brad Fitzpatrick
173bbaa1a1 all: disable TCP keep-alives on iOS/Android
Updates #2442
Updates tailscale/corp#2750

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-28 12:03:18 -07:00
Brad Fitzpatrick
a7cb241db1 cmd/tailscaled: add support for running an HTTP proxy
This adds support for tailscaled to be an HTTP proxy server.
It shares the same backend dialing code as the SOCK5 server, but the
client protocol is HTTP (including CONNECT), rather than SOCKS.

Fixes #2289

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-28 10:57:46 -07:00
Brad Fitzpatrick
29a8fb45d3 wgengine/netstack: include DNS.ExtraRecords in DNSMap
So SOCKS5 dialer can dial HTTPS cert names, for instance.

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-28 10:01:36 -07:00
Brad Fitzpatrick
56d8c2da34 cmd/tailscaled: set StateDirectoryMode=0700 in tailscaled.service
Updates #2934

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-28 09:09:24 -07:00
dependabot[bot]
8949305820 go.mod: bump github.com/creack/pty from 1.1.15 to 1.1.16
Bumps [github.com/creack/pty](https://github.com/creack/pty) from 1.1.15 to 1.1.16.
- [Release notes](https://github.com/creack/pty/releases)
- [Commits](https://github.com/creack/pty/compare/v1.1.15...v1.1.16)

---
updated-dependencies:
- dependency-name: github.com/creack/pty
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>
2021-09-28 07:39:14 -07:00
Brad Fitzpatrick
52737c14ac wgengine/monitor: ignore ipsec link monitor events on iOS/macOS
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-27 20:45:51 -07:00
Brad Fitzpatrick
5263c8d0b5 paths: skip unix chmod if state directory is already 0700
Updates #2934

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-27 16:24:49 -07:00
Brad Fitzpatrick
3b3994f0db ipn{,/localapi,ipnlocal}: infer cert dir from state file location
This fixes "tailscale cert" on Synology where the var directory is
typically like /volume2/@appdata/Tailscale, or any other tailscaled
user who specifies a non-standard state file location.

This is a interim fix on the way to #2932.

Fixes #2927
Updates #2932

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-27 15:28:50 -07:00
David Crawshaw
29fa8c17d2 .github: revert dependabot change for vm builder
In a56520c3c7 dependabot attempted to bump
the setup-go action version. It appears to work for most builders, but
not the self-hosted VM builder. Revert for now.

Signed-off-by: David Crawshaw <crawshaw@tailscale.com>
2021-09-27 14:08:56 -07:00
dependabot[bot]
7f0fcf8571 go.mod: bump github.com/pkg/sftp from 1.13.3 to 1.13.4
Bumps [github.com/pkg/sftp](https://github.com/pkg/sftp) from 1.13.3 to 1.13.4.
- [Release notes](https://github.com/pkg/sftp/releases)
- [Commits](https://github.com/pkg/sftp/compare/v1.13.3...v1.13.4)

---
updated-dependencies:
- dependency-name: github.com/pkg/sftp
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>
2021-09-27 07:22:40 -07:00
Brad Fitzpatrick
3a72ebb109 ipn: test TestFileStore in a fresh subdirectory
Fixes #2923

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-24 15:05:10 -07:00
Aaron Klotz
21e9f98fc1 ipn, paths: unconditionally attempt to set state dir perms, but only if the state dir is ours
We unconditionally set appropriate perms on the statefile dir.

We look at the basename of the statefile dir, and if it is "tailscale", then
we set perms as appropriate.

Fixes #2925
Updates #2856

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2021-09-24 15:53:58 -06:00
Brad Fitzpatrick
82117f7a63 safesocket: actually fix CLI on macsys build
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-24 13:58:26 -07:00
Brad Fitzpatrick
ec2249b6f2 cmd/tailscale: add debug -env
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-24 13:57:45 -07:00
Brad Fitzpatrick
5bc6d17f87 safesocket: fix CLI for macsys GUI variant
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-24 12:35:24 -07:00
Brad Fitzpatrick
ace2faf7ec cmd/tailscale: make debug profiling output - mean stdout
Because the macOS CLI runs in the sandbox, including the filesystem,
so users would be confused that -cpu-profile=prof.cpu succeeds but doesn't
write to their current directory, but rather in some random Library/Containers
directory somewhere on the machine (which varies depending on the Mac build
type: App Store vs System Extension)

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-23 15:06:53 -07:00
Brad Fitzpatrick
efb84ca60d ipn/localapi, cmd/tailscale: add CPU & memory profile support, debug command
This was already possible on Linux if you ran tailscaled with --debug
(which runs net/http/pprof), but it requires the user have the Go
toolchain around.

Also, it wasn't possible on macOS, as there's no way to run the IPNExtension
with a debug server (it doesn't run tailscaled).

And on Windows it's super tedious: beyond what users want to do or
what we want to explain.

Instead, put it in "tailscale debug" so it works and works the same on
all platforms. Then we can ask users to run it when we're debugging something
and they can email us the output files.

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-23 10:01:14 -07:00
Denton Gentry
27bc4e744c cmd/tailscale/web: support TLS from env vars.
pfSense stores its SSL certificate and key in the PHP config.
We wrote PHP code to pull the two out of the PHP config and
into environment variables before running "tailscale web".

The pfSense web UI is served over https, we need "tailscale web"
to also support https in order to put it in an <iframe>.

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2021-09-23 08:15:33 -07:00
dependabot[bot]
b7b7d21514 go.mod: bump github.com/frankban/quicktest from 1.13.0 to 1.13.1
Bumps [github.com/frankban/quicktest](https://github.com/frankban/quicktest) from 1.13.0 to 1.13.1.
- [Release notes](https://github.com/frankban/quicktest/releases)
- [Commits](https://github.com/frankban/quicktest/compare/v1.13.0...v1.13.1)

---
updated-dependencies:
- dependency-name: github.com/frankban/quicktest
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>
2021-09-23 08:13:41 -07:00
dependabot[bot]
46b59e8c48 go.mod: bump github.com/google/uuid from 1.1.2 to 1.3.0
Bumps [github.com/google/uuid](https://github.com/google/uuid) from 1.1.2 to 1.3.0.
- [Release notes](https://github.com/google/uuid/releases)
- [Commits](https://github.com/google/uuid/compare/v1.1.2...v1.3.0)

---
updated-dependencies:
- dependency-name: github.com/google/uuid
  dependency-type: direct:production
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <support@github.com>
2021-09-23 08:13:32 -07:00
Brad Fitzpatrick
b0481ba37a go.mod: bump x/tools
Fixes #2912 (which had rebase issues)

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-23 08:11:35 -07:00
dependabot[bot]
9219ca49f5 go.mod: bump golang.zx2c4.com/wireguard/windows from 0.3.16 to 0.4.9
Bumps golang.zx2c4.com/wireguard/windows from 0.3.16 to 0.4.9.

---
updated-dependencies:
- dependency-name: golang.zx2c4.com/wireguard/windows
  dependency-type: direct:production
  update-type: version-update:semver-minor
...

Signed-off-by: dependabot[bot] <support@github.com>
2021-09-23 08:07:52 -07:00
Brad Fitzpatrick
9ca334a560 cmd/tailscaled: appease a security scanner
There are two reasons this can't ever go to actual logs,
but rewrite it to make it happy.

Fixes tailscale/corp#2695

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-22 23:23:47 -07:00
David Anderson
1eabb5b2d9 ipn: don't log IPN messages that may contain an authkey.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-09-22 20:32:49 -07:00
dependabot[bot]
c350321eec go.mod: bump github.com/gliderlabs/ssh from 0.3.2 to 0.3.3
Bumps [github.com/gliderlabs/ssh](https://github.com/gliderlabs/ssh) from 0.3.2 to 0.3.3.
- [Release notes](https://github.com/gliderlabs/ssh/releases)
- [Commits](https://github.com/gliderlabs/ssh/compare/v0.3.2...v0.3.3)

---
updated-dependencies:
- dependency-name: github.com/gliderlabs/ssh
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>
2021-09-22 15:47:20 -07:00
dependabot[bot]
2bb915dd0a go.mod: bump github.com/creack/pty from 1.1.9 to 1.1.15
Bumps [github.com/creack/pty](https://github.com/creack/pty) from 1.1.9 to 1.1.15.
- [Release notes](https://github.com/creack/pty/releases)
- [Commits](https://github.com/creack/pty/compare/v1.1.9...v1.1.15)

---
updated-dependencies:
- dependency-name: github.com/creack/pty
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>
2021-09-22 15:46:44 -07:00
dependabot[bot]
aaea175dd0 go.mod: bump github.com/godbus/dbus/v5 from 5.0.4 to 5.0.5
Bumps [github.com/godbus/dbus/v5](https://github.com/godbus/dbus) from 5.0.4 to 5.0.5.
- [Release notes](https://github.com/godbus/dbus/releases)
- [Commits](https://github.com/godbus/dbus/compare/v5.0.4...v5.0.5)

---
updated-dependencies:
- dependency-name: github.com/godbus/dbus/v5
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>
2021-09-22 15:45:40 -07:00
dependabot[bot]
eeee713c69 go.mod: bump github.com/miekg/dns from 1.1.42 to 1.1.43
Bumps [github.com/miekg/dns](https://github.com/miekg/dns) from 1.1.42 to 1.1.43.
- [Release notes](https://github.com/miekg/dns/releases)
- [Changelog](https://github.com/miekg/dns/blob/master/Makefile.release)
- [Commits](https://github.com/miekg/dns/compare/v1.1.42...v1.1.43)

---
updated-dependencies:
- dependency-name: github.com/miekg/dns
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>
2021-09-22 15:45:17 -07:00
dependabot[bot]
dbce536316 go.mod: bump github.com/pkg/sftp from 1.13.0 to 1.13.3
Bumps [github.com/pkg/sftp](https://github.com/pkg/sftp) from 1.13.0 to 1.13.3.
- [Release notes](https://github.com/pkg/sftp/releases)
- [Commits](https://github.com/pkg/sftp/compare/v1.13.0...v1.13.3)

---
updated-dependencies:
- dependency-name: github.com/pkg/sftp
  dependency-type: direct:production
  update-type: version-update:semver-patch
...

Signed-off-by: dependabot[bot] <support@github.com>
2021-09-22 15:44:46 -07:00
dependabot[bot]
a56520c3c7 .github: Bump actions/setup-go from 1 to 2.1.4
Bumps [actions/setup-go](https://github.com/actions/setup-go) from 1 to 2.1.4.
- [Release notes](https://github.com/actions/setup-go/releases)
- [Commits](https://github.com/actions/setup-go/compare/v1...v2.1.4)

---
updated-dependencies:
- dependency-name: actions/setup-go
  dependency-type: direct:production
  update-type: version-update:semver-major
...

Signed-off-by: dependabot[bot] <support@github.com>
2021-09-22 15:43:23 -07:00
David Anderson
562622a32c .github: add dependabot config to update go.mod and github actions.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-09-22 15:35:42 -07:00
David Anderson
4cf63b8df0 net/dnsfallback: update static map for new derp11.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-09-22 15:35:42 -07:00
David Anderson
18086c4cb7 go.mod: bump github.com/klauspost/compress to 1.13.6
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-09-22 15:11:25 -07:00
Aaron Klotz
f0aa7f70a4 Merge pull request #2893 from tailscale/aaron/programdata-perms-2
ipn, paths: ensure that the state directory for Windows has the corre…
2021-09-22 14:58:16 -06:00
Aaron Klotz
9ebb5d4205 ipn, paths: ensure that the state directory for Windows has the correct perms
ProgramData has a permissive ACL. For us to safely store machine-wide
state information, we must set a more restrictive ACL on our state directory.
We set the ACL so that only talescaled's user (ie, LocalSystem) and the
Administrators group may access our directory.

We must include Administrators to ensure that logs continue to be easily
accessible; omitting that group would force users to use special tools to
log in interactively as LocalSystem, which is not ideal.

(Note that the ACL we apply matches the ACL that was used for LocalSystem's
AppData\Local).

There are two cases where we need to reset perms: One is during migration
from the old location to the new. The second case is for clean installations
where we are creating the file store for the first time.

Updates #2856

Signed-off-by: Aaron Klotz <aaron@tailscale.com>
2021-09-22 14:50:00 -06:00
Brad Fitzpatrick
b1a2abf41b client/tailscale/example/servetls: add demo program for docs
Updates #1235

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-21 22:18:09 -07:00
Dave Anderson
478775de6a github: add code security scanning 2021-09-21 15:46:39 -07:00
Brad Fitzpatrick
7d8227e7a6 logpolicy: don't use C:\ProgramData use for tailscale-ipn GUI's log dir
tailscale-ipn.exe (the GUI) shouldn't use C:\ProgramData.

Also, migrate the earlier misnamed wg32/wg64 conf files if they're present.
(That was stopped in 2db877caa3, but the
files exist from fresh 1.14 installs)

Updates #2856

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-20 21:48:46 -07:00
Brad Fitzpatrick
2db877caa3 version: fix CmdName on the tailscale-ipn.exe binary
Don't return "wg64", "wg32", etc.

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-20 14:49:45 -07:00
Denton Gentry
93c2882a2f wgengine: flush DNS cache after major link change.
Windows has a public dns.Flush used in router_windows.go.
However that won't work for platforms like Linux, where
we need a different flush mechanism for resolved versus
other implementations.

We're instead adding a FlushCaches method to the dns Manager,
which can be made to work on all platforms as needed.

Fixes https://github.com/tailscale/tailscale/issues/2132

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2021-09-19 22:58:53 -07:00
Denton Gentry
280c84e46a ipn/ipnserver, paths, logpolicy: move Window config files out of %LocalAppData%
C:\WINDOWS\system32\config\systemprofile\AppData\Local\
is frequently cleared for almost any reason: Windows updates,
System Restore, even various System Cleaner utilities.

The server-state.conf file in AppData\Local could be deleted
at any time, which would break login until the node is removed
from the Admin Panel allowing it to create a new key.

Carefully copy any AppData state to ProgramData at startup.
If copying the state fails, continue to use AppData so at
least there will be connectivity. If there is no state,
use ProgramData.

We also migrate the log.conf file. Very old versions of
Tailscale named the EXE tailscale-ipn, so the log conf was
tailscale-ipn.log.conf and more recent versions preserved
this filename and cmdName in logs. In this migration we
always update the filename to
c:\ProgramData\Tailscale\tailscaled.log.conf

Updates https://github.com/tailscale/tailscale/issues/2856

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2021-09-19 22:57:53 -07:00
Brad Fitzpatrick
aae622314e tailcfg, health: add way for control plane to add problems to health check
So if the control plane knows that something's broken about the node, it can
include problem(s) in MapResponse and "tailscale status" will show it.
(and GUIs in the future, as it's in ipnstate.Status/JSON)

This also bumps the MapRequest.Version, though it's not strictly
required. Doesn't hurt.

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-19 17:55:49 -07:00
Josh Bleecher Snyder
b14db5d943 util/codegen: reorder AssertStructUnchanged args
The fully qualified name of the type is thisPkg.tname,
so write the args like that too.

Suggested-by: Joe Tsai <joetsai@digital-static.net>
Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-09-17 16:46:08 -07:00
Josh Bleecher Snyder
3cd85c0ca6 util/codegen: add ContainsPointers
And use it in cmd/cloner.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-09-17 16:46:08 -07:00
Josh Bleecher Snyder
d5a0a4297e cmd/cloner: unify switch cases
And in the process, fix a bug:
The fmt formatting was being applied by writef,
not fmt.Sprintf, thus emitting a MISSING string.
And there's no guarantee that fmt will be imported
in the generated code.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-09-17 16:46:08 -07:00
Josh Bleecher Snyder
d8a8f70000 util/codegen: add NamedTypes
And use it in cmd/cloner.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-09-17 16:46:08 -07:00
Josh Bleecher Snyder
367a973dc2 cmd/cloner: delete some debug code
Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-09-17 16:46:08 -07:00
Josh Bleecher Snyder
081be3e96b cmd/cloner: simplify code
Change from a single-case type switch to a type assertion
with an early return.

That exposes that the name arg to gen is unneeded.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-09-17 16:46:08 -07:00
Josh Bleecher Snyder
d5ab18b2e6 cmd/cloner: add Clone context to regen struct assignments
Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-09-17 16:46:08 -07:00
Josh Bleecher Snyder
618376dbc0 util/codegen: add AssertStructUnchanged
Refactored out from cmd/cloner.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-09-17 16:46:08 -07:00
Josh Bleecher Snyder
fb66ff7c78 util/codegen: add package
This is a package for shared utilities used in doing codegen programs.
The inaugural API is for writing gofmt'd code to a file.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-09-17 16:46:08 -07:00
Adrian Dewhurst
4da559d7cc control/controlclient: update machine certificate signature version
This iterates on the original signature format.

Signed-off-by: Adrian Dewhurst <adrian@tailscale.com>
2021-09-17 17:43:06 -04:00
Josh Bleecher Snyder
a722e48cef wgengine/magicsock: skip alloc test with -race
Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-09-17 09:56:32 -07:00
Josh Bleecher Snyder
07c09f470d ipn/ipnlocal: do not shut down the backend halfway through TestStateMachine
LocalBackend.Shutdown's docs say:

> The backend can no longer be used after Shutdown returns.

Nevertheless, TestStateMachine blithely calls Shutdown, talks some smack,
and continues on, expecting things to work. Other uses of Shutdown
in the codebase are as intended.

Things mostly kinda work anyway, except that the wgengine.Engine has been
shut down, so calls to Reconfig fail. Those get logged:

> local.go:603: wgengine status error: engine closing; no status

but otherwise ignored.

However, the Reconfig failure caused one fewer call to pause/unpause
than normal. Now the assertCalls lines match the equivalent ones
earlier in the test.

I don't see an obvious correct replacement for Shutdown in the context
of this test; I'm not sure entirely what it is trying to accomplish.
It is possible that many of the tests remaining after the prior call
to Shutdown are now extraneous. They don't harm anything, though,
so err on the side of safety and leave them for now.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-09-17 09:56:32 -07:00
Josh Bleecher Snyder
f834a4ade5 ipn/ipnlocal: fix minor typo in comment
Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-09-17 09:56:32 -07:00
Josh Bleecher Snyder
221cc5f8f2 ipn/ipnlocal: reduce line noise in tests
Use helpers and variadic functions to make the call sites
a lot easier to read, since they occur a lot.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-09-17 09:56:32 -07:00
Josh Bleecher Snyder
45d3174c0d ipn/ipnlocal: add LocalBackend.broadcastStatusChanged
To reduce repetition.

Also, document why we acquire the lock.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-09-16 13:36:41 -07:00
Josh Bleecher Snyder
b7ede14396 Revert "ipn/ipnlocal: remove locks around sync.Cond.Broadcast call"
Reason for revert: Causes ipnlocal tests to deadlock intermittently.

This reverts commit 1b15349e01.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-09-16 13:36:41 -07:00
Brad Fitzpatrick
a05086ef86 portlist: add debug knob to disable portlist collection
For big servers. Per discussion with @crawshaw.

Updates tailscale/corp#2566

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-16 11:31:53 -07:00
Brad Fitzpatrick
4549d3151c cmd/tailscale: make status show health check problems
Fixes #2775

RELNOTE=tailscale status now shows health check problems

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-16 11:24:59 -07:00
Brad Fitzpatrick
73f177e4d5 derp: throttle client sends if server advertises rate limits
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-16 09:21:55 -07:00
Maxim Merzhanov
d43fcd2f02 net/dns: fix error wrapping for SetLinkDefaultRoute in resolved
Signed-off-by: Maxim Merzhanov <maksimmerzh@gmail.com>
2021-09-16 09:09:13 -07:00
Josh Bleecher Snyder
3ea8cf9c62 ipn/ipnlocal: use quicktest.IsNotNil in tests
This didn't exist when the test was written.
Now it does (frankban/quicktest#94); use it.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-09-15 15:31:51 -07:00
Josh Bleecher Snyder
1b15349e01 ipn/ipnlocal: remove locks around sync.Cond.Broadcast call
They are unnecessary.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-09-15 15:31:51 -07:00
Josh Bleecher Snyder
3b58c118dd ipn/ipnlocal: inline LocalBackend.getEngineStatus
For uniformity.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-09-15 15:31:51 -07:00
Josh Bleecher Snyder
0f4c0e558b ipn/ipnlocal: use a switch statement instead of an else-if chain
For clarity.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-09-15 15:31:51 -07:00
Josh Bleecher Snyder
7421ba91ec ipn/ipnlocal: only call UpdateEndpoints when the endpoints change
Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-09-15 15:31:51 -07:00
Josh Bleecher Snyder
5b02ad16b9 control/controlclient: replace TODO with explanation
Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-09-15 15:31:51 -07:00
Josh Bleecher Snyder
b681edc572 ipn/ipnlocal: add failing test
Concurrent calls to LocalBackend.setWgengineStatus
could result in some of the status updates being dropped.
This was exacerbated by 92077ae78c,
which increases the probability of concurrent status updates,
causing test failures (tailscale/corp#2579).

It's going to take a bit of work to fix this test.
The ipnlocal state machine is difficult to reason about,
particularly in the face of concurrency.
We could fix the test trivially by throwing a new mutex around
setWgengineStatus to serialize calls to it,
but I'd like to at least try to do better than cosmetics.

In the meantime, commit the test.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-09-15 15:31:51 -07:00
Josh Bleecher Snyder
7693d36aed all: close fake userspace engines when tests complete
We were leaking FDs.
In a few places, switch from defer to t.Cleanup.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-09-15 15:31:51 -07:00
Josh Bleecher Snyder
008f36986e .github/workflows: remove separate "build stringer" step
We now use "go run" instead of compiling stringer separately.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-09-15 12:17:57 -07:00
Josh Bleecher Snyder
9faee90744 .github/workflows: skip net/dnsfallback go generate check on release branch
We don't want to force ourselves to update the DERP list
every time we want to cut a new release.
Having an outdated DERP list on release branches is OK.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-09-15 12:17:57 -07:00
Josh Bleecher Snyder
4bbf5a8636 cmd/cloner: reduce diff noise when changing command
Spelling out the command to run for every type
means that changing the command makes for a large, repetitive diff.
Stop doing that.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-09-15 10:58:12 -07:00
Josh Bleecher Snyder
865d8c0d23 cmd: upgrade to ffcli v3
None of the breaking changes from v2 to v3 are relevant to us.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-09-14 13:21:55 -07:00
Josh Bleecher Snyder
a3c5de641b portlist: stop logging stray UDP ports
These "weird" port lines show up in logs frequently.
They're the result of uninteresting races,
and they're not actionable. Remove the noise.

Remove the isLoopbackAddr case to placate staticcheck.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-09-14 11:18:09 -07:00
Brad Fitzpatrick
a83f08c54b cmd/tailscale: provide a better error message when tailscaled isn't running
Fixes #2797

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-14 11:08:46 -07:00
Brad Fitzpatrick
3e2a7de2e9 tailcfg: don't panic on clone of nil RegisterRequest
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-14 09:10:29 -07:00
Brad Fitzpatrick
dabeda21e0 net/tstun: block looped disco traffic
Updates #1526 (maybe fixes? time will tell)

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-13 16:00:28 -07:00
Josh Bleecher Snyder
3759fb8987 derp: deflake TestSendFreeze
On about 1 out of 500 runs, TestSendFreeze failed:

    derp_test.go:416: bob: unexpected message type derp.PeerGoneMessage

Closing alice before bob created a race.
If bob closed promptly, the test passed.
If bob closed slowly, and alice's disappearance caused
bob to receive a PeerGoneMessage before closing, the test failed.

Deflake the test by closing bob first.
With this fix, the test passed 12,000 times locally.

Fixes #2668

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-09-13 15:58:04 -07:00
Brad Fitzpatrick
0be26599ca cmd/derper: refactor STUN path for testing, add serverSTUN benchmark
Real goal is to eliminate some allocs in the STUN path, but that requires
work in the standard library.

See comments in #2783.

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-13 10:12:32 -07:00
Brad Fitzpatrick
0eb6cc9321 portlist: cache field index position between runs, cut two more allocs (Linux)
name          old time/op    new time/op    delta
ParsePorts-6    6.41ms ± 7%    3.15ms ± 2%  -50.84%  (p=0.000 n=9+9)

name          old alloc/op   new alloc/op   delta
ParsePorts-6      408B ± 0%      216B ± 0%  -47.06%  (p=0.002 n=8+10)

name          old allocs/op  new allocs/op  delta
ParsePorts-6      7.00 ± 0%      4.00 ± 0%  -42.86%  (p=0.000 n=10+10)

Updates tailscale/corp#2566

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-13 08:59:12 -07:00
Brad Fitzpatrick
61f201f33d portlist: reuse bufio.Reader between files
name         old time/op    new time/op    delta
ListPorts-6    1.18ms ± 5%    1.16ms ± 5%     ~     (p=0.075 n=10+10)

name         old alloc/op   new alloc/op   delta
ListPorts-6    27.2kB ± 0%    14.9kB ± 0%  -45.14%  (p=0.001 n=8+9)

name         old allocs/op  new allocs/op  delta
ListPorts-6      90.0 ± 0%      84.0 ± 0%   -6.67%  (p=0.000 n=10+10)

Updates tailscale/corp#2566

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-13 08:28:40 -07:00
Brad Fitzpatrick
5a9d977c78 portlist: reduce CPU parsing portlist
Avoid splitting fields in the common case. Field splitting was 84% of
the overall CPU.

name          old time/op    new time/op    delta
ParsePorts-6    33.3ms ± 2%     6.3ms ± 4%  -80.97%  (p=0.000 n=9+10)

name          old alloc/op   new alloc/op   delta
ParsePorts-6      520B ±79%      408B ± 0%  -21.49%  (p=0.046 n=10+8)

name          old allocs/op  new allocs/op  delta
ParsePorts-6      7.00 ± 0%      7.00 ± 0%     ~     (all equal)

Updates tailscale/corp#2566

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-13 08:22:47 -07:00
Brad Fitzpatrick
64e9ce8df1 portlist: reduce allocs on Linux
Notably, it no longer allocates proportional to the number of open
sockets on the machine. Any alloc reduction numbers are a little
contrived with such a reduction but e.g. on a machine with 50,000
connections open:

name          old time/op    new time/op    delta
ParsePorts-6    57.7ms ± 6%    32.8ms ± 3%   -43.04%  (p=0.000 n=9+10)

name          old alloc/op   new alloc/op   delta
ParsePorts-6    24.0MB ± 0%     0.0MB ± 0%  -100.00%  (p=0.000 n=10+9)

name          old allocs/op  new allocs/op  delta
ParsePorts-6      100k ± 0%        0k ± 0%   -99.99%  (p=0.000 n=10+10)

Updates tailscale/corp#2566

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-12 16:06:46 -07:00
Brad Fitzpatrick
4f648e6fcc cmd/tailscaled: disable netns earlier in userspace-networking mode
The earlier 382b349c54 was too late,
as engine creation itself needed to listen on things.

Fixes #2827
Updates #2822

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-11 07:11:22 -07:00
Brad Fitzpatrick
382b349c54 cmd/tailscaled: disable netns in userspace-networking mode
Updates #2827
Updates #2822

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-09 15:51:41 -07:00
Brad Fitzpatrick
31c1331415 wgengine/magicsock: deflake TestReceiveFromAllocs
100 iterations isn't enough with background allocs happening
apparently. 1000 seems to be reliable.

Fixes #2826

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-09 11:49:44 -07:00
Brad Fitzpatrick
a353fbd3b4 tstest: make MemLogger.String acquire its mutex
Updates #2781 (might even fix it, but its real issue is that
SetPrivateKey starts a ReSTUN goroutines which then logs, and
that bug and data race existed prior to MemLogger existing)
2021-09-09 11:38:06 -07:00
Brad Fitzpatrick
a76c8eea58 api: document new API to authorize a device (#2825)
Fixes #2813

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-09 10:56:24 -07:00
Brad Fitzpatrick
d5851d2e06 cmd/derper: fix real staticcheck failure from prior commit
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-08 17:00:56 -07:00
Silver Bullet
d8c5d00ecb cmd/derper: support manual TLS certificate mode (#2793)
Add a mode control for derp server, and add a "manual" mode
to get derp server certificate. Under manual mode, certificate
is searched in the directory given by "--cert-dir". Certificate
should in PEM format, and use "hostname.{key,crt}" as filename.
If no hostname is used, search by the hostname given for listen.

Fixes #2794

Signed-off-by: SilverBut <SilverBut@users.noreply.github.com>
2021-09-08 16:50:34 -07:00
Brad Fitzpatrick
de63e85810 words: remove two plurals, one with a typo
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-08 12:21:22 -07:00
Brad Fitzpatrick
12dc7c2df8 net/interfaces: remove stray C header file
I meant to delete it as part of 974be2ec5c
when the darwin code was ported from C to Go.

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-08 12:01:35 -07:00
Brad Fitzpatrick
2238814b99 wgengine/magicsock: fix crash introduced in recent cleanups
Fixes #2801

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-08 08:27:51 -07:00
Brad Fitzpatrick
640134421e all: update tests to use tstest.MemLogger
And give MemLogger a mutex, as one caller had, which does match the logf
contract better.

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-07 20:06:15 -07:00
Brad Fitzpatrick
48bdffd395 net/portmapper: remove GITHUB_ACTIONS check
It's now redundant.

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-07 19:28:45 -07:00
Brad Fitzpatrick
cf855e8988 version: bump date
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-07 19:19:41 -07:00
Brad Fitzpatrick
48933b0382 ipn/ipnlocal: flesh out the dnsConfigForNetmap tests
Follow-up to #2805 and #2806

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-07 19:15:54 -07:00
Brad Fitzpatrick
7fe6ecf165 ipn/ipnlocal: add MagicDNS records for IPv6-only nodes
Updates #2268

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-07 15:56:13 -07:00
Brad Fitzpatrick
90b0cd0c51 ipn/ipnlocal: start adding some netmap to DNS config tests
Follow-up to #2805

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-07 15:33:45 -07:00
Brad Fitzpatrick
4c68b7df7c tstest: add MemLogger bytes.Buffer wrapper with Logf method
We use it tons of places. Updated three at least in this PR.

Another use in next commit.

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-07 15:33:45 -07:00
Brad Fitzpatrick
30a614f9b9 ipn/ipnlocal: return early, outdent a bunch in dnsConfigForNetmap
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-07 14:56:46 -07:00
Brad Fitzpatrick
2bb0eb5f7e ipn/ipnlocal: pull out dns.Config construction to its own func
In prep for other bug fixes & tests. It's hard to test when it was
intermingled into LocalBackend.authReconfig.

Now it's a pure function.

And rename variable 'uc' (user config?) to the since idiomatic
'prefs'.

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-07 14:54:06 -07:00
David Crawshaw
b2a3d1da13 tstest/integration/vms: use fork of goexpect to avoid proto/grpc dep
Signed-off-by: David Crawshaw <crawshaw@tailscale.com>
2021-09-07 14:44:56 -07:00
David Crawshaw
9502b515f1 net/dns: replace resolver IPs with type for DoH
We currently plumb full URLs for DNS resolvers from the control server
down to the client. But when we pass the values into the net/dns
package, we throw away any URL that isn't a bare IP. This commit
continues the plumbing, and gets the URL all the way to the built in
forwarder. (It stops before plumbing URLs into the OS configurations
that can handle them.)

For #2596

Signed-off-by: David Crawshaw <crawshaw@tailscale.com>
2021-09-07 14:44:26 -07:00
Brad Fitzpatrick
7bfd4f521d cmd/tailscale: fix "tailscale ip $self-host-hostname"
And in the process, fix the related confusing error messages from
pinging your own IP or hostname.

Fixes #2803

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-07 11:57:23 -07:00
Brad Fitzpatrick
4917a96aec cmd/tailscale: fix typo/pasteo in error message text
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-07 11:28:24 -07:00
Denton Gentry
1d1efbb599 hostinfo: add FreeBSD support.
Add specific handling for common appliances based on FreeBSD:
- pfSense
    HostInfo: {"OS":"freebsd","OSVersion":"pfSense 2.5.2-RELEASE; version=12.2-STABLE"
- OPNsense
    HostInfo: {"OS":"freebsd","OSVersion":"OPNsense 21.7.1 (amd64/OpenSSL); version=12.1-RELEASE-p19-HBSD"
- TrueNAS
    HostInfo: {"OS":"freebsd","OSVersion":"TrueNAS-12.0-U5.1 (6c639bd48a); version=12.2-RELEASE-p9"
- FreeNAS
    HostInfo: {"OS":"freebsd","OSVersion":"FreeNAS-11.3-U5 (2e4ded5a0a); version=11.3-RELEASE-p14",

- regular FreeBSD
    HostInfo: {"OS":"freebsd","OSVersion":"FreeBSD; version=12.2-RELEASE"

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2021-09-06 23:12:09 -07:00
Brad Fitzpatrick
5a58fd8933 net/dnsfallback: go generate, pick up new DERPs
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-05 17:46:34 -07:00
David Anderson
efe8020dfa wgengine/magicsock: fix race condition in tests.
AFAICT this was always present, the log read mid-execution was never safe.
But it seems like the recent magicsock refactoring made the race much
more likely.

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-09-05 17:42:33 -07:00
Evan Anderson
000f90d4d7 wgengine/wglog: Fix docstring on wireguardGoString to match args
@danderson linked this on Twitter and I noticed the mismatch.

Signed-off-by: Evan Anderson <evan.k.anderson@gmail.com>
2021-09-05 15:52:16 -07:00
David Anderson
69c897a763 net/dnsfallback: run go generate to pick up new derp9s.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-09-05 00:00:16 -07:00
David Anderson
bb6fdfb243 net/dns: fix the build on freebsd (missing default case in switch)
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-09-05 00:00:16 -07:00
David Anderson
b3b1c06b3a net/dns: only restart systemd-resolved if we changed /etc/resolv.conf.
Reported on IRC: in an edge case, you can end up with a directManager DNS
manager and --accept-dns=false, in which case we should do nothing, but
actually end up restarting resolved whenever the netmap changes, even though
the user told us to not manage DNS.

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-09-05 00:00:16 -07:00
David Anderson
10547d989d net/dns: exhaustively test DNS selection paths for linux.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-09-04 23:40:48 -07:00
David Anderson
c071bcda33 net/dns: relax systemd-resolved detection.
Reported on IRC: a resolv.conf that contained two entries for
"nameserver 127.0.0.53", which defeated our "is resolved actually
in charge" check. Relax that check to allow any number of nameservers,
as long as they're all 127.0.0.53.

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-09-04 22:32:28 -07:00
Dave Anderson
980acc38ba types/key: add a special key with custom serialization for control private keys (#2792)
* Revert "Revert "types/key: add MachinePrivate and MachinePublic.""

This reverts commit 61c3b98a24.

Signed-off-by: David Anderson <danderson@tailscale.com>

* types/key: add ControlPrivate, with custom serialization.

ControlPrivate is just a MachinePrivate that serializes differently
in JSON, to be compatible with how the Tailscale control plane
historically serialized its private key.

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-09-03 13:17:46 -07:00
David Anderson
61c3b98a24 Revert "types/key: add MachinePrivate and MachinePublic."
Broke the tailscale control plane due to surprise different serialization.

This reverts commit 4fdb88efe1.
2021-09-03 11:34:34 -07:00
David Anderson
4fdb88efe1 types/key: add MachinePrivate and MachinePublic.
Plumb throughout the codebase as a replacement for the mixed use of
tailcfg.MachineKey and wgkey.Private/Public.

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-09-03 10:07:15 -07:00
David Anderson
4ce091cbd8 version: use go from the current toolchain to compile in tests.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-09-02 20:11:20 -07:00
Brad Fitzpatrick
d1cb7a2639 metrics: use SYS_OPENAT
New systems like arm64 don't even have SYS_OPEN.
2021-09-02 15:28:19 -07:00
David Anderson
159d88aae7 go.mod: tidy.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-09-02 14:26:27 -07:00
David Anderson
b96159e820 go.mod: update github.com/ulikunitz/xz for https://github.com/advisories/GHSA-25xm-hr59-7c27
Our code is not vulnerable to the issue in question: it only happens in the decompression
path for untrusted inputs, and we only use xz as part of mkpkg, which is write-only
and operates on trusted build system outputs to construct deb and rpm packages.

Still, it's nice to keep the dependabot dashboard clean.

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-09-02 14:02:57 -07:00
Brad Fitzpatrick
99a1c74a6a metrics: optimize CurrentFDs to not allocate on Linux
It was 50% of our allocs on one of our servers. (!!)

Updates #2784

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-02 13:28:39 -07:00
Brad Fitzpatrick
db3586cd43 go.mod: upgrade staticcheck
It was crashing on a PR of mine and this fixes it.
2021-09-02 13:13:42 -07:00
Brad Fitzpatrick
ec2b7c7da6 all: bump minimum Go to 1.17
In prep for using 1.17 features.

Note the go.mod changes are due to:
https://golang.org/doc/go1.17#go-command

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-02 12:51:11 -07:00
Brad Fitzpatrick
fc160f80ee metrics: move currentFDs code to the metrics package
Updates #2784

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-02 11:14:14 -07:00
Brad Fitzpatrick
5d800152d9 cmd/derper: increase port 80's WriteTimeout to permit longer CPU profiles
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-02 10:49:14 -07:00
Chuangbo Li
e4e4d336d9 cmd/derper: listen on host of flag server addr for port 80 and 3478 (#2768)
cmd/derper: listen on host of flag server addr for port 80 and 3478

When using custom derp on the server with multiple IP addresses,
we would like to bind derp 80, 443 and stun 3478 to a certain IP.

derp command provides flag `-a` to customize which address to bind
for port 443. But port :80 and :3478 were hard-coded.

Fixes #2767

Signed-off-by: Li Chuangbo <im@chuangbo.li>
2021-09-02 10:42:27 -07:00
David Crawshaw
4e18cca62e testcontrol: replace panic with error
I have seen this once in the VM test (caused by an EOF, I believe on
shutdown) that didn't need to cause the test to fail.

Signed-off-by: David Crawshaw <crawshaw@tailscale.com>
2021-09-02 10:39:32 -07:00
Brad Fitzpatrick
5bacbf3744 wgengine/magicsock, health, ipn/ipnstate: track DERP-advertised health
And add health check errors to ipnstate.Status (tailscale status --json).

Updates #2746
Updates #2775

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-02 10:20:25 -07:00
Brad Fitzpatrick
722942dd46 tsweb: restore CPU profiling handler
It was accidentally deleted in the earlier 0022c3d2e (#2143) refactor.
Lock it in with a test.

Fixes tailscale/corp#2503

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-02 09:24:29 -07:00
David Anderson
daf54d1253 control/controlclient: remove TS_DEBUG_USE_DISCO=only.
It was useful early in development when disco clients were the
exception and tailscale logs were noisier than today, but now
non-disco is the exception.

Updates #2752

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-09-01 18:11:32 -07:00
David Anderson
39748e9562 net/dns/resolver: authoritatively return NXDOMAIN for reverse zones we own.
Fixes #2774

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-09-01 18:11:32 -07:00
David Anderson
954064bdfe wgengine/wgcfg/nmcfg: don't configure peers who can't DERP or disco.
Fixes #2770

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-09-01 18:11:32 -07:00
David Anderson
f90ac11bd8 wgengine: remove unnecessary magicConnStarted channel.
Having removed magicconn.Start, there's no need to synchronize startup
of other things to it any more.

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-09-01 18:11:32 -07:00
David Anderson
bb10443edf wgengine/wgcfg: use just the hexlified node key as the WireGuard endpoint.
The node key is all magicsock needs to find the endpoint that WireGuard
needs.

Updates #2752

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-09-01 15:13:21 -07:00
David Anderson
d00341360f wgengine/magicsock: remove unused debug knob.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-09-01 15:13:21 -07:00
David Anderson
dfd978f0f2 wgengine/magicsock: use NodeKey, not DiscoKey, as the trigger for lazy reconfig.
Updates #2752

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-09-01 15:13:21 -07:00
David Anderson
4c27e2fa22 wgengine/magicsock: remove Start method from Conn.
Over time, other magicsock refactors have made Start effectively a
no-op, except that some other functions choose to panic if called
before Start.

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-09-01 15:13:21 -07:00
David Anderson
1a899344bd wgengine/magicsock: don't store tailcfg.Nodes alongside endpoints.
Updates #2752

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-09-01 15:13:21 -07:00
David Anderson
b2181608b5 wgengine/magicsock: eagerly create endpoints in SetNetworkMap.
Updates #2752

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-09-01 15:13:21 -07:00
Maisem Ali
0842e2f45b ipn/store: add ability to store data as k8s secrets.
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2021-09-01 12:50:59 -07:00
David Crawshaw
f53792026e tstest/integration/vms: move build tags from linux to !windows
The tests build fine on other Unix's, they just can't run there.
But there is already a t.Skip by default, so `go test` ends up
working fine elsewhere and checks the code compiles.

Signed-off-by: David Crawshaw <crawshaw@tailscale.com>
2021-09-01 11:38:18 -07:00
Brad Fitzpatrick
7f29dcaac1 cmd/tailscale/cli: make up block until state Running, not just Starting
At "Starting", the DERP connection isn't yet up. After the first netmap
and DERP connect, then it transitions into "Running".

Fixes #2708

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-01 08:25:42 -07:00
Brad Fitzpatrick
fb8b821710 tsnet: fix typo in comment
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-09-01 07:55:25 -07:00
Brad Fitzpatrick
7a7aa8f2b0 cmd/derper: also add port 80 timeouts
Didn't notice this one in earlier 00b3c1c042

Updates tailscale/corp#2486

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-31 21:18:36 -07:00
Brad Fitzpatrick
3c8ca4b357 client/tailscale, cmd/tailscale/cli: move version mismatch check to CLI
So people can use the package for whois checks etc without version
skew errors.

The earlier change faa891c1f2 for #1905
was a bit too aggressive.

Fixes #2757

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-31 15:27:25 -07:00
Brad Fitzpatrick
8744394cde version: bump date
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-31 15:27:25 -07:00
Brad Fitzpatrick
21cb0b361f safesocket: add connect retry loop to wait for tailscaled
Updates #2708

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-31 15:13:42 -07:00
Brad Fitzpatrick
a59b389a6a derp: add new health update and server restarting frame types
Updates #2756
Updates #2746

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-31 13:31:51 -07:00
Christine Dodrill
0b9e938152 tstest/integration/vms: test DNS configuration
This uses a neat little tool to dump the output of DNS queries to
standard out. This is the first end-to-end test of DNS that runs against
actual linux systems. The /etc/resolv.conf test may look superflous,
however this will help for correlating system state if one of the DNS
tests fails.

Signed-off-by: Christine Dodrill <xe@tailscale.com>
2021-08-31 12:31:54 -07:00
Brad Fitzpatrick
00b3c1c042 cmd/derper: add missing read/write timeouts
Updates tailscale/corp#2486

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-31 10:23:53 -07:00
David Crawshaw
9b7fc2ed1f .github: add Ubuntu VM test
Signed-off-by: David Crawshaw <crawshaw@tailscale.com>
2021-08-31 08:50:55 -07:00
Brad Fitzpatrick
73280595a8 derp: accept dup clients without closing prior's connection
A public key should only have max one connection to a given
DERP node (or really: one connection to a node in a region).

But if people clone their machine keys (e.g. clone their VM, Raspbery
Pi SD card, etc), then we can get into a situation where a public key
is connected multiple times.

Originally, the DERP server handled this by just kicking out a prior
connections whenever a new one came. But this led to reconnect fights
where 2+ nodes were in hard loops trying to reconnect and kicking out
their peer.

Then a909d37a59 tried to add rate
limiting to how often that dup-kicking can happen, but empirically it
just doesn't work and ~leaks a bunch of goroutines and TCP
connections, tying them up for hour+ while more and more accumulate
and waste memory. Mostly because we were doing a time.Sleep forever
while not reading from their TCP connections.

Instead, just accept multiple connections per public key but track
which is the most recent. And if two both are writing back & forth,
then optionally disable them both. That last part is only enabled in
tests for now. The current default policy is just last-sender-wins
while we gather the next round of stats.

Updates #2751

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-31 08:21:21 -07:00
David Crawshaw
debaaebf3b tstest/integration/vms: turn on logcatcher logging by default
Absolutely vital to debugging failures.

Signed-off-by: David Crawshaw <crawshaw@tailscale.com>
2021-08-31 06:40:28 -07:00
David Crawshaw
a1f1020042 tstest/integration/vms: avoid log after test completion
Avoids a panic in the Go testing package if a late log comes in.

Signed-off-by: David Crawshaw <crawshaw@tailscale.com>
2021-08-31 06:40:28 -07:00
David Crawshaw
583af7c1a6 tstest/integration/vms: give guest multiple cores and use generic machine
Speeds up tests.
Allows the use of more version of qemu.

Signed-off-by: David Crawshaw <crawshaw@tailscale.com>
2021-08-31 06:40:28 -07:00
David Crawshaw
8668103f06 tstest/integration/vms: print qemu console output, fix printing issues
Fix a few test printing issues when tests fail.

Qemu console output is super useful when something is wrong in the
harness and we cannot even bring up the tests.
Also useful for figuring out where all the time goes in tests.

A little noisy, but not too noisy as long as you're only running one VM
as part of the tests, which is my plan.

Signed-off-by: David Crawshaw <crawshaw@tailscale.com>
2021-08-31 06:40:28 -07:00
David Crawshaw
1a9fba5b04 tstest/integration/vms: fix ubuntu URLs
Also remove extra distros for now.
We can bring them back later if useful.
Though our most important distros are these two Ubuntu, debian stable,
and Raspbian (not currently supported).
And before doing more Linux, we should do Windows.

Signed-off-by: David Crawshaw <crawshaw@tailscale.com>
2021-08-31 06:40:28 -07:00
Emmanuel T Odeke
0daa32943e all: add (*testing.B).ReportAllocs() to every benchmark
This ensures that we can properly track and catch allocation
slippages that could otherwise have been missed.

Fixes #2748
2021-08-30 21:41:04 -07:00
David Anderson
44d71d1e42 wgengine/magicsock: fix race in test shutdown, again.
We were returning an error almost, but not quite like errConnClosed in
a single codepath, which could still trip the panic on reconfig in the
test logic.

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-08-30 21:26:38 -07:00
David Anderson
f09ede9243 wgengine/magicsock: don't configure eager WireGuard handshaking in tests.
Our prod code doesn't eagerly handshake, because our disco layer enables
on-demand handshaking. Configuring both peers to eagerly handshake leads
to WireGuard handshake races that make TestTwoDevicePing flaky.

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-08-30 17:28:12 -07:00
David Anderson
86d1c4eceb wgengine/magicsock: ignore close races even harder.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-08-30 17:09:45 -07:00
David Anderson
8bacfe6a37 wgengine/magicsock: remove unused sendLogLimit limiter.
Magicsock these days gets its logs limited by the global log limiter.

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-08-30 17:09:45 -07:00
David Anderson
e151b74f93 wgengine/magicsock: remove opts.SimulatedNetwork.
It only existed to override one test-only behavior with a
different test-only behavior, in both cases working around
an annoying feature of our CI environments. Instead, handle
that weirdness entirely in the test code, with a tweaked
TestOnlyPacketListener that gets injected.

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-08-30 17:09:45 -07:00
David Anderson
58c1f7d51a wgengine/magicsock: rename opts.PacketListener to TestOnlyPacketListener.
The docstring said it was meant for use in tests, but it's specifically a
special codepath that is _only_ used in tests, so make the claim stronger.

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-08-30 17:09:45 -07:00
David Anderson
8049063d35 wgengine/magicsock: rename discoEndpoint to just endpoint.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-08-30 17:09:45 -07:00
David Anderson
f2d949e2db wgengine/magicsock: fold findEndpoint into its only remaining caller.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-08-30 17:09:45 -07:00
David Anderson
fe2f89deab wgengine/magicsock: fix rare shutdown race in test.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-08-30 14:33:07 -07:00
David Anderson
97693f2e42 wgengine/magicsock: delete legacy AddrSet endpoints.
Instead of using the legacy codepath, teach discoEndpoint to handle
peers that have a home DERP, but no disco key. We can still communicate
with them, but only over DERP.

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-08-30 14:33:07 -07:00
David Anderson
61c62f48d9 wgengine/bench: disable unused benchmark that relies on legacy magicsock.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-08-30 14:33:07 -07:00
David Anderson
54bc3b7d97 util/deephash: remove soon to be deleted field from wgcfg.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-08-30 14:33:07 -07:00
David Anderson
923c98cd8f types/wgkey: add TODO for a future API change.
Signed-off-by: David Anderson <danderson@tailscale.com>
2021-08-30 14:33:07 -07:00
Brad Fitzpatrick
065c4ffc2c net/dns: add start of Linux newOSConfigurator tests
Only one test case so far.

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-30 14:16:12 -07:00
Brad Fitzpatrick
09a47ea3f1 net/dns: prep for writing manager_linux tests; pull some stuff out
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-30 13:49:02 -07:00
Joe Tsai
3f1317e3e5 util/deephash: fix TestArrayAllocs
Unfortunately this test fails on certain architectures.
The problem comes down to inconsistencies in the Go escape analysis
where specific variables are marked as escaping on certain architectures.
The variables escaping to the heap are unfortunately in crypto/sha256,
which makes it impossible to fixthis locally in deephash.

For now, fix the test by compensating for the allocations that
occur from calling sha256.digest.Sum.

See golang/go#48055

Fixes #2727

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2021-08-30 10:47:21 -07:00
Joe Tsai
30458c71c8 tstime/rate: deflake TestLongRunningQPS
This test is highly dependent on the accuracy of OS timers.
Reduce the number of failures by decreasing the required
accuracy from 0.999 to 0.995.
Also, switch from repeated time.Sleep to using a time.Ticker
for improved accuracy.

Updates #2727

Signed-off-by: Joe Tsai <joetsai@digital-static.net>
2021-08-30 10:46:41 -07:00
David Crawshaw
bb47feca44 tstest/integration: prefix logs with logid
The VM test has two tailscaled instances running and interleaves the
logs. Without a prefix it is impossible to figure out what is going on.

It might be even better to include the [ABCD] node prefix here as well.
Unfortunately lots of interesting logs happen before tailscaled has a
node key, so it wouldn't be a replacement for a short ID.

Signed-off-by: David Crawshaw <crawshaw@tailscale.com>
2021-08-30 10:20:32 -07:00
Maisem Ali
fd4838dc57 wgengine/userspace: add support to automatically enable/disable the tailscale
protocol in BIRD, when the node is a primary subnet router as determined
by control.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2021-08-30 10:18:05 -07:00
Brad Fitzpatrick
7fcf86a14a wgengine: fix link monitor / magicsock Start race
Fixes #2733

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-30 09:12:10 -07:00
David Crawshaw
0b962567fa vms: make ssh-keygen quiet by default
Always succeeds. Its output clutters the log.

Signed-off-by: David Crawshaw <crawshaw@tailscale.com>
2021-08-30 09:11:17 -07:00
David Crawshaw
4fcce70df5 tstest/integration: listen on the specified IP
By default httptest listens only on the loopback adapter.
Instead, listen on the IP the user asked for.
The VM test needs this, as it wants to start DERP and STUN
servers on the host that can be reached by guest VMs.

Signed-off-by: David Crawshaw <crawshaw@tailscale.com>
2021-08-30 09:06:12 -07:00
David Crawshaw
0b2761ca92 testcontrol: plumb through DERP
Without this tailscaled does not know the DERP of a peer.

Signed-off-by: David Crawshaw <crawshaw@tailscale.com>
2021-08-30 09:06:00 -07:00
Brad Fitzpatrick
ffd22050c0 derp: export current file descriptor metric 2021-08-29 15:17:34 -07:00
Will Lachance
5d3427021b Minor corrections to the API documentation
* The right web address for configuring API keys seems to have changed
* Minor clarification on how basic authentication works (it's illustrated in the examples later, but can't hurt to be precise)

Signed-off-by: William Lachance <wlach@protonmail.com>
2021-08-28 22:32:07 -07:00
Will Lachance
a35c3ba221 cmd/tailscale: fix truncated characters in web controller (#2722)
Fixes #2204

Signed-off-by: William Lachance <wlach@protonmail.com>

Co-authored-by: William Lachance <wlach@protonmail.com>
Co-authored-by: Ross Zurowski <ross@rosszurowski.com>
2021-08-27 17:10:17 -04:00
Brad Fitzpatrick
83906abc5e wgengine/netstack: clarify a comment
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-27 11:10:56 -07:00
Maisem Ali
ae9b3f38d6 github: set GOOS/GOARCH for go list
Currently we do not set the env variables for `go list ./...` resulting
in errors like
```
build constraints exclude all Go files in
/home/runner/work/tailscale/tailscale/chirp
```

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2021-08-26 16:27:37 -07:00
Maisem Ali
baf8854f9a tempfork/wireguard-windows: remove the old windows firewall code now that we are no
longer relying on it.

Signed-off-by: Maisem Ali <maisem@tailscale.com>
2021-08-26 15:00:45 -07:00
Brad Fitzpatrick
3606e68721 net/interfaces: fix default route lookup on Windows
It wasn't using the right metric. Apparently you're supposed to sum the route
metric and interface metric. Whoops.

While here, optimize a few little things too, not that this code
should be too hot.

Fixes #2707 (at least; probably dups but I'm failing to find)

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-26 13:42:20 -07:00
Brad Fitzpatrick
4aab083cae cmd/tailscaled: add debug flag to print interfaces just once
It previously only had a polling monitor mode.

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-26 11:59:52 -07:00
David Anderson
b49d9bc74d net/portmapper: fix "running a test" condition.
Fixes #2686.

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-08-25 20:16:35 -07:00
Brad Fitzpatrick
1925fb584e wgengine/netstack: fix crash in userspace netstack TCP forwarding
Fixes #2658

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-25 15:48:05 -07:00
Brad Fitzpatrick
88bd796622 tailcfg,ipn/ipnlocal: support DNSConfig.Routes with empty values [mapver 23]
Fixes #2706
Updates #1235

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-25 11:35:48 -07:00
slowy07
ac0353e982 fix: typo spelling grammar
Signed-off-by: slowy07 <slowy.arfy@gmail.com>
2021-08-24 07:55:04 -07:00
Denton Gentry
780e65a613 VERSION.txt: new unstable v1.15.0
Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2021-08-23 13:38:15 -07:00
Brad Fitzpatrick
37053801bb wgengine/magicsock: restore a bit of logging on node becoming active
Fixes #2695

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-23 12:22:23 -07:00
Brad Fitzpatrick
51976ab3a2 tsweb: add vars for unix process start time and version
To be scraped in the Go expvar JSON format, as a string is involved.

For a future tool to record when processes restarted exactly, and at
what version.

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-23 10:36:28 -07:00
Brad Fitzpatrick
246fa67e56 version: bump date
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-23 09:16:45 -07:00
Brad Fitzpatrick
6990a314f5 hostinfo: set DeviceModel from Linux devicetree model
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-22 21:28:36 -07:00
Brad Fitzpatrick
3ac731dda1 hostinfo: fix earlier git fail, add files lost in move
This was meant to be part of 47045265b9
which instead deleted them :(

Updates tailscale/corp#1959
2021-08-22 21:14:04 -07:00
Aaditya Chaudhary
71b375c502 api.md: add acl validation docs
Signed-off-by: Aaditya Chaudhary <32117362+AadityaChaudhary@users.noreply.github.com>
2021-08-22 18:27:45 -04:00
David Crawshaw
0ac2130590 net/dns: resolveConfExists reading the wrong error
Signed-off-by: David Crawshaw <crawshaw@tailscale.com>
2021-08-21 20:15:51 -07:00
Matt Drollette
c1aa5a2e33 ipn/ipnlocal: update requested tags in host info
Fixes #2641

Signed-off-by: Matt Drollette <matt@drollette.com>
2021-08-21 20:07:00 -07:00
Brad Fitzpatrick
f35b8c3ead derp: fix meshing accounting edge case bug
If a peer is connected to multiple nodes in a region (so
multiForwarder is in use) and then a node restarts and re-sends all
its additions, this bug about whether an element is in the
multiForwarder could cause a one-time flip in the which peer node we
forward to.  Note a huge deal, but not written as intended.

Thanks to @lewgun for the bug report in #2141.

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-21 19:54:55 -07:00
Alessandro Mingione
fab296536c words: add more tails and scales
Signed-off-by: Alessandro Mingione <alessandro@tailscale.com>
2021-08-21 16:35:00 -07:00
Denton Gentry
6731f934a6 Revert "wgengine: actively log FlushDNS."
This log is quite verbose, it was only to be left in for one
unstable build to help debug a user issue.

This reverts commit 1dd2552032.

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2021-08-20 18:12:47 -07:00
Brad Fitzpatrick
47045265b9 hostinfo: add SetDeviceModel setter, move remaining code from controlclient
Updates tailscale/corp#1959

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-20 10:45:22 -07:00
Josh Bleecher Snyder
4ff0757d44 cmd/testcontrol: add test control server
This is useful for manual performance testing
of networks with many nodes.
I imagine it'll grow more knobs over time.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-08-19 17:50:48 -07:00
Denton Gentry
1dd2552032 wgengine: actively log FlushDNS.
Intended to help in resolving customer issue with
DNS caching.

We currently exec `ipconfig /flushdns` from two
places:
- SetDNS(), which logs before invoking
- here in router_windows, which doesn't

We'd like to see a positive indication in logs that flushdns
is being run.

As this log is expected to be spammy, it is proposed to
leave this in just long enough to do an unstable 1.13.x build
and then revert it. They won't run an unsigned image that
I build.

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2021-08-19 14:43:14 -07:00
Brad Fitzpatrick
36ffd509de net/dns: avoid Linux PolicyKit GUI dialog during tests
Fixes #2672

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-19 08:58:47 -07:00
Brad Fitzpatrick
edb338f542 cmd/tailscale: fix sporadic 'context canceled' error on 'up'
Fixes #2333

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-19 08:44:39 -07:00
Brad Fitzpatrick
faa891c1f2 client/tailscale,ipn/localapi: warn on tailscale/tailscaled version skew
Fixes #1905

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-19 08:36:13 -07:00
Brad Fitzpatrick
8269a23758 version: bump date
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-19 08:28:08 -07:00
David Anderson
bf8556ab86 portlist: fix build tag to build only on macOS, not macOS+iOS. 2021-08-18 16:18:02 -07:00
Josh Bleecher Snyder
6ef734e493 wgengine: predict min.Peers length across calls
The number of peers we have will be pretty stable across time.
Allocate roughly the right slice size.
This reduces memory usage when there are many peers.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-08-18 16:12:45 -07:00
Josh Bleecher Snyder
adf696172d wgengine/userspace: reduce allocations in getStatus
Two optimizations.

Use values instead of pointers.
We were using pointers to make track the "peer in progress" easier.
It's not too hard to do it manually, though.

Make two passes through the data, so that we can size our
return value accurately from the beginning.
This is cheap enough compared to the allocation,
which grows linearly in the number of peers,
that it is worth doing.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-08-18 16:12:08 -07:00
Brad Fitzpatrick
af30897f0d Makefile: add a linux/arm check
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-18 15:36:09 -07:00
Maisem Ali
1f006025c2 net/tstun: fix build on arm
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2021-08-18 15:28:14 -07:00
Josh Bleecher Snyder
fcca374fa7 tstest/integration/testcontrol: sort peers in map response
This is part of the control protocol.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-08-18 14:49:26 -07:00
Brad Fitzpatrick
cd426eaf4c net/portmapper: fix t.Log-after-test-done race in tests
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-18 14:39:45 -07:00
Maisem Ali
9f62cc665e tailscaled: try migrating old state on synology devices
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2021-08-18 13:45:15 -07:00
Maisem Ali
5c383bdf5d wgengine/router: pass in AmbientCaps when calling ip rule
Signed-off-by: Maisem Ali <maisem@tailscale.com>
2021-08-18 13:28:53 -07:00
Brad Fitzpatrick
56db3e2548 ipn/localapi: refresh ACME certs in background two weeks in advance
Updates #1235

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-18 12:55:29 -07:00
Brad Fitzpatrick
6f8c8c771b control/controlclient: tweak a couple error messages
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-18 10:11:38 -07:00
Brad Fitzpatrick
b7ae529ecc client/tailscale: make GetCertificate guess cert if SNI lacks dots
Updates #1235

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-18 10:08:44 -07:00
Simeng He
e199e407d2 tailcfg: add IP and Types field to PingRequest
Signed-off-by: Simeng He <simeng@tailscale.com>
2021-08-18 12:23:24 -04:00
Brad Fitzpatrick
d5e1abd0c4 cmd/tailscale/cli: only write cert file if it changed
Updates #1235

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-18 08:19:44 -07:00
Brad Fitzpatrick
57b794c338 ipn/localapi: move cert fetching code to localapi, cache, add cert subcommand
Updates #1235

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-17 16:02:10 -07:00
Josh Bleecher Snyder
4c8b5fdec4 control/controlclient: do not periodically print full netmap
The netmaps can get really large.
Printing, processing, and uploading them is expensive.
Only print the header on an ongoing basis.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-08-17 12:57:49 -07:00
Josh Bleecher Snyder
a666b546fb ipn/ipnlocal: log number of packet filters rather than entire filter
The number of packet filters can grow very large,
so this log entry can be very large.
We can get the packet filter server-side,
so reduce verbosity here to just the number of filters present.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-08-17 12:57:49 -07:00
Josh Bleecher Snyder
0c038b477f logtail: add a re-usable buffer for uploads
This avoids a per-upload alloc (which in practice
often means per-log-line), up to 4k.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-08-17 12:56:57 -07:00
Josh Bleecher Snyder
278e7de9c9 logtail: always send a json array
The code goes to some effort to send a single JSON object
when there's only a single line and a JSON array when there
are multiple lines.

It makes the code more complex and more expensive;
when we add a second line, we have to use a second buffer
to duplicate the first one after adding a leading square brackets.

The savings come to two bytes. Instead, always send an array.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-08-17 12:56:57 -07:00
Josh Bleecher Snyder
93284209bc logtail/filch: preallocate a scanner buffer
Scanning log lines is a frequent source of allocations.
Pre-allocate a re-usable buffer.

This still doesn't help when there are giant log lines.
Those will still be problematic from an iOS memory perspective.
For more on that, see https://github.com/tailscale/corp/issues/2423.

(For those who cannot follow that link, it is a discussion
of particular problematic types of log lines for
particular categories of customers. The "categories of customers"
part is the reason that it is a private issue.)

There is also a latent bug here. If we ever encounter
a log line longer than bufio.MaxScanTokenSize,
then bufio.Scan will return an error,
and we'll truncate the file and discard the rest of the log.
That's not good, but bufio.MaxScanTokenSize is really big,
so it probably doesn't matter much in practice now.
Unfortunately, it does prevent us from easily capping the potential
memory usage here, on pain of losing log entries.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-08-17 12:32:10 -07:00
Matt Layher
8ab44b339e net/tstun: use unix.Ifreq type for Linux TAP interface configuration
Signed-off-by: Matt Layher <mdlayher@gmail.com>
2021-08-17 12:17:51 -07:00
Josh Bleecher Snyder
6da6d47a83 all: simplify build tags involving iOS
Prior to Go 1.16, iOS used GOOS=darwin,
so we had to distinguish macOS from iOS during GOARCH.

We now require Go 1.16 in our go.mod, so we can simplify.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-08-17 11:13:03 -07:00
Josh Bleecher Snyder
a24cee0d67 all: simplify ts_macext build tags
Now that we have the easier-to-parse go:build build tags,
it is straightforward to simplify them. Yay.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-08-17 11:13:03 -07:00
Josh Bleecher Snyder
d2aa144dcc syncs: bump known good version to include Go 1.17
Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-08-17 11:13:03 -07:00
Brad Fitzpatrick
25e060a841 cmd/tailscale/cli: fix cert fetch WaitOrder retry loop, misc cleanups
Updates #1235

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-16 14:54:41 -07:00
Brad Fitzpatrick
833200da6f net/tstun: don't exec uname -r on Linux in TUN failure diagnostics
Fixes https://twitter.com/zekjur/status/1425557520513486848

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-16 12:18:40 -07:00
Brad Fitzpatrick
e804ab29fd net/tstun: move TUN failure diagnostics to OS-specific files
Mostly so the Linux one can use Linux-specific stuff in package
syscall and not use os/exec for uname for portability.

But also it helps deps a tiny bit on iOS.

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-16 11:24:25 -07:00
Brad Fitzpatrick
b2eea1ee00 cmd/tailscale/cli: make cert fetch registration automatic, show valid domains
Updates #1235

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-16 10:45:05 -07:00
Brad Fitzpatrick
39610aeb09 wgengine/magicsock: move debug knobs to their own file, compile out on iOS
No need for these knobs on iOS where you can set the environment
variables anyway.

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-15 13:21:22 -07:00
Denton Gentry
98d557dd24 Dockerfile: use alpine:3.14
golang:1.16-alpine has updated to Alpine 3.14,
update the system image to match.

Reported by @kubeworm
https://twitter.com/kubeworm/status/1426751941519020033

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2021-08-14 22:46:34 -07:00
Denton Gentry
3e7ff5ff98 cmd/tailscaled: enable hybrid netstack mode for FreeBSD.
Allows FreeBSD to function as an exit node in the same way
that Windows and Tailscaled-on-MacOS do.

RELNOTE=FreeBSD can now function as an exit node.

Fixes https://github.com/tailscale/tailscale/issues/2498

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2021-08-14 20:26:38 -07:00
Brad Fitzpatrick
954867fef5 words: fix parser to handle missing newline at end
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-13 19:37:47 -07:00
Brad Fitzpatrick
c992504375 words: group some scales, support comments
Not sure how we missed mixolydian.

Updates #1235

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-13 15:46:52 -07:00
Brad Fitzpatrick
1bca722824 words: add five types of tales, best dog
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-13 15:32:13 -07:00
Brad Fitzpatrick
00b4c2331b words: add accessors and tests for a few of our favorite words
Updates #1235

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-13 15:30:10 -07:00
Charlotte Brandhorst-Satzkorn
9547669787 words: these are a few more of my favorite words
Updates #1235

Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@catzkorn.dev>
2021-08-13 16:26:36 -04:00
Charlotte Brandhorst-Satzkorn
b5a41ff381 words: these are a few of my favorite words
Updates #1235

Signed-off-by: Charlotte Brandhorst-Satzkorn <charlotte@catzkorn.dev>
2021-08-13 15:58:59 -04:00
Brad Fitzpatrick
ec9f3f4cc0 cmd/tailscale: update depaware
Missing from prior commit.

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-13 08:56:29 -07:00
Brad Fitzpatrick
c68a12afe9 cmd/tailscale: add temporary debug command for getting DNS-01 LetsEncrypt cert
Not even close to usable or well integrated yet, but submitting this before
it bitrots or I lose it.

Updates #1235

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-13 08:49:49 -07:00
David Anderson
d2d55bd63c cmd/microproxy: delete.
Thank goodness.

Fixes #2635

Signed-off-by: David Anderson <danderson@tailscale.com>
2021-08-12 14:17:42 -07:00
Brad Fitzpatrick
c6740da624 tsweb: make VarzHandler support untyped expvar.Maps for compatibility
Updates #2635

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-12 13:35:31 -07:00
Brad Fitzpatrick
7c7eb8094b tsweb: make VarzHandler support expvar.Funcs returning ints/floats
Updates #2635
2021-08-12 13:07:34 -07:00
Brad Fitzpatrick
5aba620fb9 tsweb: make VarzHandler capable of walking structs with reflect
To be used by control, per linked bug's plan.

Updates #2635

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-11 18:31:54 -07:00
julianknodt
b9bd7dbc5d net/portmapper: log upnp information
This logs some basic statistics for UPnP, so that tailscale can better understand what routers
are being used and how to connect to them.

Signed-off-by: julianknodt <julianknodt@gmail.com>
2021-08-10 22:45:00 -07:00
julianknodt
26b6fe7f02 net/portmapper: add PCP integration test
This adds a PCP test to the IGD test server, by hardcoding in a few observed packets from
Denton's box.

Signed-off-by: julianknodt <julianknodt@gmail.com>
2021-08-10 15:14:46 -07:00
Brad Fitzpatrick
3700cf9ea4 tsweb: also support LabelMaps from expvar.Map, without metrics
We want to use tsweb to format Prometheus-style metrics from
our temporary golang.org/x/net/http2 fork, but we don't want http2
to depend on the tailscale.com module to use the concrete type
tailscale.com/metrics.LabelMap. Instead, let a expvar.Map be used
instead of it's annotated sufficiently in its name.

Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-10 14:31:54 -07:00
Brad Fitzpatrick
5f45d8f8e6 tsweb: add VarzHandler tests
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-10 13:41:16 -07:00
Josh Bleecher Snyder
a4e19f2233 version: remove rsc.io/goversion dependency
rsc.io/goversion is really expensive.
Running version.ReadExe on tailscaled on darwin
allocates 47k objects, almost 11mb.

All we want is the module info. For that, all we need to do
is scan through the binary looking for the magic start/end strings
and then grab the bytes in between them.

We can do that easily and quickly with nothing but a 64k buffer.

Signed-off-by: Josh Bleecher Snyder <josh@tailscale.com>
2021-08-09 22:46:01 -07:00
Brad Fitzpatrick
bdb93c5942 net/portmapper: actually test something in TestProbeIntegration
And use dynamic port numbers in tests, as Linux on GitHub Actions and
Windows in general have things running on these ports.

Co-Author: Julian Knodt <julianknodt@gmail.com>
Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
2021-08-09 19:49:02 -07:00
Denton Gentry
26c1183941 hostinfo: add fly.io detection
Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2021-08-09 09:54:24 -07:00
Denton Gentry
0796c53404 tsnet: add AuthKey support.
Set a TS_AUTHKEY environment variable to "tskey-01234..."

Signed-off-by: Denton Gentry <dgentry@tailscale.com>
2021-08-09 09:30:09 -07:00
Adrian Dewhurst
8bdf878832 net/dns/resolver: use forwarded dns txid directly
Previously, we hashed the question and combined it with the original
txid which was useful when concurrent queries were multiplexed on a
single local source port. We encountered some situations where the DNS
server canonicalizes the question in the response (uppercase converted
to lowercase in this case), which resulted in responses that we couldn't
match to the original request due to hash mismatches. This includes a
new test to cover that situation.

Fixes #2597

Signed-off-by: Adrian Dewhurst <adrian@tailscale.com>
2021-08-06 14:56:11 -04:00
1308 changed files with 190884 additions and 34484 deletions

1
.bencher/config.yaml Normal file
View File

@@ -0,0 +1 @@
suppress_failure_on_regression: true

1
.gitattributes vendored
View File

@@ -1 +1,2 @@
go.mod filter=go-mod
*.go diff=golang

View File

@@ -1,8 +0,0 @@
---
name: Bug report
about: Create a bug report
title: ''
labels: 'needs-triage'
assignees: ''
---

81
.github/ISSUE_TEMPLATE/bug_report.yml vendored Normal file
View File

@@ -0,0 +1,81 @@
name: Bug report
description: File a bug report. If you need help, contact support instead
labels: [needs-triage, bug]
body:
- type: markdown
attributes:
value: |
Need help with your tailnet? [Contact support](https://tailscale.com/contact/support) instead.
Otherwise, please check if your bug is [already filed](https://github.com/tailscale/tailscale/issues) before filing a new one.
- type: textarea
id: what-happened
attributes:
label: What is the issue?
description: What happened? What did you expect to happen?
validations:
required: true
- type: textarea
id: steps
attributes:
label: Steps to reproduce
description: What are the steps you took that hit this issue?
validations:
required: false
- type: textarea
id: changes
attributes:
label: Are there any recent changes that introduced the issue?
description: If so, what are those changes?
validations:
required: false
- type: dropdown
id: os
attributes:
label: OS
description: What OS are you using? You may select more than one.
multiple: true
options:
- Linux
- macOS
- Windows
- iOS
- Android
- Synology
- Other
validations:
required: false
- type: input
id: os-version
attributes:
label: OS version
description: What OS version are you using?
placeholder: e.g., Debian 11.0, macOS Big Sur 11.6, Synology DSM 7
validations:
required: false
- type: input
id: ts-version
attributes:
label: Tailscale version
description: What Tailscale version are you using?
placeholder: e.g., 1.14.4
validations:
required: false
- type: textarea
id: other-software
attributes:
label: Other software
description: What [other software](https://github.com/tailscale/tailscale/wiki/OtherSoftwareInterop) (networking, security, etc) are you running?
validations:
required: false
- type: input
id: bug-report
attributes:
label: Bug report
description: Please run [`tailscale bugreport`](https://tailscale.com/kb/1080/cli/?q=Cli#bugreport) and share the bug identifier. The identifier is a random string which allows Tailscale support to locate your account and gives a point to focus on when looking for errors.
placeholder: e.g., BUG-1b7641a16971a9cd75822c0ed8043fee70ae88cf05c52981dc220eb96a5c49a8-20210427151443Z-fbcd4fd3a4b7ad94
validations:
required: false
- type: markdown
attributes:
value: |
Thanks for filing a bug report!

View File

@@ -1,5 +1,8 @@
blank_issues_enabled: true
contact_links:
- name: Support and Product Questions
- name: Support
url: https://tailscale.com/contact/support/
about: Contact us for support
- name: Troubleshooting
url: https://tailscale.com/kb/1023/troubleshooting
about: Please send support questions and questions about the Tailscale product to support@tailscale.com
about: See the troubleshooting guide for help addressing common issues

View File

@@ -1,7 +0,0 @@
---
name: Feature request
about: Suggest an idea for this project
title: ''
labels: 'needs-triage'
assignees: ''
---

View File

@@ -0,0 +1,42 @@
name: Feature request
description: Propose a new feature
title: "FR: "
labels: [needs-triage, fr]
body:
- type: markdown
attributes:
value: |
Please check if your feature request is [already filed](https://github.com/tailscale/tailscale/issues).
Tell us about your idea!
- type: textarea
id: problem
attributes:
label: What are you trying to do?
description: Tell us about the problem you're trying to solve.
validations:
required: false
- type: textarea
id: solution
attributes:
label: How should we solve this?
description: If you have an idea of how you'd like to see this feature work, let us know.
validations:
required: false
- type: textarea
id: alternative
attributes:
label: What is the impact of not solving this?
description: (How) Are you currently working around the issue?
validations:
required: false
- type: textarea
id: context
attributes:
label: Anything else?
description: Any additional context to share, e.g., links
validations:
required: false
- type: markdown
attributes:
value: |
Thanks for filing a feature request!

21
.github/dependabot.yml vendored Normal file
View File

@@ -0,0 +1,21 @@
# Documentation for this file can be found at:
# https://docs.github.com/en/code-security/supply-chain-security/keeping-your-dependencies-updated-automatically/configuration-options-for-dependency-updates
version: 2
updates:
## Disabled between releases. We reenable it briefly after every
## stable release, pull in all changes, and close it again so that
## the tree remains more stable during development and the upstream
## changes have time to soak before the next release.
# - package-ecosystem: "gomod"
# directory: "/"
# schedule:
# interval: "daily"
# commit-message:
# prefix: "go.mod:"
# open-pull-requests-limit: 100
- package-ecosystem: "github-actions"
directory: "/"
schedule:
interval: "weekly"
commit-message:
prefix: ".github:"

17
.github/licenses.tmpl vendored Normal file
View File

@@ -0,0 +1,17 @@
# Tailscale CLI and daemon dependencies
The following open source dependencies are used to build the [tailscale][] and
[tailscaled][] commands. These are primarily used on Linux and BSD variants as
well as an [option for macOS][].
[tailscale]: https://pkg.go.dev/tailscale.com/cmd/tailscale
[tailscaled]: https://pkg.go.dev/tailscale.com/cmd/tailscaled
[option for macOS]: https://tailscale.com/kb/1065/macos-variants/
## Go Packages
Some packages may only be included on certain architectures or operating systems.
{{ range . }}
- [{{.Name}}](https://pkg.go.dev/{{.Name}}) ([{{.LicenseName}}]({{.LicenseURL}}))
{{- end }}

28
.github/workflows/checklocks.yml vendored Normal file
View File

@@ -0,0 +1,28 @@
name: checklocks
on:
push:
branches:
- main
pull_request:
paths:
- '**/*.go'
- '.github/workflows/checklocks.yml'
concurrency:
group: ${{ github.workflow }}-$${{ github.head_ref || github.run_id }}
cancel-in-progress: true
jobs:
checklocks:
runs-on: [ ubuntu-latest ]
steps:
- name: Check out code
uses: actions/checkout@v3
- name: Build checklocks
run: ./tool/go build -o /tmp/checklocks gvisor.dev/gvisor/tools/checklocks/cmd/checklocks
- name: Run checklocks vet
# TODO: remove || true once we have applied checklocks annotations everywhere.
run: ./tool/go vet -vettool=/tmp/checklocks ./... || true

77
.github/workflows/codeql-analysis.yml vendored Normal file
View File

@@ -0,0 +1,77 @@
# For most projects, this workflow file will not need changing; you simply need
# to commit it to your repository.
#
# You may wish to alter this file to override the set of languages analyzed,
# or to provide custom queries or build logic.
#
# ******** NOTE ********
# We have attempted to detect the languages in your repository. Please check
# the `language` matrix defined below to confirm you have the correct set of
# supported CodeQL languages.
#
name: "CodeQL"
on:
push:
branches: [ main, release-branch/* ]
pull_request:
# The branches below must be a subset of the branches above
branches: [ main ]
merge_group:
branches: [ main ]
schedule:
- cron: '31 14 * * 5'
concurrency:
group: ${{ github.workflow }}-$${{ github.head_ref || github.run_id }}
cancel-in-progress: true
jobs:
analyze:
name: Analyze
runs-on: ubuntu-latest
permissions:
actions: read
contents: read
security-events: write
strategy:
fail-fast: false
matrix:
language: [ 'go' ]
# CodeQL supports [ 'cpp', 'csharp', 'go', 'java', 'javascript', 'python' ]
# Learn more:
# https://docs.github.com/en/free-pro-team@latest/github/finding-security-vulnerabilities-and-errors-in-your-code/configuring-code-scanning#changing-the-languages-that-are-analyzed
steps:
- name: Checkout repository
uses: actions/checkout@v4
# Initializes the CodeQL tools for scanning.
- name: Initialize CodeQL
uses: github/codeql-action/init@v2
with:
languages: ${{ matrix.language }}
# If you wish to specify custom queries, you can do so here or in a config file.
# By default, queries listed here will override any specified in a config file.
# Prefix the list here with "+" to use these queries and those in the config file.
# queries: ./path/to/local/query, your-org/your-repo/queries@main
# Autobuild attempts to build any compiled languages (C/C++, C#, or Java).
# If this step fails, then you should remove it and run the build manually (see below)
- name: Autobuild
uses: github/codeql-action/autobuild@v2
# Command-line programs to run using the OS shell.
# 📚 https://git.io/JvXDl
# ✏️ If the Autobuild fails above, remove it and uncomment the following three lines
# and modify them (or add more) to build your code if your project
# uses a compiled language
#- run: |
# make bootstrap
# make release
- name: Perform CodeQL Analysis
uses: github/codeql-action/analyze@v2

View File

@@ -1,53 +0,0 @@
name: Darwin-Cross
on:
push:
branches:
- main
pull_request:
branches:
- '*'
jobs:
build:
runs-on: ubuntu-latest
if: "!contains(github.event.head_commit.message, '[ci skip]')"
steps:
- name: Set up Go
uses: actions/setup-go@v1
with:
go-version: 1.16
id: go
- name: Check out code into the Go module directory
uses: actions/checkout@v1
- name: macOS build cmd
env:
GOOS: darwin
GOARCH: amd64
run: go build ./cmd/...
- name: macOS build tests
env:
GOOS: darwin
GOARCH: amd64
run: for d in $(go list -f '{{if .TestGoFiles}}{{.Dir}}{{end}}' ./... ); do (echo $d; cd $d && go test -c ); done
- uses: k0kubun/action-slack@v2.0.0
with:
payload: |
{
"attachments": [{
"text": "${{ job.status }}: ${{ github.workflow }} <https://github.com/${{ github.repository }}/commit/${{ github.sha }}/checks|${{ env.COMMIT_DATE }} #${{ env.COMMIT_NUMBER_OF_DAY }}> " +
"(<https://github.com/${{ github.repository }}/commit/${{ github.sha }}|" + "${{ github.sha }}".substring(0, 10) + ">) " +
"of ${{ github.repository }}@" + "${{ github.ref }}".split('/').reverse()[0] + " by ${{ github.event.head_commit.committer.name }}",
"color": "danger"
}]
}
env:
SLACK_WEBHOOK_URL: ${{ secrets.SLACK_WEBHOOK_URL }}
if: failure() && github.event_name == 'push'

View File

@@ -1,53 +0,0 @@
name: FreeBSD-Cross
on:
push:
branches:
- main
pull_request:
branches:
- '*'
jobs:
build:
runs-on: ubuntu-latest
if: "!contains(github.event.head_commit.message, '[ci skip]')"
steps:
- name: Set up Go
uses: actions/setup-go@v1
with:
go-version: 1.16
id: go
- name: Check out code into the Go module directory
uses: actions/checkout@v1
- name: FreeBSD build cmd
env:
GOOS: freebsd
GOARCH: amd64
run: go build ./cmd/...
- name: FreeBSD build tests
env:
GOOS: freebsd
GOARCH: amd64
run: for d in $(go list -f '{{if .TestGoFiles}}{{.Dir}}{{end}}' ./... ); do (echo $d; cd $d && go test -c ); done
- uses: k0kubun/action-slack@v2.0.0
with:
payload: |
{
"attachments": [{
"text": "${{ job.status }}: ${{ github.workflow }} <https://github.com/${{ github.repository }}/commit/${{ github.sha }}/checks|${{ env.COMMIT_DATE }} #${{ env.COMMIT_NUMBER_OF_DAY }}> " +
"(<https://github.com/${{ github.repository }}/commit/${{ github.sha }}|" + "${{ github.sha }}".substring(0, 10) + ">) " +
"of ${{ github.repository }}@" + "${{ github.ref }}".split('/').reverse()[0] + " by ${{ github.event.head_commit.committer.name }}",
"color": "danger"
}]
}
env:
SLACK_WEBHOOK_URL: ${{ secrets.SLACK_WEBHOOK_URL }}
if: failure() && github.event_name == 'push'

View File

@@ -1,53 +0,0 @@
name: OpenBSD-Cross
on:
push:
branches:
- main
pull_request:
branches:
- '*'
jobs:
build:
runs-on: ubuntu-latest
if: "!contains(github.event.head_commit.message, '[ci skip]')"
steps:
- name: Set up Go
uses: actions/setup-go@v1
with:
go-version: 1.16
id: go
- name: Check out code into the Go module directory
uses: actions/checkout@v1
- name: OpenBSD build cmd
env:
GOOS: openbsd
GOARCH: amd64
run: go build ./cmd/...
- name: OpenBSD build tests
env:
GOOS: openbsd
GOARCH: amd64
run: for d in $(go list -f '{{if .TestGoFiles}}{{.Dir}}{{end}}' ./... ); do (echo $d; cd $d && go test -c ); done
- uses: k0kubun/action-slack@v2.0.0
with:
payload: |
{
"attachments": [{
"text": "${{ job.status }}: ${{ github.workflow }} <https://github.com/${{ github.repository }}/commit/${{ github.sha }}/checks|${{ env.COMMIT_DATE }} #${{ env.COMMIT_NUMBER_OF_DAY }}> " +
"(<https://github.com/${{ github.repository }}/commit/${{ github.sha }}|" + "${{ github.sha }}".substring(0, 10) + ">) " +
"of ${{ github.repository }}@" + "${{ github.ref }}".split('/').reverse()[0] + " by ${{ github.event.head_commit.committer.name }}",
"color": "danger"
}]
}
env:
SLACK_WEBHOOK_URL: ${{ secrets.SLACK_WEBHOOK_URL }}
if: failure() && github.event_name == 'push'

View File

@@ -1,53 +0,0 @@
name: Windows-Cross
on:
push:
branches:
- main
pull_request:
branches:
- '*'
jobs:
build:
runs-on: ubuntu-latest
if: "!contains(github.event.head_commit.message, '[ci skip]')"
steps:
- name: Set up Go
uses: actions/setup-go@v1
with:
go-version: 1.16
id: go
- name: Check out code into the Go module directory
uses: actions/checkout@v1
- name: Windows build cmd
env:
GOOS: windows
GOARCH: amd64
run: go build ./cmd/...
- name: Windows build tests
env:
GOOS: windows
GOARCH: amd64
run: for d in $(go list -f '{{if .TestGoFiles}}{{.Dir}}{{end}}' ./... ); do (echo $d; cd $d && go test -c ); done
- uses: k0kubun/action-slack@v2.0.0
with:
payload: |
{
"attachments": [{
"text": "${{ job.status }}: ${{ github.workflow }} <https://github.com/${{ github.repository }}/commit/${{ github.sha }}/checks|${{ env.COMMIT_DATE }} #${{ env.COMMIT_NUMBER_OF_DAY }}> " +
"(<https://github.com/${{ github.repository }}/commit/${{ github.sha }}|" + "${{ github.sha }}".substring(0, 10) + ">) " +
"of ${{ github.repository }}@" + "${{ github.ref }}".split('/').reverse()[0] + " by ${{ github.event.head_commit.committer.name }}",
"color": "danger"
}]
}
env:
SLACK_WEBHOOK_URL: ${{ secrets.SLACK_WEBHOOK_URL }}
if: failure() && github.event_name == 'push'

View File

@@ -1,28 +0,0 @@
name: depaware
on:
push:
branches:
- main
pull_request:
branches:
- '*'
jobs:
build:
runs-on: ubuntu-latest
steps:
- name: Set up Go
uses: actions/setup-go@v1
with:
go-version: 1.16
- name: Check out code
uses: actions/checkout@v1
- name: depaware tailscaled
run: go run github.com/tailscale/depaware --check tailscale.com/cmd/tailscaled
- name: depaware tailscale
run: go run github.com/tailscale/depaware --check tailscale.com/cmd/tailscale

15
.github/workflows/docker-file-build.yml vendored Normal file
View File

@@ -0,0 +1,15 @@
name: "Dockerfile build"
on:
push:
branches:
- main
pull_request:
branches:
- "*"
jobs:
deploy:
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- name: "Build Docker image"
run: docker build .

View File

@@ -0,0 +1,27 @@
name: update-flakehub
on:
push:
tags:
- "v[0-9]+.*[02468].[0-9]+"
workflow_dispatch:
inputs:
tag:
description: "The existing tag to publish to FlakeHub"
type: "string"
required: true
jobs:
flakehub-publish:
runs-on: "ubuntu-latest"
permissions:
id-token: "write"
contents: "read"
steps:
- uses: "actions/checkout@v4"
with:
ref: "${{ (inputs.tag != null) && format('refs/tags/{0}', inputs.tag) || '' }}"
- uses: "DeterminateSystems/nix-installer-action@main"
- uses: "DeterminateSystems/flakehub-push@main"
with:
visibility: "public"
tag: "${{ inputs.tag }}"

64
.github/workflows/go-licenses.yml vendored Normal file
View File

@@ -0,0 +1,64 @@
name: go-licenses
on:
# run action when a change lands in the main branch which updates go.mod or
# our license template file. Also allow manual triggering.
push:
branches:
- main
paths:
- go.mod
- .github/licenses.tmpl
- .github/workflows/go-licenses.yml
workflow_dispatch:
concurrency:
group: ${{ github.workflow }}-$${{ github.head_ref || github.run_id }}
cancel-in-progress: true
jobs:
update-licenses:
runs-on: ubuntu-latest
steps:
- name: Check out code
uses: actions/checkout@v4
- name: Set up Go
uses: actions/setup-go@v4
with:
go-version-file: go.mod
- name: Install go-licenses
run: |
go install github.com/google/go-licenses@v1.2.2-0.20220825154955-5eedde1c6584
- name: Run go-licenses
env:
# include all build tags to include platform-specific dependencies
GOFLAGS: "-tags=android,cgo,darwin,freebsd,ios,js,linux,openbsd,wasm,windows"
run: |
[ -d licenses ] || mkdir licenses
go-licenses report tailscale.com/cmd/tailscale tailscale.com/cmd/tailscaled > licenses/tailscale.md --template .github/licenses.tmpl
- name: Get access token
uses: tibdex/github-app-token@b62528385c34dbc9f38e5f4225ac829252d1ea92 # v1.8.0
id: generate-token
with:
app_id: ${{ secrets.LICENSING_APP_ID }}
installation_id: ${{ secrets.LICENSING_APP_INSTALLATION_ID }}
private_key: ${{ secrets.LICENSING_APP_PRIVATE_KEY }}
- name: Send pull request
uses: peter-evans/create-pull-request@284f54f989303d2699d373481a0cfa13ad5a6666 #v5.0.1
with:
token: ${{ steps.generate-token.outputs.token }}
author: License Updater <noreply+license-updater@tailscale.com>
committer: License Updater <noreply+license-updater@tailscale.com>
branch: licenses/cli
commit-message: "licenses: update tailscale{,d} licenses"
title: "licenses: update tailscale{,d} licenses"
body: Triggered by ${{ github.repository }}@${{ github.sha }}
signoff: true
delete-branch: true
team-reviewers: opensource-license-reviewers

View File

@@ -1,34 +0,0 @@
name: go generate
on:
push:
branches:
- main
- "release-branch/*"
pull_request:
branches:
- "*"
jobs:
check:
runs-on: ubuntu-latest
steps:
- name: Set up Go
uses: actions/setup-go@v1
with:
go-version: 1.16
- name: Check out code
uses: actions/checkout@v2
with:
fetch-depth: 0
- name: check 'go generate' is clean
run: |
mkdir gentools
go build -o gentools/stringer golang.org/x/tools/cmd/stringer
PATH="$PATH:$(pwd)/gentools" go generate ./...
echo
echo
git diff --name-only --exit-code || (echo "The files above need updating. Please run 'go generate'."; exit 1)

40
.github/workflows/golangci-lint.yml vendored Normal file
View File

@@ -0,0 +1,40 @@
name: golangci-lint
on:
# For now, only lint pull requests, not the main branches.
pull_request:
# TODO(andrew): enable for main branch after an initial waiting period.
#push:
# branches:
# - main
workflow_dispatch:
permissions:
contents: read
pull-requests: read
concurrency:
group: ${{ github.workflow }}-$${{ github.head_ref || github.run_id }}
cancel-in-progress: true
jobs:
golangci:
name: lint
runs-on: ubuntu-latest
steps:
- uses: actions/checkout@v4
- uses: actions/setup-go@v4
with:
go-version-file: go.mod
cache: false
- name: golangci-lint
# Note: this is the 'v3' tag as of 2023-08-14
uses: golangci/golangci-lint-action@639cd343e1d3b897ff35927a75193d57cfcba299
with:
version: v1.54.2
# Show only new issues if it's a pull request.
only-new-issues: true

38
.github/workflows/govulncheck.yml vendored Normal file
View File

@@ -0,0 +1,38 @@
name: govulncheck
on:
schedule:
- cron: "0 12 * * *" # 8am EST / 10am PST / 12pm UTC
workflow_dispatch: # allow manual trigger for testing
pull_request:
paths:
- ".github/workflows/govulncheck.yml"
jobs:
source-scan:
runs-on: ubuntu-latest
steps:
- name: Check out code into the Go module directory
uses: actions/checkout@v4
- name: Install govulncheck
run: ./tool/go install golang.org/x/vuln/cmd/govulncheck@latest
- name: Scan source code for known vulnerabilities
run: PATH=$PWD/tool/:$PATH "$(./tool/go env GOPATH)/bin/govulncheck" -test ./...
- uses: ruby/action-slack@v3.2.1
with:
payload: >
{
"attachments": [{
"title": "${{ job.status }}: ${{ github.workflow }}",
"title_link": "https://github.com/${{ github.repository }}/commit/${{ github.sha }}/checks",
"text": "${{ github.repository }}@${{ github.sha }}",
"color": "danger"
}]
}
env:
SLACK_WEBHOOK_URL: ${{ secrets.SLACK_WEBHOOK_URL }}
if: failure() && github.event_name == 'schedule'

102
.github/workflows/installer.yml vendored Normal file
View File

@@ -0,0 +1,102 @@
name: test installer.sh
on:
push:
branches:
- "main"
paths:
- scripts/installer.sh
pull_request:
branches:
- "*"
paths:
- scripts/installer.sh
jobs:
test:
strategy:
# Don't abort the entire matrix if one element fails.
fail-fast: false
# Don't start all of these at once, which could saturate Github workers.
max-parallel: 4
matrix:
image:
# This is a list of Docker images against which we test our installer.
# If you find that some of these no longer exist, please feel free
# to remove them from the list.
# When adding new images, please only use official ones.
- "debian:oldstable-slim"
- "debian:stable-slim"
- "debian:testing-slim"
- "debian:sid-slim"
- "ubuntu:18.04"
- "ubuntu:20.04"
- "ubuntu:22.04"
- "ubuntu:22.10"
- "ubuntu:23.04"
- "elementary/docker:stable"
- "elementary/docker:unstable"
- "parrotsec/core:lts-amd64"
- "parrotsec/core:latest"
- "kalilinux/kali-rolling"
- "kalilinux/kali-dev"
- "oraclelinux:9"
- "oraclelinux:8"
- "fedora:latest"
- "rockylinux:8.7"
- "rockylinux:9"
- "amazonlinux:latest"
- "opensuse/leap:latest"
- "opensuse/tumbleweed:latest"
- "archlinux:latest"
- "alpine:3.14"
- "alpine:latest"
- "alpine:edge"
deps:
# Run all images installing curl as a dependency.
- curl
include:
# Check a few images with wget rather than curl.
- { image: "debian:oldstable-slim", deps: "wget" }
- { image: "debian:sid-slim", deps: "wget" }
- { image: "ubuntu:23.04", deps: "wget" }
# Ubuntu 16.04 also needs apt-transport-https installed.
- { image: "ubuntu:16.04", deps: "curl apt-transport-https" }
- { image: "ubuntu:16.04", deps: "wget apt-transport-https" }
runs-on: ubuntu-latest
container:
image: ${{ matrix.image }}
options: --user root
steps:
- name: install dependencies (yum)
# tar and gzip are needed by the actions/checkout below.
run: yum install -y --allowerasing tar gzip ${{ matrix.deps }}
if: |
contains(matrix.image, 'centos')
|| contains(matrix.image, 'oraclelinux')
|| contains(matrix.image, 'fedora')
|| contains(matrix.image, 'amazonlinux')
- name: install dependencies (zypper)
# tar and gzip are needed by the actions/checkout below.
run: zypper --non-interactive install tar gzip ${{ matrix.deps }}
if: contains(matrix.image, 'opensuse')
- name: install dependencies (apt-get)
run: |
apt-get update
apt-get install -y ${{ matrix.deps }}
if: |
contains(matrix.image, 'debian')
|| contains(matrix.image, 'ubuntu')
|| contains(matrix.image, 'elementary')
|| contains(matrix.image, 'parrotsec')
|| contains(matrix.image, 'kalilinux')
- name: checkout
uses: actions/checkout@v4
- name: run installer
run: scripts/installer.sh
# Package installation can fail in docker because systemd is not running
# as PID 1, so ignore errors at this step. The real check is the
# `tailscale --version` command below.
continue-on-error: true
- name: check tailscale version
run: tailscale --version

View File

@@ -1,40 +0,0 @@
name: license
on:
push:
branches:
- main
pull_request:
branches:
- '*'
jobs:
build:
runs-on: ubuntu-latest
steps:
- name: Set up Go
uses: actions/setup-go@v1
with:
go-version: 1.16
- name: Check out code
uses: actions/checkout@v1
- name: Run license checker
run: ./scripts/check_license_headers.sh .
- uses: k0kubun/action-slack@v2.0.0
with:
payload: |
{
"attachments": [{
"text": "${{ job.status }}: ${{ github.workflow }} <https://github.com/${{ github.repository }}/commit/${{ github.sha }}/checks|${{ env.COMMIT_DATE }} #${{ env.COMMIT_NUMBER_OF_DAY }}> " +
"(<https://github.com/${{ github.repository }}/commit/${{ github.sha }}|" + "${{ github.sha }}".substring(0, 10) + ">) " +
"of ${{ github.repository }}@" + "${{ github.ref }}".split('/').reverse()[0] + " by ${{ github.event.head_commit.committer.name }}",
"color": "danger"
}]
}
env:
SLACK_WEBHOOK_URL: ${{ secrets.SLACK_WEBHOOK_URL }}
if: failure() && github.event_name == 'push'

View File

@@ -1,48 +0,0 @@
name: Linux race
on:
push:
branches:
- main
pull_request:
branches:
- '*'
jobs:
build:
runs-on: ubuntu-latest
if: "!contains(github.event.head_commit.message, '[ci skip]')"
steps:
- name: Set up Go
uses: actions/setup-go@v1
with:
go-version: 1.16
id: go
- name: Check out code into the Go module directory
uses: actions/checkout@v1
- name: Basic build
run: go build ./cmd/...
- name: Run tests and benchmarks with -race flag on linux
run: go test -race -bench=. -benchtime=1x ./...
- uses: k0kubun/action-slack@v2.0.0
with:
payload: |
{
"attachments": [{
"text": "${{ job.status }}: ${{ github.workflow }} <https://github.com/${{ github.repository }}/commit/${{ github.sha }}/checks|${{ env.COMMIT_DATE }} #${{ env.COMMIT_NUMBER_OF_DAY }}> " +
"(<https://github.com/${{ github.repository }}/commit/${{ github.sha }}|" + "${{ github.sha }}".substring(0, 10) + ">) " +
"of ${{ github.repository }}@" + "${{ github.ref }}".split('/').reverse()[0] + " by ${{ github.event.head_commit.committer.name }}",
"color": "danger"
}]
}
env:
SLACK_WEBHOOK_URL: ${{ secrets.SLACK_WEBHOOK_URL }}
if: failure() && github.event_name == 'push'

View File

@@ -1,48 +0,0 @@
name: Linux
on:
push:
branches:
- main
pull_request:
branches:
- '*'
jobs:
build:
runs-on: ubuntu-latest
if: "!contains(github.event.head_commit.message, '[ci skip]')"
steps:
- name: Set up Go
uses: actions/setup-go@v1
with:
go-version: 1.16
id: go
- name: Check out code into the Go module directory
uses: actions/checkout@v1
- name: Basic build
run: go build ./cmd/...
- name: Run tests on linux
run: go test -bench=. -benchtime=1x ./...
- uses: k0kubun/action-slack@v2.0.0
with:
payload: |
{
"attachments": [{
"text": "${{ job.status }}: ${{ github.workflow }} <https://github.com/${{ github.repository }}/commit/${{ github.sha }}/checks|${{ env.COMMIT_DATE }} #${{ env.COMMIT_NUMBER_OF_DAY }}> " +
"(<https://github.com/${{ github.repository }}/commit/${{ github.sha }}|" + "${{ github.sha }}".substring(0, 10) + ">) " +
"of ${{ github.repository }}@" + "${{ github.ref }}".split('/').reverse()[0] + " by ${{ github.event.head_commit.committer.name }}",
"color": "danger"
}]
}
env:
SLACK_WEBHOOK_URL: ${{ secrets.SLACK_WEBHOOK_URL }}
if: failure() && github.event_name == 'push'

View File

@@ -1,48 +0,0 @@
name: Linux 32-bit
on:
push:
branches:
- main
pull_request:
branches:
- '*'
jobs:
build:
runs-on: ubuntu-latest
if: "!contains(github.event.head_commit.message, '[ci skip]')"
steps:
- name: Set up Go
uses: actions/setup-go@v1
with:
go-version: 1.16
id: go
- name: Check out code into the Go module directory
uses: actions/checkout@v1
- name: Basic build
run: GOARCH=386 go build ./cmd/...
- name: Run tests on linux
run: GOARCH=386 go test -bench=. -benchtime=1x ./...
- uses: k0kubun/action-slack@v2.0.0
with:
payload: |
{
"attachments": [{
"text": "${{ job.status }}: ${{ github.workflow }} <https://github.com/${{ github.repository }}/commit/${{ github.sha }}/checks|${{ env.COMMIT_DATE }} #${{ env.COMMIT_NUMBER_OF_DAY }}> " +
"(<https://github.com/${{ github.repository }}/commit/${{ github.sha }}|" + "${{ github.sha }}".substring(0, 10) + ">) " +
"of ${{ github.repository }}@" + "${{ github.ref }}".split('/').reverse()[0] + " by ${{ github.event.head_commit.committer.name }}",
"color": "danger"
}]
}
env:
SLACK_WEBHOOK_URL: ${{ secrets.SLACK_WEBHOOK_URL }}
if: failure() && github.event_name == 'push'

View File

@@ -1,58 +0,0 @@
name: staticcheck
on:
push:
branches:
- main
pull_request:
branches:
- '*'
jobs:
build:
runs-on: ubuntu-latest
steps:
- name: Set up Go
uses: actions/setup-go@v1
with:
go-version: 1.16
- name: Check out code
uses: actions/checkout@v1
- name: Run go vet
run: go vet ./...
- name: Install staticcheck
run: "GOBIN=~/.local/bin go install honnef.co/go/tools/cmd/staticcheck"
- name: Print staticcheck version
run: "staticcheck -version"
- name: Run staticcheck (linux/amd64)
run: "GOOS=linux GOARCH=amd64 staticcheck -- $(go list ./... | grep -v tempfork)"
- name: Run staticcheck (darwin/amd64)
run: "GOOS=darwin GOARCH=amd64 staticcheck -- $(go list ./... | grep -v tempfork)"
- name: Run staticcheck (windows/amd64)
run: "GOOS=windows GOARCH=amd64 staticcheck -- $(go list ./... | grep -v tempfork)"
- name: Run staticcheck (windows/386)
run: "GOOS=windows GOARCH=386 staticcheck -- $(go list ./... | grep -v tempfork)"
- uses: k0kubun/action-slack@v2.0.0
with:
payload: |
{
"attachments": [{
"text": "${{ job.status }}: ${{ github.workflow }} <https://github.com/${{ github.repository }}/commit/${{ github.sha }}/checks|${{ env.COMMIT_DATE }} #${{ env.COMMIT_NUMBER_OF_DAY }}> " +
"(<https://github.com/${{ github.repository }}/commit/${{ github.sha }}|" + "${{ github.sha }}".substring(0, 10) + ">) " +
"of ${{ github.repository }}@" + "${{ github.ref }}".split('/').reverse()[0] + " by ${{ github.event.head_commit.committer.name }}",
"color": "danger"
}]
}
env:
SLACK_WEBHOOK_URL: ${{ secrets.SLACK_WEBHOOK_URL }}
if: failure() && github.event_name == 'push'

544
.github/workflows/test.yml vendored Normal file
View File

@@ -0,0 +1,544 @@
# This is our main "CI tests" workflow. It runs everything that should run on
# both PRs and merged commits, and for the latter reports failures to slack.
name: CI
env:
# Our fuzz job, powered by OSS-Fuzz, fails periodically because we upgrade to
# new Go versions very eagerly. OSS-Fuzz is a little more conservative, and
# ends up being unable to compile our code.
#
# When this happens, we want to disable the fuzz target until OSS-Fuzz catches
# up. However, we also don't want to forget to turn it back on when OSS-Fuzz
# can once again build our code.
#
# This variable toggles the fuzz job between two modes:
# - false: we expect fuzzing to be happy, and should report failure if it's not.
# - true: we expect fuzzing is broken, and should report failure if it start working.
TS_FUZZ_CURRENTLY_BROKEN: false
on:
push:
branches:
- "main"
- "release-branch/*"
pull_request:
# all PRs on all branches
merge_group:
branches:
- "main"
concurrency:
# For PRs, later CI runs preempt previous ones. e.g. a force push on a PR
# cancels running CI jobs and starts all new ones.
#
# For non-PR pushes, concurrency.group needs to be unique for every distinct
# CI run we want to have happen. Use run_id, which in practice means all
# non-PR CI runs will be allowed to run without preempting each other.
group: ${{ github.workflow }}-$${{ github.pull_request.number || github.run_id }}
cancel-in-progress: true
jobs:
race-root-integration:
runs-on: ubuntu-22.04
strategy:
fail-fast: false # don't abort the entire matrix if one element fails
matrix:
include:
- shard: '1/4'
- shard: '2/4'
- shard: '3/4'
- shard: '4/4'
steps:
- name: checkout
uses: actions/checkout@v4
- name: build test wrapper
run: ./tool/go build -o /tmp/testwrapper ./cmd/testwrapper
- name: integration tests as root
run: PATH=$PWD/tool:$PATH /tmp/testwrapper -exec "sudo -E" -race ./tstest/integration/
env:
TS_TEST_SHARD: ${{ matrix.shard }}
test:
strategy:
fail-fast: false # don't abort the entire matrix if one element fails
matrix:
include:
- goarch: amd64
- goarch: amd64
buildflags: "-race"
shard: '1/3'
- goarch: amd64
buildflags: "-race"
shard: '2/3'
- goarch: amd64
buildflags: "-race"
shard: '3/3'
- goarch: "386" # thanks yaml
runs-on: ubuntu-22.04
steps:
- name: checkout
uses: actions/checkout@v4
- name: Restore Cache
uses: actions/cache@v3
with:
# Note: unlike the other setups, this is only grabbing the mod download
# cache, rather than the whole mod directory, as the download cache
# contains zips that can be unpacked in parallel faster than they can be
# fetched and extracted by tar
path: |
~/.cache/go-build
~/go/pkg/mod/cache
~\AppData\Local\go-build
# The -2- here should be incremented when the scheme of data to be
# cached changes (e.g. path above changes).
key: ${{ github.job }}-${{ runner.os }}-${{ matrix.goarch }}-${{ matrix.buildflags }}-go-2-${{ hashFiles('**/go.sum') }}-${{ github.run_id }}
restore-keys: |
${{ github.job }}-${{ runner.os }}-${{ matrix.goarch }}-${{ matrix.buildflags }}-go-2-${{ hashFiles('**/go.sum') }}
${{ github.job }}-${{ runner.os }}-${{ matrix.goarch }}-${{ matrix.buildflags }}-go-2-
- name: build all
if: matrix.buildflags == '' # skip on race builder
run: ./tool/go build ${{matrix.buildflags}} ./...
env:
GOARCH: ${{ matrix.goarch }}
- name: build variant CLIs
if: matrix.buildflags == '' # skip on race builder
run: |
export TS_USE_TOOLCHAIN=1
./build_dist.sh --extra-small ./cmd/tailscaled
./build_dist.sh --box ./cmd/tailscaled
./build_dist.sh --extra-small --box ./cmd/tailscaled
rm -f tailscaled
env:
GOARCH: ${{ matrix.goarch }}
- name: get qemu # for tstest/archtest
if: matrix.goarch == 'amd64' && matrix.buildflags == ''
run: |
sudo apt-get -y update
sudo apt-get -y install qemu-user
- name: build test wrapper
run: ./tool/go build -o /tmp/testwrapper ./cmd/testwrapper
- name: test all
run: PATH=$PWD/tool:$PATH /tmp/testwrapper ./... ${{matrix.buildflags}}
env:
GOARCH: ${{ matrix.goarch }}
TS_TEST_SHARD: ${{ matrix.shard }}
- name: bench all
run: ./tool/go test ${{matrix.buildflags}} -bench=. -benchtime=1x -run=^$ $(for x in $(git grep -l "^func Benchmark" | xargs dirname | sort | uniq); do echo "./$x"; done)
env:
GOARCH: ${{ matrix.goarch }}
- name: check that no tracked files changed
run: git diff --no-ext-diff --name-only --exit-code || (echo "Build/test modified the files above."; exit 1)
- name: check that no new files were added
run: |
# Note: The "error: pathspec..." you see below is normal!
# In the success case in which there are no new untracked files,
# git ls-files complains about the pathspec not matching anything.
# That's OK. It's not worth the effort to suppress. Please ignore it.
if git ls-files --others --exclude-standard --directory --no-empty-directory --error-unmatch -- ':/*'
then
echo "Build/test created untracked files in the repo (file names above)."
exit 1
fi
windows:
runs-on: windows-2022
steps:
- name: checkout
uses: actions/checkout@v4
- name: Install Go
uses: actions/setup-go@v4
with:
go-version-file: go.mod
cache: false
- name: Restore Cache
uses: actions/cache@v3
with:
# Note: unlike the other setups, this is only grabbing the mod download
# cache, rather than the whole mod directory, as the download cache
# contains zips that can be unpacked in parallel faster than they can be
# fetched and extracted by tar
path: |
~/.cache/go-build
~/go/pkg/mod/cache
~\AppData\Local\go-build
# The -2- here should be incremented when the scheme of data to be
# cached changes (e.g. path above changes).
key: ${{ github.job }}-${{ runner.os }}-go-2-${{ hashFiles('**/go.sum') }}-${{ github.run_id }}
restore-keys: |
${{ github.job }}-${{ runner.os }}-go-2-${{ hashFiles('**/go.sum') }}
${{ github.job }}-${{ runner.os }}-go-2-
- name: test
run: go run ./cmd/testwrapper ./...
- name: bench all
# Don't use -bench=. -benchtime=1x.
# Somewhere in the layers (powershell?)
# the equals signs cause great confusion.
run: go test ./... -bench . -benchtime 1x -run "^$"
vm:
runs-on: ["self-hosted", "linux", "vm"]
# VM tests run with some privileges, don't let them run on 3p PRs.
if: github.repository == 'tailscale/tailscale'
steps:
- name: checkout
uses: actions/checkout@v4
- name: Run VM tests
run: ./tool/go test ./tstest/integration/vms -v -no-s3 -run-vm-tests -run=TestRunUbuntu2004
env:
HOME: "/tmp"
TMPDIR: "/tmp"
XDB_CACHE_HOME: "/var/lib/ghrunner/cache"
race-build:
runs-on: ubuntu-22.04
steps:
- name: checkout
uses: actions/checkout@v4
- name: build all
run: ./tool/go install -race ./cmd/...
- name: build tests
run: ./tool/go test -race -exec=true ./...
cross: # cross-compile checks, build only.
strategy:
fail-fast: false # don't abort the entire matrix if one element fails
matrix:
include:
# Note: linux/amd64 is not in this matrix, because that goos/goarch is
# tested more exhaustively in the 'test' job above.
- goos: linux
goarch: arm64
- goos: linux
goarch: "386" # thanks yaml
- goos: linux
goarch: loong64
- goos: linux
goarch: arm
goarm: "5"
- goos: linux
goarch: arm
goarm: "7"
# macOS
- goos: darwin
goarch: amd64
- goos: darwin
goarch: arm64
# Windows
- goos: windows
goarch: amd64
- goos: windows
goarch: arm64
# BSDs
- goos: freebsd
goarch: amd64
- goos: openbsd
goarch: amd64
# Plan9
- goos: plan9
goarch: amd64
runs-on: ubuntu-22.04
steps:
- name: checkout
uses: actions/checkout@v4
- name: Restore Cache
uses: actions/cache@v3
with:
# Note: unlike the other setups, this is only grabbing the mod download
# cache, rather than the whole mod directory, as the download cache
# contains zips that can be unpacked in parallel faster than they can be
# fetched and extracted by tar
path: |
~/.cache/go-build
~/go/pkg/mod/cache
~\AppData\Local\go-build
# The -2- here should be incremented when the scheme of data to be
# cached changes (e.g. path above changes).
key: ${{ github.job }}-${{ runner.os }}-${{ matrix.goos }}-${{ matrix.goarch }}-go-2-${{ hashFiles('**/go.sum') }}-${{ github.run_id }}
restore-keys: |
${{ github.job }}-${{ runner.os }}-${{ matrix.goos }}-${{ matrix.goarch }}-go-2-${{ hashFiles('**/go.sum') }}
${{ github.job }}-${{ runner.os }}-${{ matrix.goos }}-${{ matrix.goarch }}-go-2-
- name: build all
run: ./tool/go build ./cmd/...
env:
GOOS: ${{ matrix.goos }}
GOARCH: ${{ matrix.goarch }}
GOARM: ${{ matrix.goarm }}
CGO_ENABLED: "0"
- name: build tests
run: ./tool/go test -exec=true ./...
env:
GOOS: ${{ matrix.goos }}
GOARCH: ${{ matrix.goarch }}
CGO_ENABLED: "0"
ios: # similar to cross above, but iOS can't build most of the repo. So, just
#make it build a few smoke packages.
runs-on: ubuntu-22.04
steps:
- name: checkout
uses: actions/checkout@v4
- name: build some
run: ./tool/go build ./ipn/... ./wgengine/ ./types/... ./control/controlclient
env:
GOOS: ios
GOARCH: arm64
android:
# similar to cross above, but android fails to build a few pieces of the
# repo. We should fix those pieces, they're small, but as a stepping stone,
# only test the subset of android that our past smoke test checked.
runs-on: ubuntu-22.04
steps:
- name: checkout
uses: actions/checkout@v4
# Super minimal Android build that doesn't even use CGO and doesn't build everything that's needed
# and is only arm64. But it's a smoke build: it's not meant to catch everything. But it'll catch
# some Android breakages early.
# TODO(bradfitz): better; see https://github.com/tailscale/tailscale/issues/4482
- name: build some
run: ./tool/go install ./net/netns ./ipn/ipnlocal ./wgengine/magicsock/ ./wgengine/ ./wgengine/router/ ./wgengine/netstack ./util/dnsname/ ./ipn/ ./net/interfaces ./wgengine/router/ ./tailcfg/ ./types/logger/ ./net/dns ./hostinfo ./version
env:
GOOS: android
GOARCH: arm64
wasm: # builds tsconnect, which is the only wasm build we support
runs-on: ubuntu-22.04
steps:
- name: checkout
uses: actions/checkout@v4
- name: Restore Cache
uses: actions/cache@v3
with:
# Note: unlike the other setups, this is only grabbing the mod download
# cache, rather than the whole mod directory, as the download cache
# contains zips that can be unpacked in parallel faster than they can be
# fetched and extracted by tar
path: |
~/.cache/go-build
~/go/pkg/mod/cache
~\AppData\Local\go-build
# The -2- here should be incremented when the scheme of data to be
# cached changes (e.g. path above changes).
key: ${{ github.job }}-${{ runner.os }}-go-2-${{ hashFiles('**/go.sum') }}-${{ github.run_id }}
restore-keys: |
${{ github.job }}-${{ runner.os }}-go-2-${{ hashFiles('**/go.sum') }}
${{ github.job }}-${{ runner.os }}-go-2-
- name: build tsconnect client
run: ./tool/go build ./cmd/tsconnect/wasm ./cmd/tailscale/cli
env:
GOOS: js
GOARCH: wasm
- name: build tsconnect server
# Note, no GOOS/GOARCH in env on this build step, we're running a build
# tool that handles the build itself.
run: |
./tool/go run ./cmd/tsconnect --fast-compression build
./tool/go run ./cmd/tsconnect --fast-compression build-pkg
tailscale_go: # Subset of tests that depend on our custom Go toolchain.
runs-on: ubuntu-22.04
steps:
- name: checkout
uses: actions/checkout@v4
- name: test tailscale_go
run: ./tool/go test -tags=tailscale_go,ts_enable_sockstats ./net/sockstats/...
fuzz:
# This target periodically breaks (see TS_FUZZ_CURRENTLY_BROKEN at the top
# of the file), so it's more complex than usual: the 'build fuzzers' step
# might fail, and depending on the value of 'TS_FUZZ_CURRENTLY_BROKEN', that
# might or might not be fine. The steps after the build figure out whether
# the success/failure is expected, and appropriately pass/fail the job
# overall accordingly.
#
# Practically, this means that all steps after 'build fuzzers' must have an
# explicit 'if' condition, because the default condition for steps is
# 'success()', meaning "only run this if no previous steps failed".
if: github.event_name == 'pull_request'
runs-on: ubuntu-22.04
steps:
- name: build fuzzers
id: build
uses: google/oss-fuzz/infra/cifuzz/actions/build_fuzzers@master
# continue-on-error makes steps.build.conclusion be 'success' even if
# steps.build.outcome is 'failure'. This means this step does not
# contribute to the job's overall pass/fail evaluation.
continue-on-error: true
with:
oss-fuzz-project-name: 'tailscale'
dry-run: false
language: go
- name: report unexpectedly broken fuzz build
if: steps.build.outcome == 'failure' && env.TS_FUZZ_CURRENTLY_BROKEN != 'true'
run: |
echo "fuzzer build failed, see above for why"
echo "if the failure is due to OSS-Fuzz not being on the latest Go yet,"
echo "set TS_FUZZ_CURRENTLY_BROKEN=true in .github/workflows/test.yml"
echo "to temporarily disable fuzzing until OSS-Fuzz works again."
exit 1
- name: report unexpectedly working fuzz build
if: steps.build.outcome == 'success' && env.TS_FUZZ_CURRENTLY_BROKEN == 'true'
run: |
echo "fuzzer build succeeded, but we expect it to be broken"
echo "please set TS_FUZZ_CURRENTLY_BROKEN=false in .github/workflows/test.yml"
echo "to reenable fuzz testing"
exit 1
- name: run fuzzers
id: run
# Run the fuzzers whenever they're able to build, even if we're going to
# report a failure because TS_FUZZ_CURRENTLY_BROKEN is set to the wrong
# value.
if: steps.build.outcome == 'success'
uses: google/oss-fuzz/infra/cifuzz/actions/run_fuzzers@master
with:
oss-fuzz-project-name: 'tailscale'
fuzz-seconds: 300
dry-run: false
language: go
- name: upload crash
uses: actions/upload-artifact@v3
if: steps.run.outcome != 'success' && steps.build.outcome == 'success'
with:
name: artifacts
path: ./out/artifacts
depaware:
runs-on: ubuntu-22.04
steps:
- name: checkout
uses: actions/checkout@v4
- name: check depaware
run: |
export PATH=$(./tool/go env GOROOT)/bin:$PATH
find . -name 'depaware.txt' | xargs -n1 dirname | xargs ./tool/go run github.com/tailscale/depaware --check
go_generate:
runs-on: ubuntu-22.04
steps:
- name: checkout
uses: actions/checkout@v4
- name: check that 'go generate' is clean
run: |
pkgs=$(./tool/go list ./... | grep -v dnsfallback)
./tool/go generate $pkgs
echo
echo
git diff --name-only --exit-code || (echo "The files above need updating. Please run 'go generate'."; exit 1)
go_mod_tidy:
runs-on: ubuntu-22.04
steps:
- name: checkout
uses: actions/checkout@v4
- name: check that 'go mod tidy' is clean
run: |
./tool/go mod tidy
echo
echo
git diff --name-only --exit-code || (echo "Please run 'go mod tidy'."; exit 1)
licenses:
runs-on: ubuntu-22.04
steps:
- name: checkout
uses: actions/checkout@v4
- name: check licenses
run: ./scripts/check_license_headers.sh .
staticcheck:
runs-on: ubuntu-22.04
strategy:
fail-fast: false # don't abort the entire matrix if one element fails
matrix:
goos: ["linux", "windows", "darwin"]
goarch: ["amd64"]
include:
- goos: "windows"
goarch: "386"
steps:
- name: checkout
uses: actions/checkout@v4
- name: install staticcheck
run: GOBIN=~/.local/bin ./tool/go install honnef.co/go/tools/cmd/staticcheck
- name: run staticcheck
run: |
export GOROOT=$(./tool/go env GOROOT)
export PATH=$GOROOT/bin:$PATH
staticcheck -- $(./tool/go list ./... | grep -v tempfork)
env:
GOOS: ${{ matrix.goos }}
GOARCH: ${{ matrix.goarch }}
notify_slack:
if: always()
# Any of these jobs failing causes a slack notification.
needs:
- android
- test
- windows
- vm
- cross
- ios
- wasm
- tailscale_go
- fuzz
- depaware
- go_generate
- go_mod_tidy
- licenses
- staticcheck
runs-on: ubuntu-22.04
steps:
- name: notify
# Only notify slack for merged commits, not PR failures.
#
# It may be tempting to move this condition into the job's 'if' block, but
# don't: Github only collapses the test list into "everything is OK" if
# all jobs succeeded. A skipped job results in the list staying expanded.
# By having the job always run, but skipping its only step as needed, we
# let the CI output collapse nicely in PRs.
if: failure() && github.event_name == 'push'
uses: ruby/action-slack@v3.2.1
with:
payload: |
{
"attachments": [{
"title": "Failure: ${{ github.workflow }}",
"title_link": "https://github.com/${{ github.repository }}/commit/${{ github.sha }}/checks",
"text": "${{ github.repository }}@${{ github.ref_name }}: <https://github.com/${{ github.repository }}/commit/${{ github.sha }}|${{ github.sha }}>",
"fields": [{ "value": ${{ toJson(github.event.head_commit.message) }}, "short": false }],
"footer": "${{ github.event.head_commit.committer.name }} at ${{ github.event.head_commit.timestamp }}",
"color": "danger"
}]
}
env:
SLACK_WEBHOOK_URL: ${{ secrets.SLACK_WEBHOOK_URL }}
check_mergeability:
if: always()
runs-on: ubuntu-22.04
needs:
- android
- test
- windows
- vm
- cross
- ios
- wasm
- tailscale_go
- fuzz
- depaware
- go_generate
- go_mod_tidy
- licenses
- staticcheck
steps:
- name: Decide if change is okay to merge
if: github.event_name != 'push'
uses: re-actors/alls-green@release/v1
with:
jobs: ${{ toJSON(needs) }}

49
.github/workflows/update-flake.yml vendored Normal file
View File

@@ -0,0 +1,49 @@
name: update-flake
on:
# run action when a change lands in the main branch which updates go.mod. Also
# allow manual triggering.
push:
branches:
- main
paths:
- go.mod
- .github/workflows/update-flakes.yml
workflow_dispatch:
concurrency:
group: ${{ github.workflow }}-$${{ github.head_ref || github.run_id }}
cancel-in-progress: true
jobs:
update-flake:
runs-on: ubuntu-latest
steps:
- name: Check out code
uses: actions/checkout@v4
- name: Run update-flakes
run: ./update-flake.sh
- name: Get access token
uses: tibdex/github-app-token@b62528385c34dbc9f38e5f4225ac829252d1ea92 # v1.8.0
id: generate-token
with:
app_id: ${{ secrets.LICENSING_APP_ID }}
installation_id: ${{ secrets.LICENSING_APP_INSTALLATION_ID }}
private_key: ${{ secrets.LICENSING_APP_PRIVATE_KEY }}
- name: Send pull request
uses: peter-evans/create-pull-request@284f54f989303d2699d373481a0cfa13ad5a6666 #v5.0.1
with:
token: ${{ steps.generate-token.outputs.token }}
author: Flakes Updater <noreply+flakes-updater@tailscale.com>
committer: Flakes Updater <noreply+flakes-updater@tailscale.com>
branch: flakes
commit-message: "go.mod.sri: update SRI hash for go.mod changes"
title: "go.mod.sri: update SRI hash for go.mod changes"
body: Triggered by ${{ github.repository }}@${{ github.sha }}
signoff: true
delete-branch: true
reviewers: danderson

View File

@@ -1,55 +0,0 @@
name: Windows race
on:
push:
branches:
- main
pull_request:
branches:
- '*'
jobs:
test:
runs-on: windows-latest
if: "!contains(github.event.head_commit.message, '[ci skip]')"
steps:
- name: Install Go
uses: actions/setup-go@v2
with:
go-version: 1.16.x
- name: Checkout code
uses: actions/checkout@v2
- name: Restore Cache
uses: actions/cache@v2
with:
path: ~/go/pkg/mod
key: ${{ runner.os }}-go-${{ hashFiles('**/go.sum') }}
restore-keys: |
${{ runner.os }}-go-
- name: Test with -race flag
# Don't use -bench=. -benchtime=1x.
# Somewhere in the layers (powershell?)
# the equals signs cause great confusion.
run: go test -race -bench . -benchtime 1x ./...
- uses: k0kubun/action-slack@v2.0.0
with:
payload: |
{
"attachments": [{
"text": "${{ job.status }}: ${{ github.workflow }} <https://github.com/${{ github.repository }}/commit/${{ github.sha }}/checks|${{ env.COMMIT_DATE }} #${{ env.COMMIT_NUMBER_OF_DAY }}> " +
"(<https://github.com/${{ github.repository }}/commit/${{ github.sha }}|" + "${{ github.sha }}".substring(0, 10) + ">) " +
"of ${{ github.repository }}@" + "${{ github.ref }}".split('/').reverse()[0] + " by ${{ github.event.head_commit.committer.name }}",
"color": "danger"
}]
}
env:
SLACK_WEBHOOK_URL: ${{ secrets.SLACK_WEBHOOK_URL }}
if: failure() && github.event_name == 'push'

View File

@@ -1,55 +0,0 @@
name: Windows
on:
push:
branches:
- main
pull_request:
branches:
- '*'
jobs:
test:
runs-on: windows-latest
if: "!contains(github.event.head_commit.message, '[ci skip]')"
steps:
- name: Install Go
uses: actions/setup-go@v2
with:
go-version: 1.16.x
- name: Checkout code
uses: actions/checkout@v2
- name: Restore Cache
uses: actions/cache@v2
with:
path: ~/go/pkg/mod
key: ${{ runner.os }}-go-${{ hashFiles('**/go.sum') }}
restore-keys: |
${{ runner.os }}-go-
- name: Test
# Don't use -bench=. -benchtime=1x.
# Somewhere in the layers (powershell?)
# the equals signs cause great confusion.
run: go test -bench . -benchtime 1x ./...
- uses: k0kubun/action-slack@v2.0.0
with:
payload: |
{
"attachments": [{
"text": "${{ job.status }}: ${{ github.workflow }} <https://github.com/${{ github.repository }}/commit/${{ github.sha }}/checks|${{ env.COMMIT_DATE }} #${{ env.COMMIT_NUMBER_OF_DAY }}> " +
"(<https://github.com/${{ github.repository }}/commit/${{ github.sha }}|" + "${{ github.sha }}".substring(0, 10) + ">) " +
"of ${{ github.repository }}@" + "${{ github.ref }}".split('/').reverse()[0] + " by ${{ github.event.head_commit.committer.name }}",
"color": "danger"
}]
}
env:
SLACK_WEBHOOK_URL: ${{ secrets.SLACK_WEBHOOK_URL }}
if: failure() && github.event_name == 'push'

View File

@@ -1,45 +0,0 @@
name: "integration-vms"
on:
pull_request:
paths:
- "tstest/integration/vms/**"
release:
types: [ created ]
jobs:
experimental-linux-vm-test:
# To set up a new runner, see tstest/integration/vms/runner.nix
runs-on: [ self-hosted, linux, vm_integration_test ]
if: "!contains(github.event.head_commit.message, '[ci skip]')"
steps:
- name: Checkout Code
uses: actions/checkout@v1
- name: Download VM Images
run: go test ./tstest/integration/vms -run-vm-tests -run=Download -timeout=60m -no-s3
env:
XDG_CACHE_HOME: "/var/lib/ghrunner/cache"
- name: Run VM tests
run: go test ./tstest/integration/vms -v -run-vm-tests
env:
TMPDIR: "/tmp"
XDG_CACHE_HOME: "/var/lib/ghrunner/cache"
- uses: k0kubun/action-slack@v2.0.0
with:
payload: |
{
"attachments": [{
"text": "${{ job.status }}: ${{ github.workflow }} <https://github.com/${{ github.repository }}/commit/${{ github.sha }}/checks|${{ env.COMMIT_DATE }} #${{ env.COMMIT_NUMBER_OF_DAY }}> " +
"(<https://github.com/${{ github.repository }}/commit/${{ github.sha }}|" + "${{ github.sha }}".substring(0, 10) + ">) " +
"of ${{ github.repository }}@" + "${{ github.ref }}".split('/').reverse()[0] + " by ${{ github.event.head_commit.committer.name }}",
"color": "danger"
}]
}
env:
SLACK_WEBHOOK_URL: ${{ secrets.SLACK_WEBHOOK_URL }}
if: failure() && github.event_name == 'push'

21
.gitignore vendored
View File

@@ -5,6 +5,7 @@
*.dll
*.so
*.dylib
*.spk
cmd/tailscale/tailscale
cmd/tailscaled/tailscaled
@@ -21,3 +22,23 @@ cmd/tailscaled/tailscaled
# direnv config, this may be different for other people so it's probably safer
# to make this nonspecific.
.envrc
# Ignore personal VS Code settings
.vscode/
# Support personal project-specific GOPATH
.gopath/
# Ignore nix build result path
/result
# Ignore direnv nix-shell environment cache
.direnv/
# Ignore web client node modules
.vite/
client/web/node_modules
client/web/build/assets
/gocross
/dist

61
.golangci.yml Normal file
View File

@@ -0,0 +1,61 @@
linters:
# Don't enable any linters by default; just the ones that we explicitly
# enable in the list below.
disable-all: true
enable:
- bidichk
- gofmt
- goimports
- misspell
- revive
# Configuration for how we run golangci-lint
run:
timeout: 5m
issues:
# Excluding configuration per-path, per-linter, per-text and per-source
exclude-rules:
# These are forks of an upstream package and thus are exempt from stylistic
# changes that would make pulling in upstream changes harder.
- path: tempfork/.*\.go
text: "File is not `gofmt`-ed with `-s` `-r 'interface{} -> any'`"
- path: util/singleflight/.*\.go
text: "File is not `gofmt`-ed with `-s` `-r 'interface{} -> any'`"
# Per-linter settings are contained in this top-level key
linters-settings:
# Enable all rules by default; we don't use invisible unicode runes.
bidichk:
gofmt:
rewrite-rules:
- pattern: 'interface{}'
replacement: 'any'
goimports:
misspell:
revive:
enable-all-rules: false
ignore-generated-header: true
rules:
- name: atomic
- name: context-keys-type
- name: defer
arguments: [[
# Calling 'recover' at the time a defer is registered (i.e. "defer recover()") has no effect.
"immediate-recover",
# Calling 'recover' outside of a deferred function has no effect
"recover",
# Returning values from a deferred function has no effect
"return",
]]
- name: duplicated-imports
- name: errorf
- name: string-of-int
- name: time-equal
- name: unconditional-recursion
- name: useless-break
- name: waitgroup-by-value

1
ALPINE.txt Normal file
View File

@@ -0,0 +1 @@
3.16

1
CODEOWNERS Normal file
View File

@@ -0,0 +1 @@
/tailcfg/ @tailscale/control-protocol-owners

View File

@@ -1,20 +1,13 @@
# Copyright (c) 2020 Tailscale Inc & AUTHORS All rights reserved.
# Use of this source code is governed by a BSD-style
# license that can be found in the LICENSE file.
# Copyright (c) Tailscale Inc & AUTHORS
# SPDX-License-Identifier: BSD-3-Clause
############################################################################
#
# WARNING: Tailscale is not yet officially supported in Docker,
# Kubernetes, etc.
# WARNING: Tailscale is not yet officially supported in container
# environments, such as Docker and Kubernetes. Though it should work, we
# don't regularly test it, and we know there are some feature limitations.
#
# It might work, but we don't regularly test it, and it's not as polished as
# our currently supported platforms. This is provided for people who know
# how Tailscale works and what they're doing.
#
# Our tracking bug for officially support container use cases is:
# https://github.com/tailscale/tailscale/issues/504
#
# Also, see the various bugs tagged "containers":
# See current bugs tagged "containers":
# https://github.com/tailscale/tailscale/labels/containers
#
############################################################################
@@ -23,11 +16,11 @@
#
# To build the Dockerfile:
#
# $ docker build -t tailscale:tailscale .
# $ docker build -t tailscale/tailscale .
#
# To run the tailscaled agent:
#
# $ docker run -d --name=tailscaled -v /var/lib:/var/lib -v /dev/net/tun:/dev/net/tun --network=host --privileged tailscale:tailscale tailscaled
# $ docker run -d --name=tailscaled -v /var/lib:/var/lib -v /dev/net/tun:/dev/net/tun --network=host --privileged tailscale/tailscale tailscaled
#
# To then log in:
#
@@ -38,13 +31,24 @@
# $ docker exec tailscaled tailscale status
FROM golang:1.16-alpine AS build-env
FROM golang:1.21-alpine AS build-env
WORKDIR /go/src/tailscale
COPY go.mod go.sum ./
RUN go mod download
# Pre-build some stuff before the following COPY line invalidates the Docker cache.
RUN go install \
github.com/aws/aws-sdk-go-v2/aws \
github.com/aws/aws-sdk-go-v2/config \
gvisor.dev/gvisor/pkg/tcpip/adapters/gonet \
gvisor.dev/gvisor/pkg/tcpip/stack \
golang.org/x/crypto/ssh \
golang.org/x/crypto/acme \
nhooyr.io/websocket \
github.com/mdlayher/netlink
COPY . .
# see build_docker.sh
@@ -54,13 +58,18 @@ ARG VERSION_SHORT=""
ENV VERSION_SHORT=$VERSION_SHORT
ARG VERSION_GIT_HASH=""
ENV VERSION_GIT_HASH=$VERSION_GIT_HASH
ARG TARGETARCH
RUN go install -tags=xversion -ldflags="\
-X tailscale.com/version.Long=$VERSION_LONG \
-X tailscale.com/version.Short=$VERSION_SHORT \
-X tailscale.com/version.GitCommit=$VERSION_GIT_HASH" \
-v ./cmd/...
RUN GOARCH=$TARGETARCH go install -ldflags="\
-X tailscale.com/version.longStamp=$VERSION_LONG \
-X tailscale.com/version.shortStamp=$VERSION_SHORT \
-X tailscale.com/version.gitCommitStamp=$VERSION_GIT_HASH" \
-v ./cmd/tailscale ./cmd/tailscaled ./cmd/containerboot
FROM alpine:3.16
RUN apk add --no-cache ca-certificates iptables iproute2 ip6tables
FROM alpine:3.11
RUN apk add --no-cache ca-certificates iptables iproute2
COPY --from=build-env /go/bin/* /usr/local/bin/
# For compat with the previous run.sh, although ideally you should be
# using build_docker.sh which sets an entrypoint for the image.
RUN mkdir /tailscale && ln -s /usr/local/bin/containerboot /tailscale/run.sh

5
Dockerfile.base Normal file
View File

@@ -0,0 +1,5 @@
# Copyright (c) Tailscale Inc & AUTHORS
# SPDX-License-Identifier: BSD-3-Clause
FROM alpine:3.16
RUN apk add --no-cache ca-certificates iptables iproute2 ip6tables iputils

View File

@@ -1,7 +1,6 @@
BSD 3-Clause License
Copyright (c) 2020 Tailscale & AUTHORS.
All rights reserved.
Copyright (c) 2020 Tailscale Inc & AUTHORS.
Redistribution and use in source and binary forms, with or without
modification, are permitted provided that the following conditions are met:

View File

@@ -1,24 +1,87 @@
usage:
echo "See Makefile"
IMAGE_REPO ?= tailscale/tailscale
SYNO_ARCH ?= "amd64"
SYNO_DSM ?= "7"
TAGS ?= "latest"
vet:
go vet ./...
vet: ## Run go vet
./tool/go vet ./...
updatedeps:
go run github.com/tailscale/depaware --update tailscale.com/cmd/tailscaled
go run github.com/tailscale/depaware --update tailscale.com/cmd/tailscale
tidy: ## Run go mod tidy
./tool/go mod tidy
depaware:
go run github.com/tailscale/depaware --check tailscale.com/cmd/tailscaled
go run github.com/tailscale/depaware --check tailscale.com/cmd/tailscale
updatedeps: ## Update depaware deps
# depaware (via x/tools/go/packages) shells back to "go", so make sure the "go"
# it finds in its $$PATH is the right one.
PATH="$$(./tool/go env GOROOT)/bin:$$PATH" ./tool/go run github.com/tailscale/depaware --update \
tailscale.com/cmd/tailscaled \
tailscale.com/cmd/tailscale \
tailscale.com/cmd/derper
buildwindows:
GOOS=windows GOARCH=amd64 go install tailscale.com/cmd/tailscale tailscale.com/cmd/tailscaled
depaware: ## Run depaware checks
# depaware (via x/tools/go/packages) shells back to "go", so make sure the "go"
# it finds in its $$PATH is the right one.
PATH="$$(./tool/go env GOROOT)/bin:$$PATH" ./tool/go run github.com/tailscale/depaware --check \
tailscale.com/cmd/tailscaled \
tailscale.com/cmd/tailscale \
tailscale.com/cmd/derper
build386:
GOOS=linux GOARCH=386 go install tailscale.com/cmd/tailscale tailscale.com/cmd/tailscaled
buildwindows: ## Build tailscale CLI for windows/amd64
GOOS=windows GOARCH=amd64 ./tool/go install tailscale.com/cmd/tailscale tailscale.com/cmd/tailscaled
check: staticcheck vet depaware buildwindows build386
build386: ## Build tailscale CLI for linux/386
GOOS=linux GOARCH=386 ./tool/go install tailscale.com/cmd/tailscale tailscale.com/cmd/tailscaled
staticcheck:
go run honnef.co/go/tools/cmd/staticcheck -- $$(go list ./... | grep -v tempfork)
buildlinuxarm: ## Build tailscale CLI for linux/arm
GOOS=linux GOARCH=arm ./tool/go install tailscale.com/cmd/tailscale tailscale.com/cmd/tailscaled
buildwasm: ## Build tailscale CLI for js/wasm
GOOS=js GOARCH=wasm ./tool/go install ./cmd/tsconnect/wasm ./cmd/tailscale/cli
buildplan9:
GOOS=plan9 GOARCH=amd64 ./tool/go install ./cmd/tailscale ./cmd/tailscaled
buildlinuxloong64: ## Build tailscale CLI for linux/loong64
GOOS=linux GOARCH=loong64 ./tool/go install tailscale.com/cmd/tailscale tailscale.com/cmd/tailscaled
buildmultiarchimage: ## Build (and optionally push) multiarch docker image
./build_docker.sh
check: staticcheck vet depaware buildwindows build386 buildlinuxarm buildwasm ## Perform basic checks and compilation tests
staticcheck: ## Run staticcheck.io checks
./tool/go run honnef.co/go/tools/cmd/staticcheck -- $$(./tool/go list ./... | grep -v tempfork)
spk: ## Build synology package for ${SYNO_ARCH} architecture and ${SYNO_DSM} DSM version
./tool/go run ./cmd/dist build synology/dsm${SYNO_DSM}/${SYNO_ARCH}
spkall: ## Build synology packages for all architectures and DSM versions
./tool/go run ./cmd/dist build synology
pushspk: spk ## Push and install synology package on ${SYNO_HOST} host
echo "Pushing SPK to root@${SYNO_HOST} (env var SYNO_HOST) ..."
scp tailscale.spk root@${SYNO_HOST}:
ssh root@${SYNO_HOST} /usr/syno/bin/synopkg install tailscale.spk
publishdevimage: ## Build and publish tailscale image to location specified by ${REPO}
@test -n "${REPO}" || (echo "REPO=... required; e.g. REPO=ghcr.io/${USER}/tailscale" && exit 1)
@test "${REPO}" != "tailscale/tailscale" || (echo "REPO=... must not be tailscale/tailscale" && exit 1)
@test "${REPO}" != "ghcr.io/tailscale/tailscale" || (echo "REPO=... must not be ghcr.io/tailscale/tailscale" && exit 1)
@test "${REPO}" != "tailscale/k8s-operator" || (echo "REPO=... must not be tailscale/k8s-operator" && exit 1)
@test "${REPO}" != "ghcr.io/tailscale/k8s-operator" || (echo "REPO=... must not be ghcr.io/tailscale/k8s-operator" && exit 1)
TAGS="${TAGS}" REPOS=${REPO} PUSH=true TARGET=client ./build_docker.sh
publishdevoperator: ## Build and publish k8s-operator image to location specified by ${REPO}
@test -n "${REPO}" || (echo "REPO=... required; e.g. REPO=ghcr.io/${USER}/tailscale" && exit 1)
@test "${REPO}" != "tailscale/tailscale" || (echo "REPO=... must not be tailscale/tailscale" && exit 1)
@test "${REPO}" != "ghcr.io/tailscale/tailscale" || (echo "REPO=... must not be ghcr.io/tailscale/tailscale" && exit 1)
@test "${REPO}" != "tailscale/k8s-operator" || (echo "REPO=... must not be tailscale/k8s-operator" && exit 1)
@test "${REPO}" != "ghcr.io/tailscale/k8s-operator" || (echo "REPO=... must not be ghcr.io/tailscale/k8s-operator" && exit 1)
TAGS="${TAGS}" REPOS=${REPO} PUSH=true TARGET=operator ./build_docker.sh
help: ## Show this help
@echo "\nSpecify a command. The choices are:\n"
@grep -hE '^[0-9a-zA-Z_-]+:.*?## .*$$' ${MAKEFILE_LIST} | awk 'BEGIN {FS = ":.*?## "}; {printf " \033[0;36m%-20s\033[m %s\n", $$1, $$2}'
@echo ""
.PHONY: help
.DEFAULT_GOAL := help

View File

@@ -6,26 +6,41 @@ Private WireGuard® networks made easy
## Overview
This repository contains all the open source Tailscale client code and
the `tailscaled` daemon and `tailscale` CLI tool. The `tailscaled`
daemon runs primarily on Linux; it also works to varying degrees on
FreeBSD, OpenBSD, Darwin, and Windows.
This repository contains the majority of Tailscale's open source code.
Notably, it includes the `tailscaled` daemon and
the `tailscale` CLI tool. The `tailscaled` daemon runs on Linux, Windows,
[macOS](https://tailscale.com/kb/1065/macos-variants/), and to varying degrees
on FreeBSD and OpenBSD. The Tailscale iOS and Android apps use this repo's
code, but this repo doesn't contain the mobile GUI code.
The Android app is at https://github.com/tailscale/tailscale-android
Other [Tailscale repos](https://github.com/orgs/tailscale/repositories) of note:
* the Android app is at https://github.com/tailscale/tailscale-android
* the Synology package is at https://github.com/tailscale/tailscale-synology
* the QNAP package is at https://github.com/tailscale/tailscale-qpkg
* the Chocolatey packaging is at https://github.com/tailscale/tailscale-chocolatey
For background on which parts of Tailscale are open source and why,
see [https://tailscale.com/opensource/](https://tailscale.com/opensource/).
## Using
We serve packages for a variety of distros at
https://pkgs.tailscale.com .
We serve packages for a variety of distros and platforms at
[https://pkgs.tailscale.com](https://pkgs.tailscale.com/).
## Other clients
The [macOS, iOS, and Windows clients](https://tailscale.com/download)
use the code in this repository but additionally include small GUI
wrappers that are not open source.
wrappers. The GUI wrappers on non-open source platforms are themselves
not open source.
## Building
We always require the latest Go release, currently Go 1.21. (While we build
releases with our [Go fork](https://github.com/tailscale/go/), its use is not
required.)
```
go install tailscale.com/cmd/tailscale{,d}
```
@@ -42,11 +57,6 @@ If your distro has conventions that preclude the use of
`build_dist.sh`, please do the equivalent of what it does in your
distro's way, so that bug reports contain useful version information.
We only guarantee to support the latest Go release and any Go beta or
release candidate builds (currently Go 1.16) in module mode. It might
work in earlier Go versions or in GOPATH mode, but we're making no
effort to keep those working.
## Bugs
Please file any issues about this code or the hosted service on
@@ -61,6 +71,9 @@ We require [Developer Certificate of
Origin](https://en.wikipedia.org/wiki/Developer_Certificate_of_Origin)
`Signed-off-by` lines in commits.
See `git log` for our commit message style. It's basically the same as
[Go's style](https://github.com/golang/go/wiki/CommitMessage).
## About Us
[Tailscale](https://tailscale.com/) is primarily developed by the

View File

@@ -1 +1 @@
1.13.0
1.52.1

1871
api.md

File diff suppressed because it is too large Load Diff

328
appc/appc.go Normal file
View File

@@ -0,0 +1,328 @@
// Copyright (c) Tailscale Inc & AUTHORS
// SPDX-License-Identifier: BSD-3-Clause
// Package appc implements App Connectors.
package appc
import (
"expvar"
"log"
"net"
"net/netip"
"sync"
"time"
"golang.org/x/net/dns/dnsmessage"
"tailscale.com/metrics"
"tailscale.com/tailcfg"
"tailscale.com/types/appctype"
"tailscale.com/types/ipproto"
"tailscale.com/types/nettype"
"tailscale.com/util/clientmetric"
"tailscale.com/util/mak"
)
var tsMBox = dnsmessage.MustNewName("support.tailscale.com.")
// target describes the predicates which route some inbound
// traffic to the app connector to a specific handler.
type target struct {
Dest netip.Prefix
Matching tailcfg.ProtoPortRange
}
// Server implements an App Connector.
type Server struct {
mu sync.RWMutex // mu guards following fields
connectors map[appctype.ConfigID]connector
}
type appcMetrics struct {
dnsResponses expvar.Int
dnsFailures expvar.Int
tcpConns expvar.Int
sniConns expvar.Int
unhandledConns expvar.Int
}
var getMetrics = sync.OnceValue[*appcMetrics](func() *appcMetrics {
m := appcMetrics{}
stats := new(metrics.Set)
stats.Set("tls_sessions", &m.sniConns)
clientmetric.NewCounterFunc("sniproxy_tls_sessions", m.sniConns.Value)
stats.Set("tcp_sessions", &m.tcpConns)
clientmetric.NewCounterFunc("sniproxy_tcp_sessions", m.tcpConns.Value)
stats.Set("dns_responses", &m.dnsResponses)
clientmetric.NewCounterFunc("sniproxy_dns_responses", m.dnsResponses.Value)
stats.Set("dns_failed", &m.dnsFailures)
clientmetric.NewCounterFunc("sniproxy_dns_failed", m.dnsFailures.Value)
expvar.Publish("sniproxy", stats)
return &m
})
// Configure applies the provided configuration to the app connector.
func (s *Server) Configure(cfg *appctype.AppConnectorConfig) {
s.mu.Lock()
defer s.mu.Unlock()
s.connectors = makeConnectorsFromConfig(cfg)
}
// HandleTCPFlow implements tsnet.FallbackTCPHandler.
func (s *Server) HandleTCPFlow(src, dst netip.AddrPort) (handler func(net.Conn), intercept bool) {
m := getMetrics()
s.mu.RLock()
defer s.mu.RUnlock()
for _, c := range s.connectors {
if handler, intercept := c.handleTCPFlow(src, dst, m); intercept {
return handler, intercept
}
}
return nil, false
}
// HandleDNS handles a DNS request to the app connector.
func (s *Server) HandleDNS(c nettype.ConnPacketConn) {
defer c.Close()
c.SetReadDeadline(time.Now().Add(5 * time.Second))
m := getMetrics()
buf := make([]byte, 1500)
n, err := c.Read(buf)
if err != nil {
log.Printf("HandleDNS: read failed: %v\n ", err)
m.dnsFailures.Add(1)
return
}
addrPortStr := c.LocalAddr().String()
host, _, err := net.SplitHostPort(addrPortStr)
if err != nil {
log.Printf("HandleDNS: bogus addrPort %q", addrPortStr)
m.dnsFailures.Add(1)
return
}
localAddr, err := netip.ParseAddr(host)
if err != nil {
log.Printf("HandleDNS: bogus local address %q", host)
m.dnsFailures.Add(1)
return
}
var msg dnsmessage.Message
err = msg.Unpack(buf[:n])
if err != nil {
log.Printf("HandleDNS: dnsmessage unpack failed: %v\n ", err)
m.dnsFailures.Add(1)
return
}
s.mu.RLock()
defer s.mu.RUnlock()
for _, connector := range s.connectors {
resp, err := connector.handleDNS(&msg, localAddr)
if err != nil {
log.Printf("HandleDNS: connector handling failed: %v\n", err)
m.dnsFailures.Add(1)
return
}
if len(resp) > 0 {
// This connector handled the DNS request
_, err = c.Write(resp)
if err != nil {
log.Printf("HandleDNS: write failed: %v\n", err)
m.dnsFailures.Add(1)
return
}
m.dnsResponses.Add(1)
return
}
}
}
// connector describes a logical collection of
// services which need to be proxied.
type connector struct {
Handlers map[target]handler
}
// handleTCPFlow implements tsnet.FallbackTCPHandler.
func (c *connector) handleTCPFlow(src, dst netip.AddrPort, m *appcMetrics) (handler func(net.Conn), intercept bool) {
for t, h := range c.Handlers {
if t.Matching.Proto != 0 && t.Matching.Proto != int(ipproto.TCP) {
continue
}
if !t.Dest.Contains(dst.Addr()) {
continue
}
if !t.Matching.Ports.Contains(dst.Port()) {
continue
}
switch h.(type) {
case *tcpSNIHandler:
m.sniConns.Add(1)
case *tcpRoundRobinHandler:
m.tcpConns.Add(1)
default:
log.Printf("handleTCPFlow: unhandled handler type %T", h)
}
return h.Handle, true
}
m.unhandledConns.Add(1)
return nil, false
}
// handleDNS returns the DNS response to the given query. If this
// connector is unable to handle the request, nil is returned.
func (c *connector) handleDNS(req *dnsmessage.Message, localAddr netip.Addr) (response []byte, err error) {
for t, h := range c.Handlers {
if t.Dest.Contains(localAddr) {
return makeDNSResponse(req, h.ReachableOn())
}
}
// Did not match, signal 'not handled' to caller
return nil, nil
}
func makeDNSResponse(req *dnsmessage.Message, reachableIPs []netip.Addr) (response []byte, err error) {
buf := make([]byte, 1500)
resp := dnsmessage.NewBuilder(buf,
dnsmessage.Header{
ID: req.Header.ID,
Response: true,
Authoritative: true,
})
resp.EnableCompression()
if len(req.Questions) == 0 {
buf, _ = resp.Finish()
return buf, nil
}
q := req.Questions[0]
err = resp.StartQuestions()
if err != nil {
return
}
resp.Question(q)
err = resp.StartAnswers()
if err != nil {
return
}
switch q.Type {
case dnsmessage.TypeAAAA:
for _, ip := range reachableIPs {
if ip.Is6() {
err = resp.AAAAResource(
dnsmessage.ResourceHeader{Name: q.Name, Class: q.Class, TTL: 120},
dnsmessage.AAAAResource{AAAA: ip.As16()},
)
}
}
case dnsmessage.TypeA:
for _, ip := range reachableIPs {
if ip.Is4() {
err = resp.AResource(
dnsmessage.ResourceHeader{Name: q.Name, Class: q.Class, TTL: 120},
dnsmessage.AResource{A: ip.As4()},
)
}
}
case dnsmessage.TypeSOA:
err = resp.SOAResource(
dnsmessage.ResourceHeader{Name: q.Name, Class: q.Class, TTL: 120},
dnsmessage.SOAResource{NS: q.Name, MBox: tsMBox, Serial: 2023030600,
Refresh: 120, Retry: 120, Expire: 120, MinTTL: 60},
)
case dnsmessage.TypeNS:
err = resp.NSResource(
dnsmessage.ResourceHeader{Name: q.Name, Class: q.Class, TTL: 120},
dnsmessage.NSResource{NS: tsMBox},
)
}
if err != nil {
return nil, err
}
return resp.Finish()
}
type handler interface {
// Handle handles the given socket.
Handle(c net.Conn)
// ReachableOn returns the IP addresses this handler is reachable on.
ReachableOn() []netip.Addr
}
func installDNATHandler(d *appctype.DNATConfig, out *connector) {
// These handlers don't actually do DNAT, they just
// proxy the data over the connection.
var dialer net.Dialer
dialer.Timeout = 5 * time.Second
h := tcpRoundRobinHandler{
To: d.To,
DialContext: dialer.DialContext,
ReachableIPs: d.Addrs,
}
for _, addr := range d.Addrs {
for _, protoPort := range d.IP {
t := target{
Dest: netip.PrefixFrom(addr, addr.BitLen()),
Matching: protoPort,
}
mak.Set(&out.Handlers, t, handler(&h))
}
}
}
func installSNIHandler(c *appctype.SNIProxyConfig, out *connector) {
var dialer net.Dialer
dialer.Timeout = 5 * time.Second
h := tcpSNIHandler{
Allowlist: c.AllowedDomains,
DialContext: dialer.DialContext,
ReachableIPs: c.Addrs,
}
for _, addr := range c.Addrs {
for _, protoPort := range c.IP {
t := target{
Dest: netip.PrefixFrom(addr, addr.BitLen()),
Matching: protoPort,
}
mak.Set(&out.Handlers, t, handler(&h))
}
}
}
func makeConnectorsFromConfig(cfg *appctype.AppConnectorConfig) map[appctype.ConfigID]connector {
var connectors map[appctype.ConfigID]connector
for cID, d := range cfg.DNAT {
c := connectors[cID]
installDNATHandler(&d, &c)
mak.Set(&connectors, cID, c)
}
for cID, d := range cfg.SNIProxy {
c := connectors[cID]
installSNIHandler(&d, &c)
mak.Set(&connectors, cID, c)
}
return connectors
}

95
appc/appc_test.go Normal file
View File

@@ -0,0 +1,95 @@
// Copyright (c) Tailscale Inc & AUTHORS
// SPDX-License-Identifier: BSD-3-Clause
package appc
import (
"net/netip"
"testing"
"github.com/google/go-cmp/cmp"
"github.com/google/go-cmp/cmp/cmpopts"
"tailscale.com/tailcfg"
"tailscale.com/types/appctype"
)
func TestMakeConnectorsFromConfig(t *testing.T) {
tcs := []struct {
name string
input *appctype.AppConnectorConfig
want map[appctype.ConfigID]connector
}{
{
"empty",
&appctype.AppConnectorConfig{},
nil,
},
{
"DNAT",
&appctype.AppConnectorConfig{
DNAT: map[appctype.ConfigID]appctype.DNATConfig{
"swiggity_swooty": {
Addrs: []netip.Addr{netip.MustParseAddr("100.64.0.1"), netip.MustParseAddr("fd7a:115c:a1e0::1")},
To: []string{"example.org"},
IP: []tailcfg.ProtoPortRange{{Proto: 0, Ports: tailcfg.PortRange{First: 0, Last: 65535}}},
},
},
},
map[appctype.ConfigID]connector{
"swiggity_swooty": {
Handlers: map[target]handler{
{
Dest: netip.MustParsePrefix("100.64.0.1/32"),
Matching: tailcfg.ProtoPortRange{Proto: 0, Ports: tailcfg.PortRange{First: 0, Last: 65535}},
}: &tcpRoundRobinHandler{To: []string{"example.org"}, ReachableIPs: []netip.Addr{netip.MustParseAddr("100.64.0.1"), netip.MustParseAddr("fd7a:115c:a1e0::1")}},
{
Dest: netip.MustParsePrefix("fd7a:115c:a1e0::1/128"),
Matching: tailcfg.ProtoPortRange{Proto: 0, Ports: tailcfg.PortRange{First: 0, Last: 65535}},
}: &tcpRoundRobinHandler{To: []string{"example.org"}, ReachableIPs: []netip.Addr{netip.MustParseAddr("100.64.0.1"), netip.MustParseAddr("fd7a:115c:a1e0::1")}},
},
},
},
},
{
"SNIProxy",
&appctype.AppConnectorConfig{
SNIProxy: map[appctype.ConfigID]appctype.SNIProxyConfig{
"swiggity_swooty": {
Addrs: []netip.Addr{netip.MustParseAddr("100.64.0.1"), netip.MustParseAddr("fd7a:115c:a1e0::1")},
AllowedDomains: []string{"example.org"},
IP: []tailcfg.ProtoPortRange{{Proto: 0, Ports: tailcfg.PortRange{First: 0, Last: 65535}}},
},
},
},
map[appctype.ConfigID]connector{
"swiggity_swooty": {
Handlers: map[target]handler{
{
Dest: netip.MustParsePrefix("100.64.0.1/32"),
Matching: tailcfg.ProtoPortRange{Proto: 0, Ports: tailcfg.PortRange{First: 0, Last: 65535}},
}: &tcpSNIHandler{Allowlist: []string{"example.org"}, ReachableIPs: []netip.Addr{netip.MustParseAddr("100.64.0.1"), netip.MustParseAddr("fd7a:115c:a1e0::1")}},
{
Dest: netip.MustParsePrefix("fd7a:115c:a1e0::1/128"),
Matching: tailcfg.ProtoPortRange{Proto: 0, Ports: tailcfg.PortRange{First: 0, Last: 65535}},
}: &tcpSNIHandler{Allowlist: []string{"example.org"}, ReachableIPs: []netip.Addr{netip.MustParseAddr("100.64.0.1"), netip.MustParseAddr("fd7a:115c:a1e0::1")}},
},
},
},
},
}
for _, tc := range tcs {
t.Run(tc.name, func(t *testing.T) {
connectors := makeConnectorsFromConfig(tc.input)
if diff := cmp.Diff(connectors, tc.want,
cmpopts.IgnoreFields(tcpRoundRobinHandler{}, "DialContext"),
cmpopts.IgnoreFields(tcpSNIHandler{}, "DialContext"),
cmp.Comparer(func(x, y netip.Addr) bool {
return x == y
})); diff != "" {
t.Fatalf("mismatch (-want +got):\n%s", diff)
}
})
}
}

104
appc/handlers.go Normal file
View File

@@ -0,0 +1,104 @@
// Copyright (c) Tailscale Inc & AUTHORS
// SPDX-License-Identifier: BSD-3-Clause
package appc
import (
"context"
"fmt"
"log"
"math/rand"
"net"
"net/netip"
"slices"
"inet.af/tcpproxy"
"tailscale.com/net/netutil"
)
type tcpRoundRobinHandler struct {
// To is a list of destination addresses to forward to.
// An entry may be either an IP address or a DNS name.
To []string
// DialContext is used to make the outgoing TCP connection.
DialContext func(ctx context.Context, network, address string) (net.Conn, error)
// ReachableIPs enumerates the IP addresses this handler is reachable on.
ReachableIPs []netip.Addr
}
// ReachableOn returns the IP addresses this handler is reachable on.
func (h *tcpRoundRobinHandler) ReachableOn() []netip.Addr {
return h.ReachableIPs
}
func (h *tcpRoundRobinHandler) Handle(c net.Conn) {
addrPortStr := c.LocalAddr().String()
_, port, err := net.SplitHostPort(addrPortStr)
if err != nil {
log.Printf("tcpRoundRobinHandler.Handle: bogus addrPort %q", addrPortStr)
c.Close()
return
}
var p tcpproxy.Proxy
p.ListenFunc = func(net, laddr string) (net.Listener, error) {
return netutil.NewOneConnListener(c, nil), nil
}
dest := h.To[rand.Intn(len(h.To))]
dial := &tcpproxy.DialProxy{
Addr: fmt.Sprintf("%s:%s", dest, port),
DialContext: h.DialContext,
}
p.AddRoute(addrPortStr, dial)
p.Start()
}
type tcpSNIHandler struct {
// Allowlist enumerates the FQDNs which may be proxied via SNI. An
// empty slice means all domains are permitted.
Allowlist []string
// DialContext is used to make the outgoing TCP connection.
DialContext func(ctx context.Context, network, address string) (net.Conn, error)
// ReachableIPs enumerates the IP addresses this handler is reachable on.
ReachableIPs []netip.Addr
}
// ReachableOn returns the IP addresses this handler is reachable on.
func (h *tcpSNIHandler) ReachableOn() []netip.Addr {
return h.ReachableIPs
}
func (h *tcpSNIHandler) Handle(c net.Conn) {
addrPortStr := c.LocalAddr().String()
_, port, err := net.SplitHostPort(addrPortStr)
if err != nil {
log.Printf("tcpSNIHandler.Handle: bogus addrPort %q", addrPortStr)
c.Close()
return
}
var p tcpproxy.Proxy
p.ListenFunc = func(net, laddr string) (net.Listener, error) {
return netutil.NewOneConnListener(c, nil), nil
}
p.AddSNIRouteFunc(addrPortStr, func(ctx context.Context, sniName string) (t tcpproxy.Target, ok bool) {
if len(h.Allowlist) > 0 {
// TODO(tom): handle subdomains
if slices.Index(h.Allowlist, sniName) < 0 {
return nil, false
}
}
return &tcpproxy.DialProxy{
Addr: net.JoinHostPort(sniName, port),
DialContext: h.DialContext,
}, true
})
p.Start()
}

159
appc/handlers_test.go Normal file
View File

@@ -0,0 +1,159 @@
// Copyright (c) Tailscale Inc & AUTHORS
// SPDX-License-Identifier: BSD-3-Clause
package appc
import (
"bytes"
"context"
"encoding/hex"
"io"
"net"
"net/netip"
"strings"
"testing"
"tailscale.com/net/memnet"
)
func echoConnOnce(conn net.Conn) {
defer conn.Close()
b := make([]byte, 256)
n, err := conn.Read(b)
if err != nil {
return
}
if _, err := conn.Write(b[:n]); err != nil {
return
}
}
func TestTCPRoundRobinHandler(t *testing.T) {
h := tcpRoundRobinHandler{
To: []string{"yeet.com"},
DialContext: func(ctx context.Context, network, addr string) (net.Conn, error) {
if network != "tcp" {
t.Errorf("network = %s, want %s", network, "tcp")
}
if addr != "yeet.com:22" {
t.Errorf("addr = %s, want %s", addr, "yeet.com:22")
}
c, s := memnet.NewConn("outbound", 1024)
go echoConnOnce(s)
return c, nil
},
}
cSock, sSock := memnet.NewTCPConn(netip.MustParseAddrPort("10.64.1.2:22"), netip.MustParseAddrPort("10.64.1.2:22"), 1024)
h.Handle(sSock)
// Test data write and read, the other end will echo back
// a single stanza
want := "hello"
if _, err := io.WriteString(cSock, want); err != nil {
t.Fatal(err)
}
got := make([]byte, len(want))
if _, err := io.ReadAtLeast(cSock, got, len(got)); err != nil {
t.Fatal(err)
}
if string(got) != want {
t.Errorf("got %q, want %q", got, want)
}
// The other end closed the socket after the first echo, so
// any following read should error.
io.WriteString(cSock, "deadass heres some data on god fr")
if _, err := io.ReadAtLeast(cSock, got, len(got)); err == nil {
t.Error("read succeeded on closed socket")
}
}
// Capture of first TCP data segment for a connection to https://pkgs.tailscale.com
const tlsStart = `45000239ff1840004006f9f5c0a801f2
c726b5efcf9e01bbe803b21394e3b752
801801f641dc00000101080ade3474f2
2fb93ee71603010200010001fc030303
c3acbd19d2624765bb19af4bce03365e
1d197f5bb939cdadeff26b0f8e7a0620
295b04127b82bae46aac4ff58cffef25
eba75a4b7a6de729532c411bd9dd0d2c
00203a3a130113021303c02bc02fc02c
c030cca9cca8c013c014009c009d002f
003501000193caca0000000a000a0008
1a1a001d001700180010000e000c0268
3208687474702f312e31002b0007062a
2a03040303ff01000100000d00120010
04030804040105030805050108060601
000b00020100002300000033002b0029
1a1a000100001d0020d3c76bef062979
a812ce935cfb4dbe6b3a84dc5ba9226f
23b0f34af9d1d03b4a001b0003020002
00120000446900050003026832000000
170015000012706b67732e7461696c73
63616c652e636f6d002d000201010005
00050100000000001700003a3a000100
0015002d000000000000000000000000
00000000000000000000000000000000
00000000000000000000000000000000
0000290094006f0069e76f2016f963ad
38c8632d1f240cd75e00e25fdef295d4
7042b26f3a9a543b1c7dc74939d77803
20527d423ff996997bda2c6383a14f49
219eeef8a053e90a32228df37ddbe126
eccf6b085c93890d08341d819aea6111
0d909f4cd6b071d9ea40618e74588a33
90d494bbb5c3002120d5a164a16c9724
c9ef5e540d8d6f007789a7acf9f5f16f
bf6a1907a6782ed02b`
func fakeSNIHeader() []byte {
b, err := hex.DecodeString(strings.Replace(tlsStart, "\n", "", -1))
if err != nil {
panic(err)
}
return b[0x34:] // trim IP + TCP header
}
func TestTCPSNIHandler(t *testing.T) {
h := tcpSNIHandler{
Allowlist: []string{"pkgs.tailscale.com"},
DialContext: func(ctx context.Context, network, addr string) (net.Conn, error) {
if network != "tcp" {
t.Errorf("network = %s, want %s", network, "tcp")
}
if addr != "pkgs.tailscale.com:443" {
t.Errorf("addr = %s, want %s", addr, "pkgs.tailscale.com:443")
}
c, s := memnet.NewConn("outbound", 1024)
go echoConnOnce(s)
return c, nil
},
}
cSock, sSock := memnet.NewTCPConn(netip.MustParseAddrPort("10.64.1.2:22"), netip.MustParseAddrPort("10.64.1.2:443"), 1024)
h.Handle(sSock)
// Fake a TLS handshake record with an SNI in it.
if _, err := cSock.Write(fakeSNIHeader()); err != nil {
t.Fatal(err)
}
// Test read, the other end will echo back
// a single stanza, which is at least the beginning of the SNI header.
want := fakeSNIHeader()[:5]
if _, err := cSock.Write(want); err != nil {
t.Fatal(err)
}
got := make([]byte, len(want))
if _, err := io.ReadAtLeast(cSock, got, len(got)); err != nil {
t.Fatal(err)
}
if !bytes.Equal(got, want) {
t.Errorf("got %q, want %q", got, want)
}
}

View File

@@ -1,6 +1,5 @@
// Copyright (c) 2019 Tailscale Inc & AUTHORS All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
// Copyright (c) Tailscale Inc & AUTHORS
// SPDX-License-Identifier: BSD-3-Clause
// Package atomicfile contains code related to writing to filesystems
// atomically.
@@ -9,16 +8,21 @@
package atomicfile // import "tailscale.com/atomicfile"
import (
"io/ioutil"
"fmt"
"os"
"path/filepath"
"runtime"
)
// WriteFile writes data to filename+some suffix, then renames it
// into filename.
// WriteFile writes data to filename+some suffix, then renames it into filename.
// The perm argument is ignored on Windows. If the target filename already
// exists but is not a regular file, WriteFile returns an error.
func WriteFile(filename string, data []byte, perm os.FileMode) (err error) {
f, err := ioutil.TempFile(filepath.Dir(filename), filepath.Base(filename)+".tmp")
fi, err := os.Stat(filename)
if err == nil && !fi.Mode().IsRegular() {
return fmt.Errorf("%s already exists and is not a regular file", filename)
}
f, err := os.CreateTemp(filepath.Dir(filename), filepath.Base(filename)+".tmp")
if err != nil {
return err
}

View File

@@ -0,0 +1,47 @@
// Copyright (c) Tailscale Inc & AUTHORS
// SPDX-License-Identifier: BSD-3-Clause
//go:build !js && !windows
package atomicfile
import (
"net"
"os"
"path/filepath"
"runtime"
"strings"
"testing"
)
func TestDoesNotOverwriteIrregularFiles(t *testing.T) {
// Per tailscale/tailscale#7658 as one example, almost any imagined use of
// atomicfile.Write should likely not attempt to overwrite an irregular file
// such as a device node, socket, or named pipe.
const filename = "TestDoesNotOverwriteIrregularFiles"
var path string
// macOS private temp does not allow unix socket creation, but /tmp does.
if runtime.GOOS == "darwin" {
path = filepath.Join("/tmp", filename)
t.Cleanup(func() { os.Remove(path) })
} else {
path = filepath.Join(t.TempDir(), filename)
}
// The least troublesome thing to make that is not a file is a unix socket.
// Making a null device sadly requires root.
l, err := net.ListenUnix("unix", &net.UnixAddr{Name: path, Net: "unix"})
if err != nil {
t.Fatal(err)
}
defer l.Close()
err = WriteFile(path, []byte("hello"), 0644)
if err == nil {
t.Fatal("expected error, got nil")
}
if !strings.Contains(err.Error(), "is not a regular file") {
t.Fatalf("unexpected error: %v", err)
}
}

View File

@@ -11,36 +11,42 @@
set -eu
IFS=".$IFS" read -r major minor patch <VERSION.txt
git_hash=$(git rev-parse HEAD)
if ! git diff-index --quiet HEAD; then
git_hash="${git_hash}-dirty"
fi
base_hash=$(git rev-list --max-count=1 HEAD -- VERSION.txt)
change_count=$(git rev-list --count HEAD "^$base_hash")
short_hash=$(echo "$git_hash" | cut -c1-9)
if expr "$minor" : "[0-9]*[13579]$" >/dev/null; then
patch="$change_count"
change_suffix=""
elif [ "$change_count" != "0" ]; then
change_suffix="-$change_count"
else
change_suffix=""
go="go"
if [ -n "${TS_USE_TOOLCHAIN:-}" ]; then
go="./tool/go"
fi
long_suffix="$change_suffix-t$short_hash"
SHORT="$major.$minor.$patch"
LONG="${SHORT}$long_suffix"
GIT_HASH="$git_hash"
eval `CGO_ENABLED=0 GOOS=$($go env GOHOSTOS) GOARCH=$($go env GOHOSTARCH) $go run ./cmd/mkversion`
if [ "$1" = "shellvars" ]; then
cat <<EOF
VERSION_SHORT="$SHORT"
VERSION_LONG="$LONG"
VERSION_GIT_HASH="$GIT_HASH"
VERSION_MINOR="$VERSION_MINOR"
VERSION_SHORT="$VERSION_SHORT"
VERSION_LONG="$VERSION_LONG"
VERSION_GIT_HASH="$VERSION_GIT_HASH"
EOF
exit 0
fi
exec go build -ldflags "-X tailscale.com/version.Long=${LONG} -X tailscale.com/version.Short=${SHORT} -X tailscale.com/version.GitCommit=${GIT_HASH}" "$@"
tags=""
ldflags="-X tailscale.com/version.longStamp=${VERSION_LONG} -X tailscale.com/version.shortStamp=${VERSION_SHORT}"
# build_dist.sh arguments must precede go build arguments.
while [ "$#" -gt 1 ]; do
case "$1" in
--extra-small)
shift
ldflags="$ldflags -w -s"
tags="${tags:+$tags,}ts_omit_aws,ts_omit_bird,ts_omit_tap,ts_omit_kube"
;;
--box)
shift
tags="${tags:+$tags,}ts_include_cli"
;;
*)
break
;;
esac
done
exec $go build ${tags:+-tags=$tags} -ldflags "$ldflags" "$@"

View File

@@ -8,27 +8,67 @@
#
############################################################################
#
# WARNING: Tailscale is not yet officially supported in Docker,
# Kubernetes, etc.
# WARNING: Tailscale is not yet officially supported in container
# environments, such as Docker and Kubernetes. Though it should work, we
# don't regularly test it, and we know there are some feature limitations.
#
# It might work, but we don't regularly test it, and it's not as polished as
# our currently supported platforms. This is provided for people who know
# how Tailscale works and what they're doing.
#
# Our tracking bug for officially support container use cases is:
# https://github.com/tailscale/tailscale/issues/504
#
# Also, see the various bugs tagged "containers":
# See current bugs tagged "containers":
# https://github.com/tailscale/tailscale/labels/containers
#
############################################################################
set -eu
# Use the "go" binary from the "tool" directory (which is github.com/tailscale/go)
export PATH=$PWD/tool:$PATH
eval $(./build_dist.sh shellvars)
docker build \
--build-arg VERSION_LONG=$VERSION_LONG \
--build-arg VERSION_SHORT=$VERSION_SHORT \
--build-arg VERSION_GIT_HASH=$VERSION_GIT_HASH \
-t tailscale:tailscale .
DEFAULT_TARGET="client"
DEFAULT_TAGS="v${VERSION_SHORT},v${VERSION_MINOR}"
DEFAULT_BASE="tailscale/alpine-base:3.16"
PUSH="${PUSH:-false}"
TARGET="${TARGET:-${DEFAULT_TARGET}}"
TAGS="${TAGS:-${DEFAULT_TAGS}}"
BASE="${BASE:-${DEFAULT_BASE}}"
case "$TARGET" in
client)
DEFAULT_REPOS="tailscale/tailscale"
REPOS="${REPOS:-${DEFAULT_REPOS}}"
go run github.com/tailscale/mkctr \
--gopaths="\
tailscale.com/cmd/tailscale:/usr/local/bin/tailscale, \
tailscale.com/cmd/tailscaled:/usr/local/bin/tailscaled, \
tailscale.com/cmd/containerboot:/usr/local/bin/containerboot" \
--ldflags="\
-X tailscale.com/version.longStamp=${VERSION_LONG} \
-X tailscale.com/version.shortStamp=${VERSION_SHORT} \
-X tailscale.com/version.gitCommitStamp=${VERSION_GIT_HASH}" \
--base="${BASE}" \
--tags="${TAGS}" \
--repos="${REPOS}" \
--push="${PUSH}" \
/usr/local/bin/containerboot
;;
operator)
DEFAULT_REPOS="tailscale/k8s-operator"
REPOS="${REPOS:-${DEFAULT_REPOS}}"
go run github.com/tailscale/mkctr \
--gopaths="tailscale.com/cmd/k8s-operator:/usr/local/bin/operator" \
--ldflags="\
-X tailscale.com/version.longStamp=${VERSION_LONG} \
-X tailscale.com/version.shortStamp=${VERSION_SHORT} \
-X tailscale.com/version.gitCommitStamp=${VERSION_GIT_HASH}" \
--base="${BASE}" \
--tags="${TAGS}" \
--repos="${REPOS}" \
--push="${PUSH}" \
/usr/local/bin/operator
;;
*)
echo "unknown target: $TARGET"
exit 1
;;
esac

163
chirp/chirp.go Normal file
View File

@@ -0,0 +1,163 @@
// Copyright (c) Tailscale Inc & AUTHORS
// SPDX-License-Identifier: BSD-3-Clause
// Package chirp implements a client to communicate with the BIRD Internet
// Routing Daemon.
package chirp
import (
"bufio"
"fmt"
"net"
"strings"
"time"
)
const (
// Maximum amount of time we should wait when reading a response from BIRD.
responseTimeout = 10 * time.Second
)
// New creates a BIRDClient.
func New(socket string) (*BIRDClient, error) {
return newWithTimeout(socket, responseTimeout)
}
func newWithTimeout(socket string, timeout time.Duration) (_ *BIRDClient, err error) {
conn, err := net.Dial("unix", socket)
if err != nil {
return nil, fmt.Errorf("failed to connect to BIRD: %w", err)
}
defer func() {
if err != nil {
conn.Close()
}
}()
b := &BIRDClient{
socket: socket,
conn: conn,
scanner: bufio.NewScanner(conn),
timeNow: time.Now,
timeout: timeout,
}
// Read and discard the first line as that is the welcome message.
if _, err := b.readResponse(); err != nil {
return nil, err
}
return b, nil
}
// BIRDClient handles communication with the BIRD Internet Routing Daemon.
type BIRDClient struct {
socket string
conn net.Conn
scanner *bufio.Scanner
timeNow func() time.Time
timeout time.Duration
}
// Close closes the underlying connection to BIRD.
func (b *BIRDClient) Close() error { return b.conn.Close() }
// DisableProtocol disables the provided protocol.
func (b *BIRDClient) DisableProtocol(protocol string) error {
out, err := b.exec("disable %s", protocol)
if err != nil {
return err
}
if strings.Contains(out, fmt.Sprintf("%s: already disabled", protocol)) {
return nil
} else if strings.Contains(out, fmt.Sprintf("%s: disabled", protocol)) {
return nil
}
return fmt.Errorf("failed to disable %s: %v", protocol, out)
}
// EnableProtocol enables the provided protocol.
func (b *BIRDClient) EnableProtocol(protocol string) error {
out, err := b.exec("enable %s", protocol)
if err != nil {
return err
}
if strings.Contains(out, fmt.Sprintf("%s: already enabled", protocol)) {
return nil
} else if strings.Contains(out, fmt.Sprintf("%s: enabled", protocol)) {
return nil
}
return fmt.Errorf("failed to enable %s: %v", protocol, out)
}
// BIRD CLI docs from https://bird.network.cz/?get_doc&v=20&f=prog-2.html#ss2.9
// Each session of the CLI consists of a sequence of request and replies,
// slightly resembling the FTP and SMTP protocols.
// Requests are commands encoded as a single line of text,
// replies are sequences of lines starting with a four-digit code
// followed by either a space (if it's the last line of the reply) or
// a minus sign (when the reply is going to continue with the next line),
// the rest of the line contains a textual message semantics of which depends on the numeric code.
// If a reply line has the same code as the previous one and it's a continuation line,
// the whole prefix can be replaced by a single white space character.
//
// Reply codes starting with 0 stand for action successfully completed messages,
// 1 means table entry, 8 runtime error and 9 syntax error.
func (b *BIRDClient) exec(cmd string, args ...any) (string, error) {
if err := b.conn.SetWriteDeadline(b.timeNow().Add(b.timeout)); err != nil {
return "", err
}
if _, err := fmt.Fprintf(b.conn, cmd, args...); err != nil {
return "", err
}
if _, err := fmt.Fprintln(b.conn); err != nil {
return "", err
}
return b.readResponse()
}
// hasResponseCode reports whether the provided byte slice is
// prefixed with a BIRD response code.
// Equivalent regex: `^\d{4}[ -]`.
func hasResponseCode(s []byte) bool {
if len(s) < 5 {
return false
}
for _, b := range s[:4] {
if '0' <= b && b <= '9' {
continue
}
return false
}
return s[4] == ' ' || s[4] == '-'
}
func (b *BIRDClient) readResponse() (string, error) {
// Set the read timeout before we start reading anything.
if err := b.conn.SetReadDeadline(b.timeNow().Add(b.timeout)); err != nil {
return "", err
}
var resp strings.Builder
var done bool
for !done {
if !b.scanner.Scan() {
if err := b.scanner.Err(); err != nil {
return "", err
}
return "", fmt.Errorf("reading response from bird failed (EOF): %q", resp.String())
}
out := b.scanner.Bytes()
if _, err := resp.Write(out); err != nil {
return "", err
}
if hasResponseCode(out) {
done = out[4] == ' '
}
if !done {
resp.WriteRune('\n')
}
}
return resp.String(), nil
}

192
chirp/chirp_test.go Normal file
View File

@@ -0,0 +1,192 @@
// Copyright (c) Tailscale Inc & AUTHORS
// SPDX-License-Identifier: BSD-3-Clause
package chirp
import (
"bufio"
"errors"
"fmt"
"net"
"os"
"path/filepath"
"strings"
"sync"
"testing"
"time"
)
type fakeBIRD struct {
net.Listener
protocolsEnabled map[string]bool
sock string
}
func newFakeBIRD(t *testing.T, protocols ...string) *fakeBIRD {
sock := filepath.Join(t.TempDir(), "sock")
l, err := net.Listen("unix", sock)
if err != nil {
t.Fatal(err)
}
pe := make(map[string]bool)
for _, p := range protocols {
pe[p] = false
}
return &fakeBIRD{
Listener: l,
protocolsEnabled: pe,
sock: sock,
}
}
func (fb *fakeBIRD) listen() error {
for {
c, err := fb.Accept()
if err != nil {
if errors.Is(err, net.ErrClosed) {
return nil
}
return err
}
go fb.handle(c)
}
}
func (fb *fakeBIRD) handle(c net.Conn) {
fmt.Fprintln(c, "0001 BIRD 2.0.8 ready.")
sc := bufio.NewScanner(c)
for sc.Scan() {
cmd := sc.Text()
args := strings.Split(cmd, " ")
switch args[0] {
case "enable":
en, ok := fb.protocolsEnabled[args[1]]
if !ok {
fmt.Fprintln(c, "9001 syntax error, unexpected CF_SYM_UNDEFINED, expecting CF_SYM_KNOWN or TEXT or ALL")
} else if en {
fmt.Fprintf(c, "0010-%s: already enabled\n", args[1])
} else {
fmt.Fprintf(c, "0011-%s: enabled\n", args[1])
}
fmt.Fprintln(c, "0000 ")
fb.protocolsEnabled[args[1]] = true
case "disable":
en, ok := fb.protocolsEnabled[args[1]]
if !ok {
fmt.Fprintln(c, "9001 syntax error, unexpected CF_SYM_UNDEFINED, expecting CF_SYM_KNOWN or TEXT or ALL")
} else if !en {
fmt.Fprintf(c, "0008-%s: already disabled\n", args[1])
} else {
fmt.Fprintf(c, "0009-%s: disabled\n", args[1])
}
fmt.Fprintln(c, "0000 ")
fb.protocolsEnabled[args[1]] = false
}
}
}
func TestChirp(t *testing.T) {
fb := newFakeBIRD(t, "tailscale")
defer fb.Close()
go fb.listen()
c, err := New(fb.sock)
if err != nil {
t.Fatal(err)
}
if err := c.EnableProtocol("tailscale"); err != nil {
t.Fatal(err)
}
if err := c.EnableProtocol("tailscale"); err != nil {
t.Fatal(err)
}
if err := c.DisableProtocol("tailscale"); err != nil {
t.Fatal(err)
}
if err := c.DisableProtocol("tailscale"); err != nil {
t.Fatal(err)
}
if err := c.EnableProtocol("rando"); err == nil {
t.Fatalf("enabling %q succeeded", "rando")
}
if err := c.DisableProtocol("rando"); err == nil {
t.Fatalf("disabling %q succeeded", "rando")
}
}
type hangingListener struct {
net.Listener
t *testing.T
done chan struct{}
wg sync.WaitGroup
sock string
}
func newHangingListener(t *testing.T) *hangingListener {
sock := filepath.Join(t.TempDir(), "sock")
l, err := net.Listen("unix", sock)
if err != nil {
t.Fatal(err)
}
return &hangingListener{
Listener: l,
t: t,
done: make(chan struct{}),
sock: sock,
}
}
func (hl *hangingListener) Stop() {
hl.Close()
close(hl.done)
hl.wg.Wait()
}
func (hl *hangingListener) listen() error {
for {
c, err := hl.Accept()
if err != nil {
if errors.Is(err, net.ErrClosed) {
return nil
}
return err
}
hl.wg.Add(1)
go hl.handle(c)
}
}
func (hl *hangingListener) handle(c net.Conn) {
defer hl.wg.Done()
// Write our fake first line of response so that we get into the read loop
fmt.Fprintln(c, "0001 BIRD 2.0.8 ready.")
ticker := time.NewTicker(2 * time.Second)
defer ticker.Stop()
for {
select {
case <-ticker.C:
hl.t.Logf("connection still hanging")
case <-hl.done:
return
}
}
}
func TestChirpTimeout(t *testing.T) {
fb := newHangingListener(t)
defer fb.Stop()
go fb.listen()
c, err := newWithTimeout(fb.sock, 500*time.Millisecond)
if err != nil {
t.Fatal(err)
}
err = c.EnableProtocol("tailscale")
if err == nil {
t.Fatal("got err=nil, want timeout")
}
if !os.IsTimeout(err) {
t.Fatalf("got err=%v, want os.IsTimeout(err)=true", err)
}
}

476
client/tailscale/acl.go Normal file
View File

@@ -0,0 +1,476 @@
// Copyright (c) Tailscale Inc & AUTHORS
// SPDX-License-Identifier: BSD-3-Clause
//go:build go1.19
package tailscale
import (
"bytes"
"context"
"encoding/json"
"fmt"
"net/http"
"net/netip"
)
// ACLRow defines a rule that grants access by a set of users or groups to a set
// of servers and ports.
// Only one of Src/Dst or Users/Ports may be specified.
type ACLRow struct {
Action string `json:"action,omitempty"` // valid values: "accept"
Users []string `json:"users,omitempty"` // old name for src
Ports []string `json:"ports,omitempty"` // old name for dst
Src []string `json:"src,omitempty"`
Dst []string `json:"dst,omitempty"`
}
// ACLTest defines a test for your ACLs to prevent accidental exposure or
// revoking of access to key servers and ports. Only one of Src or User may be
// specified, and only one of Allow/Accept may be specified.
type ACLTest struct {
Src string `json:"src,omitempty"` // source
User string `json:"user,omitempty"` // old name for source
Accept []string `json:"accept,omitempty"` // expected destination ip:port that user can access
Deny []string `json:"deny,omitempty"` // expected destination ip:port that user cannot access
Allow []string `json:"allow,omitempty"` // old name for accept
}
// ACLDetails contains all the details for an ACL.
type ACLDetails struct {
Tests []ACLTest `json:"tests,omitempty"`
ACLs []ACLRow `json:"acls,omitempty"`
Groups map[string][]string `json:"groups,omitempty"`
TagOwners map[string][]string `json:"tagowners,omitempty"`
Hosts map[string]string `json:"hosts,omitempty"`
}
// ACL contains an ACLDetails and metadata.
type ACL struct {
ACL ACLDetails
ETag string // to check with version on server
}
// ACLHuJSON contains the HuJSON string of the ACL and metadata.
type ACLHuJSON struct {
ACL string
Warnings []string
ETag string // to check with version on server
}
// ACL makes a call to the Tailscale server to get a JSON-parsed version of the ACL.
// The JSON-parsed version of the ACL contains no comments as proper JSON does not support
// comments.
func (c *Client) ACL(ctx context.Context) (acl *ACL, err error) {
// Format return errors to be descriptive.
defer func() {
if err != nil {
err = fmt.Errorf("tailscale.ACL: %w", err)
}
}()
path := fmt.Sprintf("%s/api/v2/tailnet/%s/acl", c.baseURL(), c.tailnet)
req, err := http.NewRequestWithContext(ctx, "GET", path, nil)
if err != nil {
return nil, err
}
req.Header.Set("Accept", "application/json")
b, resp, err := c.sendRequest(req)
if err != nil {
return nil, err
}
// If status code was not successful, return the error.
// TODO: Change the check for the StatusCode to include other 2XX success codes.
if resp.StatusCode != http.StatusOK {
return nil, handleErrorResponse(b, resp)
}
// Otherwise, try to decode the response.
var aclDetails ACLDetails
if err = json.Unmarshal(b, &aclDetails); err != nil {
return nil, err
}
acl = &ACL{
ACL: aclDetails,
ETag: resp.Header.Get("ETag"),
}
return acl, nil
}
// ACLHuJSON makes a call to the Tailscale server to get the ACL HuJSON and returns
// it as a string.
// HuJSON is JSON with a few modifications to make it more human-friendly. The primary
// changes are allowing comments and trailing comments. See the following links for more info:
// https://tailscale.com/s/acl-format
// https://github.com/tailscale/hujson
func (c *Client) ACLHuJSON(ctx context.Context) (acl *ACLHuJSON, err error) {
// Format return errors to be descriptive.
defer func() {
if err != nil {
err = fmt.Errorf("tailscale.ACLHuJSON: %w", err)
}
}()
path := fmt.Sprintf("%s/api/v2/tailnet/%s/acl?details=1", c.baseURL(), c.tailnet)
req, err := http.NewRequestWithContext(ctx, "GET", path, nil)
if err != nil {
return nil, err
}
req.Header.Set("Accept", "application/hujson")
b, resp, err := c.sendRequest(req)
if err != nil {
return nil, err
}
if resp.StatusCode != http.StatusOK {
return nil, handleErrorResponse(b, resp)
}
data := struct {
ACL []byte `json:"acl"`
Warnings []string `json:"warnings"`
}{}
if err := json.Unmarshal(b, &data); err != nil {
return nil, err
}
acl = &ACLHuJSON{
ACL: string(data.ACL),
Warnings: data.Warnings,
ETag: resp.Header.Get("ETag"),
}
return acl, nil
}
// ACLTestFailureSummary specifies a user for which ACL tests
// failed and the related user-friendly error messages.
//
// ACLTestFailureSummary specifies the JSON format sent to the
// JavaScript client to be rendered in the HTML.
type ACLTestFailureSummary struct {
User string `json:"user,omitempty"`
Errors []string `json:"errors,omitempty"`
Warnings []string `json:"warnings,omitempty"`
}
// ACLTestError is ErrResponse but with an extra field to account for ACLTestFailureSummary.
type ACLTestError struct {
ErrResponse
Data []ACLTestFailureSummary `json:"data"`
}
func (e ACLTestError) Error() string {
return fmt.Sprintf("%s, Data: %+v", e.ErrResponse.Error(), e.Data)
}
func (c *Client) aclPOSTRequest(ctx context.Context, body []byte, avoidCollisions bool, etag, acceptHeader string) ([]byte, string, error) {
path := fmt.Sprintf("%s/api/v2/tailnet/%s/acl", c.baseURL(), c.tailnet)
req, err := http.NewRequestWithContext(ctx, "POST", path, bytes.NewBuffer(body))
if err != nil {
return nil, "", err
}
if avoidCollisions {
req.Header.Set("If-Match", etag)
}
req.Header.Set("Accept", acceptHeader)
req.Header.Set("Content-Type", "application/hujson")
b, resp, err := c.sendRequest(req)
if err != nil {
return nil, "", err
}
// If status code was not successful, return the error.
// TODO: Change the check for the StatusCode to include other 2XX success codes.
if resp.StatusCode != http.StatusOK {
// check if test error
var ate ACLTestError
if err := json.Unmarshal(b, &ate); err != nil {
return nil, "", err
}
ate.Status = resp.StatusCode
return nil, "", ate
}
return b, resp.Header.Get("ETag"), nil
}
// SetACL sends a POST request to update the ACL according to the provided ACL object. If
// `avoidCollisions` is true, it will use the ETag obtained in the GET request in an If-Match
// header to check if the previously obtained ACL was the latest version and that no updates
// were missed.
//
// Returns error with status code 412 if mistmached ETag and avoidCollisions is set to true.
// Returns error if ACL has tests that fail.
// Returns error if there are other errors with the ACL.
func (c *Client) SetACL(ctx context.Context, acl ACL, avoidCollisions bool) (res *ACL, err error) {
// Format return errors to be descriptive.
defer func() {
if err != nil {
err = fmt.Errorf("tailscale.SetACL: %w", err)
}
}()
postData, err := json.Marshal(acl.ACL)
if err != nil {
return nil, err
}
b, etag, err := c.aclPOSTRequest(ctx, postData, avoidCollisions, acl.ETag, "application/json")
if err != nil {
return nil, err
}
// Otherwise, try to decode the response.
var aclDetails ACLDetails
if err = json.Unmarshal(b, &aclDetails); err != nil {
return nil, err
}
res = &ACL{
ACL: aclDetails,
ETag: etag,
}
return res, nil
}
// SetACLHuJSON sends a POST request to update the ACL according to the provided ACL object. If
// `avoidCollisions` is true, it will use the ETag obtained in the GET request in an If-Match
// header to check if the previously obtained ACL was the latest version and that no updates
// were missed.
//
// Returns error with status code 412 if mistmached ETag and avoidCollisions is set to true.
// Returns error if the HuJSON is invalid.
// Returns error if ACL has tests that fail.
// Returns error if there are other errors with the ACL.
func (c *Client) SetACLHuJSON(ctx context.Context, acl ACLHuJSON, avoidCollisions bool) (res *ACLHuJSON, err error) {
// Format return errors to be descriptive.
defer func() {
if err != nil {
err = fmt.Errorf("tailscale.SetACLHuJSON: %w", err)
}
}()
postData := []byte(acl.ACL)
b, etag, err := c.aclPOSTRequest(ctx, postData, avoidCollisions, acl.ETag, "application/hujson")
if err != nil {
return nil, err
}
res = &ACLHuJSON{
ACL: string(b),
ETag: etag,
}
return res, nil
}
// UserRuleMatch specifies the source users/groups/hosts that a rule targets
// and the destination ports that they can access.
// LineNumber is only useful for requests provided in HuJSON form.
// While JSON requests will have LineNumber, the value is not useful.
type UserRuleMatch struct {
Users []string `json:"users"`
Ports []string `json:"ports"`
LineNumber int `json:"lineNumber"`
}
// ACLPreviewResponse is the response type of previewACLPostRequest
type ACLPreviewResponse struct {
Matches []UserRuleMatch `json:"matches"` // ACL rules that match the specified user or ipport.
Type string `json:"type"` // The request type: currently only "user" or "ipport".
PreviewFor string `json:"previewFor"` // A specific user or ipport.
}
// ACLPreview is the response type of PreviewACLForUser, PreviewACLForIPPort, PreviewACLHuJSONForUser, and PreviewACLHuJSONForIPPort
type ACLPreview struct {
Matches []UserRuleMatch `json:"matches"`
User string `json:"user,omitempty"` // Filled if response of PreviewACLForUser or PreviewACLHuJSONForUser
IPPort string `json:"ipport,omitempty"` // Filled if response of PreviewACLForIPPort or PreviewACLHuJSONForIPPort
}
func (c *Client) previewACLPostRequest(ctx context.Context, body []byte, previewType string, previewFor string) (res *ACLPreviewResponse, err error) {
path := fmt.Sprintf("%s/api/v2/tailnet/%s/acl/preview", c.baseURL(), c.tailnet)
req, err := http.NewRequestWithContext(ctx, "POST", path, bytes.NewBuffer(body))
if err != nil {
return nil, err
}
q := req.URL.Query()
q.Add("type", previewType)
q.Add("previewFor", previewFor)
req.URL.RawQuery = q.Encode()
req.Header.Set("Content-Type", "application/hujson")
c.setAuth(req)
b, resp, err := c.sendRequest(req)
if err != nil {
return nil, err
}
// If status code was not successful, return the error.
// TODO: Change the check for the StatusCode to include other 2XX success codes.
if resp.StatusCode != http.StatusOK {
return nil, handleErrorResponse(b, resp)
}
if err = json.Unmarshal(b, &res); err != nil {
return nil, err
}
return res, nil
}
// PreviewACLForUser determines what rules match a given ACL for a user.
// The ACL can be a locally modified or clean ACL obtained from server.
//
// Returns ACLPreview on success with matches in a slice. If there are no matches,
// the call is still successful but Matches will be an empty slice.
// Returns error if the provided ACL is invalid.
func (c *Client) PreviewACLForUser(ctx context.Context, acl ACL, user string) (res *ACLPreview, err error) {
// Format return errors to be descriptive.
defer func() {
if err != nil {
err = fmt.Errorf("tailscale.PreviewACLForUser: %w", err)
}
}()
postData, err := json.Marshal(acl.ACL)
if err != nil {
return nil, err
}
b, err := c.previewACLPostRequest(ctx, postData, "user", user)
if err != nil {
return nil, err
}
return &ACLPreview{
Matches: b.Matches,
User: b.PreviewFor,
}, nil
}
// PreviewACLForIPPort determines what rules match a given ACL for a ipport.
// The ACL can be a locally modified or clean ACL obtained from server.
//
// Returns ACLPreview on success with matches in a slice. If there are no matches,
// the call is still successful but Matches will be an empty slice.
// Returns error if the provided ACL is invalid.
func (c *Client) PreviewACLForIPPort(ctx context.Context, acl ACL, ipport netip.AddrPort) (res *ACLPreview, err error) {
// Format return errors to be descriptive.
defer func() {
if err != nil {
err = fmt.Errorf("tailscale.PreviewACLForIPPort: %w", err)
}
}()
postData, err := json.Marshal(acl.ACL)
if err != nil {
return nil, err
}
b, err := c.previewACLPostRequest(ctx, postData, "ipport", ipport.String())
if err != nil {
return nil, err
}
return &ACLPreview{
Matches: b.Matches,
IPPort: b.PreviewFor,
}, nil
}
// PreviewACLHuJSONForUser determines what rules match a given ACL for a user.
// The ACL can be a locally modified or clean ACL obtained from server.
//
// Returns ACLPreview on success with matches in a slice. If there are no matches,
// the call is still successful but Matches will be an empty slice.
// Returns error if the provided ACL is invalid.
func (c *Client) PreviewACLHuJSONForUser(ctx context.Context, acl ACLHuJSON, user string) (res *ACLPreview, err error) {
// Format return errors to be descriptive.
defer func() {
if err != nil {
err = fmt.Errorf("tailscale.PreviewACLHuJSONForUser: %w", err)
}
}()
postData := []byte(acl.ACL)
b, err := c.previewACLPostRequest(ctx, postData, "user", user)
if err != nil {
return nil, err
}
return &ACLPreview{
Matches: b.Matches,
User: b.PreviewFor,
}, nil
}
// PreviewACLHuJSONForIPPort determines what rules match a given ACL for a ipport.
// The ACL can be a locally modified or clean ACL obtained from server.
//
// Returns ACLPreview on success with matches in a slice. If there are no matches,
// the call is still successful but Matches will be an empty slice.
// Returns error if the provided ACL is invalid.
func (c *Client) PreviewACLHuJSONForIPPort(ctx context.Context, acl ACLHuJSON, ipport string) (res *ACLPreview, err error) {
// Format return errors to be descriptive.
defer func() {
if err != nil {
err = fmt.Errorf("tailscale.PreviewACLHuJSONForIPPort: %w", err)
}
}()
postData := []byte(acl.ACL)
b, err := c.previewACLPostRequest(ctx, postData, "ipport", ipport)
if err != nil {
return nil, err
}
return &ACLPreview{
Matches: b.Matches,
IPPort: b.PreviewFor,
}, nil
}
// ValidateACLJSON takes in the given source and destination (in this situation,
// it is assumed that you are checking whether the source can connect to destination)
// and creates an ACLTest from that. It then sends the ACLTest to the control api acl
// validate endpoint, where the test is run. It returns a nil ACLTestError pointer if
// no test errors occur.
func (c *Client) ValidateACLJSON(ctx context.Context, source, dest string) (testErr *ACLTestError, err error) {
// Format return errors to be descriptive.
defer func() {
if err != nil {
err = fmt.Errorf("tailscale.ValidateACLJSON: %w", err)
}
}()
tests := []ACLTest{{User: source, Allow: []string{dest}}}
postData, err := json.Marshal(tests)
if err != nil {
return nil, err
}
path := fmt.Sprintf("%s/api/v2/tailnet/%s/acl/validate", c.baseURL(), c.tailnet)
req, err := http.NewRequestWithContext(ctx, "POST", path, bytes.NewBuffer(postData))
if err != nil {
return nil, err
}
req.Header.Set("Content-Type", "application/json")
c.setAuth(req)
b, resp, err := c.sendRequest(req)
if err != nil {
return nil, err
}
if resp.StatusCode != http.StatusOK {
return nil, fmt.Errorf("control api responded with %d status code", resp.StatusCode)
}
// The test ran without fail
if len(b) == 0 {
return nil, nil
}
var res ACLTestError
// The test returned errors.
if err = json.Unmarshal(b, &res); err != nil {
// failed to unmarshal
return nil, err
}
return &res, nil
}

View File

@@ -1,16 +1,23 @@
// Copyright (c) 2021 Tailscale Inc & AUTHORS All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
// Copyright (c) Tailscale Inc & AUTHORS
// SPDX-License-Identifier: BSD-3-Clause
// Package apitype contains types for the Tailscale local API.
// Package apitype contains types for the Tailscale LocalAPI and control plane API.
package apitype
import "tailscale.com/tailcfg"
// LocalAPIHost is the Host header value used by the LocalAPI.
const LocalAPIHost = "local-tailscaled.sock"
// WhoIsResponse is the JSON type returned by tailscaled debug server's /whois?ip=$IP handler.
// In successful whois responses, Node and UserProfile are never nil.
type WhoIsResponse struct {
Node *tailcfg.Node
UserProfile *tailcfg.UserProfile
// CapMap is a map of capabilities to their values.
// See tailcfg.PeerCapMap and tailcfg.PeerCapability for details.
CapMap tailcfg.PeerCapMap
}
// FileTarget is a node to which files can be sent, and the PeerAPI
@@ -18,7 +25,7 @@ type WhoIsResponse struct {
type FileTarget struct {
Node *tailcfg.Node
// PeerAPI is the http://ip:port URL base of the node's peer API,
// PeerAPI is the http://ip:port URL base of the node's PeerAPI,
// without any path (not even a single slash).
PeerAPIURL string
}
@@ -27,3 +34,18 @@ type WaitingFile struct {
Name string
Size int64
}
// SetPushDeviceTokenRequest is the body POSTed to the LocalAPI endpoint /set-device-token.
type SetPushDeviceTokenRequest struct {
// PushDeviceToken is the iOS/macOS APNs device token (and any future Android equivalent).
PushDeviceToken string
}
// ReloadConfigResponse is the response to a LocalAPI reload-config request.
//
// There are three possible outcomes: (false, "") if no config mode in use,
// (true, "") on success, or (false, "error message") on failure.
type ReloadConfigResponse struct {
Reloaded bool // whether the config was reloaded
Err string // any error message
}

View File

@@ -0,0 +1,19 @@
// Copyright (c) Tailscale Inc & AUTHORS
// SPDX-License-Identifier: BSD-3-Clause
package apitype
type DNSConfig struct {
Resolvers []DNSResolver `json:"resolvers"`
FallbackResolvers []DNSResolver `json:"fallbackResolvers"`
Routes map[string][]DNSResolver `json:"routes"`
Domains []string `json:"domains"`
Nameservers []string `json:"nameservers"`
Proxied bool `json:"proxied"`
TempCorpIssue13969 string `json:"TempCorpIssue13969,omitempty"`
}
type DNSResolver struct {
Addr string `json:"addr"`
BootstrapResolution []string `json:"bootstrapResolution,omitempty"`
}

272
client/tailscale/devices.go Normal file
View File

@@ -0,0 +1,272 @@
// Copyright (c) Tailscale Inc & AUTHORS
// SPDX-License-Identifier: BSD-3-Clause
//go:build go1.19
package tailscale
import (
"bytes"
"context"
"encoding/json"
"fmt"
"net/http"
"net/url"
"tailscale.com/types/opt"
)
type GetDevicesResponse struct {
Devices []*Device `json:"devices"`
}
type DerpRegion struct {
Preferred bool `json:"preferred,omitempty"`
LatencyMilliseconds float64 `json:"latencyMs"`
}
type ClientConnectivity struct {
Endpoints []string `json:"endpoints"`
DERP string `json:"derp"`
MappingVariesByDestIP opt.Bool `json:"mappingVariesByDestIP"`
// DERPLatency is mapped by region name (e.g. "New York City", "Seattle").
DERPLatency map[string]DerpRegion `json:"latency"`
ClientSupports map[string]opt.Bool `json:"clientSupports"`
}
type Device struct {
// Addresses is a list of the devices's Tailscale IP addresses.
// It's currently just 1 element, the 100.x.y.z Tailscale IP.
Addresses []string `json:"addresses"`
DeviceID string `json:"id"`
User string `json:"user"`
Name string `json:"name"`
Hostname string `json:"hostname"`
ClientVersion string `json:"clientVersion"` // Empty for external devices.
UpdateAvailable bool `json:"updateAvailable"` // Empty for external devices.
OS string `json:"os"`
Tags []string `json:"tags"`
Created string `json:"created"` // Empty for external devices.
LastSeen string `json:"lastSeen"`
KeyExpiryDisabled bool `json:"keyExpiryDisabled"`
Expires string `json:"expires"`
Authorized bool `json:"authorized"`
IsExternal bool `json:"isExternal"`
MachineKey string `json:"machineKey"` // Empty for external devices.
NodeKey string `json:"nodeKey"`
// BlocksIncomingConnections is configured via the device's
// Tailscale client preferences. This field is only reported
// to the API starting with Tailscale 1.3.x clients.
BlocksIncomingConnections bool `json:"blocksIncomingConnections"`
// The following fields are not included by default:
// EnabledRoutes are the previously-approved subnet routes
// (e.g. "192.168.4.16/24", "10.5.2.4/32").
EnabledRoutes []string `json:"enabledRoutes"` // Empty for external devices.
// AdvertisedRoutes are the subnets (both enabled and not enabled)
// being requested from the node.
AdvertisedRoutes []string `json:"advertisedRoutes"` // Empty for external devices.
ClientConnectivity *ClientConnectivity `json:"clientConnectivity"`
}
// DeviceFieldsOpts determines which fields should be returned in the response.
//
// Please only use DeviceAllFields and DeviceDefaultFields.
// Other DeviceFieldsOpts are not supported.
//
// TODO: Support other DeviceFieldsOpts.
// In the future, users should be able to create their own DeviceFieldsOpts
// as valid arguments by setting the fields they want returned to a "non-nil"
// value. For example, DeviceFieldsOpts{NodeID: "true"} should only return NodeIDs.
type DeviceFieldsOpts Device
func (d *DeviceFieldsOpts) addFieldsToQueryParameter() string {
if d == DeviceDefaultFields || d == nil {
return "default"
}
if d == DeviceAllFields {
return "all"
}
return ""
}
var (
DeviceAllFields = &DeviceFieldsOpts{}
// DeviceDefaultFields specifies that the following fields are returned:
// Addresses, NodeID, User, Name, Hostname, ClientVersion, UpdateAvailable,
// OS, Created, LastSeen, KeyExpiryDisabled, Expires, Authorized, IsExternal
// MachineKey, NodeKey, BlocksIncomingConnections.
DeviceDefaultFields = &DeviceFieldsOpts{}
)
// Devices retrieves the list of devices for a tailnet.
//
// See the Device structure for the list of fields hidden for external devices.
// The optional fields parameter specifies which fields of the devices to return; currently
// only DeviceDefaultFields (equivalent to nil) and DeviceAllFields are supported.
// Other values are currently undefined.
func (c *Client) Devices(ctx context.Context, fields *DeviceFieldsOpts) (deviceList []*Device, err error) {
defer func() {
if err != nil {
err = fmt.Errorf("tailscale.Devices: %w", err)
}
}()
path := fmt.Sprintf("%s/api/v2/tailnet/%s/devices", c.baseURL(), c.tailnet)
req, err := http.NewRequestWithContext(ctx, "GET", path, nil)
if err != nil {
return nil, err
}
// Add fields.
fieldStr := fields.addFieldsToQueryParameter()
q := req.URL.Query()
q.Add("fields", fieldStr)
req.URL.RawQuery = q.Encode()
b, resp, err := c.sendRequest(req)
if err != nil {
return nil, err
}
// If status code was not successful, return the error.
// TODO: Change the check for the StatusCode to include other 2XX success codes.
if resp.StatusCode != http.StatusOK {
return nil, handleErrorResponse(b, resp)
}
var devices GetDevicesResponse
err = json.Unmarshal(b, &devices)
return devices.Devices, err
}
// Device retrieved the details for a specific device.
//
// See the Device structure for the list of fields hidden for an external device.
// The optional fields parameter specifies which fields of the devices to return; currently
// only DeviceDefaultFields (equivalent to nil) and DeviceAllFields are supported.
// Other values are currently undefined.
func (c *Client) Device(ctx context.Context, deviceID string, fields *DeviceFieldsOpts) (device *Device, err error) {
defer func() {
if err != nil {
err = fmt.Errorf("tailscale.Device: %w", err)
}
}()
path := fmt.Sprintf("%s/api/v2/device/%s", c.baseURL(), deviceID)
req, err := http.NewRequestWithContext(ctx, "GET", path, nil)
if err != nil {
return nil, err
}
// Add fields.
fieldStr := fields.addFieldsToQueryParameter()
q := req.URL.Query()
q.Add("fields", fieldStr)
req.URL.RawQuery = q.Encode()
b, resp, err := c.sendRequest(req)
if err != nil {
return nil, err
}
// If status code was not successful, return the error.
// TODO: Change the check for the StatusCode to include other 2XX success codes.
if resp.StatusCode != http.StatusOK {
return nil, handleErrorResponse(b, resp)
}
err = json.Unmarshal(b, &device)
return device, err
}
// DeleteDevice deletes the specified device from the Client's tailnet.
// NOTE: Only devices that belong to the Client's tailnet can be deleted.
// Deleting external devices is not supported.
func (c *Client) DeleteDevice(ctx context.Context, deviceID string) (err error) {
defer func() {
if err != nil {
err = fmt.Errorf("tailscale.DeleteDevice: %w", err)
}
}()
path := fmt.Sprintf("%s/api/v2/device/%s", c.baseURL(), url.PathEscape(deviceID))
req, err := http.NewRequestWithContext(ctx, "DELETE", path, nil)
if err != nil {
return err
}
b, resp, err := c.sendRequest(req)
if err != nil {
return err
}
// If status code was not successful, return the error.
// TODO: Change the check for the StatusCode to include other 2XX success codes.
if resp.StatusCode != http.StatusOK {
return handleErrorResponse(b, resp)
}
return nil
}
// AuthorizeDevice marks a device as authorized.
func (c *Client) AuthorizeDevice(ctx context.Context, deviceID string) error {
return c.SetAuthorized(ctx, deviceID, true)
}
// SetAuthorized marks a device as authorized or not.
func (c *Client) SetAuthorized(ctx context.Context, deviceID string, authorized bool) error {
params := &struct {
Authorized bool `json:"authorized"`
}{Authorized: authorized}
data, err := json.Marshal(params)
if err != nil {
return err
}
path := fmt.Sprintf("%s/api/v2/device/%s/authorized", c.baseURL(), url.PathEscape(deviceID))
req, err := http.NewRequestWithContext(ctx, "POST", path, bytes.NewBuffer(data))
if err != nil {
return err
}
b, resp, err := c.sendRequest(req)
if err != nil {
return err
}
// If status code was not successful, return the error.
// TODO: Change the check for the StatusCode to include other 2XX success codes.
if resp.StatusCode != http.StatusOK {
return handleErrorResponse(b, resp)
}
return nil
}
// SetTags updates the ACL tags on a device.
func (c *Client) SetTags(ctx context.Context, deviceID string, tags []string) error {
params := &struct {
Tags []string `json:"tags"`
}{Tags: tags}
data, err := json.Marshal(params)
if err != nil {
return err
}
path := fmt.Sprintf("%s/api/v2/device/%s/tags", c.baseURL(), url.PathEscape(deviceID))
req, err := http.NewRequestWithContext(ctx, "POST", path, bytes.NewBuffer(data))
if err != nil {
return err
}
b, resp, err := c.sendRequest(req)
if err != nil {
return err
}
// If status code was not successful, return the error.
// TODO: Change the check for the StatusCode to include other 2XX success codes.
if resp.StatusCode != http.StatusOK {
return handleErrorResponse(b, resp)
}
return nil
}

233
client/tailscale/dns.go Normal file
View File

@@ -0,0 +1,233 @@
// Copyright (c) Tailscale Inc & AUTHORS
// SPDX-License-Identifier: BSD-3-Clause
//go:build go1.19
package tailscale
import (
"bytes"
"context"
"encoding/json"
"fmt"
"net/http"
"tailscale.com/client/tailscale/apitype"
)
// DNSNameServers is returned when retrieving the list of nameservers.
// It is also the structure provided when setting nameservers.
type DNSNameServers struct {
DNS []string `json:"dns"` // DNS name servers
}
// DNSNameServersPostResponse is returned when setting the list of DNS nameservers.
//
// It includes the MagicDNS status since nameservers changes may affect MagicDNS.
type DNSNameServersPostResponse struct {
DNS []string `json:"dns"` // DNS name servers
MagicDNS bool `json:"magicDNS"` // whether MagicDNS is active for this tailnet (enabled + has fallback nameservers)
}
// DNSSearchpaths is the list of search paths for a given domain.
type DNSSearchPaths struct {
SearchPaths []string `json:"searchPaths"` // DNS search paths
}
// DNSPreferences is the preferences set for a given tailnet.
//
// It includes MagicDNS which can be turned on or off. To enable MagicDNS,
// there must be at least one nameserver. When all nameservers are removed,
// MagicDNS is disabled.
type DNSPreferences struct {
MagicDNS bool `json:"magicDNS"` // whether MagicDNS is active for this tailnet (enabled + has fallback nameservers)
}
func (c *Client) dnsGETRequest(ctx context.Context, endpoint string) ([]byte, error) {
path := fmt.Sprintf("%s/api/v2/tailnet/%s/dns/%s", c.baseURL(), c.tailnet, endpoint)
req, err := http.NewRequestWithContext(ctx, "GET", path, nil)
if err != nil {
return nil, err
}
b, resp, err := c.sendRequest(req)
if err != nil {
return nil, err
}
// If status code was not successful, return the error.
// TODO: Change the check for the StatusCode to include other 2XX success codes.
if resp.StatusCode != http.StatusOK {
return nil, handleErrorResponse(b, resp)
}
return b, nil
}
func (c *Client) dnsPOSTRequest(ctx context.Context, endpoint string, postData any) ([]byte, error) {
path := fmt.Sprintf("%s/api/v2/tailnet/%s/dns/%s", c.baseURL(), c.tailnet, endpoint)
data, err := json.Marshal(&postData)
if err != nil {
return nil, err
}
req, err := http.NewRequestWithContext(ctx, "POST", path, bytes.NewBuffer(data))
req.Header.Set("Content-Type", "application/json")
if err != nil {
return nil, err
}
b, resp, err := c.sendRequest(req)
if err != nil {
return nil, err
}
// If status code was not successful, return the error.
// TODO: Change the check for the StatusCode to include other 2XX success codes.
if resp.StatusCode != http.StatusOK {
return nil, handleErrorResponse(b, resp)
}
return b, nil
}
// DNSConfig retrieves the DNSConfig settings for a domain.
func (c *Client) DNSConfig(ctx context.Context) (cfg *apitype.DNSConfig, err error) {
// Format return errors to be descriptive.
defer func() {
if err != nil {
err = fmt.Errorf("tailscale.DNSConfig: %w", err)
}
}()
b, err := c.dnsGETRequest(ctx, "config")
if err != nil {
return nil, err
}
var dnsResp apitype.DNSConfig
err = json.Unmarshal(b, &dnsResp)
return &dnsResp, err
}
func (c *Client) SetDNSConfig(ctx context.Context, cfg apitype.DNSConfig) (resp *apitype.DNSConfig, err error) {
// Format return errors to be descriptive.
defer func() {
if err != nil {
err = fmt.Errorf("tailscale.SetDNSConfig: %w", err)
}
}()
var dnsResp apitype.DNSConfig
b, err := c.dnsPOSTRequest(ctx, "config", cfg)
if err != nil {
return nil, err
}
err = json.Unmarshal(b, &dnsResp)
return &dnsResp, err
}
// NameServers retrieves the list of nameservers set for a domain.
func (c *Client) NameServers(ctx context.Context) (nameservers []string, err error) {
// Format return errors to be descriptive.
defer func() {
if err != nil {
err = fmt.Errorf("tailscale.NameServers: %w", err)
}
}()
b, err := c.dnsGETRequest(ctx, "nameservers")
if err != nil {
return nil, err
}
var dnsResp DNSNameServers
err = json.Unmarshal(b, &dnsResp)
return dnsResp.DNS, err
}
// SetNameServers sets the list of nameservers for a tailnet to the list provided
// by the user.
//
// It returns the new list of nameservers and the MagicDNS status in case it was
// affected by the change. For example, removing all nameservers will turn off
// MagicDNS.
func (c *Client) SetNameServers(ctx context.Context, nameservers []string) (dnsResp *DNSNameServersPostResponse, err error) {
defer func() {
if err != nil {
err = fmt.Errorf("tailscale.SetNameServers: %w", err)
}
}()
dnsReq := DNSNameServers{DNS: nameservers}
b, err := c.dnsPOSTRequest(ctx, "nameservers", dnsReq)
if err != nil {
return nil, err
}
err = json.Unmarshal(b, &dnsResp)
return dnsResp, err
}
// DNSPreferences retrieves the DNS preferences set for a tailnet.
//
// It returns the status of MagicDNS.
func (c *Client) DNSPreferences(ctx context.Context) (dnsResp *DNSPreferences, err error) {
// Format return errors to be descriptive.
defer func() {
if err != nil {
err = fmt.Errorf("tailscale.DNSPreferences: %w", err)
}
}()
b, err := c.dnsGETRequest(ctx, "preferences")
if err != nil {
return nil, err
}
err = json.Unmarshal(b, &dnsResp)
return dnsResp, err
}
// SetDNSPreferences sets the DNS preferences for a tailnet.
//
// MagicDNS can only be enabled when there is at least one nameserver provided.
// When all nameservers are removed, MagicDNS is disabled and will stay disabled,
// unless explicitly enabled by a user again.
func (c *Client) SetDNSPreferences(ctx context.Context, magicDNS bool) (dnsResp *DNSPreferences, err error) {
defer func() {
if err != nil {
err = fmt.Errorf("tailscale.SetDNSPreferences: %w", err)
}
}()
dnsReq := DNSPreferences{MagicDNS: magicDNS}
b, err := c.dnsPOSTRequest(ctx, "preferences", dnsReq)
if err != nil {
return
}
err = json.Unmarshal(b, &dnsResp)
return dnsResp, err
}
// SearchPaths retrieves the list of searchpaths set for a tailnet.
func (c *Client) SearchPaths(ctx context.Context) (searchpaths []string, err error) {
defer func() {
if err != nil {
err = fmt.Errorf("tailscale.SearchPaths: %w", err)
}
}()
b, err := c.dnsGETRequest(ctx, "searchpaths")
if err != nil {
return nil, err
}
var dnsResp *DNSSearchPaths
err = json.Unmarshal(b, &dnsResp)
return dnsResp.SearchPaths, err
}
// SetSearchPaths sets the list of searchpaths for a tailnet.
func (c *Client) SetSearchPaths(ctx context.Context, searchpaths []string) (newSearchPaths []string, err error) {
defer func() {
if err != nil {
err = fmt.Errorf("tailscale.SetSearchPaths: %w", err)
}
}()
dnsReq := DNSSearchPaths{SearchPaths: searchpaths}
b, err := c.dnsPOSTRequest(ctx, "searchpaths", dnsReq)
if err != nil {
return nil, err
}
var dnsResp DNSSearchPaths
err = json.Unmarshal(b, &dnsResp)
return dnsResp.SearchPaths, err
}

View File

@@ -0,0 +1,28 @@
// Copyright (c) Tailscale Inc & AUTHORS
// SPDX-License-Identifier: BSD-3-Clause
// The servetls program shows how to run an HTTPS server
// using a Tailscale cert via LetsEncrypt.
package main
import (
"crypto/tls"
"io"
"log"
"net/http"
"tailscale.com/client/tailscale"
)
func main() {
s := &http.Server{
TLSConfig: &tls.Config{
GetCertificate: tailscale.GetCertificate,
},
Handler: http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
io.WriteString(w, "<h1>Hello from Tailscale!</h1> It works.")
}),
}
log.Printf("Running TLS server on :443 ...")
log.Fatal(s.ListenAndServeTLS("", ""))
}

166
client/tailscale/keys.go Normal file
View File

@@ -0,0 +1,166 @@
// Copyright (c) Tailscale Inc & AUTHORS
// SPDX-License-Identifier: BSD-3-Clause
package tailscale
import (
"bytes"
"context"
"encoding/json"
"fmt"
"net/http"
"time"
)
// Key represents a Tailscale API or auth key.
type Key struct {
ID string `json:"id"`
Created time.Time `json:"created"`
Expires time.Time `json:"expires"`
Capabilities KeyCapabilities `json:"capabilities"`
}
// KeyCapabilities are the capabilities of a Key.
type KeyCapabilities struct {
Devices KeyDeviceCapabilities `json:"devices,omitempty"`
}
// KeyDeviceCapabilities are the device-related capabilities of a Key.
type KeyDeviceCapabilities struct {
Create KeyDeviceCreateCapabilities `json:"create"`
}
// KeyDeviceCreateCapabilities are the device creation capabilities of a Key.
type KeyDeviceCreateCapabilities struct {
Reusable bool `json:"reusable"`
Ephemeral bool `json:"ephemeral"`
Preauthorized bool `json:"preauthorized"`
Tags []string `json:"tags,omitempty"`
}
// Keys returns the list of keys for the current user.
func (c *Client) Keys(ctx context.Context) ([]string, error) {
path := fmt.Sprintf("%s/api/v2/tailnet/%s/keys", c.baseURL(), c.tailnet)
req, err := http.NewRequestWithContext(ctx, "GET", path, nil)
if err != nil {
return nil, err
}
b, resp, err := c.sendRequest(req)
if err != nil {
return nil, err
}
if resp.StatusCode != http.StatusOK {
return nil, handleErrorResponse(b, resp)
}
var keys struct {
Keys []*Key `json:"keys"`
}
if err := json.Unmarshal(b, &keys); err != nil {
return nil, err
}
ret := make([]string, 0, len(keys.Keys))
for _, k := range keys.Keys {
ret = append(ret, k.ID)
}
return ret, nil
}
// CreateKey creates a new key for the current user. Currently, only auth keys
// can be created. It returns the secret key itself, which cannot be retrieved again
// later, and the key metadata.
//
// To create a key with a specific expiry, use CreateKeyWithExpiry.
func (c *Client) CreateKey(ctx context.Context, caps KeyCapabilities) (keySecret string, keyMeta *Key, _ error) {
return c.CreateKeyWithExpiry(ctx, caps, 0)
}
// CreateKeyWithExpiry is like CreateKey, but allows specifying a expiration time.
//
// The time is truncated to a whole number of seconds. If zero, that means no expiration.
func (c *Client) CreateKeyWithExpiry(ctx context.Context, caps KeyCapabilities, expiry time.Duration) (keySecret string, keyMeta *Key, _ error) {
// convert expirySeconds to an int64 (seconds)
expirySeconds := int64(expiry.Seconds())
if expirySeconds < 0 {
return "", nil, fmt.Errorf("expiry must be positive")
}
if expirySeconds == 0 && expiry != 0 {
return "", nil, fmt.Errorf("non-zero expiry must be at least one second")
}
keyRequest := struct {
Capabilities KeyCapabilities `json:"capabilities"`
ExpirySeconds int64 `json:"expirySeconds,omitempty"`
}{caps, int64(expirySeconds)}
bs, err := json.Marshal(keyRequest)
if err != nil {
return "", nil, err
}
path := fmt.Sprintf("%s/api/v2/tailnet/%s/keys", c.baseURL(), c.tailnet)
req, err := http.NewRequestWithContext(ctx, "POST", path, bytes.NewReader(bs))
if err != nil {
return "", nil, err
}
b, resp, err := c.sendRequest(req)
if err != nil {
return "", nil, err
}
if resp.StatusCode != http.StatusOK {
return "", nil, handleErrorResponse(b, resp)
}
var key struct {
Key
Secret string `json:"key"`
}
if err := json.Unmarshal(b, &key); err != nil {
return "", nil, err
}
return key.Secret, &key.Key, nil
}
// Key returns the metadata for the given key ID. Currently, capabilities are
// only returned for auth keys, API keys only return general metadata.
func (c *Client) Key(ctx context.Context, id string) (*Key, error) {
path := fmt.Sprintf("%s/api/v2/tailnet/%s/keys/%s", c.baseURL(), c.tailnet, id)
req, err := http.NewRequestWithContext(ctx, "GET", path, nil)
if err != nil {
return nil, err
}
b, resp, err := c.sendRequest(req)
if err != nil {
return nil, err
}
if resp.StatusCode != http.StatusOK {
return nil, handleErrorResponse(b, resp)
}
var key Key
if err := json.Unmarshal(b, &key); err != nil {
return nil, err
}
return &key, nil
}
// DeleteKey deletes the key with the given ID.
func (c *Client) DeleteKey(ctx context.Context, id string) error {
path := fmt.Sprintf("%s/api/v2/tailnet/%s/keys/%s", c.baseURL(), c.tailnet, id)
req, err := http.NewRequestWithContext(ctx, "DELETE", path, nil)
if err != nil {
return err
}
b, resp, err := c.sendRequest(req)
if err != nil {
return err
}
if resp.StatusCode != http.StatusOK {
return handleErrorResponse(b, resp)
}
return nil
}

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,27 @@
// Copyright (c) Tailscale Inc & AUTHORS
// SPDX-License-Identifier: BSD-3-Clause
//go:build go1.19
package tailscale
import "testing"
func TestGetServeConfigFromJSON(t *testing.T) {
sc, err := getServeConfigFromJSON([]byte("null"))
if sc != nil {
t.Errorf("want nil for null")
}
if err != nil {
t.Errorf("reading null: %v", err)
}
sc, err = getServeConfigFromJSON([]byte(`{"TCP":{}}`))
if err != nil {
t.Errorf("reading object: %v", err)
} else if sc == nil {
t.Errorf("want non-nil for object")
} else if sc.TCP == nil {
t.Errorf("want non-nil TCP for object")
}
}

View File

@@ -0,0 +1,10 @@
// Copyright (c) Tailscale Inc & AUTHORS
// SPDX-License-Identifier: BSD-3-Clause
//go:build !go1.21
package tailscale
func init() {
you_need_Go_1_21_to_compile_Tailscale()
}

View File

@@ -0,0 +1,95 @@
// Copyright (c) Tailscale Inc & AUTHORS
// SPDX-License-Identifier: BSD-3-Clause
//go:build go1.19
package tailscale
import (
"bytes"
"context"
"encoding/json"
"fmt"
"net/http"
"net/netip"
)
// Routes contains the lists of subnet routes that are currently advertised by a device,
// as well as the subnets that are enabled to be routed by the device.
type Routes struct {
AdvertisedRoutes []netip.Prefix `json:"advertisedRoutes"`
EnabledRoutes []netip.Prefix `json:"enabledRoutes"`
}
// Routes retrieves the list of subnet routes that have been enabled for a device.
// The routes that are returned are not necessarily advertised by the device,
// they have only been preapproved.
func (c *Client) Routes(ctx context.Context, deviceID string) (routes *Routes, err error) {
defer func() {
if err != nil {
err = fmt.Errorf("tailscale.Routes: %w", err)
}
}()
path := fmt.Sprintf("%s/api/v2/device/%s/routes", c.baseURL(), deviceID)
req, err := http.NewRequestWithContext(ctx, "GET", path, nil)
if err != nil {
return nil, err
}
b, resp, err := c.sendRequest(req)
if err != nil {
return nil, err
}
// If status code was not successful, return the error.
// TODO: Change the check for the StatusCode to include other 2XX success codes.
if resp.StatusCode != http.StatusOK {
return nil, handleErrorResponse(b, resp)
}
var sr Routes
err = json.Unmarshal(b, &sr)
return &sr, err
}
type postRoutesParams struct {
Routes []netip.Prefix `json:"routes"`
}
// SetRoutes updates the list of subnets that are enabled for a device.
// Subnets must be parsable by net/netip.ParsePrefix.
// Subnets do not have to be currently advertised by a device, they may be pre-enabled.
// Returns the updated list of enabled and advertised subnet routes in a *Routes object.
func (c *Client) SetRoutes(ctx context.Context, deviceID string, subnets []netip.Prefix) (routes *Routes, err error) {
defer func() {
if err != nil {
err = fmt.Errorf("tailscale.SetRoutes: %w", err)
}
}()
params := &postRoutesParams{Routes: subnets}
data, err := json.Marshal(params)
if err != nil {
return nil, err
}
path := fmt.Sprintf("%s/api/v2/device/%s/routes", c.baseURL(), deviceID)
req, err := http.NewRequestWithContext(ctx, "POST", path, bytes.NewBuffer(data))
if err != nil {
return nil, err
}
b, resp, err := c.sendRequest(req)
if err != nil {
return nil, err
}
// If status code was not successful, return the error.
// TODO: Change the check for the StatusCode to include other 2XX success codes.
if resp.StatusCode != http.StatusOK {
return nil, handleErrorResponse(b, resp)
}
var srr *Routes
if err := json.Unmarshal(b, &srr); err != nil {
return nil, err
}
return srr, err
}

View File

@@ -0,0 +1,42 @@
// Copyright (c) Tailscale Inc & AUTHORS
// SPDX-License-Identifier: BSD-3-Clause
//go:build go1.19
package tailscale
import (
"context"
"fmt"
"net/http"
"net/url"
"tailscale.com/util/httpm"
)
// TailnetDeleteRequest handles sending a DELETE request for a tailnet to control.
func (c *Client) TailnetDeleteRequest(ctx context.Context, tailnetID string) (err error) {
defer func() {
if err != nil {
err = fmt.Errorf("tailscale.DeleteTailnet: %w", err)
}
}()
path := fmt.Sprintf("%s/api/v2/tailnet/%s", c.baseURL(), url.PathEscape(string(tailnetID)))
req, err := http.NewRequestWithContext(ctx, httpm.DELETE, path, nil)
if err != nil {
return err
}
c.setAuth(req)
b, resp, err := c.sendRequest(req)
if err != nil {
return err
}
if resp.StatusCode != http.StatusOK {
return handleErrorResponse(b, resp)
}
return nil
}

View File

@@ -1,295 +1,157 @@
// Copyright (c) 2021 Tailscale Inc & AUTHORS All rights reserved.
// Use of this source code is governed by a BSD-style
// license that can be found in the LICENSE file.
// Copyright (c) Tailscale Inc & AUTHORS
// SPDX-License-Identifier: BSD-3-Clause
// Package tailscale contains Tailscale client code.
//go:build go1.19
// Package tailscale contains Go clients for the Tailscale LocalAPI and
// Tailscale control plane API.
//
// Warning: this package is in development and makes no API compatibility
// promises as of 2022-04-29. It is subject to change at any time.
package tailscale
import (
"bytes"
"context"
"encoding/json"
"errors"
"fmt"
"io"
"io/ioutil"
"net"
"net/http"
"net/url"
"strconv"
"strings"
"tailscale.com/client/tailscale/apitype"
"tailscale.com/ipn"
"tailscale.com/ipn/ipnstate"
"tailscale.com/paths"
"tailscale.com/safesocket"
"tailscale.com/tailcfg"
)
// TailscaledSocket is the tailscaled Unix socket.
var TailscaledSocket = paths.DefaultTailscaledSocket()
// tsClient does HTTP requests to the local Tailscale daemon.
var tsClient = &http.Client{
Transport: &http.Transport{
DialContext: func(ctx context.Context, network, addr string) (net.Conn, error) {
if addr != "local-tailscaled.sock:80" {
return nil, fmt.Errorf("unexpected URL address %q", addr)
}
if TailscaledSocket == paths.DefaultTailscaledSocket() {
// On macOS, when dialing from non-sandboxed program to sandboxed GUI running
// a TCP server on a random port, find the random port. For HTTP connections,
// we don't send the token. It gets added in an HTTP Basic-Auth header.
if port, _, err := safesocket.LocalTCPPortAndToken(); err == nil {
var d net.Dialer
return d.DialContext(ctx, "tcp", "localhost:"+strconv.Itoa(port))
}
}
return safesocket.Connect(TailscaledSocket, 41112)
},
},
}
// DoLocalRequest makes an HTTP request to the local machine's Tailscale daemon.
// I_Acknowledge_This_API_Is_Unstable must be set true to use this package
// for now. It was added 2022-04-29 when it was moved to this git repo
// and will be removed when the public API has settled.
//
// URLs are of the form http://local-tailscaled.sock/localapi/v0/whois?ip=1.2.3.4.
// TODO(bradfitz): remove this after the we're happy with the public API.
var I_Acknowledge_This_API_Is_Unstable = false
// TODO: use url.PathEscape() for deviceID and tailnets when constructing requests.
const defaultAPIBase = "https://api.tailscale.com"
// maxSize is the maximum read size (10MB) of responses from the server.
const maxReadSize = 10 << 20
// Client makes API calls to the Tailscale control plane API server.
//
// The hostname must be "local-tailscaled.sock", even though it
// doesn't actually do any DNS lookup. The actual means of connecting to and
// authenticating to the local Tailscale daemon vary by platform.
// Use NewClient to instantiate one. Exported fields should be set before
// the client is used and not changed thereafter.
type Client struct {
// tailnet is the globally unique identifier for a Tailscale network, such
// as "example.com" or "user@gmail.com".
tailnet string
// auth is the authentication method to use for this client.
// nil means none, which generally won't work, but won't crash.
auth AuthMethod
// BaseURL optionally specifies an alternate API server to use.
// If empty, "https://api.tailscale.com" is used.
BaseURL string
// HTTPClient optionally specifies an alternate HTTP client to use.
// If nil, http.DefaultClient is used.
HTTPClient *http.Client
}
func (c *Client) httpClient() *http.Client {
if c.HTTPClient != nil {
return c.HTTPClient
}
return http.DefaultClient
}
func (c *Client) baseURL() string {
if c.BaseURL != "" {
return c.BaseURL
}
return defaultAPIBase
}
// AuthMethod is the interface for API authentication methods.
//
// DoLocalRequest may mutate the request to add Authorization headers.
func DoLocalRequest(req *http.Request) (*http.Response, error) {
if _, token, err := safesocket.LocalTCPPortAndToken(); err == nil {
req.SetBasicAuth("", token)
// Most users will use AuthKey.
type AuthMethod interface {
modifyRequest(req *http.Request)
}
// APIKey is an AuthMethod for NewClient that authenticates requests
// using an authkey.
type APIKey string
func (ak APIKey) modifyRequest(req *http.Request) {
req.SetBasicAuth(string(ak), "")
}
func (c *Client) setAuth(r *http.Request) {
if c.auth != nil {
c.auth.modifyRequest(r)
}
return tsClient.Do(req)
}
type errorJSON struct {
Error string
}
// bestError returns either err, or if body contains a valid JSON
// object of type errorJSON, its non-empty error body.
func bestError(err error, body []byte) error {
var j errorJSON
if err := json.Unmarshal(body, &j); err == nil && j.Error != "" {
return errors.New(j.Error)
// NewClient is a convenience method for instantiating a new Client.
//
// tailnet is the globally unique identifier for a Tailscale network, such
// as "example.com" or "user@gmail.com".
// If httpClient is nil, then http.DefaultClient is used.
// "api.tailscale.com" is set as the BaseURL for the returned client
// and can be changed manually by the user.
func NewClient(tailnet string, auth AuthMethod) *Client {
return &Client{
tailnet: tailnet,
auth: auth,
}
return err
}
func send(ctx context.Context, method, path string, wantStatus int, body io.Reader) ([]byte, error) {
req, err := http.NewRequestWithContext(ctx, method, "http://local-tailscaled.sock"+path, body)
func (c *Client) Tailnet() string { return c.tailnet }
// Do sends a raw HTTP request, after adding any authentication headers.
func (c *Client) Do(req *http.Request) (*http.Response, error) {
if !I_Acknowledge_This_API_Is_Unstable {
return nil, errors.New("use of Client without setting I_Acknowledge_This_API_Is_Unstable")
}
c.setAuth(req)
return c.httpClient().Do(req)
}
// sendRequest add the authentication key to the request and sends it. It
// receives the response and reads up to 10MB of it.
func (c *Client) sendRequest(req *http.Request) ([]byte, *http.Response, error) {
if !I_Acknowledge_This_API_Is_Unstable {
return nil, nil, errors.New("use of Client without setting I_Acknowledge_This_API_Is_Unstable")
}
c.setAuth(req)
resp, err := c.httpClient().Do(req)
if err != nil {
return nil, err
return nil, resp, err
}
res, err := DoLocalRequest(req)
if err != nil {
return nil, err
defer resp.Body.Close()
// Read response. Limit the response to 10MB.
body := io.LimitReader(resp.Body, maxReadSize+1)
b, err := io.ReadAll(body)
if len(b) > maxReadSize {
err = errors.New("API response too large")
}
defer res.Body.Close()
slurp, err := ioutil.ReadAll(res.Body)
if err != nil {
return nil, err
}
if res.StatusCode != wantStatus {
err := fmt.Errorf("HTTP %s: %s (expected %v)", res.Status, slurp, wantStatus)
return nil, bestError(err, slurp)
}
return slurp, nil
return b, resp, err
}
func get200(ctx context.Context, path string) ([]byte, error) {
return send(ctx, "GET", path, 200, nil)
// ErrResponse is the HTTP error returned by the Tailscale server.
type ErrResponse struct {
Status int
Message string
}
// WhoIs returns the owner of the remoteAddr, which must be an IP or IP:port.
func WhoIs(ctx context.Context, remoteAddr string) (*apitype.WhoIsResponse, error) {
body, err := get200(ctx, "/localapi/v0/whois?addr="+url.QueryEscape(remoteAddr))
if err != nil {
return nil, err
}
r := new(apitype.WhoIsResponse)
if err := json.Unmarshal(body, r); err != nil {
if max := 200; len(body) > max {
body = append(body[:max], "..."...)
}
return nil, fmt.Errorf("failed to parse JSON WhoIsResponse from %q", body)
}
return r, nil
func (e ErrResponse) Error() string {
return fmt.Sprintf("Status: %d, Message: %q", e.Status, e.Message)
}
// Goroutines returns a dump of the Tailscale daemon's current goroutines.
func Goroutines(ctx context.Context) ([]byte, error) {
return get200(ctx, "/localapi/v0/goroutines")
}
// BugReport logs and returns a log marker that can be shared by the user with support.
func BugReport(ctx context.Context, note string) (string, error) {
body, err := send(ctx, "POST", "/localapi/v0/bugreport?note="+url.QueryEscape(note), 200, nil)
if err != nil {
return "", err
}
return strings.TrimSpace(string(body)), nil
}
// Status returns the Tailscale daemon's status.
func Status(ctx context.Context) (*ipnstate.Status, error) {
return status(ctx, "")
}
// StatusWithPeers returns the Tailscale daemon's status, without the peer info.
func StatusWithoutPeers(ctx context.Context) (*ipnstate.Status, error) {
return status(ctx, "?peers=false")
}
func status(ctx context.Context, queryString string) (*ipnstate.Status, error) {
body, err := get200(ctx, "/localapi/v0/status"+queryString)
if err != nil {
return nil, err
}
st := new(ipnstate.Status)
if err := json.Unmarshal(body, st); err != nil {
return nil, err
}
return st, nil
}
func WaitingFiles(ctx context.Context) ([]apitype.WaitingFile, error) {
body, err := get200(ctx, "/localapi/v0/files/")
if err != nil {
return nil, err
}
var wfs []apitype.WaitingFile
if err := json.Unmarshal(body, &wfs); err != nil {
return nil, err
}
return wfs, nil
}
func DeleteWaitingFile(ctx context.Context, baseName string) error {
_, err := send(ctx, "DELETE", "/localapi/v0/files/"+url.PathEscape(baseName), http.StatusNoContent, nil)
return err
}
func GetWaitingFile(ctx context.Context, baseName string) (rc io.ReadCloser, size int64, err error) {
req, err := http.NewRequestWithContext(ctx, "GET", "http://local-tailscaled.sock/localapi/v0/files/"+url.PathEscape(baseName), nil)
if err != nil {
return nil, 0, err
}
res, err := DoLocalRequest(req)
if err != nil {
return nil, 0, err
}
if res.ContentLength == -1 {
res.Body.Close()
return nil, 0, fmt.Errorf("unexpected chunking")
}
if res.StatusCode != 200 {
body, _ := ioutil.ReadAll(res.Body)
res.Body.Close()
return nil, 0, fmt.Errorf("HTTP %s: %s", res.Status, body)
}
return res.Body, res.ContentLength, nil
}
func FileTargets(ctx context.Context) ([]apitype.FileTarget, error) {
body, err := get200(ctx, "/localapi/v0/file-targets")
if err != nil {
return nil, err
}
var fts []apitype.FileTarget
if err := json.Unmarshal(body, &fts); err != nil {
return nil, fmt.Errorf("invalid JSON: %w", err)
}
return fts, nil
}
func CheckIPForwarding(ctx context.Context) error {
body, err := get200(ctx, "/localapi/v0/check-ip-forwarding")
if err != nil {
// handleErrorResponse decodes the error message from the server and returns
// an ErrResponse from it.
func handleErrorResponse(b []byte, resp *http.Response) error {
var errResp ErrResponse
if err := json.Unmarshal(b, &errResp); err != nil {
return err
}
var jres struct {
Warning string
}
if err := json.Unmarshal(body, &jres); err != nil {
return fmt.Errorf("invalid JSON from check-ip-forwarding: %w", err)
}
if jres.Warning != "" {
return errors.New(jres.Warning)
}
return nil
}
func GetPrefs(ctx context.Context) (*ipn.Prefs, error) {
body, err := get200(ctx, "/localapi/v0/prefs")
if err != nil {
return nil, err
}
var p ipn.Prefs
if err := json.Unmarshal(body, &p); err != nil {
return nil, fmt.Errorf("invalid prefs JSON: %w", err)
}
return &p, nil
}
func EditPrefs(ctx context.Context, mp *ipn.MaskedPrefs) (*ipn.Prefs, error) {
mpj, err := json.Marshal(mp)
if err != nil {
return nil, err
}
body, err := send(ctx, "PATCH", "/localapi/v0/prefs", http.StatusOK, bytes.NewReader(mpj))
if err != nil {
return nil, err
}
var p ipn.Prefs
if err := json.Unmarshal(body, &p); err != nil {
return nil, fmt.Errorf("invalid prefs JSON: %w", err)
}
return &p, nil
}
func Logout(ctx context.Context) error {
_, err := send(ctx, "POST", "/localapi/v0/logout", http.StatusNoContent, nil)
return err
}
// SetDNS adds a DNS TXT record for the given domain name, containing
// the provided TXT value. The intended use case is answering
// LetsEncrypt/ACME dns-01 challenges.
//
// The control plane will only permit SetDNS requests with very
// specific names and values. The name should be
// "_acme-challenge." + your node's MagicDNS name. It's expected that
// clients cache the certs from LetsEncrypt (or whichever CA is
// providing them) and only request new ones as needed; the control plane
// rate limits SetDNS requests.
//
// This is a low-level interface; it's expected that most Tailscale
// users use a higher level interface to getting/using TLS
// certificates.
func SetDNS(ctx context.Context, name, value string) error {
v := url.Values{}
v.Set("name", name)
v.Set("value", value)
_, err := send(ctx, "POST", "/localapi/v0/set-dns?"+v.Encode(), 200, nil)
return err
}
// CurrentDERPMap returns the current DERPMap that is being used by the local tailscaled.
// It is intended to be used with netcheck to see availability of DERPs.
func CurrentDERPMap(ctx context.Context) (*tailcfg.DERPMap, error) {
var derpMap tailcfg.DERPMap
res, err := send(ctx, "GET", "/localapi/v0/derpmap", 200, nil)
if err != nil {
return nil, err
}
if err = json.Unmarshal(res, &derpMap); err != nil {
return nil, fmt.Errorf("invalid derp map json: %w", err)
}
return &derpMap, nil
errResp.Status = resp.StatusCode
return errResp
}

85
client/web/assets.go Normal file
View File

@@ -0,0 +1,85 @@
// Copyright (c) Tailscale Inc & AUTHORS
// SPDX-License-Identifier: BSD-3-Clause
package web
import (
"log"
"net/http"
"net/http/httputil"
"net/url"
"os"
"os/exec"
"path/filepath"
"strings"
prebuilt "github.com/tailscale/web-client-prebuilt"
)
func assetsHandler(devMode bool) (_ http.Handler, cleanup func()) {
if devMode {
// When in dev mode, proxy asset requests to the Vite dev server.
cleanup := startDevServer()
return devServerProxy(), cleanup
}
return http.FileServer(http.FS(prebuilt.FS())), nil
}
// startDevServer starts the JS dev server that does on-demand rebuilding
// and serving of web client JS and CSS resources.
func startDevServer() (cleanup func()) {
root := gitRootDir()
webClientPath := filepath.Join(root, "client", "web")
yarn := filepath.Join(root, "tool", "yarn")
node := filepath.Join(root, "tool", "node")
vite := filepath.Join(webClientPath, "node_modules", ".bin", "vite")
log.Printf("installing JavaScript deps using %s... (might take ~30s)", yarn)
out, err := exec.Command(yarn, "--non-interactive", "-s", "--cwd", webClientPath, "install").CombinedOutput()
if err != nil {
log.Fatalf("error running tailscale web's yarn install: %v, %s", err, out)
}
log.Printf("starting JavaScript dev server...")
cmd := exec.Command(node, vite)
cmd.Dir = webClientPath
cmd.Stdout = os.Stdout
cmd.Stderr = os.Stderr
if err := cmd.Start(); err != nil {
log.Fatalf("Starting JS dev server: %v", err)
}
log.Printf("JavaScript dev server running as pid %d", cmd.Process.Pid)
return func() {
cmd.Process.Signal(os.Interrupt)
err := cmd.Wait()
log.Printf("JavaScript dev server exited: %v", err)
}
}
// devServerProxy returns a reverse proxy to the vite dev server.
func devServerProxy() *httputil.ReverseProxy {
// We use Vite to develop on the web client.
// Vite starts up its own local server for development,
// which we proxy requests to from Server.ServeHTTP.
// Here we set up the proxy to Vite's server.
handleErr := func(w http.ResponseWriter, r *http.Request, err error) {
w.Header().Set("Content-Type", "text/plain")
w.WriteHeader(http.StatusBadGateway)
w.Write([]byte("The web client development server isn't running. " +
"Run `./tool/yarn --cwd client/web start` from " +
"the repo root to start the development server."))
w.Write([]byte("\n\nError: " + err.Error()))
}
viteTarget, _ := url.Parse("http://127.0.0.1:4000")
devProxy := httputil.NewSingleHostReverseProxy(viteTarget)
devProxy.ErrorHandler = handleErr
return devProxy
}
func gitRootDir() string {
top, err := exec.Command("git", "rev-parse", "--show-toplevel").Output()
if err != nil {
log.Fatalf("failed to find git top level (not in corp git?): %v", err)
}
return strings.TrimSpace(string(top))
}

View File

@@ -0,0 +1,28 @@
<!doctype html>
<html class="bg-gray-50">
<head>
<title>Tailscale</title>
<meta charset="utf-8" />
<meta name="viewport" content="width=device-width, initial-scale=1" />
<link rel="shortcut icon" href="data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAACAAAAAgCAQAAADZc7J/AAAABGdBTUEAALGPC/xhBQAAACBjSFJNAAB6JgAAgIQAAPoAAACA6AAAdTAAAOpgAAA6mAAAF3CculE8AAAAAmJLR0QA/4ePzL8AAAAHdElNRQflAx4QGA4EvmzDAAAA30lEQVRIx2NgGAWMCKa8JKM4A8Ovt88ekyLCDGOoyDBJMjExMbFy8zF8/EKsCAMDE8yAPyIwFps48SJIBpAL4AZwvoSx/r0lXgQpDN58EWL5x/7/H+vL20+JFxluQKVe5b3Ke5V+0kQQCamfoYKBg4GDwUKI8d0BYkWQkrLKewYBKPPDHUFiRaiZkBgmwhj/F5IgggyUJ6i8V3mv0kCayDAAeEsklXqGAgYGhgV3CnGrwVciYSYk0kokhgS44/JxqqFpiYSZbEgskd4dEBRk1GD4wdB5twKXmlHAwMDAAACdEZau06NQUwAAACV0RVh0ZGF0ZTpjcmVhdGUAMjAyMC0wNy0xNVQxNTo1Mzo0MCswMDowMCVXsDIAAAAldEVYdGRhdGU6bW9kaWZ5ADIwMjAtMDctMTVUMTU6NTM6NDArMDA6MDBUCgiOAAAAAElFTkSuQmCC" />
<script type="module" crossorigin src="./assets/index-4d1f45ea.js"></script>
<link rel="stylesheet" href="./assets/index-8612dca6.css">
</head>
<body>
<noscript>
<p class="mb-2">You need to enable Javascript to access the Tailscale web client.</p>
<p>If you need any help, feel free to <a href="mailto:support+webclient@tailscale.com" class="link">contact us</a>.</p>
</noscript>
<script>
window.addEventListener("load", () => {
if (!window.Tailscale) {
const rootEl = document.createElement("p")
rootEl.innerHTML = 'Tailscale was built without the web client. See <a href="https://github.com/tailscale/tailscale#building-the-web-client">Building the web client</a> for more information.'
document.body.append(rootEl)
}
});
</script>
</body>
</html>

26
client/web/index.html Normal file
View File

@@ -0,0 +1,26 @@
<!doctype html>
<html class="bg-gray-50">
<head>
<title>Tailscale</title>
<meta charset="utf-8" />
<meta name="viewport" content="width=device-width, initial-scale=1" />
<link rel="shortcut icon" href="data:image/png;base64,iVBORw0KGgoAAAANSUhEUgAAACAAAAAgCAQAAADZc7J/AAAABGdBTUEAALGPC/xhBQAAACBjSFJNAAB6JgAAgIQAAPoAAACA6AAAdTAAAOpgAAA6mAAAF3CculE8AAAAAmJLR0QA/4ePzL8AAAAHdElNRQflAx4QGA4EvmzDAAAA30lEQVRIx2NgGAWMCKa8JKM4A8Ovt88ekyLCDGOoyDBJMjExMbFy8zF8/EKsCAMDE8yAPyIwFps48SJIBpAL4AZwvoSx/r0lXgQpDN58EWL5x/7/H+vL20+JFxluQKVe5b3Ke5V+0kQQCamfoYKBg4GDwUKI8d0BYkWQkrLKewYBKPPDHUFiRaiZkBgmwhj/F5IgggyUJ6i8V3mv0kCayDAAeEsklXqGAgYGhgV3CnGrwVciYSYk0kokhgS44/JxqqFpiYSZbEgskd4dEBRk1GD4wdB5twKXmlHAwMDAAACdEZau06NQUwAAACV0RVh0ZGF0ZTpjcmVhdGUAMjAyMC0wNy0xNVQxNTo1Mzo0MCswMDowMCVXsDIAAAAldEVYdGRhdGU6bW9kaWZ5ADIwMjAtMDctMTVUMTU6NTM6NDArMDA6MDBUCgiOAAAAAElFTkSuQmCC" />
<link rel="stylesheet" type="text/css" href="/src/index.css" />
</head>
<body>
<noscript>
<p class="mb-2">You need to enable Javascript to access the Tailscale web client.</p>
<p>If you need any help, feel free to <a href="mailto:support+webclient@tailscale.com" class="link">contact us</a>.</p>
</noscript>
<script type="module" src="/src/index.tsx"></script>
<script>
window.addEventListener("load", () => {
if (!window.Tailscale) {
const rootEl = document.createElement("p")
rootEl.innerHTML = 'Tailscale was built without the web client. See <a href="https://github.com/tailscale/tailscale#building-the-web-client">Building the web client</a> for more information.'
document.body.append(rootEl)
}
});
</script>
</body>
</html>

44
client/web/package.json Normal file
View File

@@ -0,0 +1,44 @@
{
"name": "webclient",
"version": "0.0.1",
"license": "BSD-3-Clause",
"engines": {
"node": "18.16.1",
"yarn": "1.22.19"
},
"private": true,
"dependencies": {
"classnames": "^2.3.1",
"react": "^18.2.0",
"react-dom": "^18.2.0"
},
"devDependencies": {
"@types/classnames": "^2.2.10",
"@types/react": "^18.0.20",
"@types/react-dom": "^18.0.6",
"@vitejs/plugin-react-swc": "^3.3.2",
"autoprefixer": "^10.4.15",
"postcss": "^8.4.27",
"prettier": "^2.5.1",
"prettier-plugin-organize-imports": "^3.2.2",
"tailwindcss": "^3.3.3",
"typescript": "^4.7.4",
"vite": "^4.3.9",
"vite-plugin-rewrite-all": "^1.0.1",
"vite-plugin-svgr": "^3.2.0",
"vite-tsconfig-paths": "^3.5.0",
"vitest": "^0.32.0"
},
"scripts": {
"build": "vite build",
"start": "vite",
"lint": "tsc --noEmit",
"test": "vitest",
"format": "prettier --write 'src/**/*.{ts,tsx}'",
"format-check": "prettier --check 'src/**/*.{ts,tsx}'"
},
"prettier": {
"semi": false,
"printWidth": 80
}
}

View File

@@ -0,0 +1,6 @@
module.exports = {
plugins: {
tailwindcss: {},
autoprefixer: {},
},
}

130
client/web/qnap.go Normal file
View File

@@ -0,0 +1,130 @@
// Copyright (c) Tailscale Inc & AUTHORS
// SPDX-License-Identifier: BSD-3-Clause
// qnap.go contains handlers and logic, such as authentication,
// that is specific to running the web client on QNAP.
package web
import (
"crypto/tls"
"encoding/xml"
"fmt"
"io"
"log"
"net/http"
"net/url"
)
// authorizeQNAP authenticates the logged-in QNAP user and verifies that they
// are authorized to use the web client.
// It reports true if the request is authorized to continue, and false otherwise.
// authorizeQNAP manages writing out any relevant authorization errors to the
// ResponseWriter itself.
func authorizeQNAP(w http.ResponseWriter, r *http.Request) (ok bool) {
_, resp, err := qnapAuthn(r)
if err != nil {
http.Error(w, err.Error(), http.StatusUnauthorized)
return false
}
if resp.IsAdmin == 0 {
http.Error(w, "user is not an admin", http.StatusForbidden)
return false
}
return true
}
type qnapAuthResponse struct {
AuthPassed int `xml:"authPassed"`
IsAdmin int `xml:"isAdmin"`
AuthSID string `xml:"authSid"`
ErrorValue int `xml:"errorValue"`
}
func qnapAuthn(r *http.Request) (string, *qnapAuthResponse, error) {
user, err := r.Cookie("NAS_USER")
if err != nil {
return "", nil, err
}
token, err := r.Cookie("qtoken")
if err == nil {
return qnapAuthnQtoken(r, user.Value, token.Value)
}
sid, err := r.Cookie("NAS_SID")
if err == nil {
return qnapAuthnSid(r, user.Value, sid.Value)
}
return "", nil, fmt.Errorf("not authenticated by any mechanism")
}
// qnapAuthnURL returns the auth URL to use by inferring where the UI is
// running based on the request URL. This is necessary because QNAP has so
// many options, see https://github.com/tailscale/tailscale/issues/7108
// and https://github.com/tailscale/tailscale/issues/6903
func qnapAuthnURL(requestUrl string, query url.Values) string {
in, err := url.Parse(requestUrl)
scheme := ""
host := ""
if err != nil || in.Scheme == "" {
log.Printf("Cannot parse QNAP login URL %v", err)
// try localhost and hope for the best
scheme = "http"
host = "localhost"
} else {
scheme = in.Scheme
host = in.Host
}
u := url.URL{
Scheme: scheme,
Host: host,
Path: "/cgi-bin/authLogin.cgi",
RawQuery: query.Encode(),
}
return u.String()
}
func qnapAuthnQtoken(r *http.Request, user, token string) (string, *qnapAuthResponse, error) {
query := url.Values{
"qtoken": []string{token},
"user": []string{user},
}
return qnapAuthnFinish(user, qnapAuthnURL(r.URL.String(), query))
}
func qnapAuthnSid(r *http.Request, user, sid string) (string, *qnapAuthResponse, error) {
query := url.Values{
"sid": []string{sid},
}
return qnapAuthnFinish(user, qnapAuthnURL(r.URL.String(), query))
}
func qnapAuthnFinish(user, url string) (string, *qnapAuthResponse, error) {
// QNAP Force HTTPS mode uses a self-signed certificate. Even importing
// the QNAP root CA isn't enough, the cert doesn't have a usable CN nor
// SAN. See https://github.com/tailscale/tailscale/issues/6903
tr := &http.Transport{
TLSClientConfig: &tls.Config{InsecureSkipVerify: true},
}
client := &http.Client{Transport: tr}
resp, err := client.Get(url)
if err != nil {
return "", nil, err
}
defer resp.Body.Close()
out, err := io.ReadAll(resp.Body)
if err != nil {
return "", nil, err
}
authResp := &qnapAuthResponse{}
if err := xml.Unmarshal(out, authResp); err != nil {
return "", nil, err
}
if authResp.AuthPassed == 0 {
return "", nil, fmt.Errorf("not authenticated")
}
return user, authResp, nil
}

67
client/web/src/api.ts Normal file
View File

@@ -0,0 +1,67 @@
let csrfToken: string
let unraidCsrfToken: string | undefined // required for unraid POST requests (#8062)
// apiFetch wraps the standard JS fetch function with csrf header
// management and param additions specific to the web client.
//
// apiFetch adds the `api` prefix to the request URL,
// so endpoint should be provided without the `api` prefix
// (i.e. provide `/data` rather than `api/data`).
export function apiFetch(
endpoint: string,
method: "GET" | "POST",
body?: any,
params?: Record<string, string>
): Promise<Response> {
const urlParams = new URLSearchParams(window.location.search)
const nextParams = new URLSearchParams(params)
const token = urlParams.get("SynoToken")
if (token) {
nextParams.set("SynoToken", token)
}
const search = nextParams.toString()
const url = `api${endpoint}${search ? `?${search}` : ""}`
var contentType: string
if (unraidCsrfToken && method === "POST") {
const params = new URLSearchParams()
params.append("csrf_token", unraidCsrfToken)
if (body) {
params.append("ts_data", JSON.stringify(body))
}
body = params.toString()
contentType = "application/x-www-form-urlencoded;charset=UTF-8"
} else {
body = body ? JSON.stringify(body) : undefined
contentType = "application/json"
}
return fetch(url, {
method: method,
headers: {
Accept: "application/json",
"Content-Type": contentType,
"X-CSRF-Token": csrfToken,
},
body,
}).then((r) => {
updateCsrfToken(r)
if (!r.ok) {
return r.text().then((err) => {
throw new Error(err)
})
}
return r
})
}
function updateCsrfToken(r: Response) {
const tok = r.headers.get("X-CSRF-Token")
if (tok) {
csrfToken = tok
}
}
export function setUnraidCsrfToken(token?: string) {
unraidCsrfToken = token
}

View File

@@ -0,0 +1,156 @@
import React from "react"
import { Footer, Header, IP, State } from "src/components/legacy"
import useAuth, { AuthResponse } from "src/hooks/auth"
import useNodeData, { NodeData } from "src/hooks/node-data"
import { ReactComponent as ConnectedDeviceIcon } from "src/icons/connected-device.svg"
import { ReactComponent as TailscaleIcon } from "src/icons/tailscale-icon.svg"
import { ReactComponent as TailscaleLogo } from "src/icons/tailscale-logo.svg"
export default function App() {
// TODO(sonia): use isPosting value from useNodeData
// to fill loading states.
const { data, refreshData, updateNode } = useNodeData()
if (!data) {
// TODO(sonia): add a loading view
return <div className="text-center py-14">Loading...</div>
}
const needsLogin = data?.Status === "NeedsLogin" || data?.Status === "NoState"
return !needsLogin &&
(data.DebugMode === "login" || data.DebugMode === "full") ? (
<WebClient {...data} />
) : (
// Legacy client UI
<div className="py-14">
<main className="container max-w-lg mx-auto mb-8 py-6 px-8 bg-white rounded-md shadow-2xl">
<Header data={data} refreshData={refreshData} updateNode={updateNode} />
<IP data={data} />
<State data={data} updateNode={updateNode} />
</main>
<Footer licensesURL={data.LicensesURL} />
</div>
)
}
function WebClient(props: NodeData) {
const { data: auth, loading: loadingAuth, waitOnAuth } = useAuth()
if (loadingAuth) {
return <div className="text-center py-14">Loading...</div>
}
return (
<div className="flex flex-col items-center min-w-sm max-w-lg mx-auto py-10">
{props.DebugMode === "full" && auth?.ok ? (
<ManagementView {...props} />
) : (
<ReadonlyView data={props} auth={auth} waitOnAuth={waitOnAuth} />
)}
<Footer className="mt-20" licensesURL={props.LicensesURL} />
</div>
)
}
function ReadonlyView({
data,
auth,
waitOnAuth,
}: {
data: NodeData
auth?: AuthResponse
waitOnAuth: () => Promise<void>
}) {
return (
<>
<div className="pb-52 mx-auto">
<TailscaleLogo />
</div>
<div className="w-full p-4 bg-stone-50 rounded-3xl border border-gray-200 flex flex-col gap-4">
<div className="flex gap-2.5">
<ProfilePic url={data.Profile.ProfilePicURL} />
<div className="font-medium">
<div className="text-neutral-500 text-xs uppercase tracking-wide">
Owned by
</div>
<div className="text-neutral-800 text-sm leading-tight">
{/* TODO(sonia): support tagged node profile view more eloquently */}
{data.Profile.LoginName}
</div>
</div>
</div>
<div className="px-5 py-4 bg-white rounded-lg border border-gray-200 justify-between items-center flex">
<div className="flex gap-3">
<ConnectedDeviceIcon />
<div className="text-neutral-800">
<div className="text-lg font-medium leading-[25.20px]">
{data.DeviceName}
</div>
<div className="text-sm leading-tight">{data.IP}</div>
</div>
</div>
{data.DebugMode === "full" && (
<button
className="button button-blue ml-6"
onClick={() => {
window.open(auth?.authUrl, "_blank")
waitOnAuth()
}}
>
Access
</button>
)}
</div>
</div>
</>
)
}
function ManagementView(props: NodeData) {
return (
<div className="px-5">
<div className="flex justify-between mb-12">
<TailscaleIcon />
<div className="flex">
<p className="mr-2">{props.Profile.LoginName}</p>
{/* TODO(sonia): support tagged node profile view more eloquently */}
<ProfilePic url={props.Profile.ProfilePicURL} />
</div>
</div>
<p className="tracking-wide uppercase text-gray-600 pb-3">This device</p>
<div className="-mx-5 border rounded-md px-5 py-4 bg-white">
<div className="flex justify-between items-center text-lg">
<div className="flex items-center">
<ConnectedDeviceIcon />
<p className="font-medium ml-3">{props.DeviceName}</p>
</div>
<p className="tracking-widest">{props.IP}</p>
</div>
</div>
<p className="text-gray-500 pt-2">
Tailscale is up and running. You can connect to this device from devices
in your tailnet by using its name or IP address.
</p>
<button className="button button-blue mt-6">Advertise exit node</button>
</div>
)
}
function ProfilePic({ url }: { url: string }) {
return (
<div className="relative flex-shrink-0 w-8 h-8 rounded-full overflow-hidden">
{url ? (
<div
className="w-8 h-8 flex pointer-events-none rounded-full bg-gray-200"
style={{
backgroundImage: `url(${url})`,
backgroundSize: "cover",
}}
/>
) : (
<div className="w-8 h-8 flex pointer-events-none rounded-full border border-gray-400 border-dashed" />
)}
</div>
)
}

View File

@@ -0,0 +1,298 @@
import cx from "classnames"
import React from "react"
import { apiFetch } from "src/api"
import { NodeData, NodeUpdate } from "src/hooks/node-data"
// TODO(tailscale/corp#13775): legacy.tsx contains a set of components
// that (crudely) implement the pre-2023 web client. These are implemented
// purely to ease migration to the new React-based web client, and will
// eventually be completely removed.
export function Header({
data,
refreshData,
updateNode,
}: {
data: NodeData
refreshData: () => void
updateNode: (update: NodeUpdate) => void
}) {
return (
<header className="flex justify-between items-center min-width-0 py-2 mb-8">
<svg
width="26"
height="26"
viewBox="0 0 23 23"
fill="none"
xmlns="http://www.w3.org/2000/svg"
className="flex-shrink-0 mr-4"
>
<circle
opacity="0.2"
cx="3.4"
cy="3.25"
r="2.7"
fill="currentColor"
></circle>
<circle cx="3.4" cy="11.3" r="2.7" fill="currentColor"></circle>
<circle
opacity="0.2"
cx="3.4"
cy="19.5"
r="2.7"
fill="currentColor"
></circle>
<circle cx="11.5" cy="11.3" r="2.7" fill="currentColor"></circle>
<circle cx="11.5" cy="19.5" r="2.7" fill="currentColor"></circle>
<circle
opacity="0.2"
cx="11.5"
cy="3.25"
r="2.7"
fill="currentColor"
></circle>
<circle
opacity="0.2"
cx="19.5"
cy="3.25"
r="2.7"
fill="currentColor"
></circle>
<circle cx="19.5" cy="11.3" r="2.7" fill="currentColor"></circle>
<circle
opacity="0.2"
cx="19.5"
cy="19.5"
r="2.7"
fill="currentColor"
></circle>
</svg>
<div className="flex items-center justify-end space-x-2 w-2/3">
{data.Profile &&
data.Status !== "NoState" &&
data.Status !== "NeedsLogin" && (
<>
<div className="text-right w-full leading-4">
<h4 className="truncate leading-normal">
{data.Profile.LoginName}
</h4>
<div className="text-xs text-gray-500 text-right">
<button
onClick={() => updateNode({ Reauthenticate: true })}
className="hover:text-gray-700"
>
Switch account
</button>{" "}
|{" "}
<button
onClick={() => updateNode({ Reauthenticate: true })}
className="hover:text-gray-700"
>
Reauthenticate
</button>{" "}
|{" "}
<button
onClick={() =>
apiFetch("/local/v0/logout", "POST")
.then(refreshData)
.catch((err) => alert("Logout failed: " + err.message))
}
className="hover:text-gray-700"
>
Logout
</button>
</div>
</div>
<div className="relative flex-shrink-0 w-8 h-8 rounded-full overflow-hidden">
{data.Profile.ProfilePicURL ? (
<div
className="w-8 h-8 flex pointer-events-none rounded-full bg-gray-200"
style={{
backgroundImage: `url(${data.Profile.ProfilePicURL})`,
backgroundSize: "cover",
}}
/>
) : (
<div className="w-8 h-8 flex pointer-events-none rounded-full border border-gray-400 border-dashed" />
)}
</div>
</>
)}
</div>
</header>
)
}
export function IP(props: { data: NodeData }) {
const { data } = props
if (!data.IP) {
return null
}
return (
<>
<div className="border border-gray-200 bg-gray-50 rounded-md p-2 pl-3 pr-3 width-full flex items-center justify-between">
<div className="flex items-center min-width-0">
<svg
className="flex-shrink-0 text-gray-600 mr-3 ml-1"
xmlns="http://www.w3.org/2000/svg"
width="20"
height="20"
viewBox="0 0 24 24"
fill="none"
stroke="currentColor"
strokeWidth="2"
strokeLinecap="round"
strokeLinejoin="round"
>
<rect x="2" y="2" width="20" height="8" rx="2" ry="2"></rect>
<rect x="2" y="14" width="20" height="8" rx="2" ry="2"></rect>
<line x1="6" y1="6" x2="6.01" y2="6"></line>
<line x1="6" y1="18" x2="6.01" y2="18"></line>
</svg>
<h4 className="font-semibold truncate mr-2">
{data.DeviceName || "Your device"}
</h4>
</div>
<h5>{data.IP}</h5>
</div>
<p className="mt-1 ml-1 mb-6 text-xs text-gray-600">
Debug info: Tailscale {data.IPNVersion}, tun={data.TUNMode.toString()}
{data.IsSynology && (
<>
, DSM{data.DSMVersion}
{data.TUNMode || (
<>
{" "}
(
<a
href="https://tailscale.com/kb/1152/synology-outbound/"
className="link-underline text-gray-600"
target="_blank"
aria-label="Configure outbound synology traffic"
rel="noopener noreferrer"
>
outgoing access not configured
</a>
)
</>
)}
</>
)}
</p>
</>
)
}
export function State({
data,
updateNode,
}: {
data: NodeData
updateNode: (update: NodeUpdate) => void
}) {
switch (data.Status) {
case "NeedsLogin":
case "NoState":
if (data.IP) {
return (
<>
<div className="mb-6">
<p className="text-gray-700">
Your device's key has expired. Reauthenticate this device by
logging in again, or{" "}
<a
href="https://tailscale.com/kb/1028/key-expiry"
className="link"
target="_blank"
>
learn more
</a>
.
</p>
</div>
<button
onClick={() => updateNode({ Reauthenticate: true })}
className="button button-blue w-full mb-4"
>
Reauthenticate
</button>
</>
)
} else {
return (
<>
<div className="mb-6">
<h3 className="text-3xl font-semibold mb-3">Log in</h3>
<p className="text-gray-700">
Get started by logging in to your Tailscale network.
Or,&nbsp;learn&nbsp;more at{" "}
<a
href="https://tailscale.com/"
className="link"
target="_blank"
>
tailscale.com
</a>
.
</p>
</div>
<button
onClick={() => updateNode({ Reauthenticate: true })}
className="button button-blue w-full mb-4"
>
Log In
</button>
</>
)
}
case "NeedsMachineAuth":
return (
<div className="mb-4">
This device is authorized, but needs approval from a network admin
before it can connect to the network.
</div>
)
default:
return (
<>
<div className="mb-4">
<p>
You are connected! Access this device over Tailscale using the
device name or IP address above.
</p>
</div>
<button
className={cx("button button-medium mb-4", {
"button-red": data.AdvertiseExitNode,
"button-blue": !data.AdvertiseExitNode,
})}
id="enabled"
onClick={() =>
updateNode({ AdvertiseExitNode: !data.AdvertiseExitNode })
}
>
{data.AdvertiseExitNode
? "Stop advertising Exit Node"
: "Advertise as Exit Node"}
</button>
</>
)
}
}
export function Footer(props: { licensesURL: string; className?: string }) {
return (
<footer
className={cx("container max-w-lg mx-auto text-center", props.className)}
>
<a
className="text-xs text-gray-500 hover:text-gray-600"
href={props.licensesURL}
>
Open Source Licenses
</a>
</footer>
)
}

View File

@@ -0,0 +1,37 @@
import { useCallback, useEffect, useState } from "react"
import { apiFetch } from "src/api"
export type AuthResponse = {
ok: boolean
authUrl?: string
}
// useAuth reports and refreshes Tailscale auth status
// for the web client.
export default function useAuth() {
const [data, setData] = useState<AuthResponse>()
const [loading, setLoading] = useState<boolean>(false)
const loadAuth = useCallback((wait?: boolean) => {
const url = wait ? "/auth?wait=true" : "/auth"
setLoading(true)
return apiFetch(url, "GET")
.then((r) => r.json())
.then((d) => {
setLoading(false)
setData(d)
})
.catch((error) => {
setLoading(false)
console.error(error)
})
}, [])
useEffect(() => {
loadAuth()
}, [])
const waitOnAuth = useCallback(() => loadAuth(true), [])
return { data, loading, waitOnAuth }
}

View File

@@ -0,0 +1,117 @@
import { useCallback, useEffect, useState } from "react"
import { apiFetch, setUnraidCsrfToken } from "src/api"
export type NodeData = {
Profile: UserProfile
Status: string
DeviceName: string
IP: string
AdvertiseExitNode: boolean
AdvertiseRoutes: string
LicensesURL: string
TUNMode: boolean
IsSynology: boolean
DSMVersion: number
IsUnraid: boolean
UnraidToken: string
IPNVersion: string
DebugMode: "" | "login" | "full" // empty when not running in any debug mode
}
export type UserProfile = {
LoginName: string
DisplayName: string
ProfilePicURL: string
}
export type NodeUpdate = {
AdvertiseRoutes?: string
AdvertiseExitNode?: boolean
Reauthenticate?: boolean
ForceLogout?: boolean
}
// useNodeData returns basic data about the current node.
export default function useNodeData() {
const [data, setData] = useState<NodeData>()
const [isPosting, setIsPosting] = useState<boolean>(false)
const refreshData = useCallback(
() =>
apiFetch("/data", "GET")
.then((r) => r.json())
.then((d: NodeData) => {
setData(d)
setUnraidCsrfToken(d.IsUnraid ? d.UnraidToken : undefined)
})
.catch((error) => console.error(error)),
[setData]
)
const updateNode = useCallback(
(update: NodeUpdate) => {
// The contents of this function are mostly copied over
// from the legacy client's web.html file.
// It makes all data updates through one API endpoint.
// As we build out the web client in React,
// this endpoint will eventually be deprecated.
if (isPosting || !data) {
return
}
setIsPosting(true)
update = {
...update,
// Default to current data value for any unset fields.
AdvertiseRoutes:
update.AdvertiseRoutes !== undefined
? update.AdvertiseRoutes
: data.AdvertiseRoutes,
AdvertiseExitNode:
update.AdvertiseExitNode !== undefined
? update.AdvertiseExitNode
: data.AdvertiseExitNode,
}
apiFetch("/data", "POST", update, { up: "true" })
.then((r) => r.json())
.then((r) => {
setIsPosting(false)
const err = r["error"]
if (err) {
throw new Error(err)
}
const url = r["url"]
if (url) {
window.open(url, "_blank")
}
refreshData()
})
.catch((err) => alert("Failed operation: " + err.message))
},
[data]
)
useEffect(
() => {
// Initial data load.
refreshData()
// Refresh on browser tab focus.
const onVisibilityChange = () => {
document.visibilityState === "visible" && refreshData()
}
window.addEventListener("visibilitychange", onVisibilityChange)
return () => {
// Cleanup browser tab listener.
window.removeEventListener("visibilitychange", onVisibilityChange)
}
},
// Run once.
[]
)
return { data, refreshData, updateNode, isPosting }
}

View File

@@ -0,0 +1,15 @@
<svg width="40" height="40" viewBox="0 0 40 40" fill="none" xmlns="http://www.w3.org/2000/svg">
<rect width="40" height="40" rx="20" fill="#F7F5F4"/>
<g clip-path="url(#clip0_13627_11903)">
<path d="M26.6666 11.6667H13.3333C12.4128 11.6667 11.6666 12.4129 11.6666 13.3333V16.6667C11.6666 17.5871 12.4128 18.3333 13.3333 18.3333H26.6666C27.5871 18.3333 28.3333 17.5871 28.3333 16.6667V13.3333C28.3333 12.4129 27.5871 11.6667 26.6666 11.6667Z" stroke="black" stroke-width="1.5" stroke-linecap="round" stroke-linejoin="round"/>
<path d="M26.6666 21.6667H13.3333C12.4128 21.6667 11.6666 22.4129 11.6666 23.3333V26.6667C11.6666 27.5871 12.4128 28.3333 13.3333 28.3333H26.6666C27.5871 28.3333 28.3333 27.5871 28.3333 26.6667V23.3333C28.3333 22.4129 27.5871 21.6667 26.6666 21.6667Z" stroke="black" stroke-width="1.5" stroke-linecap="round" stroke-linejoin="round"/>
<path d="M15 15H15.01" stroke="black" stroke-width="1.5" stroke-linecap="round" stroke-linejoin="round"/>
<path d="M15 25H15.01" stroke="black" stroke-width="1.5" stroke-linecap="round" stroke-linejoin="round"/>
</g>
<circle cx="34" cy="34" r="4.5" fill="#1EA672" stroke="white"/>
<defs>
<clipPath id="clip0_13627_11903">
<rect width="20" height="20" fill="white" transform="translate(10 10)"/>
</clipPath>
</defs>
</svg>

After

Width:  |  Height:  |  Size: 1.3 KiB

View File

@@ -0,0 +1,18 @@
<svg width="26" height="26" viewBox="0 0 26 26" fill="none" xmlns="http://www.w3.org/2000/svg">
<g clip-path="url(#clip0_13627_11860)">
<path opacity="0.2" d="M3.8696 6.77137C5.56662 6.77137 6.94233 5.39567 6.94233 3.69865C6.94233 2.00163 5.56662 0.625919 3.8696 0.625919C2.17258 0.625919 0.796875 2.00163 0.796875 3.69865C0.796875 5.39567 2.17258 6.77137 3.8696 6.77137Z" fill="black"/>
<path d="M3.8696 15.9327C5.56662 15.9327 6.94233 14.5569 6.94233 12.8599C6.94233 11.1629 5.56662 9.7872 3.8696 9.7872C2.17258 9.7872 0.796875 11.1629 0.796875 12.8599C0.796875 14.5569 2.17258 15.9327 3.8696 15.9327Z" fill="black"/>
<path opacity="0.2" d="M3.8696 25.2646C5.56662 25.2646 6.94233 23.8889 6.94233 22.1919C6.94233 20.4949 5.56662 19.1192 3.8696 19.1192C2.17258 19.1192 0.796875 20.4949 0.796875 22.1919C0.796875 23.8889 2.17258 25.2646 3.8696 25.2646Z" fill="black"/>
<path d="M13.0879 15.9327C14.7849 15.9327 16.1606 14.5569 16.1606 12.8599C16.1606 11.1629 14.7849 9.7872 13.0879 9.7872C11.3908 9.7872 10.0151 11.1629 10.0151 12.8599C10.0151 14.5569 11.3908 15.9327 13.0879 15.9327Z" fill="black"/>
<path d="M13.0879 25.2646C14.7849 25.2646 16.1606 23.8889 16.1606 22.1919C16.1606 20.4949 14.7849 19.1192 13.0879 19.1192C11.3908 19.1192 10.0151 20.4949 10.0151 22.1919C10.0151 23.8889 11.3908 25.2646 13.0879 25.2646Z" fill="black"/>
<path opacity="0.2" d="M13.0879 6.77137C14.7849 6.77137 16.1606 5.39567 16.1606 3.69865C16.1606 2.00163 14.7849 0.625919 13.0879 0.625919C11.3908 0.625919 10.0151 2.00163 10.0151 3.69865C10.0151 5.39567 11.3908 6.77137 13.0879 6.77137Z" fill="black"/>
<path opacity="0.2" d="M22.1919 6.77137C23.8889 6.77137 25.2646 5.39567 25.2646 3.69865C25.2646 2.00163 23.8889 0.625919 22.1919 0.625919C20.4948 0.625919 19.1191 2.00163 19.1191 3.69865C19.1191 5.39567 20.4948 6.77137 22.1919 6.77137Z" fill="black"/>
<path d="M22.1919 15.9327C23.8889 15.9327 25.2646 14.5569 25.2646 12.8599C25.2646 11.1629 23.8889 9.7872 22.1919 9.7872C20.4948 9.7872 19.1191 11.1629 19.1191 12.8599C19.1191 14.5569 20.4948 15.9327 22.1919 15.9327Z" fill="black"/>
<path opacity="0.2" d="M22.1919 25.2646C23.8889 25.2646 25.2646 23.8889 25.2646 22.1919C25.2646 20.4949 23.8889 19.1192 22.1919 19.1192C20.4948 19.1192 19.1191 20.4949 19.1191 22.1919C19.1191 23.8889 20.4948 25.2646 22.1919 25.2646Z" fill="black"/>
</g>
<defs>
<clipPath id="clip0_13627_11860">
<rect width="26" height="26" fill="white"/>
</clipPath>
</defs>
</svg>

After

Width:  |  Height:  |  Size: 2.4 KiB

View File

@@ -0,0 +1,20 @@
<svg width="121" height="22" viewBox="0 0 121 22" fill="none" xmlns="http://www.w3.org/2000/svg">
<ellipse cx="2.69191" cy="10.7677" rx="2.69191" ry="2.69191" fill="#141414"/>
<ellipse cx="10.7676" cy="10.7677" rx="2.69191" ry="2.69191" fill="#141414"/>
<ellipse opacity="0.2" cx="2.69191" cy="18.8434" rx="2.69191" ry="2.69191" fill="#141414"/>
<circle opacity="0.2" cx="18.8433" cy="18.8434" r="2.69191" fill="#141414"/>
<ellipse cx="10.7676" cy="18.8434" rx="2.69191" ry="2.69191" fill="#141414"/>
<circle cx="18.8433" cy="10.7677" r="2.69191" fill="#141414"/>
<ellipse opacity="0.2" cx="2.69191" cy="2.69191" rx="2.69191" ry="2.69191" fill="#141414"/>
<ellipse opacity="0.2" cx="10.7676" cy="2.69191" rx="2.69191" ry="2.69191" fill="#141414"/>
<circle opacity="0.2" cx="18.8433" cy="2.69191" r="2.69191" fill="#141414"/>
<path d="M37.8847 19.9603C38.6525 19.9603 39.2764 19.8883 40.0202 19.7443V16.9609C39.5643 17.1289 39.0605 17.1769 38.5806 17.1769C37.4048 17.1769 36.9729 16.601 36.9729 15.4973V9.83453H40.0202V7.05116H36.9729V2.92409H33.6137V7.05116H31.4302V9.83453H33.6137V15.8092C33.6137 18.4486 35.0054 19.9603 37.8847 19.9603Z" fill="#141414"/>
<path d="M45.5064 19.9603C47.306 19.9603 48.5057 19.3604 49.1056 18.4246C49.1536 18.8325 49.2975 19.3844 49.4895 19.7203H52.5128C52.3448 19.1444 52.2249 18.2326 52.2249 17.6328V11.0583C52.2249 8.34687 50.2813 6.81121 46.994 6.81121C44.4986 6.81121 42.555 7.747 41.4753 9.1147L43.3949 11.0103C44.2587 10.0505 45.3624 9.5466 46.7061 9.5466C48.3377 9.5466 49.0576 10.0985 49.0576 10.9143C49.0576 11.6101 48.5777 12.09 45.9863 12.09C43.4908 12.09 40.9714 13.1218 40.9714 16.0011C40.9714 18.6645 42.891 19.9603 45.5064 19.9603ZM46.1782 17.4168C44.8825 17.4168 44.2827 16.8649 44.2827 15.8812C44.2827 15.0174 45.0025 14.4415 46.2022 14.4415C48.1218 14.4415 48.6497 14.3215 49.0576 13.9136V14.9454C49.0576 16.3131 47.9058 17.4168 46.1782 17.4168Z" fill="#141414"/>
<path d="M54.4086 5.44352H57.9118V2.30023H54.4086V5.44352ZM54.4805 19.7203H57.8398V7.05116H54.4805V19.7203Z" fill="#141414"/>
<path d="M60.287 19.7203H63.6463V2.68414H60.287V19.7203Z" fill="#141414"/>
<path d="M70.6285 19.9603C74.3237 19.9603 76.2193 18.0167 76.2193 15.9771C76.2193 14.1296 75.2835 12.7619 72.2122 12.21C70.0527 11.8261 68.709 11.3462 68.709 10.6024C68.709 9.95451 69.4768 9.49861 70.7725 9.49861C71.9242 9.49861 72.884 9.88252 73.6038 10.7223L75.7394 8.92274C74.6596 7.57904 72.884 6.81121 70.7725 6.81121C67.5332 6.81121 65.5177 8.53883 65.5177 10.6503C65.5177 12.9538 67.6292 13.9856 69.9087 14.3935C71.8043 14.7294 72.86 15.0893 72.86 15.9052C72.86 16.601 72.1162 17.1769 70.7005 17.1769C69.3088 17.1769 68.2291 16.529 67.7252 15.5692L64.8938 16.9129C65.5897 18.6405 67.9651 19.9603 70.6285 19.9603Z" fill="#141414"/>
<path d="M83.7294 19.9603C86.1288 19.9603 87.8564 19.0005 89.1521 16.841L86.4648 15.4733C85.9609 16.481 85.1451 17.1769 83.7294 17.1769C81.5939 17.1769 80.4421 15.4493 80.4421 13.3617C80.4421 11.2742 81.6658 9.59459 83.7294 9.59459C85.0251 9.59459 85.8889 10.2904 86.3928 11.3462L89.1042 9.90652C88.1924 7.91497 86.3928 6.81121 83.7294 6.81121C79.3384 6.81121 77.0829 10.0265 77.0829 13.3617C77.0829 16.9849 79.8183 19.9603 83.7294 19.9603Z" fill="#141414"/>
<path d="M94.5031 19.9603C96.3027 19.9603 97.5025 19.3604 98.1023 18.4246C98.1503 18.8325 98.2943 19.3844 98.4862 19.7203H101.51C101.342 19.1444 101.222 18.2326 101.222 17.6328V11.0583C101.222 8.34687 99.2781 6.81121 95.9908 6.81121C93.4954 6.81121 91.5518 7.747 90.472 9.1147L92.3916 11.0103C93.2554 10.0505 94.3592 9.5466 95.7029 9.5466C97.3345 9.5466 98.0543 10.0985 98.0543 10.9143C98.0543 11.6101 97.5744 12.09 94.983 12.09C92.4876 12.09 89.9682 13.1218 89.9682 16.0011C89.9682 18.6645 91.8877 19.9603 94.5031 19.9603ZM95.175 17.4168C93.8793 17.4168 93.2794 16.8649 93.2794 15.8812C93.2794 15.0174 93.9992 14.4415 95.199 14.4415C97.1185 14.4415 97.6464 14.3215 98.0543 13.9136V14.9454C98.0543 16.3131 96.9026 17.4168 95.175 17.4168Z" fill="#141414"/>
<path d="M103.196 19.7203H106.555V2.68414H103.196V19.7203Z" fill="#141414"/>
<path d="M114.617 19.9603C117.089 19.9603 119.08 18.9765 120.184 17.2249L117.641 15.5932C116.969 16.649 116.081 17.2249 114.617 17.2249C112.962 17.2249 111.762 16.3131 111.45 14.5375H121V13.3617C121 10.0265 118.96 6.81121 114.593 6.81121C110.442 6.81121 108.187 10.0505 108.187 13.3857C108.187 18.1367 111.762 19.9603 114.617 19.9603ZM111.57 11.8981C112.098 10.2904 113.202 9.5466 114.665 9.5466C116.321 9.5466 117.329 10.5304 117.665 11.8981H111.57Z" fill="#141414"/>
</svg>

After

Width:  |  Height:  |  Size: 4.4 KiB

130
client/web/src/index.css Normal file
View File

@@ -0,0 +1,130 @@
@tailwind base;
@tailwind components;
@tailwind utilities;
/**
* Non-Tailwind styles begin here.
*/
.bg-gray-0 {
--tw-bg-opacity: 1;
background-color: rgba(250, 249, 248, var(--tw-bg-opacity));
}
.bg-gray-50 {
--tw-bg-opacity: 1;
background-color: rgba(249, 247, 246, var(--tw-bg-opacity));
}
html {
letter-spacing: -0.015em;
text-rendering: optimizeLegibility;
-webkit-font-smoothing: antialiased;
-moz-osx-font-smoothing: grayscale;
}
.link {
--text-opacity: 1;
color: #4b70cc;
color: rgba(75, 112, 204, var(--text-opacity));
}
.link:hover,
.link:active {
--text-opacity: 1;
color: #19224a;
color: rgba(25, 34, 74, var(--text-opacity));
}
.link-underline {
text-decoration: underline;
}
.link-underline:hover,
.link-underline:active {
text-decoration: none;
}
.link-muted {
/* same as text-gray-500 */
--tw-text-opacity: 1;
color: rgba(112, 110, 109, var(--tw-text-opacity));
}
.link-muted:hover,
.link-muted:active {
/* same as text-gray-500 */
--tw-text-opacity: 1;
color: rgba(68, 67, 66, var(--tw-text-opacity));
}
.button {
font-weight: 500;
padding-top: 0.45rem;
padding-bottom: 0.45rem;
padding-left: 1rem;
padding-right: 1rem;
border-radius: 0.375rem;
border-width: 1px;
border-color: transparent;
transition-property: background-color, border-color, color, box-shadow;
transition-duration: 120ms;
box-shadow: 0 1px 1px rgba(0, 0, 0, 0.04);
min-width: 80px;
}
.button:focus {
outline: 0;
box-shadow: 0 0 0 3px rgba(66, 153, 225, 0.5);
}
.button:disabled {
cursor: not-allowed;
-webkit-user-select: none;
-ms-user-select: none;
user-select: none;
}
.button-blue {
--bg-opacity: 1;
background-color: #4b70cc;
background-color: rgba(75, 112, 204, var(--bg-opacity));
--border-opacity: 1;
border-color: #4b70cc;
border-color: rgba(75, 112, 204, var(--border-opacity));
--text-opacity: 1;
color: #fff;
color: rgba(255, 255, 255, var(--text-opacity));
}
.button-blue:enabled:hover {
--bg-opacity: 1;
background-color: #3f5db3;
background-color: rgba(63, 93, 179, var(--bg-opacity));
--border-opacity: 1;
border-color: #3f5db3;
border-color: rgba(63, 93, 179, var(--border-opacity));
}
.button-blue:disabled {
--text-opacity: 1;
color: #cedefd;
color: rgba(206, 222, 253, var(--text-opacity));
--bg-opacity: 1;
background-color: #6c94ec;
background-color: rgba(108, 148, 236, var(--bg-opacity));
--border-opacity: 1;
border-color: #6c94ec;
border-color: rgba(108, 148, 236, var(--border-opacity));
}
.button-red {
background-color: #d04841;
border-color: #d04841;
color: #fff;
}
.button-red:enabled:hover {
background-color: #b22d30;
border-color: #b22d30;
}

20
client/web/src/index.tsx Normal file
View File

@@ -0,0 +1,20 @@
import React from "react"
import { createRoot } from "react-dom/client"
import App from "src/components/app"
declare var window: any
// This is used to determine if the react client is built.
window.Tailscale = true
const rootEl = document.createElement("div")
rootEl.id = "app-root"
rootEl.classList.add("relative", "z-0")
document.body.append(rootEl)
const root = createRoot(rootEl)
root.render(
<React.StrictMode>
<App />
</React.StrictMode>
)

78
client/web/synology.go Normal file
View File

@@ -0,0 +1,78 @@
// Copyright (c) Tailscale Inc & AUTHORS
// SPDX-License-Identifier: BSD-3-Clause
// synology.go contains handlers and logic, such as authentication,
// that is specific to running the web client on Synology.
package web
import (
"fmt"
"net/http"
"os/exec"
"strings"
"tailscale.com/util/groupmember"
)
// authorizeSynology authenticates the logged-in Synology user and verifies
// that they are authorized to use the web client.
// It reports true if the request is authorized to continue, and false otherwise.
// authorizeSynology manages writing out any relevant authorization errors to the
// ResponseWriter itself.
func authorizeSynology(w http.ResponseWriter, r *http.Request) (ok bool) {
if synoTokenRedirect(w, r) {
return false
}
// authenticate the Synology user
cmd := exec.Command("/usr/syno/synoman/webman/modules/authenticate.cgi")
out, err := cmd.CombinedOutput()
if err != nil {
http.Error(w, fmt.Sprintf("auth: %v: %s", err, out), http.StatusUnauthorized)
return false
}
user := strings.TrimSpace(string(out))
// check if the user is in the administrators group
isAdmin, err := groupmember.IsMemberOfGroup("administrators", user)
if err != nil {
http.Error(w, err.Error(), http.StatusForbidden)
return false
}
if !isAdmin {
http.Error(w, "not a member of administrators group", http.StatusForbidden)
return false
}
return true
}
func synoTokenRedirect(w http.ResponseWriter, r *http.Request) bool {
if r.Header.Get("X-Syno-Token") != "" {
return false
}
if r.URL.Query().Get("SynoToken") != "" {
return false
}
if r.Method == "POST" && r.FormValue("SynoToken") != "" {
return false
}
// We need a SynoToken for authenticate.cgi.
// So we tell the client to get one.
_, _ = fmt.Fprint(w, synoTokenRedirectHTML)
return true
}
const synoTokenRedirectHTML = `<html>
Redirecting with session token...
<script>
fetch("/webman/login.cgi")
.then(r => r.json())
.then(data => {
u = new URL(window.location)
u.searchParams.set("SynoToken", data.SynoToken)
document.location = u
})
</script>
`

View File

@@ -0,0 +1,12 @@
/** @type {import('tailwindcss').Config} */
module.exports = {
content: [
"./index.html",
"./src/**/*.{js,ts,jsx,tsx}",
],
theme: {
extend: {},
},
plugins: [],
}

17
client/web/tsconfig.json Normal file
View File

@@ -0,0 +1,17 @@
{
"compilerOptions": {
"baseUrl": ".",
"target": "ES2017",
"module": "ES2020",
"strict": true,
"sourceMap": true,
"isolatedModules": true,
"moduleResolution": "node",
"forceConsistentCasingInFileNames": true,
"allowSyntheticDefaultImports": true,
"jsx": "react",
"types": ["vite-plugin-svgr/client", "vite/client"]
},
"include": ["src/**/*"],
"exclude": ["node_modules"]
}

69
client/web/vite.config.ts Normal file
View File

@@ -0,0 +1,69 @@
/// <reference types="vitest" />
import { createLogger, defineConfig } from "vite"
import rewrite from "vite-plugin-rewrite-all"
import svgr from "vite-plugin-svgr"
import paths from "vite-tsconfig-paths"
// Use a custom logger that filters out Vite's logging of server URLs, since
// they are an attractive nuisance (we run a proxy in front of Vite, and the
// tailscale web client should be accessed through that).
// Unfortunately there's no option to disable this logging, so the best we can
// do it to ignore calls from a specific function.
const filteringLogger = createLogger(undefined, { allowClearScreen: false })
const originalInfoLog = filteringLogger.info
filteringLogger.info = (...args) => {
if (new Error("ignored").stack?.includes("printServerUrls")) {
return
}
originalInfoLog.apply(filteringLogger, args)
}
// https://vitejs.dev/config/
export default defineConfig({
base: "./",
plugins: [
paths(),
svgr(),
// By default, the Vite dev server doesn't handle dots
// in path names and treats them as static files.
// This plugin changes Vite's routing logic to fix this.
// See: https://github.com/vitejs/vite/issues/2415
rewrite(),
],
build: {
outDir: "build",
sourcemap: false,
},
esbuild: {
logOverride: {
// Silence a warning about `this` being undefined in ESM when at the
// top-level. The way JSX is transpiled causes this to happen, but it
// isn't a problem.
// See: https://github.com/vitejs/vite/issues/8644
"this-is-undefined-in-esm": "silent",
},
},
server: {
// This needs to be 127.0.0.1 instead of localhost, because of how our
// Go proxy connects to it.
host: "127.0.0.1",
// If you change the port, be sure to update the proxy in adminhttp.go too.
port: 4000,
// Don't proxy the WebSocket connection used for live reloading by running
// it on a separate port.
hmr: {
protocol: "ws",
port: 4001,
},
},
test: {
exclude: ["**/node_modules/**", "**/dist/**"],
testTimeout: 20000,
environment: "jsdom",
deps: {
inline: ["date-fns", /\.wasm\?url$/],
},
},
clearScreen: false,
customLogger: filteringLogger,
})

850
client/web/web.go Normal file
View File

@@ -0,0 +1,850 @@
// Copyright (c) Tailscale Inc & AUTHORS
// SPDX-License-Identifier: BSD-3-Clause
// Package web provides the Tailscale client for web.
package web
import (
"bytes"
"context"
"crypto/rand"
"encoding/base64"
"encoding/json"
"errors"
"fmt"
"io"
"log"
"net/http"
"net/netip"
"os"
"path/filepath"
"slices"
"strings"
"sync"
"time"
"github.com/gorilla/csrf"
"tailscale.com/client/tailscale"
"tailscale.com/client/tailscale/apitype"
"tailscale.com/envknob"
"tailscale.com/ipn"
"tailscale.com/ipn/ipnstate"
"tailscale.com/licenses"
"tailscale.com/net/netutil"
"tailscale.com/tailcfg"
"tailscale.com/util/httpm"
"tailscale.com/version/distro"
)
// Server is the backend server for a Tailscale web client.
type Server struct {
lc *tailscale.LocalClient
timeNow func() time.Time
devMode bool
tsDebugMode string
cgiMode bool
pathPrefix string
assetsHandler http.Handler // serves frontend assets
apiHandler http.Handler // serves api endpoints; csrf-protected
// browserSessions is an in-memory cache of browser sessions for the
// full management web client, which is only accessible over Tailscale.
//
// Users obtain a valid browser session by connecting to the web client
// over Tailscale and verifying their identity by authenticating on the
// control server.
//
// browserSessions get reset on every Server restart.
//
// The map provides a lookup of the session by cookie value
// (browserSession.ID => browserSession).
browserSessions sync.Map
}
const (
sessionCookieName = "TS-Web-Session"
sessionCookieExpiry = time.Hour * 24 * 30 // 30 days
)
var (
exitNodeRouteV4 = netip.MustParsePrefix("0.0.0.0/0")
exitNodeRouteV6 = netip.MustParsePrefix("::/0")
)
// browserSession holds data about a user's browser session
// on the full management web client.
type browserSession struct {
// ID is the unique identifier for the session.
// It is passed in the user's "TS-Web-Session" browser cookie.
ID string
SrcNode tailcfg.NodeID
SrcUser tailcfg.UserID
AuthID string // from tailcfg.WebClientAuthResponse
AuthURL string // from tailcfg.WebClientAuthResponse
Created time.Time
Authenticated bool
}
// isAuthorized reports true if the given session is authorized
// to be used by its associated user to access the full management
// web client.
//
// isAuthorized is true only when s.Authenticated is true (i.e.
// the user has authenticated the session) and the session is not
// expired.
// 2023-10-05: Sessions expire by default 30 days after creation.
func (s *browserSession) isAuthorized(now time.Time) bool {
switch {
case s == nil:
return false
case !s.Authenticated:
return false // awaiting auth
case s.isExpired(now):
return false // expired
}
return true
}
// isExpired reports true if s is expired.
// 2023-10-05: Sessions expire by default 30 days after creation.
func (s *browserSession) isExpired(now time.Time) bool {
return !s.Created.IsZero() && now.After(s.expires())
}
// expires reports when the given session expires.
func (s *browserSession) expires() time.Time {
return s.Created.Add(sessionCookieExpiry)
}
// ServerOpts contains options for constructing a new Server.
type ServerOpts struct {
DevMode bool
// CGIMode indicates if the server is running as a CGI script.
CGIMode bool
// PathPrefix is the URL prefix added to requests by CGI or reverse proxy.
PathPrefix string
// LocalClient is the tailscale.LocalClient to use for this web server.
// If nil, a new one will be created.
LocalClient *tailscale.LocalClient
// TimeNow optionally provides a time function.
// time.Now is used as default.
TimeNow func() time.Time
}
// NewServer constructs a new Tailscale web client server.
func NewServer(opts ServerOpts) (s *Server, cleanup func()) {
if opts.LocalClient == nil {
opts.LocalClient = &tailscale.LocalClient{}
}
s = &Server{
devMode: opts.DevMode,
lc: opts.LocalClient,
cgiMode: opts.CGIMode,
pathPrefix: opts.PathPrefix,
timeNow: opts.TimeNow,
}
if s.timeNow == nil {
s.timeNow = time.Now
}
s.tsDebugMode = s.debugMode()
s.assetsHandler, cleanup = assetsHandler(opts.DevMode)
// Create handler for "/api" requests with CSRF protection.
// We don't require secure cookies, since the web client is regularly used
// on network appliances that are served on local non-https URLs.
// The client is secured by limiting the interface it listens on,
// or by authenticating requests before they reach the web client.
csrfProtect := csrf.Protect(s.csrfKey(), csrf.Secure(false))
if s.tsDebugMode == "login" {
// For the login client, we don't serve the full web client API,
// only the login endpoints.
s.apiHandler = csrfProtect(http.HandlerFunc(s.serveLoginAPI))
s.lc.IncrementCounter(context.Background(), "web_login_client_initialization", 1)
} else {
s.apiHandler = csrfProtect(http.HandlerFunc(s.serveAPI))
s.lc.IncrementCounter(context.Background(), "web_client_initialization", 1)
}
return s, cleanup
}
// debugMode returns the debug mode the web client is being run in.
// The empty string is returned in the case that this instance is
// not running in any debug mode.
func (s *Server) debugMode() string {
if !s.devMode {
return "" // debug modes only available in dev
}
switch mode := os.Getenv("TS_DEBUG_WEB_CLIENT_MODE"); mode {
case "login", "full": // valid debug modes
return mode
}
return ""
}
// ServeHTTP processes all requests for the Tailscale web client.
func (s *Server) ServeHTTP(w http.ResponseWriter, r *http.Request) {
handler := s.serve
// if path prefix is defined, strip it from requests.
if s.pathPrefix != "" {
handler = enforcePrefix(s.pathPrefix, handler)
}
handler(w, r)
}
func (s *Server) serve(w http.ResponseWriter, r *http.Request) {
if ok := s.authorizeRequest(w, r); !ok {
return
}
if strings.HasPrefix(r.URL.Path, "/api/") {
// Pass API requests through to the API handler.
s.apiHandler.ServeHTTP(w, r)
return
}
if !s.devMode {
s.lc.IncrementCounter(r.Context(), "web_client_page_load", 1)
}
s.assetsHandler.ServeHTTP(w, r)
}
// authorizeRequest reports whether the request from the web client
// is authorized to be completed.
// It reports true if the request is authorized, and false otherwise.
// authorizeRequest manages writing out any relevant authorization
// errors to the ResponseWriter itself.
func (s *Server) authorizeRequest(w http.ResponseWriter, r *http.Request) (ok bool) {
if s.tsDebugMode == "full" { // client using tailscale auth
_, err := s.lc.WhoIs(r.Context(), r.RemoteAddr)
switch {
case err != nil:
// All requests must be made over tailscale.
http.Error(w, "must access over tailscale", http.StatusUnauthorized)
return false
case r.URL.Path == "/api/data" && r.Method == httpm.GET:
// Readonly endpoint allowed without browser session.
return true
case r.URL.Path == "/api/auth":
// Endpoint for browser to request auth allowed without browser session.
return true
case strings.HasPrefix(r.URL.Path, "/api/"):
// All other /api/ endpoints require a valid browser session.
//
// TODO(sonia): s.getTailscaleBrowserSession calls whois again,
// should try and use the above call instead of running another
// localapi request.
session, _, err := s.getTailscaleBrowserSession(r)
if err != nil || !session.isAuthorized(s.timeNow()) {
http.Error(w, "no valid session", http.StatusUnauthorized)
return false
}
return true
default:
// No additional auth on non-api (assets, index.html, etc).
return true
}
}
// Client using system-specific auth.
d := distro.Get()
switch {
case strings.HasPrefix(r.URL.Path, "/assets/") && r.Method == httpm.GET:
// Don't require authorization for static assets.
return true
case d == distro.Synology:
return authorizeSynology(w, r)
case d == distro.QNAP:
return authorizeQNAP(w, r)
default:
return true // no additional auth for this distro
}
}
// serveLoginAPI serves requests for the web login client.
// It should only be called by Server.ServeHTTP, via Server.apiHandler,
// which protects the handler using gorilla csrf.
func (s *Server) serveLoginAPI(w http.ResponseWriter, r *http.Request) {
w.Header().Set("X-CSRF-Token", csrf.Token(r))
if r.URL.Path != "/api/data" { // only endpoint allowed for login client
http.Error(w, "invalid endpoint", http.StatusNotFound)
return
}
switch r.Method {
case httpm.GET:
// TODO(soniaappasamy): we may want a minimal node data response here
s.serveGetNodeData(w, r)
case httpm.POST:
// TODO(soniaappasamy): implement
default:
http.Error(w, "method not allowed", http.StatusMethodNotAllowed)
}
return
}
var (
errNoSession = errors.New("no-browser-session")
errNotUsingTailscale = errors.New("not-using-tailscale")
errTaggedRemoteSource = errors.New("tagged-remote-source")
errTaggedLocalSource = errors.New("tagged-local-source")
errNotOwner = errors.New("not-owner")
)
// getTailscaleBrowserSession retrieves the browser session associated with
// the request, if one exists.
//
// An error is returned in any of the following cases:
//
// - (errNotUsingTailscale) The request was not made over tailscale.
//
// - (errNoSession) The request does not have a session.
//
// - (errTaggedRemoteSource) The source is remote (another node) and tagged.
// Users must use their own user-owned devices to manage other nodes'
// web clients.
//
// - (errTaggedLocalSource) The source is local (the same node) and tagged.
// Tagged nodes can only be remotely managed, allowing ACLs to dictate
// access to web clients.
//
// - (errNotOwner) The source is not the owner of this client (if the
// client is user-owned). Only the owner is allowed to manage the
// node via the web client.
//
// If no error is returned, the browserSession is always non-nil.
// getTailscaleBrowserSession does not check whether the session has been
// authorized by the user. Callers can use browserSession.isAuthorized.
//
// The WhoIsResponse is always populated, with a non-nil Node and UserProfile,
// unless getTailscaleBrowserSession reports errNotUsingTailscale.
func (s *Server) getTailscaleBrowserSession(r *http.Request) (*browserSession, *apitype.WhoIsResponse, error) {
whoIs, whoIsErr := s.lc.WhoIs(r.Context(), r.RemoteAddr)
status, statusErr := s.lc.StatusWithoutPeers(r.Context())
switch {
case whoIsErr != nil:
return nil, nil, errNotUsingTailscale
case statusErr != nil:
return nil, whoIs, statusErr
case status.Self == nil:
return nil, whoIs, errors.New("missing self node in tailscale status")
case whoIs.Node.IsTagged() && whoIs.Node.StableID == status.Self.ID:
return nil, whoIs, errTaggedLocalSource
case whoIs.Node.IsTagged():
return nil, whoIs, errTaggedRemoteSource
case !status.Self.IsTagged() && status.Self.UserID != whoIs.UserProfile.ID:
return nil, whoIs, errNotOwner
}
srcNode := whoIs.Node.ID
srcUser := whoIs.UserProfile.ID
cookie, err := r.Cookie(sessionCookieName)
if errors.Is(err, http.ErrNoCookie) {
return nil, whoIs, errNoSession
} else if err != nil {
return nil, whoIs, err
}
v, ok := s.browserSessions.Load(cookie.Value)
if !ok {
return nil, whoIs, errNoSession
}
session := v.(*browserSession)
if session.SrcNode != srcNode || session.SrcUser != srcUser {
// In this case the browser cookie is associated with another tailscale node.
// Maybe the source browser's machine was logged out and then back in as a different node.
// Return errNoSession because there is no session for this user.
return nil, whoIs, errNoSession
} else if session.isExpired(s.timeNow()) {
// Session expired, remove from session map and return errNoSession.
s.browserSessions.Delete(session.ID)
return nil, whoIs, errNoSession
}
return session, whoIs, nil
}
type authResponse struct {
OK bool `json:"ok"` // true when user has valid auth session
AuthURL string `json:"authUrl,omitempty"` // filled when user has control auth action to take
}
func (s *Server) serveTailscaleAuth(w http.ResponseWriter, r *http.Request) {
if r.Method != httpm.GET {
http.Error(w, "method not allowed", http.StatusMethodNotAllowed)
return
}
var resp authResponse
session, whois, err := s.getTailscaleBrowserSession(r)
switch {
case err != nil && !errors.Is(err, errNoSession):
http.Error(w, err.Error(), http.StatusUnauthorized)
return
case session == nil:
// Create a new session.
d, err := s.getOrAwaitAuth(r.Context(), "", whois.Node.ID)
if err != nil {
http.Error(w, err.Error(), http.StatusInternalServerError)
return
}
sid, err := s.newSessionID()
if err != nil {
http.Error(w, err.Error(), http.StatusInternalServerError)
return
}
session := &browserSession{
ID: sid,
SrcNode: whois.Node.ID,
SrcUser: whois.UserProfile.ID,
AuthID: d.ID,
AuthURL: d.URL,
Created: s.timeNow(),
}
s.browserSessions.Store(sid, session)
// Set the cookie on browser.
http.SetCookie(w, &http.Cookie{
Name: sessionCookieName,
Value: sid,
Raw: sid,
Path: "/",
Expires: session.expires(),
})
resp = authResponse{OK: false, AuthURL: d.URL}
case !session.isAuthorized(s.timeNow()):
if r.URL.Query().Get("wait") == "true" {
// Client requested we block until user completes auth.
d, err := s.getOrAwaitAuth(r.Context(), session.AuthID, whois.Node.ID)
if err != nil {
http.Error(w, err.Error(), http.StatusUnauthorized)
// Clean up the session. Doing this on any error from control
// server to avoid the user getting stuck with a bad session
// cookie.
s.browserSessions.Delete(session.ID)
return
}
if d.Complete {
session.Authenticated = d.Complete
s.browserSessions.Store(session.ID, session)
}
}
if session.isAuthorized(s.timeNow()) {
resp = authResponse{OK: true}
} else {
resp = authResponse{OK: false, AuthURL: session.AuthURL}
}
default:
resp = authResponse{OK: true}
}
if err := json.NewEncoder(w).Encode(resp); err != nil {
http.Error(w, err.Error(), http.StatusInternalServerError)
return
}
w.Header().Set("Content-Type", "application/json")
}
func (s *Server) newSessionID() (string, error) {
raw := make([]byte, 16)
for i := 0; i < 5; i++ {
if _, err := rand.Read(raw); err != nil {
return "", err
}
cookie := "ts-web-" + base64.RawURLEncoding.EncodeToString(raw)
if _, ok := s.browserSessions.Load(cookie); !ok {
return cookie, nil
}
}
return "", errors.New("too many collisions generating new session; please refresh page")
}
// getOrAwaitAuth connects to the control server for user auth,
// with the following behavior:
//
// 1. If authID is provided empty, a new auth URL is created on the control
// server and reported back here, which can then be used to redirect the
// user on the frontend.
// 2. If authID is provided non-empty, the connection to control blocks until
// the user has completed authenticating the associated auth URL,
// or until ctx is canceled.
func (s *Server) getOrAwaitAuth(ctx context.Context, authID string, src tailcfg.NodeID) (*tailcfg.WebClientAuthResponse, error) {
type data struct {
ID string
Src tailcfg.NodeID
}
var b bytes.Buffer
if err := json.NewEncoder(&b).Encode(data{ID: authID, Src: src}); err != nil {
return nil, err
}
url := "http://" + apitype.LocalAPIHost + "/localapi/v0/debug-web-client"
req, err := http.NewRequestWithContext(ctx, "POST", url, &b)
if err != nil {
return nil, err
}
resp, err := s.lc.DoLocalRequest(req)
if err != nil {
return nil, err
}
body, _ := io.ReadAll(resp.Body)
resp.Body.Close()
if resp.StatusCode != http.StatusOK {
return nil, fmt.Errorf("failed request: %s", body)
}
var authResp *tailcfg.WebClientAuthResponse
if err := json.Unmarshal(body, &authResp); err != nil {
return nil, err
}
return authResp, nil
}
// serveAPI serves requests for the web client api.
// It should only be called by Server.ServeHTTP, via Server.apiHandler,
// which protects the handler using gorilla csrf.
func (s *Server) serveAPI(w http.ResponseWriter, r *http.Request) {
w.Header().Set("X-CSRF-Token", csrf.Token(r))
path := strings.TrimPrefix(r.URL.Path, "/api")
switch {
case path == "/auth":
if s.tsDebugMode == "full" { // behind debug flag
s.serveTailscaleAuth(w, r)
return
}
case path == "/data":
switch r.Method {
case httpm.GET:
s.serveGetNodeData(w, r)
case httpm.POST:
s.servePostNodeUpdate(w, r)
default:
http.Error(w, "method not allowed", http.StatusMethodNotAllowed)
}
return
case strings.HasPrefix(path, "/local/"):
s.proxyRequestToLocalAPI(w, r)
return
}
http.Error(w, "invalid endpoint", http.StatusNotFound)
}
type nodeData struct {
Profile tailcfg.UserProfile
Status string
DeviceName string
IP string
AdvertiseExitNode bool
AdvertiseRoutes string
LicensesURL string
TUNMode bool
IsSynology bool
DSMVersion int // 6 or 7, if IsSynology=true
IsUnraid bool
UnraidToken string
IPNVersion string
DebugMode string // empty when not running in any debug mode
}
func (s *Server) serveGetNodeData(w http.ResponseWriter, r *http.Request) {
st, err := s.lc.Status(r.Context())
if err != nil {
http.Error(w, err.Error(), http.StatusInternalServerError)
return
}
prefs, err := s.lc.GetPrefs(r.Context())
if err != nil {
http.Error(w, err.Error(), http.StatusInternalServerError)
return
}
profile := st.User[st.Self.UserID]
deviceName := strings.Split(st.Self.DNSName, ".")[0]
versionShort := strings.Split(st.Version, "-")[0]
data := &nodeData{
Profile: profile,
Status: st.BackendState,
DeviceName: deviceName,
LicensesURL: licenses.LicensesURL(),
TUNMode: st.TUN,
IsSynology: distro.Get() == distro.Synology || envknob.Bool("TS_FAKE_SYNOLOGY"),
DSMVersion: distro.DSMVersion(),
IsUnraid: distro.Get() == distro.Unraid,
UnraidToken: os.Getenv("UNRAID_CSRF_TOKEN"),
IPNVersion: versionShort,
DebugMode: s.tsDebugMode,
}
for _, r := range prefs.AdvertiseRoutes {
if r == exitNodeRouteV4 || r == exitNodeRouteV6 {
data.AdvertiseExitNode = true
} else {
if data.AdvertiseRoutes != "" {
data.AdvertiseRoutes += ","
}
data.AdvertiseRoutes += r.String()
}
}
if len(st.TailscaleIPs) != 0 {
data.IP = st.TailscaleIPs[0].String()
}
if err := json.NewEncoder(w).Encode(*data); err != nil {
http.Error(w, err.Error(), http.StatusInternalServerError)
return
}
w.Header().Set("Content-Type", "application/json")
}
type nodeUpdate struct {
AdvertiseRoutes string
AdvertiseExitNode bool
Reauthenticate bool
ForceLogout bool
}
func (s *Server) servePostNodeUpdate(w http.ResponseWriter, r *http.Request) {
defer r.Body.Close()
st, err := s.lc.Status(r.Context())
if err != nil {
http.Error(w, err.Error(), http.StatusInternalServerError)
return
}
var postData nodeUpdate
type mi map[string]any
if err := json.NewDecoder(r.Body).Decode(&postData); err != nil {
w.WriteHeader(400)
json.NewEncoder(w).Encode(mi{"error": err.Error()})
return
}
prefs, err := s.lc.GetPrefs(r.Context())
if err != nil {
http.Error(w, err.Error(), http.StatusInternalServerError)
return
}
isCurrentlyExitNode := slices.Contains(prefs.AdvertiseRoutes, exitNodeRouteV4) || slices.Contains(prefs.AdvertiseRoutes, exitNodeRouteV6)
if postData.AdvertiseExitNode != isCurrentlyExitNode {
if postData.AdvertiseExitNode {
s.lc.IncrementCounter(r.Context(), "web_client_advertise_exitnode_enable", 1)
} else {
s.lc.IncrementCounter(r.Context(), "web_client_advertise_exitnode_disable", 1)
}
}
routes, err := netutil.CalcAdvertiseRoutes(postData.AdvertiseRoutes, postData.AdvertiseExitNode)
if err != nil {
w.WriteHeader(http.StatusInternalServerError)
json.NewEncoder(w).Encode(mi{"error": err.Error()})
return
}
mp := &ipn.MaskedPrefs{
AdvertiseRoutesSet: true,
WantRunningSet: true,
}
mp.Prefs.WantRunning = true
mp.Prefs.AdvertiseRoutes = routes
log.Printf("Doing edit: %v", mp.Pretty())
if _, err := s.lc.EditPrefs(r.Context(), mp); err != nil {
w.WriteHeader(http.StatusInternalServerError)
json.NewEncoder(w).Encode(mi{"error": err.Error()})
return
}
w.Header().Set("Content-Type", "application/json")
var reauth, logout bool
if postData.Reauthenticate {
reauth = true
}
if postData.ForceLogout {
logout = true
}
log.Printf("tailscaleUp(reauth=%v, logout=%v) ...", reauth, logout)
url, err := s.tailscaleUp(r.Context(), st, postData)
log.Printf("tailscaleUp = (URL %v, %v)", url != "", err)
if err != nil {
w.WriteHeader(http.StatusInternalServerError)
json.NewEncoder(w).Encode(mi{"error": err.Error()})
return
}
if url != "" {
json.NewEncoder(w).Encode(mi{"url": url})
} else {
io.WriteString(w, "{}")
}
}
func (s *Server) tailscaleUp(ctx context.Context, st *ipnstate.Status, postData nodeUpdate) (authURL string, retErr error) {
if postData.ForceLogout {
if err := s.lc.Logout(ctx); err != nil {
return "", fmt.Errorf("Logout error: %w", err)
}
return "", nil
}
origAuthURL := st.AuthURL
isRunning := st.BackendState == ipn.Running.String()
forceReauth := postData.Reauthenticate
if !forceReauth {
if origAuthURL != "" {
return origAuthURL, nil
}
if isRunning {
return "", nil
}
}
// printAuthURL reports whether we should print out the
// provided auth URL from an IPN notify.
printAuthURL := func(url string) bool {
return url != origAuthURL
}
watchCtx, cancelWatch := context.WithCancel(ctx)
defer cancelWatch()
watcher, err := s.lc.WatchIPNBus(watchCtx, 0)
if err != nil {
return "", err
}
defer watcher.Close()
go func() {
if !isRunning {
s.lc.Start(ctx, ipn.Options{})
}
if forceReauth {
s.lc.StartLoginInteractive(ctx)
}
}()
for {
n, err := watcher.Next()
if err != nil {
return "", err
}
if n.ErrMessage != nil {
msg := *n.ErrMessage
return "", fmt.Errorf("backend error: %v", msg)
}
if url := n.BrowseToURL; url != nil && printAuthURL(*url) {
return *url, nil
}
}
}
// proxyRequestToLocalAPI proxies the web API request to the localapi.
//
// The web API request path is expected to exactly match a localapi path,
// with prefix /api/local/ rather than /localapi/.
//
// If the localapi path is not included in localapiAllowlist,
// the request is rejected.
func (s *Server) proxyRequestToLocalAPI(w http.ResponseWriter, r *http.Request) {
path := strings.TrimPrefix(r.URL.Path, "/api/local")
if r.URL.Path == path { // missing prefix
http.Error(w, "invalid request", http.StatusBadRequest)
return
}
if !slices.Contains(localapiAllowlist, path) {
http.Error(w, fmt.Sprintf("%s not allowed from localapi proxy", path), http.StatusForbidden)
return
}
localAPIURL := "http://" + apitype.LocalAPIHost + "/localapi" + path
req, err := http.NewRequestWithContext(r.Context(), r.Method, localAPIURL, r.Body)
if err != nil {
http.Error(w, "failed to construct request", http.StatusInternalServerError)
return
}
// Make request to tailscaled localapi.
resp, err := s.lc.DoLocalRequest(req)
if err != nil {
http.Error(w, err.Error(), resp.StatusCode)
return
}
defer resp.Body.Close()
// Send response back to web frontend.
w.Header().Set("Content-Type", resp.Header.Get("Content-Type"))
w.WriteHeader(resp.StatusCode)
if _, err := io.Copy(w, resp.Body); err != nil {
http.Error(w, err.Error(), http.StatusInternalServerError)
}
}
// localapiAllowlist is an allowlist of localapi endpoints the
// web client is allowed to proxy to the client's localapi.
//
// Rather than exposing all localapi endpoints over the proxy,
// this limits to just the ones actually used from the web
// client frontend.
//
// TODO(sonia,will): Shouldn't expand this beyond the existing
// localapi endpoints until the larger web client auth story
// is worked out (tailscale/corp#14335).
var localapiAllowlist = []string{
"/v0/logout",
}
// csrfKey returns a key that can be used for CSRF protection.
// If an error occurs during key creation, the error is logged and the active process terminated.
// If the server is running in CGI mode, the key is cached to disk and reused between requests.
// If an error occurs during key storage, the error is logged and the active process terminated.
func (s *Server) csrfKey() []byte {
csrfFile := filepath.Join(os.TempDir(), "tailscale-web-csrf.key")
// if running in CGI mode, try to read from disk, but ignore errors
if s.cgiMode {
key, _ := os.ReadFile(csrfFile)
if len(key) == 32 {
return key
}
}
// create a new key
key := make([]byte, 32)
if _, err := rand.Read(key); err != nil {
log.Fatalf("error generating CSRF key: %v", err)
}
// if running in CGI mode, try to write the newly created key to disk, and exit if it fails.
if s.cgiMode {
if err := os.WriteFile(csrfFile, key, 0600); err != nil {
log.Fatalf("unable to store CSRF key: %v", err)
}
}
return key
}
// enforcePrefix returns a HandlerFunc that enforces a given path prefix is used in requests,
// then strips it before invoking h.
// Unlike http.StripPrefix, it does not return a 404 if the prefix is not present.
// Instead, it returns a redirect to the prefix path.
func enforcePrefix(prefix string, h http.HandlerFunc) http.HandlerFunc {
if prefix == "" {
return h
}
// ensure that prefix always has both a leading and trailing slash so
// that relative links for JS and CSS assets work correctly.
if !strings.HasPrefix(prefix, "/") {
prefix = "/" + prefix
}
if !strings.HasSuffix(prefix, "/") {
prefix += "/"
}
return func(w http.ResponseWriter, r *http.Request) {
if !strings.HasPrefix(r.URL.Path, prefix) {
http.Redirect(w, r, prefix, http.StatusFound)
return
}
prefix = strings.TrimSuffix(prefix, "/")
http.StripPrefix(prefix, h).ServeHTTP(w, r)
}
}

713
client/web/web_test.go Normal file
View File

@@ -0,0 +1,713 @@
// Copyright (c) Tailscale Inc & AUTHORS
// SPDX-License-Identifier: BSD-3-Clause
package web
import (
"encoding/json"
"errors"
"fmt"
"io"
"net/http"
"net/http/httptest"
"net/url"
"strings"
"testing"
"time"
"github.com/google/go-cmp/cmp"
"tailscale.com/client/tailscale"
"tailscale.com/client/tailscale/apitype"
"tailscale.com/ipn/ipnstate"
"tailscale.com/net/memnet"
"tailscale.com/tailcfg"
"tailscale.com/types/views"
"tailscale.com/util/httpm"
)
func TestQnapAuthnURL(t *testing.T) {
query := url.Values{
"qtoken": []string{"token"},
}
tests := []struct {
name string
in string
want string
}{
{
name: "localhost http",
in: "http://localhost:8088/",
want: "http://localhost:8088/cgi-bin/authLogin.cgi?qtoken=token",
},
{
name: "localhost https",
in: "https://localhost:5000/",
want: "https://localhost:5000/cgi-bin/authLogin.cgi?qtoken=token",
},
{
name: "IP http",
in: "http://10.1.20.4:80/",
want: "http://10.1.20.4:80/cgi-bin/authLogin.cgi?qtoken=token",
},
{
name: "IP6 https",
in: "https://[ff7d:0:1:2::1]/",
want: "https://[ff7d:0:1:2::1]/cgi-bin/authLogin.cgi?qtoken=token",
},
{
name: "hostname https",
in: "https://qnap.example.com/",
want: "https://qnap.example.com/cgi-bin/authLogin.cgi?qtoken=token",
},
{
name: "invalid URL",
in: "This is not a URL, it is a really really really really really really really really really really really really long string to exercise the URL truncation code in the error path.",
want: "http://localhost/cgi-bin/authLogin.cgi?qtoken=token",
},
{
name: "err != nil",
in: "http://192.168.0.%31/",
want: "http://localhost/cgi-bin/authLogin.cgi?qtoken=token",
},
}
for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
u := qnapAuthnURL(tt.in, query)
if u != tt.want {
t.Errorf("expected url: %q, got: %q", tt.want, u)
}
})
}
}
// TestServeAPI tests the web client api's handling of
// 1. invalid endpoint errors
// 2. localapi proxy allowlist
func TestServeAPI(t *testing.T) {
lal := memnet.Listen("local-tailscaled.sock:80")
defer lal.Close()
// Serve dummy localapi. Just returns "success".
localapi := &http.Server{Handler: http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
fmt.Fprintf(w, "success")
})}
defer localapi.Close()
go localapi.Serve(lal)
s := &Server{lc: &tailscale.LocalClient{Dial: lal.Dial}}
tests := []struct {
name string
reqPath string
wantResp string
wantStatus int
}{{
name: "invalid_endpoint",
reqPath: "/not-an-endpoint",
wantResp: "invalid endpoint",
wantStatus: http.StatusNotFound,
}, {
name: "not_in_localapi_allowlist",
reqPath: "/local/v0/not-allowlisted",
wantResp: "/v0/not-allowlisted not allowed from localapi proxy",
wantStatus: http.StatusForbidden,
}, {
name: "in_localapi_allowlist",
reqPath: "/local/v0/logout",
wantResp: "success", // Successfully allowed to hit localapi.
wantStatus: http.StatusOK,
}}
for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
r := httptest.NewRequest("POST", "/api"+tt.reqPath, nil)
w := httptest.NewRecorder()
s.serveAPI(w, r)
res := w.Result()
defer res.Body.Close()
if gotStatus := res.StatusCode; tt.wantStatus != gotStatus {
t.Errorf("wrong status; want=%v, got=%v", tt.wantStatus, gotStatus)
}
body, err := io.ReadAll(res.Body)
if err != nil {
t.Fatal(err)
}
gotResp := strings.TrimSuffix(string(body), "\n") // trim trailing newline
if tt.wantResp != gotResp {
t.Errorf("wrong response; want=%q, got=%q", tt.wantResp, gotResp)
}
})
}
}
func TestGetTailscaleBrowserSession(t *testing.T) {
userA := &tailcfg.UserProfile{ID: tailcfg.UserID(1)}
userB := &tailcfg.UserProfile{ID: tailcfg.UserID(2)}
userANodeIP := "100.100.100.101"
userBNodeIP := "100.100.100.102"
taggedNodeIP := "100.100.100.103"
var selfNode *ipnstate.PeerStatus
tags := views.SliceOf([]string{"tag:server"})
tailnetNodes := map[string]*apitype.WhoIsResponse{
userANodeIP: {
Node: &tailcfg.Node{ID: 1, StableID: "1"},
UserProfile: userA,
},
userBNodeIP: {
Node: &tailcfg.Node{ID: 2, StableID: "2"},
UserProfile: userB,
},
taggedNodeIP: {
Node: &tailcfg.Node{ID: 3, StableID: "3", Tags: tags.AsSlice()},
},
}
lal := memnet.Listen("local-tailscaled.sock:80")
defer lal.Close()
localapi := mockLocalAPI(t, tailnetNodes, func() *ipnstate.PeerStatus { return selfNode })
defer localapi.Close()
go localapi.Serve(lal)
s := &Server{
timeNow: time.Now,
lc: &tailscale.LocalClient{Dial: lal.Dial},
}
// Add some browser sessions to cache state.
userASession := &browserSession{
ID: "cookie1",
SrcNode: 1,
SrcUser: userA.ID,
Created: time.Now(),
Authenticated: false, // not yet authenticated
}
userBSession := &browserSession{
ID: "cookie2",
SrcNode: 2,
SrcUser: userB.ID,
Created: time.Now().Add(-2 * sessionCookieExpiry),
Authenticated: true, // expired
}
userASessionAuthorized := &browserSession{
ID: "cookie3",
SrcNode: 1,
SrcUser: userA.ID,
Created: time.Now(),
Authenticated: true, // authenticated and not expired
}
s.browserSessions.Store(userASession.ID, userASession)
s.browserSessions.Store(userBSession.ID, userBSession)
s.browserSessions.Store(userASessionAuthorized.ID, userASessionAuthorized)
tests := []struct {
name string
selfNode *ipnstate.PeerStatus
remoteAddr string
cookie string
wantSession *browserSession
wantError error
wantIsAuthorized bool // response from session.isAuthorized
}{
{
name: "not-connected-over-tailscale",
selfNode: &ipnstate.PeerStatus{ID: "self", UserID: userA.ID},
remoteAddr: "77.77.77.77",
wantSession: nil,
wantError: errNotUsingTailscale,
},
{
name: "no-session-user-self-node",
selfNode: &ipnstate.PeerStatus{ID: "self", UserID: userA.ID},
remoteAddr: userANodeIP,
cookie: "not-a-cookie",
wantSession: nil,
wantError: errNoSession,
},
{
name: "no-session-tagged-self-node",
selfNode: &ipnstate.PeerStatus{ID: "self", Tags: &tags},
remoteAddr: userANodeIP,
wantSession: nil,
wantError: errNoSession,
},
{
name: "not-owner",
selfNode: &ipnstate.PeerStatus{ID: "self", UserID: userA.ID},
remoteAddr: userBNodeIP,
wantSession: nil,
wantError: errNotOwner,
},
{
name: "tagged-remote-source",
selfNode: &ipnstate.PeerStatus{ID: "self", UserID: userA.ID},
remoteAddr: taggedNodeIP,
wantSession: nil,
wantError: errTaggedRemoteSource,
},
{
name: "tagged-local-source",
selfNode: &ipnstate.PeerStatus{ID: "3"},
remoteAddr: taggedNodeIP, // same node as selfNode
wantSession: nil,
wantError: errTaggedLocalSource,
},
{
name: "not-tagged-local-source",
selfNode: &ipnstate.PeerStatus{ID: "1", UserID: userA.ID},
remoteAddr: userANodeIP, // same node as selfNode
cookie: userASession.ID,
wantSession: userASession,
wantError: nil, // should not error
},
{
name: "has-session",
selfNode: &ipnstate.PeerStatus{ID: "self", UserID: userA.ID},
remoteAddr: userANodeIP,
cookie: userASession.ID,
wantSession: userASession,
wantError: nil,
},
{
name: "has-authorized-session",
selfNode: &ipnstate.PeerStatus{ID: "self", UserID: userA.ID},
remoteAddr: userANodeIP,
cookie: userASessionAuthorized.ID,
wantSession: userASessionAuthorized,
wantError: nil,
wantIsAuthorized: true,
},
{
name: "session-associated-with-different-source",
selfNode: &ipnstate.PeerStatus{ID: "self", UserID: userB.ID},
remoteAddr: userBNodeIP,
cookie: userASession.ID,
wantSession: nil,
wantError: errNoSession,
},
{
name: "session-expired",
selfNode: &ipnstate.PeerStatus{ID: "self", UserID: userB.ID},
remoteAddr: userBNodeIP,
cookie: userBSession.ID,
wantSession: nil,
wantError: errNoSession,
},
}
for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
selfNode = tt.selfNode
r := &http.Request{RemoteAddr: tt.remoteAddr, Header: http.Header{}}
if tt.cookie != "" {
r.AddCookie(&http.Cookie{Name: sessionCookieName, Value: tt.cookie})
}
session, _, err := s.getTailscaleBrowserSession(r)
if !errors.Is(err, tt.wantError) {
t.Errorf("wrong error; want=%v, got=%v", tt.wantError, err)
}
if diff := cmp.Diff(session, tt.wantSession); diff != "" {
t.Errorf("wrong session; (-got+want):%v", diff)
}
if gotIsAuthorized := session.isAuthorized(s.timeNow()); gotIsAuthorized != tt.wantIsAuthorized {
t.Errorf("wrong isAuthorized; want=%v, got=%v", tt.wantIsAuthorized, gotIsAuthorized)
}
})
}
}
// TestAuthorizeRequest tests the s.authorizeRequest function.
// 2023-10-18: These tests currently cover tailscale auth mode (not platform auth).
func TestAuthorizeRequest(t *testing.T) {
// Create self and remoteNode owned by same user.
// See TestGetTailscaleBrowserSession for tests of
// browser sessions w/ different users.
user := &tailcfg.UserProfile{ID: tailcfg.UserID(1)}
self := &ipnstate.PeerStatus{ID: "self", UserID: user.ID}
remoteNode := &apitype.WhoIsResponse{Node: &tailcfg.Node{StableID: "node"}, UserProfile: user}
remoteIP := "100.100.100.101"
lal := memnet.Listen("local-tailscaled.sock:80")
defer lal.Close()
localapi := mockLocalAPI(t,
map[string]*apitype.WhoIsResponse{remoteIP: remoteNode},
func() *ipnstate.PeerStatus { return self },
)
defer localapi.Close()
go localapi.Serve(lal)
s := &Server{
lc: &tailscale.LocalClient{Dial: lal.Dial},
tsDebugMode: "full",
timeNow: time.Now,
}
validCookie := "ts-cookie"
s.browserSessions.Store(validCookie, &browserSession{
ID: validCookie,
SrcNode: remoteNode.Node.ID,
SrcUser: user.ID,
Created: time.Now(),
Authenticated: true,
})
tests := []struct {
reqPath string
reqMethod string
wantOkNotOverTailscale bool // simulates req over public internet
wantOkWithoutSession bool // simulates req over TS without valid browser session
wantOkWithSession bool // simulates req over TS with valid browser session
}{{
reqPath: "/api/data",
reqMethod: httpm.GET,
wantOkNotOverTailscale: false,
wantOkWithoutSession: true,
wantOkWithSession: true,
}, {
reqPath: "/api/data",
reqMethod: httpm.POST,
wantOkNotOverTailscale: false,
wantOkWithoutSession: false,
wantOkWithSession: true,
}, {
reqPath: "/api/auth",
reqMethod: httpm.GET,
wantOkNotOverTailscale: false,
wantOkWithoutSession: true,
wantOkWithSession: true,
}, {
reqPath: "/api/somethingelse",
reqMethod: httpm.GET,
wantOkNotOverTailscale: false,
wantOkWithoutSession: false,
wantOkWithSession: true,
}, {
reqPath: "/assets/styles.css",
wantOkNotOverTailscale: false,
wantOkWithoutSession: true,
wantOkWithSession: true,
}}
for _, tt := range tests {
t.Run(fmt.Sprintf("%s-%s", tt.reqMethod, tt.reqPath), func(t *testing.T) {
doAuthorize := func(remoteAddr string, cookie string) bool {
r := httptest.NewRequest(tt.reqMethod, tt.reqPath, nil)
r.RemoteAddr = remoteAddr
if cookie != "" {
r.AddCookie(&http.Cookie{Name: sessionCookieName, Value: cookie})
}
w := httptest.NewRecorder()
return s.authorizeRequest(w, r)
}
// Do request from non-Tailscale IP.
if gotOk := doAuthorize("123.456.789.999", ""); gotOk != tt.wantOkNotOverTailscale {
t.Errorf("wantOkNotOverTailscale; want=%v, got=%v", tt.wantOkNotOverTailscale, gotOk)
}
// Do request from Tailscale IP w/o associated session.
if gotOk := doAuthorize(remoteIP, ""); gotOk != tt.wantOkWithoutSession {
t.Errorf("wantOkWithoutSession; want=%v, got=%v", tt.wantOkWithoutSession, gotOk)
}
// Do request from Tailscale IP w/ associated session.
if gotOk := doAuthorize(remoteIP, validCookie); gotOk != tt.wantOkWithSession {
t.Errorf("wantOkWithSession; want=%v, got=%v", tt.wantOkWithSession, gotOk)
}
})
}
}
func TestServeTailscaleAuth(t *testing.T) {
user := &tailcfg.UserProfile{ID: tailcfg.UserID(1)}
self := &ipnstate.PeerStatus{ID: "self", UserID: user.ID}
remoteNode := &apitype.WhoIsResponse{Node: &tailcfg.Node{ID: 1}, UserProfile: user}
remoteIP := "100.100.100.101"
lal := memnet.Listen("local-tailscaled.sock:80")
defer lal.Close()
localapi := mockLocalAPI(t,
map[string]*apitype.WhoIsResponse{remoteIP: remoteNode},
func() *ipnstate.PeerStatus { return self },
)
defer localapi.Close()
go localapi.Serve(lal)
timeNow := time.Now()
oneHourAgo := timeNow.Add(-time.Hour)
sixtyDaysAgo := timeNow.Add(-sessionCookieExpiry * 2)
s := &Server{
lc: &tailscale.LocalClient{Dial: lal.Dial},
tsDebugMode: "full",
timeNow: func() time.Time { return timeNow },
}
successCookie := "ts-cookie-success"
s.browserSessions.Store(successCookie, &browserSession{
ID: successCookie,
SrcNode: remoteNode.Node.ID,
SrcUser: user.ID,
Created: oneHourAgo,
AuthID: testAuthPathSuccess,
AuthURL: testControlURL + testAuthPathSuccess,
})
failureCookie := "ts-cookie-failure"
s.browserSessions.Store(failureCookie, &browserSession{
ID: failureCookie,
SrcNode: remoteNode.Node.ID,
SrcUser: user.ID,
Created: oneHourAgo,
AuthID: testAuthPathError,
AuthURL: testControlURL + testAuthPathError,
})
expiredCookie := "ts-cookie-expired"
s.browserSessions.Store(expiredCookie, &browserSession{
ID: expiredCookie,
SrcNode: remoteNode.Node.ID,
SrcUser: user.ID,
Created: sixtyDaysAgo,
AuthID: "/a/old-auth-url",
AuthURL: testControlURL + "/a/old-auth-url",
})
tests := []struct {
name string
cookie string
query string
wantStatus int
wantResp *authResponse
wantNewCookie bool // new cookie generated
wantSession *browserSession // session associated w/ cookie at end of request
}{
{
name: "new-session-created",
wantStatus: http.StatusOK,
wantResp: &authResponse{OK: false, AuthURL: testControlURL + testAuthPath},
wantNewCookie: true,
wantSession: &browserSession{
ID: "GENERATED_ID", // gets swapped for newly created ID by test
SrcNode: remoteNode.Node.ID,
SrcUser: user.ID,
Created: timeNow,
AuthID: testAuthPath,
AuthURL: testControlURL + testAuthPath,
Authenticated: false,
},
},
{
name: "query-existing-incomplete-session",
cookie: successCookie,
wantStatus: http.StatusOK,
wantResp: &authResponse{OK: false, AuthURL: testControlURL + testAuthPathSuccess},
wantSession: &browserSession{
ID: successCookie,
SrcNode: remoteNode.Node.ID,
SrcUser: user.ID,
Created: oneHourAgo,
AuthID: testAuthPathSuccess,
AuthURL: testControlURL + testAuthPathSuccess,
Authenticated: false,
},
},
{
name: "transition-to-successful-session",
cookie: successCookie,
// query "wait" indicates the FE wants to make
// local api call to wait until session completed.
query: "wait=true",
wantStatus: http.StatusOK,
wantResp: &authResponse{OK: true},
wantSession: &browserSession{
ID: successCookie,
SrcNode: remoteNode.Node.ID,
SrcUser: user.ID,
Created: oneHourAgo,
AuthID: testAuthPathSuccess,
AuthURL: testControlURL + testAuthPathSuccess,
Authenticated: true,
},
},
{
name: "query-existing-complete-session",
cookie: successCookie,
wantStatus: http.StatusOK,
wantResp: &authResponse{OK: true},
wantSession: &browserSession{
ID: successCookie,
SrcNode: remoteNode.Node.ID,
SrcUser: user.ID,
Created: oneHourAgo,
AuthID: testAuthPathSuccess,
AuthURL: testControlURL + testAuthPathSuccess,
Authenticated: true,
},
},
{
name: "transition-to-failed-session",
cookie: failureCookie,
query: "wait=true",
wantStatus: http.StatusUnauthorized,
wantResp: nil,
wantSession: nil, // session deleted
},
{
name: "failed-session-cleaned-up",
cookie: failureCookie,
wantStatus: http.StatusOK,
wantResp: &authResponse{OK: false, AuthURL: testControlURL + testAuthPath},
wantNewCookie: true,
wantSession: &browserSession{
ID: "GENERATED_ID",
SrcNode: remoteNode.Node.ID,
SrcUser: user.ID,
Created: timeNow,
AuthID: testAuthPath,
AuthURL: testControlURL + testAuthPath,
Authenticated: false,
},
},
{
name: "expired-cookie-gets-new-session",
cookie: expiredCookie,
wantStatus: http.StatusOK,
wantResp: &authResponse{OK: false, AuthURL: testControlURL + testAuthPath},
wantNewCookie: true,
wantSession: &browserSession{
ID: "GENERATED_ID",
SrcNode: remoteNode.Node.ID,
SrcUser: user.ID,
Created: timeNow,
AuthID: testAuthPath,
AuthURL: testControlURL + testAuthPath,
Authenticated: false,
},
},
}
for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
r := httptest.NewRequest("GET", "/api/auth", nil)
r.URL.RawQuery = tt.query
r.RemoteAddr = remoteIP
r.AddCookie(&http.Cookie{Name: sessionCookieName, Value: tt.cookie})
w := httptest.NewRecorder()
s.serveTailscaleAuth(w, r)
res := w.Result()
defer res.Body.Close()
// Validate response status/data.
if gotStatus := res.StatusCode; tt.wantStatus != gotStatus {
t.Errorf("wrong status; want=%v, got=%v", tt.wantStatus, gotStatus)
}
var gotResp *authResponse
if res.StatusCode == http.StatusOK {
body, err := io.ReadAll(res.Body)
if err != nil {
t.Fatal(err)
}
if err := json.Unmarshal(body, &gotResp); err != nil {
t.Fatal(err)
}
}
if diff := cmp.Diff(gotResp, tt.wantResp); diff != "" {
t.Errorf("wrong response; (-got+want):%v", diff)
}
// Validate cookie creation.
sessionID := tt.cookie
var gotCookie bool
for _, c := range w.Result().Cookies() {
if c.Name == sessionCookieName {
gotCookie = true
sessionID = c.Value
break
}
}
if gotCookie != tt.wantNewCookie {
t.Errorf("wantNewCookie wrong; want=%v, got=%v", tt.wantNewCookie, gotCookie)
}
// Validate browser session contents.
var gotSesson *browserSession
if s, ok := s.browserSessions.Load(sessionID); ok {
gotSesson = s.(*browserSession)
}
if tt.wantSession != nil && tt.wantSession.ID == "GENERATED_ID" {
// If requested, swap in the generated session ID before
// comparing got/want.
tt.wantSession.ID = sessionID
}
if diff := cmp.Diff(gotSesson, tt.wantSession); diff != "" {
t.Errorf("wrong session; (-got+want):%v", diff)
}
})
}
}
var (
testControlURL = "http://localhost:8080"
testAuthPath = "/a/12345"
testAuthPathSuccess = "/a/will-succeed"
testAuthPathError = "/a/will-error"
)
// mockLocalAPI constructs a test localapi handler that can be used
// to simulate localapi responses without a functioning tailnet.
//
// self accepts a function that resolves to a self node status,
// so that tests may swap out the /localapi/v0/status response
// as desired.
func mockLocalAPI(t *testing.T, whoIs map[string]*apitype.WhoIsResponse, self func() *ipnstate.PeerStatus) *http.Server {
return &http.Server{Handler: http.HandlerFunc(func(w http.ResponseWriter, r *http.Request) {
switch r.URL.Path {
case "/localapi/v0/whois":
addr := r.URL.Query().Get("addr")
if addr == "" {
t.Fatalf("/whois call missing \"addr\" query")
}
if node := whoIs[addr]; node != nil {
if err := json.NewEncoder(w).Encode(&node); err != nil {
http.Error(w, err.Error(), http.StatusInternalServerError)
return
}
w.Header().Set("Content-Type", "application/json")
return
}
http.Error(w, "not a node", http.StatusUnauthorized)
return
case "/localapi/v0/status":
status := ipnstate.Status{Self: self()}
if err := json.NewEncoder(w).Encode(status); err != nil {
http.Error(w, err.Error(), http.StatusInternalServerError)
return
}
w.Header().Set("Content-Type", "application/json")
return
case "/localapi/v0/debug-web-client": // used by TestServeTailscaleAuth
type reqData struct {
ID string
Src tailcfg.NodeID
}
var data reqData
if err := json.NewDecoder(r.Body).Decode(&data); err != nil {
http.Error(w, "invalid JSON body", http.StatusBadRequest)
return
}
if data.Src == 0 {
http.Error(w, "missing Src node", http.StatusBadRequest)
return
}
var resp *tailcfg.WebClientAuthResponse
if data.ID == "" {
resp = &tailcfg.WebClientAuthResponse{ID: testAuthPath, URL: testControlURL + testAuthPath}
} else if data.ID == testAuthPathSuccess {
resp = &tailcfg.WebClientAuthResponse{Complete: true}
} else if data.ID == testAuthPathError {
http.Error(w, "authenticated as wrong user", http.StatusUnauthorized)
return
}
if err := json.NewEncoder(w).Encode(resp); err != nil {
http.Error(w, err.Error(), http.StatusInternalServerError)
return
}
w.Header().Set("Content-Type", "application/json")
return
default:
t.Fatalf("unhandled localapi test endpoint %q, add to localapi handler func in test", r.URL.Path)
}
})}
}

1818
client/web/yarn.lock Normal file

File diff suppressed because it is too large Load Diff

1175
clientupdate/clientupdate.go Normal file

File diff suppressed because it is too large Load Diff

View File

@@ -0,0 +1,797 @@
// Copyright (c) Tailscale Inc & AUTHORS
// SPDX-License-Identifier: BSD-3-Clause
package clientupdate
import (
"archive/tar"
"compress/gzip"
"fmt"
"io/fs"
"maps"
"os"
"path/filepath"
"slices"
"sort"
"strings"
"testing"
)
func TestUpdateDebianAptSourcesListBytes(t *testing.T) {
tests := []struct {
name string
toTrack string
in string
want string // empty means want no change
wantErr string
}{
{
name: "stable-to-unstable",
toTrack: UnstableTrack,
in: "# Tailscale packages for debian buster\ndeb https://pkgs.tailscale.com/stable/debian bullseye main\n",
want: "# Tailscale packages for debian buster\ndeb https://pkgs.tailscale.com/unstable/debian bullseye main\n",
},
{
name: "stable-unchanged",
toTrack: StableTrack,
in: "# Tailscale packages for debian buster\ndeb https://pkgs.tailscale.com/stable/debian bullseye main\n",
},
{
name: "if-both-stable-and-unstable-dont-change",
toTrack: StableTrack,
in: "# Tailscale packages for debian buster\n" +
"deb https://pkgs.tailscale.com/stable/debian bullseye main\n" +
"deb https://pkgs.tailscale.com/unstable/debian bullseye main\n",
},
{
name: "if-both-stable-and-unstable-dont-change-unstable",
toTrack: UnstableTrack,
in: "# Tailscale packages for debian buster\n" +
"deb https://pkgs.tailscale.com/stable/debian bullseye main\n" +
"deb https://pkgs.tailscale.com/unstable/debian bullseye main\n",
},
{
name: "signed-by-form",
toTrack: UnstableTrack,
in: "# Tailscale packages for ubuntu jammy\ndeb [signed-by=/usr/share/keyrings/tailscale-archive-keyring.gpg] https://pkgs.tailscale.com/stable/ubuntu jammy main\n",
want: "# Tailscale packages for ubuntu jammy\ndeb [signed-by=/usr/share/keyrings/tailscale-archive-keyring.gpg] https://pkgs.tailscale.com/unstable/ubuntu jammy main\n",
},
{
name: "unsupported-lines",
toTrack: UnstableTrack,
in: "# Tailscale packages for ubuntu jammy\ndeb [signed-by=/usr/share/keyrings/tailscale-archive-keyring.gpg] https://pkgs.tailscale.com/foobar/ubuntu jammy main\n",
wantErr: "unexpected/unsupported /etc/apt/sources.list.d/tailscale.list contents",
},
}
for _, tt := range tests {
t.Run(tt.name, func(t *testing.T) {
newContent, err := updateDebianAptSourcesListBytes([]byte(tt.in), tt.toTrack)
if err != nil {
if err.Error() != tt.wantErr {
t.Fatalf("error = %v; want %q", err, tt.wantErr)
}
return
}
if tt.wantErr != "" {
t.Fatalf("got no error; want %q", tt.wantErr)
}
var gotChange string
if string(newContent) != tt.in {
gotChange = string(newContent)
}
if gotChange != tt.want {
t.Errorf("wrong result\n got: %q\nwant: %q", gotChange, tt.want)
}
})
}
}
func TestUpdateYUMRepoTrack(t *testing.T) {
tests := []struct {
desc string
before string
track string
after string
rewrote bool
wantErr bool
}{
{
desc: "same track",
before: `
[tailscale-stable]
name=Tailscale stable
baseurl=https://pkgs.tailscale.com/stable/fedora/$basearch
enabled=1
type=rpm
repo_gpgcheck=1
gpgcheck=0
gpgkey=https://pkgs.tailscale.com/stable/fedora/repo.gpg
`,
track: StableTrack,
after: `
[tailscale-stable]
name=Tailscale stable
baseurl=https://pkgs.tailscale.com/stable/fedora/$basearch
enabled=1
type=rpm
repo_gpgcheck=1
gpgcheck=0
gpgkey=https://pkgs.tailscale.com/stable/fedora/repo.gpg
`,
},
{
desc: "change track",
before: `
[tailscale-stable]
name=Tailscale stable
baseurl=https://pkgs.tailscale.com/stable/fedora/$basearch
enabled=1
type=rpm
repo_gpgcheck=1
gpgcheck=0
gpgkey=https://pkgs.tailscale.com/stable/fedora/repo.gpg
`,
track: UnstableTrack,
after: `
[tailscale-unstable]
name=Tailscale unstable
baseurl=https://pkgs.tailscale.com/unstable/fedora/$basearch
enabled=1
type=rpm
repo_gpgcheck=1
gpgcheck=0
gpgkey=https://pkgs.tailscale.com/unstable/fedora/repo.gpg
`,
rewrote: true,
},
{
desc: "non-tailscale repo file",
before: `
[fedora]
name=Fedora $releasever - $basearch
#baseurl=http://download.example/pub/fedora/linux/releases/$releasever/Everything/$basearch/os/
metalink=https://mirrors.fedoraproject.org/metalink?repo=fedora-$releasever&arch=$basearch
enabled=1
countme=1
metadata_expire=7d
repo_gpgcheck=0
type=rpm
gpgcheck=1
gpgkey=file:///etc/pki/rpm-gpg/RPM-GPG-KEY-fedora-$releasever-$basearch
skip_if_unavailable=False
`,
track: StableTrack,
wantErr: true,
},
}
for _, tt := range tests {
t.Run(tt.desc, func(t *testing.T) {
path := filepath.Join(t.TempDir(), "tailscale.repo")
if err := os.WriteFile(path, []byte(tt.before), 0644); err != nil {
t.Fatal(err)
}
rewrote, err := updateYUMRepoTrack(path, tt.track)
if err == nil && tt.wantErr {
t.Fatal("got nil error, want non-nil")
}
if err != nil && !tt.wantErr {
t.Fatalf("got error %q, want nil", err)
}
if err != nil {
return
}
if rewrote != tt.rewrote {
t.Errorf("got rewrote flag %v, want %v", rewrote, tt.rewrote)
}
after, err := os.ReadFile(path)
if err != nil {
t.Fatal(err)
}
if string(after) != tt.after {
t.Errorf("got repo file after update:\n%swant:\n%s", after, tt.after)
}
})
}
}
func TestParseAlpinePackageVersion(t *testing.T) {
tests := []struct {
desc string
out string
want string
wantErr bool
}{
{
desc: "valid version",
out: `
tailscale-1.44.2-r0 description:
The easiest, most secure way to use WireGuard and 2FA
tailscale-1.44.2-r0 webpage:
https://tailscale.com/
tailscale-1.44.2-r0 installed size:
32 MiB
`,
want: "1.44.2",
},
{
desc: "wrong package output",
out: `
busybox-1.36.1-r0 description:
Size optimized toolbox of many common UNIX utilities
busybox-1.36.1-r0 webpage:
https://busybox.net/
busybox-1.36.1-r0 installed size:
924 KiB
`,
wantErr: true,
},
{
desc: "missing version",
out: `
tailscale description:
The easiest, most secure way to use WireGuard and 2FA
tailscale webpage:
https://tailscale.com/
tailscale installed size:
32 MiB
`,
wantErr: true,
},
{
desc: "empty output",
out: "",
wantErr: true,
},
}
for _, tt := range tests {
t.Run(tt.desc, func(t *testing.T) {
got, err := parseAlpinePackageVersion([]byte(tt.out))
if err == nil && tt.wantErr {
t.Fatalf("got nil error and version %q, want non-nil error", got)
}
if err != nil && !tt.wantErr {
t.Fatalf("got error: %q, want nil", err)
}
if got != tt.want {
t.Fatalf("got version: %q, want %q", got, tt.want)
}
})
}
}
func TestSynoArch(t *testing.T) {
tests := []struct {
goarch string
synoinfoUnique string
want string
wantErr bool
}{
{goarch: "amd64", synoinfoUnique: "synology_x86_224", want: "x86_64"},
{goarch: "arm64", synoinfoUnique: "synology_armv8_124", want: "armv8"},
{goarch: "386", synoinfoUnique: "synology_i686_415play", want: "i686"},
{goarch: "arm", synoinfoUnique: "synology_88f6281_213air", want: "88f6281"},
{goarch: "arm", synoinfoUnique: "synology_88f6282_413j", want: "88f6282"},
{goarch: "arm", synoinfoUnique: "synology_hi3535_NVR1218", want: "hi3535"},
{goarch: "arm", synoinfoUnique: "synology_alpine_1517", want: "alpine"},
{goarch: "arm", synoinfoUnique: "synology_armada370_216se", want: "armada370"},
{goarch: "arm", synoinfoUnique: "synology_armada375_115", want: "armada375"},
{goarch: "arm", synoinfoUnique: "synology_armada38x_419slim", want: "armada38x"},
{goarch: "arm", synoinfoUnique: "synology_armadaxp_RS815", want: "armadaxp"},
{goarch: "arm", synoinfoUnique: "synology_comcerto2k_414j", want: "comcerto2k"},
{goarch: "arm", synoinfoUnique: "synology_monaco_216play", want: "monaco"},
{goarch: "ppc64", synoinfoUnique: "synology_qoriq_413", wantErr: true},
}
for _, tt := range tests {
t.Run(fmt.Sprintf("%s-%s", tt.goarch, tt.synoinfoUnique), func(t *testing.T) {
synoinfoConfPath := filepath.Join(t.TempDir(), "synoinfo.conf")
if err := os.WriteFile(
synoinfoConfPath,
[]byte(fmt.Sprintf("unique=%q\n", tt.synoinfoUnique)),
0600,
); err != nil {
t.Fatal(err)
}
got, err := synoArch(tt.goarch, synoinfoConfPath)
if err != nil {
if !tt.wantErr {
t.Fatalf("got unexpected error %v", err)
}
return
}
if tt.wantErr {
t.Fatalf("got %q, expected an error", got)
}
if got != tt.want {
t.Errorf("got %q, want %q", got, tt.want)
}
})
}
}
func TestParseSynoinfo(t *testing.T) {
tests := []struct {
desc string
content string
want string
wantErr bool
}{
{
desc: "double-quoted",
content: `
company_title="Synology"
unique="synology_88f6281_213air"
`,
want: "88f6281",
},
{
desc: "single-quoted",
content: `
company_title="Synology"
unique='synology_88f6281_213air'
`,
want: "88f6281",
},
{
desc: "unquoted",
content: `
company_title="Synology"
unique=synology_88f6281_213air
`,
want: "88f6281",
},
{
desc: "missing unique",
content: `
company_title="Synology"
`,
wantErr: true,
},
{
desc: "empty unique",
content: `
company_title="Synology"
unique=
`,
wantErr: true,
},
{
desc: "empty unique double-quoted",
content: `
company_title="Synology"
unique=""
`,
wantErr: true,
},
{
desc: "empty unique single-quoted",
content: `
company_title="Synology"
unique=''
`,
wantErr: true,
},
{
desc: "malformed unique",
content: `
company_title="Synology"
unique="synology_88f6281"
`,
wantErr: true,
},
{
desc: "empty file",
content: ``,
wantErr: true,
},
{
desc: "empty lines and comments",
content: `
# In a file named synoinfo? Shocking!
company_title="Synology"
# unique= is_a_field_that_follows
unique="synology_88f6281_213air"
`,
want: "88f6281",
},
}
for _, tt := range tests {
t.Run(tt.desc, func(t *testing.T) {
synoinfoConfPath := filepath.Join(t.TempDir(), "synoinfo.conf")
if err := os.WriteFile(synoinfoConfPath, []byte(tt.content), 0600); err != nil {
t.Fatal(err)
}
got, err := parseSynoinfo(synoinfoConfPath)
if err != nil {
if !tt.wantErr {
t.Fatalf("got unexpected error %v", err)
}
return
}
if tt.wantErr {
t.Fatalf("got %q, expected an error", got)
}
if got != tt.want {
t.Errorf("got %q, want %q", got, tt.want)
}
})
}
}
func TestUnpackLinuxTarball(t *testing.T) {
oldBinaryPaths := binaryPaths
t.Cleanup(func() { binaryPaths = oldBinaryPaths })
tests := []struct {
desc string
tarball map[string]string
before map[string]string
after map[string]string
wantErr bool
}{
{
desc: "success",
before: map[string]string{
"tailscale": "v1",
"tailscaled": "v1",
},
tarball: map[string]string{
"/usr/bin/tailscale": "v2",
"/usr/bin/tailscaled": "v2",
},
after: map[string]string{
"tailscale": "v2",
"tailscaled": "v2",
},
},
{
desc: "don't touch unrelated files",
before: map[string]string{
"tailscale": "v1",
"tailscaled": "v1",
"foo": "bar",
},
tarball: map[string]string{
"/usr/bin/tailscale": "v2",
"/usr/bin/tailscaled": "v2",
},
after: map[string]string{
"tailscale": "v2",
"tailscaled": "v2",
"foo": "bar",
},
},
{
desc: "unmodified",
before: map[string]string{
"tailscale": "v1",
"tailscaled": "v1",
},
tarball: map[string]string{
"/usr/bin/tailscale": "v1",
"/usr/bin/tailscaled": "v1",
},
after: map[string]string{
"tailscale": "v1",
"tailscaled": "v1",
},
},
{
desc: "ignore extra tarball files",
before: map[string]string{
"tailscale": "v1",
"tailscaled": "v1",
},
tarball: map[string]string{
"/usr/bin/tailscale": "v2",
"/usr/bin/tailscaled": "v2",
"/systemd/tailscaled.service": "v2",
},
after: map[string]string{
"tailscale": "v2",
"tailscaled": "v2",
},
},
{
desc: "tarball missing tailscaled",
before: map[string]string{
"tailscale": "v1",
"tailscaled": "v1",
},
tarball: map[string]string{
"/usr/bin/tailscale": "v2",
},
after: map[string]string{
"tailscale": "v1",
"tailscale.new": "v2",
"tailscaled": "v1",
},
wantErr: true,
},
{
desc: "duplicate tailscale binary",
before: map[string]string{
"tailscale": "v1",
"tailscaled": "v1",
},
tarball: map[string]string{
"/usr/bin/tailscale": "v2",
"/usr/sbin/tailscale": "v2",
"/usr/bin/tailscaled": "v2",
},
after: map[string]string{
"tailscale": "v1",
"tailscale.new": "v2",
"tailscaled": "v1",
"tailscaled.new": "v2",
},
wantErr: true,
},
{
desc: "empty archive",
before: map[string]string{
"tailscale": "v1",
"tailscaled": "v1",
},
tarball: map[string]string{},
after: map[string]string{
"tailscale": "v1",
"tailscaled": "v1",
},
wantErr: true,
},
}
for _, tt := range tests {
t.Run(tt.desc, func(t *testing.T) {
// Swap out binaryPaths function to point at dummy file paths.
tmp := t.TempDir()
tailscalePath := filepath.Join(tmp, "tailscale")
tailscaledPath := filepath.Join(tmp, "tailscaled")
binaryPaths = func() (string, string, error) {
return tailscalePath, tailscaledPath, nil
}
for name, content := range tt.before {
if err := os.WriteFile(filepath.Join(tmp, name), []byte(content), 0755); err != nil {
t.Fatal(err)
}
}
tarPath := filepath.Join(tmp, "tailscale.tgz")
genTarball(t, tarPath, tt.tarball)
up := &Updater{Arguments: Arguments{Logf: t.Logf}}
err := up.unpackLinuxTarball(tarPath)
if err != nil {
if !tt.wantErr {
t.Fatalf("unexpected error: %v", err)
}
} else if tt.wantErr {
t.Fatalf("unpack succeeded, expected an error")
}
gotAfter := make(map[string]string)
err = filepath.WalkDir(tmp, func(path string, d fs.DirEntry, err error) error {
if err != nil {
return err
}
if d.Type().IsDir() {
return nil
}
if path == tarPath {
return nil
}
content, err := os.ReadFile(path)
if err != nil {
return err
}
path = filepath.ToSlash(path)
base := filepath.ToSlash(tmp)
gotAfter[strings.TrimPrefix(path, base+"/")] = string(content)
return nil
})
if err != nil {
t.Fatal(err)
}
if !maps.Equal(gotAfter, tt.after) {
t.Errorf("files after unpack: %+v, want %+v", gotAfter, tt.after)
}
})
}
}
func genTarball(t *testing.T, path string, files map[string]string) {
f, err := os.Create(path)
if err != nil {
t.Fatal(err)
}
defer f.Close()
gw := gzip.NewWriter(f)
defer gw.Close()
tw := tar.NewWriter(gw)
defer tw.Close()
for file, content := range files {
if err := tw.WriteHeader(&tar.Header{
Name: file,
Size: int64(len(content)),
Mode: 0755,
}); err != nil {
t.Fatal(err)
}
if _, err := tw.Write([]byte(content)); err != nil {
t.Fatal(err)
}
}
}
func TestWriteFileOverwrite(t *testing.T) {
path := filepath.Join(t.TempDir(), "test")
for i := 0; i < 2; i++ {
content := fmt.Sprintf("content %d", i)
if err := writeFile(strings.NewReader(content), path, 0600); err != nil {
t.Fatal(err)
}
got, err := os.ReadFile(path)
if err != nil {
t.Fatal(err)
}
if string(got) != content {
t.Errorf("got content: %q, want: %q", got, content)
}
}
}
func TestWriteFileSymlink(t *testing.T) {
// Test for a malicious symlink at the destination path.
// f2 points to f1 and writeFile(f2) should not end up overwriting f1.
tmp := t.TempDir()
f1 := filepath.Join(tmp, "f1")
if err := os.WriteFile(f1, []byte("old"), 0600); err != nil {
t.Fatal(err)
}
f2 := filepath.Join(tmp, "f2")
if err := os.Symlink(f1, f2); err != nil {
t.Fatal(err)
}
if err := writeFile(strings.NewReader("new"), f2, 0600); err != nil {
t.Errorf("writeFile(%q) failed: %v", f2, err)
}
want := map[string]string{
f1: "old",
f2: "new",
}
for f, content := range want {
got, err := os.ReadFile(f)
if err != nil {
t.Fatal(err)
}
if string(got) != content {
t.Errorf("%q: got content %q, want %q", f, got, content)
}
}
}
func TestCleanupOldDownloads(t *testing.T) {
tests := []struct {
desc string
before []string
symlinks map[string]string
glob string
after []string
}{
{
desc: "MSIs",
before: []string{
"MSICache/tailscale-1.0.0.msi",
"MSICache/tailscale-1.1.0.msi",
"MSICache/readme.txt",
},
glob: "MSICache/*.msi",
after: []string{
"MSICache/readme.txt",
},
},
{
desc: "SPKs",
before: []string{
"tmp/tailscale-update-1/tailscale-1.0.0.spk",
"tmp/tailscale-update-2/tailscale-1.1.0.spk",
"tmp/readme.txt",
"tmp/tailscale-update-3",
"tmp/tailscale-update-4/tailscale-1.3.0",
},
glob: "tmp/tailscale-update*/*.spk",
after: []string{
"tmp/readme.txt",
"tmp/tailscale-update-3",
"tmp/tailscale-update-4/tailscale-1.3.0",
},
},
{
desc: "empty-target",
before: []string{},
glob: "tmp/tailscale-update*/*.spk",
after: []string{},
},
{
desc: "keep-dirs",
before: []string{
"tmp/tailscale-update-1/tailscale-1.0.0.spk",
},
glob: "tmp/tailscale-update*",
after: []string{
"tmp/tailscale-update-1/tailscale-1.0.0.spk",
},
},
{
desc: "no-follow-symlinks",
before: []string{
"MSICache/tailscale-1.0.0.msi",
"MSICache/tailscale-1.1.0.msi",
"MSICache/readme.txt",
},
symlinks: map[string]string{
"MSICache/tailscale-1.3.0.msi": "MSICache/tailscale-1.0.0.msi",
"MSICache/tailscale-1.4.0.msi": "MSICache/readme.txt",
},
glob: "MSICache/*.msi",
after: []string{
"MSICache/tailscale-1.3.0.msi",
"MSICache/tailscale-1.4.0.msi",
"MSICache/readme.txt",
},
},
}
for _, tt := range tests {
t.Run(tt.desc, func(t *testing.T) {
dir := t.TempDir()
for _, p := range tt.before {
if err := os.MkdirAll(filepath.Join(dir, filepath.Dir(p)), 0700); err != nil {
t.Fatal(err)
}
if err := os.WriteFile(filepath.Join(dir, p), []byte(tt.desc), 0600); err != nil {
t.Fatal(err)
}
}
for from, to := range tt.symlinks {
if err := os.Symlink(filepath.Join(dir, to), filepath.Join(dir, from)); err != nil {
t.Fatal(err)
}
}
up := &Updater{Arguments: Arguments{Logf: t.Logf}}
up.cleanupOldDownloads(filepath.Join(dir, tt.glob))
var after []string
if err := filepath.WalkDir(dir, func(path string, d fs.DirEntry, err error) error {
if !d.IsDir() {
after = append(after, strings.TrimPrefix(filepath.ToSlash(path), filepath.ToSlash(dir)+"/"))
}
return nil
}); err != nil {
t.Fatal(err)
}
sort.Strings(after)
sort.Strings(tt.after)
if !slices.Equal(after, tt.after) {
t.Errorf("got files after cleanup: %q, want: %q", after, tt.after)
}
})
}
}

View File

@@ -0,0 +1,57 @@
// Copyright (c) Tailscale Inc & AUTHORS
// SPDX-License-Identifier: BSD-3-Clause
// Windows-specific stuff that can't go in clientupdate.go because it needs
// x/sys/windows.
package clientupdate
import (
"os/exec"
"os/user"
"path/filepath"
"syscall"
"golang.org/x/sys/windows"
"tailscale.com/util/winutil"
"tailscale.com/util/winutil/authenticode"
)
func init() {
markTempFileFunc = markTempFileWindows
verifyAuthenticode = verifyTailscale
launchTailscaleAsWinGUIUser = launchTailscaleAsGUIUser
}
func markTempFileWindows(name string) error {
name16 := windows.StringToUTF16Ptr(name)
return windows.MoveFileEx(name16, nil, windows.MOVEFILE_DELAY_UNTIL_REBOOT)
}
const certSubjectTailscale = "Tailscale Inc."
func verifyTailscale(path string) error {
return authenticode.Verify(path, certSubjectTailscale)
}
func launchTailscaleAsGUIUser(exePath string) error {
exePath = filepath.Join(filepath.Dir(exePath), "tailscale-ipn.exe")
var token windows.Token
if u, err := user.Current(); err == nil && u.Name == "SYSTEM" {
sessionID := winutil.WTSGetActiveConsoleSessionId()
if sessionID != 0xFFFFFFFF {
if err := windows.WTSQueryUserToken(sessionID, &token); err != nil {
return err
}
defer token.Close()
}
}
cmd := exec.Command(exePath)
cmd.SysProcAttr = &syscall.SysProcAttr{
Token: syscall.Token(token),
HideWindow: true,
}
return cmd.Start()
}

View File

@@ -0,0 +1,486 @@
// Copyright (c) Tailscale Inc & AUTHORS
// SPDX-License-Identifier: BSD-3-Clause
// Package distsign implements signature and validation of arbitrary
// distributable files.
//
// There are 3 parties in this exchange:
// - builder, which creates files, signs them with signing keys and publishes
// to server
// - server, which distributes public signing keys, files and signatures
// - client, which downloads files and signatures from server, and validates
// the signatures
//
// There are 2 types of keys:
// - signing keys, that sign individual distributable files on the builder
// - root keys, that sign signing keys and are kept offline
//
// root keys -(sign)-> signing keys -(sign)-> files
//
// All keys are asymmetric Ed25519 key pairs.
//
// The server serves static files under some known prefix. The kinds of files are:
// - distsign.pub - bundle of PEM-encoded public signing keys
// - distsign.pub.sig - signature of distsign.pub using one of the root keys
// - $file - any distributable file
// - $file.sig - signature of $file using any of the signing keys
//
// The root public keys are baked into the client software at compile time.
// These keys are long-lived and prove the validity of current signing keys
// from distsign.pub. To rotate root keys, a new client release must be
// published, they are not rotated dynamically. There are multiple root keys in
// different locations specifically to allow this rotation without using the
// discarded root key for any new signatures.
//
// The signing public keys are fetched by the client dynamically before every
// download and can be rotated more readily, assuming that most deployed
// clients trust the root keys used to issue fresh signing keys.
package distsign
import (
"context"
"crypto/ed25519"
"crypto/rand"
"encoding/binary"
"encoding/pem"
"errors"
"fmt"
"hash"
"io"
"log"
"net/http"
"net/url"
"os"
"time"
"github.com/hdevalence/ed25519consensus"
"golang.org/x/crypto/blake2s"
"tailscale.com/net/tshttpproxy"
"tailscale.com/types/logger"
"tailscale.com/util/httpm"
"tailscale.com/util/must"
)
const (
pemTypeRootPrivate = "ROOT PRIVATE KEY"
pemTypeRootPublic = "ROOT PUBLIC KEY"
pemTypeSigningPrivate = "SIGNING PRIVATE KEY"
pemTypeSigningPublic = "SIGNING PUBLIC KEY"
downloadSizeLimit = 1 << 29 // 512MB
signingKeysSizeLimit = 1 << 20 // 1MB
signatureSizeLimit = ed25519.SignatureSize
)
// RootKey is a root key used to sign signing keys.
type RootKey struct {
k ed25519.PrivateKey
}
// GenerateRootKey generates a new root key pair and encodes it as PEM.
func GenerateRootKey() (priv, pub []byte, err error) {
pub, priv, err = ed25519.GenerateKey(rand.Reader)
if err != nil {
return nil, nil, err
}
return pem.EncodeToMemory(&pem.Block{
Type: pemTypeRootPrivate,
Bytes: []byte(priv),
}), pem.EncodeToMemory(&pem.Block{
Type: pemTypeRootPublic,
Bytes: []byte(pub),
}), nil
}
// ParseRootKey parses the PEM-encoded private root key. The key must be in the
// same format as returned by GenerateRootKey.
func ParseRootKey(privKey []byte) (*RootKey, error) {
k, err := parsePrivateKey(privKey, pemTypeRootPrivate)
if err != nil {
return nil, fmt.Errorf("failed to parse root key: %w", err)
}
return &RootKey{k: k}, nil
}
// SignSigningKeys signs the bundle of public signing keys. The bundle must be
// a sequence of PEM blocks joined with newlines.
func (r *RootKey) SignSigningKeys(pubBundle []byte) ([]byte, error) {
if _, err := ParseSigningKeyBundle(pubBundle); err != nil {
return nil, err
}
return ed25519.Sign(r.k, pubBundle), nil
}
// SigningKey is a signing key used to sign packages.
type SigningKey struct {
k ed25519.PrivateKey
}
// GenerateSigningKey generates a new signing key pair and encodes it as PEM.
func GenerateSigningKey() (priv, pub []byte, err error) {
pub, priv, err = ed25519.GenerateKey(rand.Reader)
if err != nil {
return nil, nil, err
}
return pem.EncodeToMemory(&pem.Block{
Type: pemTypeSigningPrivate,
Bytes: []byte(priv),
}), pem.EncodeToMemory(&pem.Block{
Type: pemTypeSigningPublic,
Bytes: []byte(pub),
}), nil
}
// ParseSigningKey parses the PEM-encoded private signing key. The key must be
// in the same format as returned by GenerateSigningKey.
func ParseSigningKey(privKey []byte) (*SigningKey, error) {
k, err := parsePrivateKey(privKey, pemTypeSigningPrivate)
if err != nil {
return nil, fmt.Errorf("failed to parse root key: %w", err)
}
return &SigningKey{k: k}, nil
}
// SignPackageHash signs the hash and the length of a package. Use PackageHash
// to compute the inputs.
func (s *SigningKey) SignPackageHash(hash []byte, len int64) ([]byte, error) {
if len <= 0 {
return nil, fmt.Errorf("package length must be positive, got %d", len)
}
msg := binary.LittleEndian.AppendUint64(hash, uint64(len))
return ed25519.Sign(s.k, msg), nil
}
// PackageHash is a hash.Hash that counts the number of bytes written. Use it
// to get the hash and length inputs to SigningKey.SignPackageHash.
type PackageHash struct {
hash.Hash
len int64
}
// NewPackageHash returns an initialized PackageHash using BLAKE2s.
func NewPackageHash() *PackageHash {
h, err := blake2s.New256(nil)
if err != nil {
// Should never happen with a nil key passed to blake2s.
panic(err)
}
return &PackageHash{Hash: h}
}
func (ph *PackageHash) Write(b []byte) (int, error) {
ph.len += int64(len(b))
return ph.Hash.Write(b)
}
// Reset the PackageHash to its initial state.
func (ph *PackageHash) Reset() {
ph.len = 0
ph.Hash.Reset()
}
// Len returns the total number of bytes written.
func (ph *PackageHash) Len() int64 { return ph.len }
// Client downloads and validates files from a distribution server.
type Client struct {
logf logger.Logf
roots []ed25519.PublicKey
pkgsAddr *url.URL
}
// NewClient returns a new client for distribution server located at pkgsAddr,
// and uses embedded root keys from the roots/ subdirectory of this package.
func NewClient(logf logger.Logf, pkgsAddr string) (*Client, error) {
if logf == nil {
logf = log.Printf
}
u, err := url.Parse(pkgsAddr)
if err != nil {
return nil, fmt.Errorf("invalid pkgsAddr %q: %w", pkgsAddr, err)
}
return &Client{logf: logf, roots: roots(), pkgsAddr: u}, nil
}
func (c *Client) url(path string) string {
return c.pkgsAddr.JoinPath(path).String()
}
// Download fetches a file at path srcPath from pkgsAddr passed in NewClient.
// The file is downloaded to dstPath and its signature is validated using the
// embedded root keys. Download returns an error if anything goes wrong with
// the actual file download or with signature validation.
func (c *Client) Download(ctx context.Context, srcPath, dstPath string) error {
// Always fetch a fresh signing key.
sigPub, err := c.signingKeys()
if err != nil {
return err
}
srcURL := c.url(srcPath)
sigURL := srcURL + ".sig"
c.logf("Downloading %q", srcURL)
dstPathUnverified := dstPath + ".unverified"
hash, len, err := c.download(ctx, srcURL, dstPathUnverified, downloadSizeLimit)
if err != nil {
return err
}
c.logf("Downloading %q", sigURL)
sig, err := fetch(sigURL, signatureSizeLimit)
if err != nil {
// Best-effort clean up of downloaded package.
os.Remove(dstPathUnverified)
return err
}
msg := binary.LittleEndian.AppendUint64(hash, uint64(len))
if !VerifyAny(sigPub, msg, sig) {
// Best-effort clean up of downloaded package.
os.Remove(dstPathUnverified)
return fmt.Errorf("signature %q for file %q does not validate with the current release signing key; either you are under attack, or attempting to download an old version of Tailscale which was signed with an older signing key", sigURL, srcURL)
}
c.logf("Signature OK")
if err := os.Rename(dstPathUnverified, dstPath); err != nil {
return fmt.Errorf("failed to move %q to %q after signature validation", dstPathUnverified, dstPath)
}
return nil
}
// ValidateLocalBinary fetches the latest signature associated with the binary
// at srcURLPath and uses it to validate the file located on disk via
// localFilePath. ValidateLocalBinary returns an error if anything goes wrong
// with the signature download or with signature validation.
func (c *Client) ValidateLocalBinary(srcURLPath, localFilePath string) error {
// Always fetch a fresh signing key.
sigPub, err := c.signingKeys()
if err != nil {
return err
}
srcURL := c.url(srcURLPath)
sigURL := srcURL + ".sig"
localFile, err := os.Open(localFilePath)
if err != nil {
return err
}
defer localFile.Close()
h := NewPackageHash()
_, err = io.Copy(h, localFile)
if err != nil {
return err
}
hash, hashLen := h.Sum(nil), h.Len()
c.logf("Downloading %q", sigURL)
sig, err := fetch(sigURL, signatureSizeLimit)
if err != nil {
return err
}
msg := binary.LittleEndian.AppendUint64(hash, uint64(hashLen))
if !VerifyAny(sigPub, msg, sig) {
return fmt.Errorf("signature %q for file %q does not validate with the current release signing key; either you are under attack, or attempting to download an old version of Tailscale which was signed with an older signing key", sigURL, localFilePath)
}
c.logf("Signature OK")
return nil
}
// signingKeys fetches current signing keys from the server and validates them
// against the roots. Should be called before validation of any downloaded file
// to get the fresh keys.
func (c *Client) signingKeys() ([]ed25519.PublicKey, error) {
keyURL := c.url("distsign.pub")
sigURL := keyURL + ".sig"
raw, err := fetch(keyURL, signingKeysSizeLimit)
if err != nil {
return nil, err
}
sig, err := fetch(sigURL, signatureSizeLimit)
if err != nil {
return nil, err
}
if !VerifyAny(c.roots, raw, sig) {
return nil, fmt.Errorf("signature %q for key %q does not validate with any known root key; either you are under attack, or running a very old version of Tailscale with outdated root keys", sigURL, keyURL)
}
keys, err := ParseSigningKeyBundle(raw)
if err != nil {
return nil, fmt.Errorf("cannot parse signing key bundle from %q: %w", keyURL, err)
}
return keys, nil
}
// fetch reads the response body from url into memory, up to limit bytes.
func fetch(url string, limit int64) ([]byte, error) {
resp, err := http.Get(url)
if err != nil {
return nil, err
}
defer resp.Body.Close()
return io.ReadAll(io.LimitReader(resp.Body, limit))
}
// download writes the response body of url into a local file at dst, up to
// limit bytes. On success, the returned value is a BLAKE2s hash of the file.
func (c *Client) download(ctx context.Context, url, dst string, limit int64) ([]byte, int64, error) {
tr := http.DefaultTransport.(*http.Transport).Clone()
tr.Proxy = tshttpproxy.ProxyFromEnvironment
defer tr.CloseIdleConnections()
hc := &http.Client{Transport: tr}
quickCtx, cancel := context.WithTimeout(ctx, 30*time.Second)
defer cancel()
headReq := must.Get(http.NewRequestWithContext(quickCtx, httpm.HEAD, url, nil))
res, err := hc.Do(headReq)
if err != nil {
return nil, 0, err
}
if res.StatusCode != http.StatusOK {
return nil, 0, fmt.Errorf("HEAD %q: %v", url, res.Status)
}
if res.ContentLength <= 0 {
return nil, 0, fmt.Errorf("HEAD %q: unexpected Content-Length %v", url, res.ContentLength)
}
c.logf("Download size: %v", res.ContentLength)
dlReq := must.Get(http.NewRequestWithContext(ctx, httpm.GET, url, nil))
dlRes, err := hc.Do(dlReq)
if err != nil {
return nil, 0, err
}
defer dlRes.Body.Close()
// TODO(bradfitz): resume from existing partial file on disk
if dlRes.StatusCode != http.StatusOK {
return nil, 0, fmt.Errorf("GET %q: %v", url, dlRes.Status)
}
of, err := os.Create(dst)
if err != nil {
return nil, 0, err
}
defer of.Close()
pw := &progressWriter{total: res.ContentLength, logf: c.logf}
h := NewPackageHash()
n, err := io.Copy(io.MultiWriter(of, h, pw), io.LimitReader(dlRes.Body, limit))
if err != nil {
return nil, n, err
}
if n != res.ContentLength {
return nil, n, fmt.Errorf("GET %q: downloaded %v, want %v", url, n, res.ContentLength)
}
if err := dlRes.Body.Close(); err != nil {
return nil, n, err
}
if err := of.Close(); err != nil {
return nil, n, err
}
pw.print()
return h.Sum(nil), h.Len(), nil
}
type progressWriter struct {
done int64
total int64
lastPrint time.Time
logf logger.Logf
}
func (pw *progressWriter) Write(p []byte) (n int, err error) {
pw.done += int64(len(p))
if time.Since(pw.lastPrint) > 2*time.Second {
pw.print()
}
return len(p), nil
}
func (pw *progressWriter) print() {
pw.lastPrint = time.Now()
pw.logf("Downloaded %v/%v (%.1f%%)", pw.done, pw.total, float64(pw.done)/float64(pw.total)*100)
}
func parsePrivateKey(data []byte, typeTag string) (ed25519.PrivateKey, error) {
b, rest := pem.Decode(data)
if b == nil {
return nil, errors.New("failed to decode PEM data")
}
if len(rest) > 0 {
return nil, errors.New("trailing PEM data")
}
if b.Type != typeTag {
return nil, fmt.Errorf("PEM type is %q, want %q", b.Type, typeTag)
}
if len(b.Bytes) != ed25519.PrivateKeySize {
return nil, errors.New("private key has incorrect length for an Ed25519 private key")
}
return ed25519.PrivateKey(b.Bytes), nil
}
// ParseSigningKeyBundle parses the bundle of PEM-encoded public signing keys.
func ParseSigningKeyBundle(bundle []byte) ([]ed25519.PublicKey, error) {
return parsePublicKeyBundle(bundle, pemTypeSigningPublic)
}
// ParseRootKeyBundle parses the bundle of PEM-encoded public root keys.
func ParseRootKeyBundle(bundle []byte) ([]ed25519.PublicKey, error) {
return parsePublicKeyBundle(bundle, pemTypeRootPublic)
}
func parsePublicKeyBundle(bundle []byte, typeTag string) ([]ed25519.PublicKey, error) {
var keys []ed25519.PublicKey
for len(bundle) > 0 {
pub, rest, err := parsePublicKey(bundle, typeTag)
if err != nil {
return nil, err
}
keys = append(keys, pub)
bundle = rest
}
if len(keys) == 0 {
return nil, errors.New("no signing keys found in the bundle")
}
return keys, nil
}
func parseSinglePublicKey(data []byte, typeTag string) (ed25519.PublicKey, error) {
pub, rest, err := parsePublicKey(data, typeTag)
if err != nil {
return nil, err
}
if len(rest) > 0 {
return nil, errors.New("trailing PEM data")
}
return pub, err
}
func parsePublicKey(data []byte, typeTag string) (pub ed25519.PublicKey, rest []byte, retErr error) {
b, rest := pem.Decode(data)
if b == nil {
return nil, nil, errors.New("failed to decode PEM data")
}
if b.Type != typeTag {
return nil, nil, fmt.Errorf("PEM type is %q, want %q", b.Type, typeTag)
}
if len(b.Bytes) != ed25519.PublicKeySize {
return nil, nil, errors.New("public key has incorrect length for an Ed25519 public key")
}
return ed25519.PublicKey(b.Bytes), rest, nil
}
// VerifyAny verifies whether sig is valid for msg using any of the keys.
// VerifyAny will panic if any of the keys have the wrong size for Ed25519.
func VerifyAny(keys []ed25519.PublicKey, msg, sig []byte) bool {
for _, k := range keys {
if ed25519consensus.Verify(k, msg, sig) {
return true
}
}
return false
}

View File

@@ -0,0 +1,585 @@
// Copyright (c) Tailscale Inc & AUTHORS
// SPDX-License-Identifier: BSD-3-Clause
package distsign
import (
"bytes"
"context"
"crypto/ed25519"
"net/http"
"net/http/httptest"
"net/url"
"os"
"path/filepath"
"strings"
"testing"
"golang.org/x/crypto/blake2s"
)
func TestDownload(t *testing.T) {
srv := newTestServer(t)
c := srv.client(t)
tests := []struct {
desc string
before func(*testing.T)
src string
want []byte
wantErr bool
}{
{
desc: "missing file",
before: func(*testing.T) {},
src: "hello",
wantErr: true,
},
{
desc: "success",
before: func(*testing.T) {
srv.addSigned("hello", []byte("world"))
},
src: "hello",
want: []byte("world"),
},
{
desc: "no signature",
before: func(*testing.T) {
srv.add("hello", []byte("world"))
},
src: "hello",
wantErr: true,
},
{
desc: "bad signature",
before: func(*testing.T) {
srv.add("hello", []byte("world"))
srv.add("hello.sig", []byte("potato"))
},
src: "hello",
wantErr: true,
},
{
desc: "signed with untrusted key",
before: func(t *testing.T) {
srv.add("hello", []byte("world"))
srv.add("hello.sig", newSigningKeyPair(t).sign([]byte("world")))
},
src: "hello",
wantErr: true,
},
{
desc: "signed with root key",
before: func(t *testing.T) {
srv.add("hello", []byte("world"))
srv.add("hello.sig", ed25519.Sign(srv.roots[0].k, []byte("world")))
},
src: "hello",
wantErr: true,
},
{
desc: "bad signing key signature",
before: func(t *testing.T) {
srv.add("distsign.pub.sig", []byte("potato"))
srv.addSigned("hello", []byte("world"))
},
src: "hello",
wantErr: true,
},
}
for _, tt := range tests {
t.Run(tt.desc, func(t *testing.T) {
srv.reset()
tt.before(t)
dst := filepath.Join(t.TempDir(), tt.src)
t.Cleanup(func() {
os.Remove(dst)
})
err := c.Download(context.Background(), tt.src, dst)
if err != nil {
if tt.wantErr {
return
}
t.Fatalf("unexpected error from Download(%q): %v", tt.src, err)
}
if tt.wantErr {
t.Fatalf("Download(%q) succeeded, expected an error", tt.src)
}
got, err := os.ReadFile(dst)
if err != nil {
t.Fatal(err)
}
if !bytes.Equal(tt.want, got) {
t.Errorf("Download(%q): got %q, want %q", tt.src, got, tt.want)
}
})
}
}
func TestValidateLocalBinary(t *testing.T) {
srv := newTestServer(t)
c := srv.client(t)
tests := []struct {
desc string
before func(*testing.T)
src string
wantErr bool
}{
{
desc: "missing file",
before: func(*testing.T) {},
src: "hello",
wantErr: true,
},
{
desc: "success",
before: func(*testing.T) {
srv.addSigned("hello", []byte("world"))
},
src: "hello",
},
{
desc: "contents changed",
before: func(*testing.T) {
srv.addSigned("hello", []byte("new world"))
},
src: "hello",
wantErr: true,
},
{
desc: "no signature",
before: func(*testing.T) {
srv.add("hello", []byte("world"))
},
src: "hello",
wantErr: true,
},
{
desc: "bad signature",
before: func(*testing.T) {
srv.add("hello", []byte("world"))
srv.add("hello.sig", []byte("potato"))
},
src: "hello",
wantErr: true,
},
{
desc: "signed with untrusted key",
before: func(t *testing.T) {
srv.add("hello", []byte("world"))
srv.add("hello.sig", newSigningKeyPair(t).sign([]byte("world")))
},
src: "hello",
wantErr: true,
},
{
desc: "signed with root key",
before: func(t *testing.T) {
srv.add("hello", []byte("world"))
srv.add("hello.sig", ed25519.Sign(srv.roots[0].k, []byte("world")))
},
src: "hello",
wantErr: true,
},
{
desc: "bad signing key signature",
before: func(t *testing.T) {
srv.add("distsign.pub.sig", []byte("potato"))
srv.addSigned("hello", []byte("world"))
},
src: "hello",
wantErr: true,
},
}
for _, tt := range tests {
t.Run(tt.desc, func(t *testing.T) {
srv.reset()
// First just do a successful Download.
want := []byte("world")
srv.addSigned("hello", want)
dst := filepath.Join(t.TempDir(), tt.src)
err := c.Download(context.Background(), tt.src, dst)
if err != nil {
t.Fatalf("unexpected error from Download(%q): %v", tt.src, err)
}
got, err := os.ReadFile(dst)
if err != nil {
t.Fatal(err)
}
if !bytes.Equal(want, got) {
t.Errorf("Download(%q): got %q, want %q", tt.src, got, want)
}
// Now we reset srv with the test case and validate against the local dst.
srv.reset()
tt.before(t)
err = c.ValidateLocalBinary(tt.src, dst)
if err != nil {
if tt.wantErr {
return
}
t.Fatalf("unexpected error from ValidateLocalBinary(%q): %v", tt.src, err)
}
if tt.wantErr {
t.Fatalf("ValidateLocalBinary(%q) succeeded, expected an error", tt.src)
}
})
}
}
func TestRotateRoot(t *testing.T) {
srv := newTestServer(t)
c1 := srv.client(t)
ctx := context.Background()
srv.addSigned("hello", []byte("world"))
if err := c1.Download(ctx, "hello", filepath.Join(t.TempDir(), "hello")); err != nil {
t.Fatalf("Download failed on a fresh server: %v", err)
}
// Remove first root and replace it with a new key.
srv.roots = append(srv.roots[1:], newRootKeyPair(t))
// Old client can still download files because it still trusts the old
// root key.
if err := c1.Download(ctx, "hello", filepath.Join(t.TempDir(), "hello")); err != nil {
t.Fatalf("Download failed after root rotation on old client: %v", err)
}
// New client should fail download because current signing key is signed by
// the revoked root that new client doesn't trust.
c2 := srv.client(t)
if err := c2.Download(ctx, "hello", filepath.Join(t.TempDir(), "hello")); err == nil {
t.Fatalf("Download succeeded on new client, but signing key is signed with revoked root key")
}
// Re-sign signing key with another valid root that client still trusts.
srv.resignSigningKeys()
// Both old and new clients should now be able to download.
//
// Note: we don't need to re-sign the "hello" file because signing key
// didn't change (only signing key's signature).
if err := c1.Download(ctx, "hello", filepath.Join(t.TempDir(), "hello")); err != nil {
t.Fatalf("Download failed after root rotation on old client with re-signed signing key: %v", err)
}
if err := c2.Download(ctx, "hello", filepath.Join(t.TempDir(), "hello")); err != nil {
t.Fatalf("Download failed after root rotation on new client with re-signed signing key: %v", err)
}
}
func TestRotateSigning(t *testing.T) {
srv := newTestServer(t)
c := srv.client(t)
ctx := context.Background()
srv.addSigned("hello", []byte("world"))
if err := c.Download(ctx, "hello", filepath.Join(t.TempDir(), "hello")); err != nil {
t.Fatalf("Download failed on a fresh server: %v", err)
}
// Replace signing key but don't publish it yet.
srv.sign = append(srv.sign, newSigningKeyPair(t))
if err := c.Download(ctx, "hello", filepath.Join(t.TempDir(), "hello")); err != nil {
t.Fatalf("Download failed after new signing key added but before publishing it: %v", err)
}
// Publish new signing key bundle with both keys.
srv.resignSigningKeys()
if err := c.Download(ctx, "hello", filepath.Join(t.TempDir(), "hello")); err != nil {
t.Fatalf("Download failed after new signing key was published: %v", err)
}
// Re-sign the "hello" file with new signing key.
srv.add("hello.sig", srv.sign[1].sign([]byte("world")))
if err := c.Download(ctx, "hello", filepath.Join(t.TempDir(), "hello")); err != nil {
t.Fatalf("Download failed after re-signing with new signing key: %v", err)
}
// Drop the old signing key.
srv.sign = srv.sign[1:]
srv.resignSigningKeys()
if err := c.Download(ctx, "hello", filepath.Join(t.TempDir(), "hello")); err != nil {
t.Fatalf("Download failed after removing old signing key: %v", err)
}
// Add another key and re-sign the file with it *before* publishing.
srv.sign = append(srv.sign, newSigningKeyPair(t))
srv.add("hello.sig", srv.sign[1].sign([]byte("world")))
if err := c.Download(ctx, "hello", filepath.Join(t.TempDir(), "hello")); err == nil {
t.Fatalf("Download succeeded when signed with a not-yet-published signing key")
}
// Fix this by publishing the new key.
srv.resignSigningKeys()
if err := c.Download(ctx, "hello", filepath.Join(t.TempDir(), "hello")); err != nil {
t.Fatalf("Download failed after publishing new signing key: %v", err)
}
}
func TestParseRootKey(t *testing.T) {
tests := []struct {
desc string
generate func() ([]byte, []byte, error)
wantErr bool
}{
{
desc: "valid",
generate: GenerateRootKey,
},
{
desc: "signing",
generate: GenerateSigningKey,
wantErr: true,
},
{
desc: "nil",
generate: func() ([]byte, []byte, error) { return nil, nil, nil },
wantErr: true,
},
{
desc: "invalid PEM tag",
generate: func() ([]byte, []byte, error) {
priv, pub, err := GenerateRootKey()
priv = bytes.Replace(priv, []byte("ROOT "), nil, -1)
return priv, pub, err
},
wantErr: true,
},
{
desc: "not PEM",
generate: func() ([]byte, []byte, error) { return []byte("s3cr3t"), nil, nil },
wantErr: true,
},
}
for _, tt := range tests {
t.Run(tt.desc, func(t *testing.T) {
priv, _, err := tt.generate()
if err != nil {
t.Fatal(err)
}
r, err := ParseRootKey(priv)
if err != nil {
if tt.wantErr {
return
}
t.Fatalf("unexpected error: %v", err)
}
if tt.wantErr {
t.Fatal("expected non-nil error")
}
if r == nil {
t.Errorf("got nil error and nil RootKey")
}
})
}
}
func TestParseSigningKey(t *testing.T) {
tests := []struct {
desc string
generate func() ([]byte, []byte, error)
wantErr bool
}{
{
desc: "valid",
generate: GenerateSigningKey,
},
{
desc: "root",
generate: GenerateRootKey,
wantErr: true,
},
{
desc: "nil",
generate: func() ([]byte, []byte, error) { return nil, nil, nil },
wantErr: true,
},
{
desc: "invalid PEM tag",
generate: func() ([]byte, []byte, error) {
priv, pub, err := GenerateSigningKey()
priv = bytes.Replace(priv, []byte("SIGNING "), nil, -1)
return priv, pub, err
},
wantErr: true,
},
{
desc: "not PEM",
generate: func() ([]byte, []byte, error) { return []byte("s3cr3t"), nil, nil },
wantErr: true,
},
}
for _, tt := range tests {
t.Run(tt.desc, func(t *testing.T) {
priv, _, err := tt.generate()
if err != nil {
t.Fatal(err)
}
r, err := ParseSigningKey(priv)
if err != nil {
if tt.wantErr {
return
}
t.Fatalf("unexpected error: %v", err)
}
if tt.wantErr {
t.Fatal("expected non-nil error")
}
if r == nil {
t.Errorf("got nil error and nil SigningKey")
}
})
}
}
type testServer struct {
roots []rootKeyPair
sign []signingKeyPair
files map[string][]byte
srv *httptest.Server
}
func newTestServer(t *testing.T) *testServer {
var roots []rootKeyPair
for i := 0; i < 3; i++ {
roots = append(roots, newRootKeyPair(t))
}
ts := &testServer{
roots: roots,
sign: []signingKeyPair{newSigningKeyPair(t)},
}
ts.reset()
ts.srv = httptest.NewServer(ts)
t.Cleanup(ts.srv.Close)
return ts
}
func (s *testServer) client(t *testing.T) *Client {
roots := make([]ed25519.PublicKey, 0, len(s.roots))
for _, r := range s.roots {
pub, err := parseSinglePublicKey(r.pubRaw, pemTypeRootPublic)
if err != nil {
t.Fatalf("parsePublicKey: %v", err)
}
roots = append(roots, pub)
}
u, err := url.Parse(s.srv.URL)
if err != nil {
t.Fatal(err)
}
return &Client{
logf: t.Logf,
roots: roots,
pkgsAddr: u,
}
}
func (s *testServer) ServeHTTP(w http.ResponseWriter, r *http.Request) {
path := strings.TrimPrefix(r.URL.Path, "/")
data, ok := s.files[path]
if !ok {
http.NotFound(w, r)
return
}
w.Write(data)
}
func (s *testServer) addSigned(name string, data []byte) {
s.files[name] = data
s.files[name+".sig"] = s.sign[0].sign(data)
}
func (s *testServer) add(name string, data []byte) {
s.files[name] = data
}
func (s *testServer) reset() {
s.files = make(map[string][]byte)
s.resignSigningKeys()
}
func (s *testServer) resignSigningKeys() {
var pubs [][]byte
for _, k := range s.sign {
pubs = append(pubs, k.pubRaw)
}
bundle := bytes.Join(pubs, []byte("\n"))
sig := s.roots[0].sign(bundle)
s.files["distsign.pub"] = bundle
s.files["distsign.pub.sig"] = sig
}
type rootKeyPair struct {
*RootKey
keyPair
}
func newRootKeyPair(t *testing.T) rootKeyPair {
privRaw, pubRaw, err := GenerateRootKey()
if err != nil {
t.Fatalf("GenerateRootKey: %v", err)
}
kp := keyPair{
privRaw: privRaw,
pubRaw: pubRaw,
}
priv, err := parsePrivateKey(kp.privRaw, pemTypeRootPrivate)
if err != nil {
t.Fatalf("parsePrivateKey: %v", err)
}
return rootKeyPair{
RootKey: &RootKey{k: priv},
keyPair: kp,
}
}
func (s rootKeyPair) sign(bundle []byte) []byte {
sig, err := s.SignSigningKeys(bundle)
if err != nil {
panic(err)
}
return sig
}
type signingKeyPair struct {
*SigningKey
keyPair
}
func newSigningKeyPair(t *testing.T) signingKeyPair {
privRaw, pubRaw, err := GenerateSigningKey()
if err != nil {
t.Fatalf("GenerateSigningKey: %v", err)
}
kp := keyPair{
privRaw: privRaw,
pubRaw: pubRaw,
}
priv, err := parsePrivateKey(kp.privRaw, pemTypeSigningPrivate)
if err != nil {
t.Fatalf("parsePrivateKey: %v", err)
}
return signingKeyPair{
SigningKey: &SigningKey{k: priv},
keyPair: kp,
}
}
func (s signingKeyPair) sign(blob []byte) []byte {
hash := blake2s.Sum256(blob)
sig, err := s.SignPackageHash(hash[:], int64(len(blob)))
if err != nil {
panic(err)
}
return sig
}
type keyPair struct {
privRaw []byte
pubRaw []byte
}

View File

@@ -0,0 +1,54 @@
// Copyright (c) Tailscale Inc & AUTHORS
// SPDX-License-Identifier: BSD-3-Clause
package distsign
import (
"crypto/ed25519"
"embed"
"errors"
"fmt"
"path"
"path/filepath"
"sync"
)
//go:embed roots
var rootsFS embed.FS
var roots = sync.OnceValue(func() []ed25519.PublicKey {
roots, err := parseRoots()
if err != nil {
panic(err)
}
return roots
})
func parseRoots() ([]ed25519.PublicKey, error) {
files, err := rootsFS.ReadDir("roots")
if err != nil {
return nil, err
}
var keys []ed25519.PublicKey
for _, f := range files {
if !f.Type().IsRegular() {
continue
}
if filepath.Ext(f.Name()) != ".pem" {
continue
}
raw, err := rootsFS.ReadFile(path.Join("roots", f.Name()))
if err != nil {
return nil, err
}
key, err := parseSinglePublicKey(raw, pemTypeRootPublic)
if err != nil {
return nil, fmt.Errorf("parsing root key %q: %w", f.Name(), err)
}
keys = append(keys, key)
}
if len(keys) == 0 {
return nil, errors.New("no embedded root keys, please check clientupdate/distsign/roots/")
}
return keys, nil
}

View File

@@ -0,0 +1,3 @@
-----BEGIN ROOT PUBLIC KEY-----
Psrabv2YNiEDhPlnLVSMtB5EKACm7zxvKxfvYD4i7X8=
-----END ROOT PUBLIC KEY-----

View File

@@ -0,0 +1,3 @@
-----BEGIN ROOT PUBLIC KEY-----
ZjjKhUHBtLNRSO1dhOTjrXJGJ8lDe1594WM2XDuheVQ=
-----END ROOT PUBLIC KEY-----

View File

@@ -0,0 +1,16 @@
// Copyright (c) Tailscale Inc & AUTHORS
// SPDX-License-Identifier: BSD-3-Clause
package distsign
import "testing"
func TestParseRoots(t *testing.T) {
roots, err := parseRoots()
if err != nil {
t.Fatal(err)
}
if len(roots) == 0 {
t.Error("parseRoots returned no root keys")
}
}

View File

@@ -0,0 +1,37 @@
// Copyright (c) Tailscale Inc & AUTHORS
// SPDX-License-Identifier: BSD-3-Clause
package clientupdate
import (
"context"
"errors"
"fmt"
"github.com/coreos/go-systemd/v22/dbus"
)
func restartSystemdUnit(ctx context.Context) error {
c, err := dbus.NewWithContext(ctx)
if err != nil {
// Likely not a systemd-managed distro.
return errors.ErrUnsupported
}
defer c.Close()
if err := c.ReloadContext(ctx); err != nil {
return fmt.Errorf("failed to reload tailsacled.service: %w", err)
}
ch := make(chan string, 1)
if _, err := c.RestartUnitContext(ctx, "tailscaled.service", "replace", ch); err != nil {
return fmt.Errorf("failed to restart tailsacled.service: %w", err)
}
select {
case res := <-ch:
if res != "done" {
return fmt.Errorf("systemd service restart failed with result %q", res)
}
case <-ctx.Done():
return ctx.Err()
}
return nil
}

Some files were not shown because too many files have changed in this diff Show More