Skip to content

Commit a98b8e7

Browse files
committed
Merge branch 'release-branch/1.86' into cpierre/coreweave-1.86
2 parents 290409f + db392ae commit a98b8e7

File tree

385 files changed

+31083
-6027
lines changed

Some content is hidden

Large Commits have some content hidden by default. Use the searchbox below for content that may be hidden.

385 files changed

+31083
-6027
lines changed

.github/workflows/natlab-integrationtest.yml

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -3,7 +3,7 @@
33
name: "natlab-integrationtest"
44

55
concurrency:
6-
group: ${{ github.workflow }}-$${{ github.head_ref || github.run_id }}
6+
group: ${{ github.workflow }}-${{ github.head_ref || github.run_id }}
77
cancel-in-progress: true
88

99
on:
Lines changed: 31 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,31 @@
1+
name: request-dataplane-review
2+
3+
on:
4+
pull_request:
5+
branches:
6+
- "*"
7+
paths:
8+
- ".github/workflows/request-dataplane-review.yml"
9+
- "**/*derp*"
10+
- "**/derp*/**"
11+
12+
jobs:
13+
request-dataplane-review:
14+
name: Request Dataplane Review
15+
runs-on: ubuntu-latest
16+
steps:
17+
- name: Check out code
18+
uses: actions/checkout@11bd71901bbe5b1630ceea73d27597364c9af683 # v4.2.2
19+
- name: Get access token
20+
uses: actions/create-github-app-token@df432ceedc7162793a195dd1713ff69aefc7379e # v2.0.6
21+
id: generate-token
22+
with:
23+
# Get token for app: https://github.com/apps/change-visibility-bot
24+
app-id: ${{ secrets.VISIBILITY_BOT_APP_ID }}
25+
private-key: ${{ secrets.VISIBILITY_BOT_APP_PRIVATE_KEY }}
26+
- name: Add reviewers
27+
env:
28+
GH_TOKEN: ${{ steps.generate-token.outputs.token }}
29+
url: ${{ github.event.pull_request.html_url }}
30+
run: |
31+
gh pr edit "$url" --add-reviewer tailscale/dataplane

.gitignore

Lines changed: 3 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -49,3 +49,6 @@ client/web/build/assets
4949
*.xcworkspacedata
5050
/tstest/tailmac/bin
5151
/tstest/tailmac/build
52+
53+
# Ignore personal IntelliJ settings
54+
.idea/

Dockerfile

Lines changed: 9 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -7,6 +7,15 @@
77
# Tailscale images are currently built using https://github.com/tailscale/mkctr,
88
# and the build script can be found in ./build_docker.sh.
99
#
10+
# If you want to build local images for testing, you can use make.
11+
#
12+
# To build a Tailscale image and push to the local docker registry:
13+
#
14+
# $ REPO=local/tailscale TAGS=v0.0.1 PLATFORM=local make publishdevimage
15+
#
16+
# To build a Tailscale image and push to a remote docker registry:
17+
#
18+
# $ REPO=<your-registry>/<your-repo>/tailscale TAGS=v0.0.1 make publishdevimage
1019
#
1120
# This Dockerfile includes all the tailscale binaries.
1221
#

Makefile

Lines changed: 33 additions & 23 deletions
Original file line numberDiff line numberDiff line change
@@ -22,7 +22,8 @@ updatedeps: ## Update depaware deps
2222
tailscale.com/cmd/tailscale \
2323
tailscale.com/cmd/derper \
2424
tailscale.com/cmd/k8s-operator \
25-
tailscale.com/cmd/stund
25+
tailscale.com/cmd/stund \
26+
tailscale.com/cmd/tsidp
2627
PATH="$$(./tool/go env GOROOT)/bin:$$PATH" ./tool/go run github.com/tailscale/depaware --update -goos=linux,darwin,windows,android,ios --internal \
2728
tailscale.com/tsnet
2829

@@ -34,7 +35,8 @@ depaware: ## Run depaware checks
3435
tailscale.com/cmd/tailscale \
3536
tailscale.com/cmd/derper \
3637
tailscale.com/cmd/k8s-operator \
37-
tailscale.com/cmd/stund
38+
tailscale.com/cmd/stund \
39+
tailscale.com/cmd/tsidp
3840
PATH="$$(./tool/go env GOROOT)/bin:$$PATH" ./tool/go run github.com/tailscale/depaware --check --goos=linux,darwin,windows,android,ios --internal \
3941
tailscale.com/tsnet
4042

@@ -62,7 +64,7 @@ buildmultiarchimage: ## Build (and optionally push) multiarch docker image
6264
check: staticcheck vet depaware buildwindows build386 buildlinuxarm buildwasm ## Perform basic checks and compilation tests
6365

6466
staticcheck: ## Run staticcheck.io checks
65-
./tool/go run honnef.co/go/tools/cmd/staticcheck -- $$(./tool/go list ./... | grep -v tempfork)
67+
./tool/go run honnef.co/go/tools/cmd/staticcheck -- $$(./tool/go run ./tool/listpkgs --ignore-3p ./...)
6668

6769
kube-generate-all: kube-generate-deepcopy ## Refresh generated files for Tailscale Kubernetes Operator
6870
./tool/go generate ./cmd/k8s-operator
@@ -90,34 +92,42 @@ pushspk: spk ## Push and install synology package on ${SYNO_HOST} host
9092
scp tailscale.spk root@${SYNO_HOST}:
9193
ssh root@${SYNO_HOST} /usr/syno/bin/synopkg install tailscale.spk
9294

93-
publishdevimage: ## Build and publish tailscale image to location specified by ${REPO}
94-
@test -n "${REPO}" || (echo "REPO=... required; e.g. REPO=ghcr.io/${USER}/tailscale" && exit 1)
95-
@test "${REPO}" != "tailscale/tailscale" || (echo "REPO=... must not be tailscale/tailscale" && exit 1)
96-
@test "${REPO}" != "ghcr.io/tailscale/tailscale" || (echo "REPO=... must not be ghcr.io/tailscale/tailscale" && exit 1)
97-
@test "${REPO}" != "tailscale/k8s-operator" || (echo "REPO=... must not be tailscale/k8s-operator" && exit 1)
98-
@test "${REPO}" != "ghcr.io/tailscale/k8s-operator" || (echo "REPO=... must not be ghcr.io/tailscale/k8s-operator" && exit 1)
95+
.PHONY: check-image-repo
96+
check-image-repo:
97+
@if [ -z "$(REPO)" ]; then \
98+
echo "REPO=... required; e.g. REPO=ghcr.io/$$USER/tailscale" >&2; \
99+
exit 1; \
100+
fi
101+
@for repo in tailscale/tailscale ghcr.io/tailscale/tailscale \
102+
tailscale/k8s-operator ghcr.io/tailscale/k8s-operator \
103+
tailscale/k8s-nameserver ghcr.io/tailscale/k8s-nameserver \
104+
tailscale/tsidp ghcr.io/tailscale/tsidp \
105+
tailscale/k8s-proxy ghcr.io/tailscale/k8s-proxy; do \
106+
if [ "$(REPO)" = "$$repo" ]; then \
107+
echo "REPO=... must not be $$repo" >&2; \
108+
exit 1; \
109+
fi; \
110+
done
111+
112+
publishdevimage: check-image-repo ## Build and publish tailscale image to location specified by ${REPO}
99113
TAGS="${TAGS}" REPOS=${REPO} PLATFORM=${PLATFORM} PUSH=true TARGET=client ./build_docker.sh
100114

101-
publishdevoperator: ## Build and publish k8s-operator image to location specified by ${REPO}
102-
@test -n "${REPO}" || (echo "REPO=... required; e.g. REPO=ghcr.io/${USER}/tailscale" && exit 1)
103-
@test "${REPO}" != "tailscale/tailscale" || (echo "REPO=... must not be tailscale/tailscale" && exit 1)
104-
@test "${REPO}" != "ghcr.io/tailscale/tailscale" || (echo "REPO=... must not be ghcr.io/tailscale/tailscale" && exit 1)
105-
@test "${REPO}" != "tailscale/k8s-operator" || (echo "REPO=... must not be tailscale/k8s-operator" && exit 1)
106-
@test "${REPO}" != "ghcr.io/tailscale/k8s-operator" || (echo "REPO=... must not be ghcr.io/tailscale/k8s-operator" && exit 1)
115+
publishdevoperator: check-image-repo ## Build and publish k8s-operator image to location specified by ${REPO}
107116
TAGS="${TAGS}" REPOS=${REPO} PLATFORM=${PLATFORM} PUSH=true TARGET=k8s-operator ./build_docker.sh
108117

109-
publishdevnameserver: ## Build and publish k8s-nameserver image to location specified by ${REPO}
110-
@test -n "${REPO}" || (echo "REPO=... required; e.g. REPO=ghcr.io/${USER}/tailscale" && exit 1)
111-
@test "${REPO}" != "tailscale/tailscale" || (echo "REPO=... must not be tailscale/tailscale" && exit 1)
112-
@test "${REPO}" != "ghcr.io/tailscale/tailscale" || (echo "REPO=... must not be ghcr.io/tailscale/tailscale" && exit 1)
113-
@test "${REPO}" != "tailscale/k8s-nameserver" || (echo "REPO=... must not be tailscale/k8s-nameserver" && exit 1)
114-
@test "${REPO}" != "ghcr.io/tailscale/k8s-nameserver" || (echo "REPO=... must not be ghcr.io/tailscale/k8s-nameserver" && exit 1)
118+
publishdevnameserver: check-image-repo ## Build and publish k8s-nameserver image to location specified by ${REPO}
115119
TAGS="${TAGS}" REPOS=${REPO} PLATFORM=${PLATFORM} PUSH=true TARGET=k8s-nameserver ./build_docker.sh
116120

121+
publishdevtsidp: check-image-repo ## Build and publish tsidp image to location specified by ${REPO}
122+
TAGS="${TAGS}" REPOS=${REPO} PLATFORM=${PLATFORM} PUSH=true TARGET=tsidp ./build_docker.sh
123+
124+
publishdevproxy: check-image-repo ## Build and publish k8s-proxy image to location specified by ${REPO}
125+
TAGS="${TAGS}" REPOS=${REPO} PLATFORM=${PLATFORM} PUSH=true TARGET=k8s-proxy ./build_docker.sh
126+
117127
.PHONY: sshintegrationtest
118128
sshintegrationtest: ## Run the SSH integration tests in various Docker containers
119-
@GOOS=linux GOARCH=amd64 ./tool/go test -tags integrationtest -c ./ssh/tailssh -o ssh/tailssh/testcontainers/tailssh.test && \
120-
GOOS=linux GOARCH=amd64 ./tool/go build -o ssh/tailssh/testcontainers/tailscaled ./cmd/tailscaled && \
129+
@GOOS=linux GOARCH=amd64 CGO_ENABLED=0 ./tool/go test -tags integrationtest -c ./ssh/tailssh -o ssh/tailssh/testcontainers/tailssh.test && \
130+
GOOS=linux GOARCH=amd64 CGO_ENABLED=0 ./tool/go build -o ssh/tailssh/testcontainers/tailscaled ./cmd/tailscaled && \
121131
echo "Testing on ubuntu:focal" && docker build --build-arg="BASE=ubuntu:focal" -t ssh-ubuntu-focal ssh/tailssh/testcontainers && \
122132
echo "Testing on ubuntu:jammy" && docker build --build-arg="BASE=ubuntu:jammy" -t ssh-ubuntu-jammy ssh/tailssh/testcontainers && \
123133
echo "Testing on ubuntu:noble" && docker build --build-arg="BASE=ubuntu:noble" -t ssh-ubuntu-noble ssh/tailssh/testcontainers && \

VERSION.txt

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -1 +1 @@
1-
1.84.1
1+
1.86.5

atomicfile/atomicfile.go

Lines changed: 5 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -48,5 +48,9 @@ func WriteFile(filename string, data []byte, perm os.FileMode) (err error) {
4848
if err := f.Close(); err != nil {
4949
return err
5050
}
51-
return rename(tmpName, filename)
51+
return Rename(tmpName, filename)
5252
}
53+
54+
// Rename srcFile to dstFile, similar to [os.Rename] but preserving file
55+
// attributes and ACLs on Windows.
56+
func Rename(srcFile, dstFile string) error { return rename(srcFile, dstFile) }

build_docker.sh

Lines changed: 46 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,6 +6,16 @@
66
# hash of this repository as produced by ./cmd/mkversion.
77
# This is the image build mechanim used to build the official Tailscale
88
# container images.
9+
#
10+
# If you want to build local images for testing, you can use make, which provides few convenience wrappers around this script.
11+
#
12+
# To build a Tailscale image and push to the local docker registry:
13+
14+
# $ REPO=local/tailscale TAGS=v0.0.1 PLATFORM=local make publishdevimage
15+
#
16+
# To build a Tailscale image and push to a remote docker registry:
17+
#
18+
# $ REPO=<your-registry>/<your-repo>/tailscale TAGS=v0.0.1 make publishdevimage
919

1020
set -eu
1121

@@ -90,6 +100,42 @@ case "$TARGET" in
90100
--annotations="${ANNOTATIONS}" \
91101
/usr/local/bin/k8s-nameserver
92102
;;
103+
tsidp)
104+
DEFAULT_REPOS="tailscale/tsidp"
105+
REPOS="${REPOS:-${DEFAULT_REPOS}}"
106+
go run github.com/tailscale/mkctr \
107+
--gopaths="tailscale.com/cmd/tsidp:/usr/local/bin/tsidp" \
108+
--ldflags=" \
109+
-X tailscale.com/version.longStamp=${VERSION_LONG} \
110+
-X tailscale.com/version.shortStamp=${VERSION_SHORT} \
111+
-X tailscale.com/version.gitCommitStamp=${VERSION_GIT_HASH}" \
112+
--base="${BASE}" \
113+
--tags="${TAGS}" \
114+
--gotags="ts_package_container" \
115+
--repos="${REPOS}" \
116+
--push="${PUSH}" \
117+
--target="${PLATFORM}" \
118+
--annotations="${ANNOTATIONS}" \
119+
/usr/local/bin/tsidp
120+
;;
121+
k8s-proxy)
122+
DEFAULT_REPOS="tailscale/k8s-proxy"
123+
REPOS="${REPOS:-${DEFAULT_REPOS}}"
124+
go run github.com/tailscale/mkctr \
125+
--gopaths="tailscale.com/cmd/k8s-proxy:/usr/local/bin/k8s-proxy" \
126+
--ldflags=" \
127+
-X tailscale.com/version.longStamp=${VERSION_LONG} \
128+
-X tailscale.com/version.shortStamp=${VERSION_SHORT} \
129+
-X tailscale.com/version.gitCommitStamp=${VERSION_GIT_HASH}" \
130+
--base="${BASE}" \
131+
--tags="${TAGS}" \
132+
--gotags="ts_kube,ts_package_container" \
133+
--repos="${REPOS}" \
134+
--push="${PUSH}" \
135+
--target="${PLATFORM}" \
136+
--annotations="${ANNOTATIONS}" \
137+
/usr/local/bin/k8s-proxy
138+
;;
93139
*)
94140
echo "unknown target: $TARGET"
95141
exit 1

chirp/chirp_test.go

Lines changed: 1 addition & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -1,5 +1,6 @@
11
// Copyright (c) Tailscale Inc & AUTHORS
22
// SPDX-License-Identifier: BSD-3-Clause
3+
34
package chirp
45

56
import (

client/local/local.go

Lines changed: 83 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -1,12 +1,11 @@
11
// Copyright (c) Tailscale Inc & AUTHORS
22
// SPDX-License-Identifier: BSD-3-Clause
33

4-
//go:build go1.22
5-
64
// Package local contains a Go client for the Tailscale LocalAPI.
75
package local
86

97
import (
8+
"bufio"
109
"bytes"
1110
"cmp"
1211
"context"
@@ -16,6 +15,7 @@ import (
1615
"errors"
1716
"fmt"
1817
"io"
18+
"iter"
1919
"net"
2020
"net/http"
2121
"net/http/httptrace"
@@ -42,6 +42,7 @@ import (
4242
"tailscale.com/types/dnstype"
4343
"tailscale.com/types/key"
4444
"tailscale.com/types/tkatype"
45+
"tailscale.com/util/eventbus"
4546
"tailscale.com/util/syspolicy/setting"
4647
)
4748

@@ -397,6 +398,23 @@ func (lc *Client) IncrementCounter(ctx context.Context, name string, delta int)
397398
return err
398399
}
399400

401+
// IncrementGauge increments the value of a Tailscale daemon's gauge
402+
// metric by the given delta. If the metric has yet to exist, a new gauge
403+
// metric is created and initialized to delta. The delta value can be negative.
404+
func (lc *Client) IncrementGauge(ctx context.Context, name string, delta int) error {
405+
type metricUpdate struct {
406+
Name string `json:"name"`
407+
Type string `json:"type"`
408+
Value int `json:"value"` // amount to increment by
409+
}
410+
_, err := lc.send(ctx, "POST", "/localapi/v0/upload-client-metrics", 200, jsonBody([]metricUpdate{{
411+
Name: name,
412+
Type: "gauge",
413+
Value: delta,
414+
}}))
415+
return err
416+
}
417+
400418
// TailDaemonLogs returns a stream the Tailscale daemon's logs as they arrive.
401419
// Close the context to stop the stream.
402420
func (lc *Client) TailDaemonLogs(ctx context.Context) (io.Reader, error) {
@@ -414,6 +432,50 @@ func (lc *Client) TailDaemonLogs(ctx context.Context) (io.Reader, error) {
414432
return res.Body, nil
415433
}
416434

435+
// EventBusGraph returns a graph of active publishers and subscribers in the eventbus
436+
// as a [eventbus.DebugTopics]
437+
func (lc *Client) EventBusGraph(ctx context.Context) ([]byte, error) {
438+
return lc.get200(ctx, "/localapi/v0/debug-bus-graph")
439+
}
440+
441+
// StreamBusEvents returns an iterator of Tailscale bus events as they arrive.
442+
// Each pair is a valid event and a nil error, or a zero event a non-nil error.
443+
// In case of error, the iterator ends after the pair reporting the error.
444+
// Iteration stops if ctx ends.
445+
func (lc *Client) StreamBusEvents(ctx context.Context) iter.Seq2[eventbus.DebugEvent, error] {
446+
return func(yield func(eventbus.DebugEvent, error) bool) {
447+
req, err := http.NewRequestWithContext(ctx, "GET",
448+
"http://"+apitype.LocalAPIHost+"/localapi/v0/debug-bus-events", nil)
449+
if err != nil {
450+
yield(eventbus.DebugEvent{}, err)
451+
return
452+
}
453+
res, err := lc.doLocalRequestNiceError(req)
454+
if err != nil {
455+
yield(eventbus.DebugEvent{}, err)
456+
return
457+
}
458+
if res.StatusCode != http.StatusOK {
459+
yield(eventbus.DebugEvent{}, errors.New(res.Status))
460+
return
461+
}
462+
defer res.Body.Close()
463+
dec := json.NewDecoder(bufio.NewReader(res.Body))
464+
for {
465+
var evt eventbus.DebugEvent
466+
if err := dec.Decode(&evt); err == io.EOF {
467+
return
468+
} else if err != nil {
469+
yield(eventbus.DebugEvent{}, err)
470+
return
471+
}
472+
if !yield(evt, nil) {
473+
return
474+
}
475+
}
476+
}
477+
}
478+
417479
// Pprof returns a pprof profile of the Tailscale daemon.
418480
func (lc *Client) Pprof(ctx context.Context, pprofType string, sec int) ([]byte, error) {
419481
var secArg string
@@ -788,6 +850,25 @@ func (lc *Client) CheckUDPGROForwarding(ctx context.Context) error {
788850
return nil
789851
}
790852

853+
// CheckReversePathFiltering asks the local Tailscale daemon whether strict
854+
// reverse path filtering is enabled, which would break exit node usage on Linux.
855+
func (lc *Client) CheckReversePathFiltering(ctx context.Context) error {
856+
body, err := lc.get200(ctx, "/localapi/v0/check-reverse-path-filtering")
857+
if err != nil {
858+
return err
859+
}
860+
var jres struct {
861+
Warning string
862+
}
863+
if err := json.Unmarshal(body, &jres); err != nil {
864+
return fmt.Errorf("invalid JSON from check-reverse-path-filtering: %w", err)
865+
}
866+
if jres.Warning != "" {
867+
return errors.New(jres.Warning)
868+
}
869+
return nil
870+
}
871+
791872
// SetUDPGROForwarding enables UDP GRO forwarding for the main interface of this
792873
// node. This can be done to improve performance of tailnet nodes acting as exit
793874
// nodes or subnet routers.

0 commit comments

Comments
 (0)