mirror of
https://github.com/tailscale/tailscale.git
synced 2025-04-16 03:31:39 +00:00
all: add Node.HomeDERP int, phase out "127.3.3.40:$region" hack [capver 111]
This deprecates the old "DERP string" packing a DERP region ID into an IP:port of 127.3.3.40:$REGION_ID and just uses an integer, like PeerChange.DERPRegion does. We still support servers sending the old form; they're converted to the new form internally right when they're read off the network. Updates #14636 Change-Id: I9427ec071f02a2c6d75ccb0fcbf0ecff9f19f26f Signed-off-by: Brad Fitzpatrick <bradfitz@tailscale.com>
This commit is contained in:
parent
66269dc934
commit
2fc4455e6d
@ -280,7 +280,7 @@ func TestConnMemoryOverhead(t *testing.T) {
|
||||
growthTotal := int64(ms.HeapAlloc) - int64(ms0.HeapAlloc)
|
||||
growthEach := float64(growthTotal) / float64(num)
|
||||
t.Logf("Alloced %v bytes, %.2f B/each", growthTotal, growthEach)
|
||||
const max = 2000
|
||||
const max = 2048
|
||||
if growthEach > max {
|
||||
t.Errorf("allocated more than expected; want max %v bytes/each", max)
|
||||
}
|
||||
|
@ -7,7 +7,6 @@ import (
|
||||
"cmp"
|
||||
"context"
|
||||
"encoding/json"
|
||||
"fmt"
|
||||
"maps"
|
||||
"net"
|
||||
"reflect"
|
||||
@ -166,6 +165,7 @@ func (ms *mapSession) HandleNonKeepAliveMapResponse(ctx context.Context, resp *t
|
||||
|
||||
// For responses that mutate the self node, check for updated nodeAttrs.
|
||||
if resp.Node != nil {
|
||||
upgradeNode(resp.Node)
|
||||
if DevKnob.StripCaps() {
|
||||
resp.Node.Capabilities = nil
|
||||
resp.Node.CapMap = nil
|
||||
@ -181,6 +181,13 @@ func (ms *mapSession) HandleNonKeepAliveMapResponse(ctx context.Context, resp *t
|
||||
ms.controlKnobs.UpdateFromNodeAttributes(resp.Node.CapMap)
|
||||
}
|
||||
|
||||
for _, p := range resp.Peers {
|
||||
upgradeNode(p)
|
||||
}
|
||||
for _, p := range resp.PeersChanged {
|
||||
upgradeNode(p)
|
||||
}
|
||||
|
||||
// Call Node.InitDisplayNames on any changed nodes.
|
||||
initDisplayNames(cmp.Or(resp.Node.View(), ms.lastNode), resp)
|
||||
|
||||
@ -216,6 +223,26 @@ func (ms *mapSession) HandleNonKeepAliveMapResponse(ctx context.Context, resp *t
|
||||
return nil
|
||||
}
|
||||
|
||||
// upgradeNode upgrades Node fields from the server into the modern forms
|
||||
// not using deprecated fields.
|
||||
func upgradeNode(n *tailcfg.Node) {
|
||||
if n == nil {
|
||||
return
|
||||
}
|
||||
if n.LegacyDERPString != "" {
|
||||
if n.HomeDERP == 0 {
|
||||
ip, portStr, err := net.SplitHostPort(n.LegacyDERPString)
|
||||
if ip == tailcfg.DerpMagicIP && err == nil {
|
||||
port, err := strconv.Atoi(portStr)
|
||||
if err == nil {
|
||||
n.HomeDERP = port
|
||||
}
|
||||
}
|
||||
}
|
||||
n.LegacyDERPString = ""
|
||||
}
|
||||
}
|
||||
|
||||
func (ms *mapSession) tryHandleIncrementally(res *tailcfg.MapResponse) bool {
|
||||
if ms.controlKnobs != nil && ms.controlKnobs.DisableDeltaUpdates.Load() {
|
||||
return false
|
||||
@ -443,7 +470,7 @@ func (ms *mapSession) updatePeersStateFromResponse(resp *tailcfg.MapResponse) (s
|
||||
stats.changed++
|
||||
mut := vp.AsStruct()
|
||||
if pc.DERPRegion != 0 {
|
||||
mut.DERP = fmt.Sprintf("%s:%v", tailcfg.DerpMagicIP, pc.DERPRegion)
|
||||
mut.HomeDERP = pc.DERPRegion
|
||||
patchDERPRegion.Add(1)
|
||||
}
|
||||
if pc.Cap != 0 {
|
||||
@ -631,17 +658,13 @@ func peerChangeDiff(was tailcfg.NodeView, n *tailcfg.Node) (_ *tailcfg.PeerChang
|
||||
if !views.SliceEqual(was.Endpoints(), views.SliceOf(n.Endpoints)) {
|
||||
pc().Endpoints = slices.Clone(n.Endpoints)
|
||||
}
|
||||
case "DERP":
|
||||
if was.DERP() != n.DERP {
|
||||
ip, portStr, err := net.SplitHostPort(n.DERP)
|
||||
if err != nil || ip != "127.3.3.40" {
|
||||
return nil, false
|
||||
}
|
||||
port, err := strconv.Atoi(portStr)
|
||||
if err != nil || port < 1 || port > 65535 {
|
||||
return nil, false
|
||||
}
|
||||
pc().DERPRegion = port
|
||||
case "LegacyDERPString":
|
||||
if was.LegacyDERPString() != "" || n.LegacyDERPString != "" {
|
||||
panic("unexpected; caller should've already called upgradeNode")
|
||||
}
|
||||
case "HomeDERP":
|
||||
if was.HomeDERP() != n.HomeDERP {
|
||||
pc().DERPRegion = n.HomeDERP
|
||||
}
|
||||
case "Hostinfo":
|
||||
if !was.Hostinfo().Valid() && !n.Hostinfo.Valid() {
|
||||
|
@ -50,9 +50,9 @@ func TestUpdatePeersStateFromResponse(t *testing.T) {
|
||||
n.LastSeen = &t
|
||||
}
|
||||
}
|
||||
withDERP := func(d string) func(*tailcfg.Node) {
|
||||
withDERP := func(regionID int) func(*tailcfg.Node) {
|
||||
return func(n *tailcfg.Node) {
|
||||
n.DERP = d
|
||||
n.HomeDERP = regionID
|
||||
}
|
||||
}
|
||||
withEP := func(ep string) func(*tailcfg.Node) {
|
||||
@ -189,14 +189,14 @@ func TestUpdatePeersStateFromResponse(t *testing.T) {
|
||||
},
|
||||
{
|
||||
name: "ep_change_derp",
|
||||
prev: peers(n(1, "foo", withDERP("127.3.3.40:3"))),
|
||||
prev: peers(n(1, "foo", withDERP(3))),
|
||||
mapRes: &tailcfg.MapResponse{
|
||||
PeersChangedPatch: []*tailcfg.PeerChange{{
|
||||
NodeID: 1,
|
||||
DERPRegion: 4,
|
||||
}},
|
||||
},
|
||||
want: peers(n(1, "foo", withDERP("127.3.3.40:4"))),
|
||||
want: peers(n(1, "foo", withDERP(4))),
|
||||
wantStats: updateStats{changed: 1},
|
||||
},
|
||||
{
|
||||
@ -213,19 +213,19 @@ func TestUpdatePeersStateFromResponse(t *testing.T) {
|
||||
},
|
||||
{
|
||||
name: "ep_change_udp_2",
|
||||
prev: peers(n(1, "foo", withDERP("127.3.3.40:3"), withEP("1.2.3.4:111"))),
|
||||
prev: peers(n(1, "foo", withDERP(3), withEP("1.2.3.4:111"))),
|
||||
mapRes: &tailcfg.MapResponse{
|
||||
PeersChangedPatch: []*tailcfg.PeerChange{{
|
||||
NodeID: 1,
|
||||
Endpoints: eps("1.2.3.4:56"),
|
||||
}},
|
||||
},
|
||||
want: peers(n(1, "foo", withDERP("127.3.3.40:3"), withEP("1.2.3.4:56"))),
|
||||
want: peers(n(1, "foo", withDERP(3), withEP("1.2.3.4:56"))),
|
||||
wantStats: updateStats{changed: 1},
|
||||
},
|
||||
{
|
||||
name: "ep_change_both",
|
||||
prev: peers(n(1, "foo", withDERP("127.3.3.40:3"), withEP("1.2.3.4:111"))),
|
||||
prev: peers(n(1, "foo", withDERP(3), withEP("1.2.3.4:111"))),
|
||||
mapRes: &tailcfg.MapResponse{
|
||||
PeersChangedPatch: []*tailcfg.PeerChange{{
|
||||
NodeID: 1,
|
||||
@ -233,7 +233,7 @@ func TestUpdatePeersStateFromResponse(t *testing.T) {
|
||||
Endpoints: eps("1.2.3.4:56"),
|
||||
}},
|
||||
},
|
||||
want: peers(n(1, "foo", withDERP("127.3.3.40:2"), withEP("1.2.3.4:56"))),
|
||||
want: peers(n(1, "foo", withDERP(2), withEP("1.2.3.4:56"))),
|
||||
wantStats: updateStats{changed: 1},
|
||||
},
|
||||
{
|
||||
@ -744,8 +744,8 @@ func TestPeerChangeDiff(t *testing.T) {
|
||||
},
|
||||
{
|
||||
name: "patch-derp",
|
||||
a: &tailcfg.Node{ID: 1, DERP: "127.3.3.40:1"},
|
||||
b: &tailcfg.Node{ID: 1, DERP: "127.3.3.40:2"},
|
||||
a: &tailcfg.Node{ID: 1, HomeDERP: 1},
|
||||
b: &tailcfg.Node{ID: 1, HomeDERP: 2},
|
||||
want: &tailcfg.PeerChange{NodeID: 1, DERPRegion: 2},
|
||||
},
|
||||
{
|
||||
@ -929,23 +929,23 @@ func TestPatchifyPeersChanged(t *testing.T) {
|
||||
mr0: &tailcfg.MapResponse{
|
||||
Node: &tailcfg.Node{Name: "foo.bar.ts.net."},
|
||||
Peers: []*tailcfg.Node{
|
||||
{ID: 1, DERP: "127.3.3.40:1", Hostinfo: hi},
|
||||
{ID: 2, DERP: "127.3.3.40:2", Hostinfo: hi},
|
||||
{ID: 3, DERP: "127.3.3.40:3", Hostinfo: hi},
|
||||
{ID: 1, HomeDERP: 1, Hostinfo: hi},
|
||||
{ID: 2, HomeDERP: 2, Hostinfo: hi},
|
||||
{ID: 3, HomeDERP: 3, Hostinfo: hi},
|
||||
},
|
||||
},
|
||||
mr1: &tailcfg.MapResponse{
|
||||
PeersChanged: []*tailcfg.Node{
|
||||
{ID: 1, DERP: "127.3.3.40:11", Hostinfo: hi},
|
||||
{ID: 1, HomeDERP: 11, Hostinfo: hi},
|
||||
{ID: 2, StableID: "other-change", Hostinfo: hi},
|
||||
{ID: 3, DERP: "127.3.3.40:33", Hostinfo: hi},
|
||||
{ID: 4, DERP: "127.3.3.40:4", Hostinfo: hi},
|
||||
{ID: 3, HomeDERP: 33, Hostinfo: hi},
|
||||
{ID: 4, HomeDERP: 4, Hostinfo: hi},
|
||||
},
|
||||
},
|
||||
want: &tailcfg.MapResponse{
|
||||
PeersChanged: []*tailcfg.Node{
|
||||
{ID: 2, StableID: "other-change", Hostinfo: hi},
|
||||
{ID: 4, DERP: "127.3.3.40:4", Hostinfo: hi},
|
||||
{ID: 4, HomeDERP: 4, Hostinfo: hi},
|
||||
},
|
||||
PeersChangedPatch: []*tailcfg.PeerChange{
|
||||
{NodeID: 1, DERPRegion: 11},
|
||||
@ -1006,6 +1006,53 @@ func TestPatchifyPeersChanged(t *testing.T) {
|
||||
}
|
||||
}
|
||||
|
||||
func TestUpgradeNode(t *testing.T) {
|
||||
tests := []struct {
|
||||
name string
|
||||
in *tailcfg.Node
|
||||
want *tailcfg.Node
|
||||
}{
|
||||
{
|
||||
name: "nil",
|
||||
in: nil,
|
||||
want: nil,
|
||||
},
|
||||
{
|
||||
name: "empty",
|
||||
in: new(tailcfg.Node),
|
||||
want: new(tailcfg.Node),
|
||||
},
|
||||
{
|
||||
name: "derp-both",
|
||||
in: &tailcfg.Node{HomeDERP: 1, LegacyDERPString: tailcfg.DerpMagicIP + ":2"},
|
||||
want: &tailcfg.Node{HomeDERP: 1},
|
||||
},
|
||||
{
|
||||
name: "derp-str-only",
|
||||
in: &tailcfg.Node{LegacyDERPString: tailcfg.DerpMagicIP + ":2"},
|
||||
want: &tailcfg.Node{HomeDERP: 2},
|
||||
},
|
||||
{
|
||||
name: "derp-int-only",
|
||||
in: &tailcfg.Node{HomeDERP: 2},
|
||||
want: &tailcfg.Node{HomeDERP: 2},
|
||||
},
|
||||
}
|
||||
for _, tt := range tests {
|
||||
t.Run(tt.name, func(t *testing.T) {
|
||||
var got *tailcfg.Node
|
||||
if tt.in != nil {
|
||||
got = ptr.To(*tt.in) // shallow clone
|
||||
}
|
||||
upgradeNode(got)
|
||||
if diff := cmp.Diff(tt.want, got); diff != "" {
|
||||
t.Errorf("wrong result (-want +got):\n%s", diff)
|
||||
}
|
||||
})
|
||||
}
|
||||
|
||||
}
|
||||
|
||||
func BenchmarkMapSessionDelta(b *testing.B) {
|
||||
for _, size := range []int{10, 100, 1_000, 10_000} {
|
||||
b.Run(fmt.Sprintf("size_%d", size), func(b *testing.B) {
|
||||
@ -1022,7 +1069,7 @@ func BenchmarkMapSessionDelta(b *testing.B) {
|
||||
res.Peers = append(res.Peers, &tailcfg.Node{
|
||||
ID: tailcfg.NodeID(i + 2),
|
||||
Name: fmt.Sprintf("peer%d.bar.ts.net.", i),
|
||||
DERP: "127.3.3.40:10",
|
||||
HomeDERP: 10,
|
||||
Addresses: []netip.Prefix{netip.MustParsePrefix("100.100.2.3/32"), netip.MustParsePrefix("fd7a:115c:a1e0::123/128")},
|
||||
AllowedIPs: []netip.Prefix{netip.MustParsePrefix("100.100.2.3/32"), netip.MustParsePrefix("fd7a:115c:a1e0::123/128")},
|
||||
Endpoints: eps("192.168.1.2:345", "192.168.1.3:678"),
|
||||
|
@ -116,7 +116,7 @@ func (em *expiryManager) flagExpiredPeers(netmap *netmap.NetworkMap, localNow ti
|
||||
// since we discover endpoints via DERP, and due to DERP return
|
||||
// path optimization.
|
||||
mut.Endpoints = nil
|
||||
mut.DERP = ""
|
||||
mut.HomeDERP = 0
|
||||
|
||||
// Defense-in-depth: break the node's public key as well, in
|
||||
// case something tries to communicate.
|
||||
|
@ -7381,15 +7381,7 @@ func suggestExitNode(report *netcheck.Report, netMap *netmap.NetworkMap, prevSug
|
||||
}
|
||||
distances := make([]nodeDistance, 0, len(candidates))
|
||||
for _, c := range candidates {
|
||||
if c.DERP() != "" {
|
||||
ipp, err := netip.ParseAddrPort(c.DERP())
|
||||
if err != nil {
|
||||
continue
|
||||
}
|
||||
if ipp.Addr() != tailcfg.DerpMagicIPAddr {
|
||||
continue
|
||||
}
|
||||
regionID := int(ipp.Port())
|
||||
if regionID := c.HomeDERP(); regionID != 0 {
|
||||
candidatesByRegion[regionID] = append(candidatesByRegion[regionID], c)
|
||||
continue
|
||||
}
|
||||
|
@ -1007,8 +1007,8 @@ func TestUpdateNetmapDelta(t *testing.T) {
|
||||
|
||||
wants := []*tailcfg.Node{
|
||||
{
|
||||
ID: 1,
|
||||
DERP: "127.3.3.40:1",
|
||||
ID: 1,
|
||||
HomeDERP: 1,
|
||||
},
|
||||
{
|
||||
ID: 2,
|
||||
@ -2021,7 +2021,7 @@ func TestAutoExitNodeSetNetInfoCallback(t *testing.T) {
|
||||
netip.MustParsePrefix("100.64.1.1/32"),
|
||||
netip.MustParsePrefix("fe70::1/128"),
|
||||
},
|
||||
DERP: "127.3.3.40:2",
|
||||
HomeDERP: 2,
|
||||
}
|
||||
defaultDERPMap := &tailcfg.DERPMap{
|
||||
Regions: map[int]*tailcfg.DERPRegion{
|
||||
@ -2985,7 +2985,7 @@ func makePeer(id tailcfg.NodeID, opts ...peerOptFunc) tailcfg.NodeView {
|
||||
ID: id,
|
||||
StableID: tailcfg.StableNodeID(fmt.Sprintf("stable%d", id)),
|
||||
Name: fmt.Sprintf("peer%d", id),
|
||||
DERP: fmt.Sprintf("127.3.3.40:%d", id),
|
||||
HomeDERP: int(id),
|
||||
}
|
||||
for _, opt := range opts {
|
||||
opt(node)
|
||||
@ -3001,13 +3001,13 @@ func withName(name string) peerOptFunc {
|
||||
|
||||
func withDERP(region int) peerOptFunc {
|
||||
return func(n *tailcfg.Node) {
|
||||
n.DERP = fmt.Sprintf("127.3.3.40:%d", region)
|
||||
n.HomeDERP = region
|
||||
}
|
||||
}
|
||||
|
||||
func withoutDERP() peerOptFunc {
|
||||
return func(n *tailcfg.Node) {
|
||||
n.DERP = ""
|
||||
n.HomeDERP = 0
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -153,7 +153,8 @@ type CapabilityVersion int
|
||||
// - 108: 2024-11-08: Client sends ServicesHash in Hostinfo, understands c2n GET /vip-services.
|
||||
// - 109: 2024-11-18: Client supports filtertype.Match.SrcCaps (issue #12542)
|
||||
// - 110: 2024-12-12: removed never-before-used Tailscale SSH public key support (#14373)
|
||||
const CurrentCapabilityVersion CapabilityVersion = 110
|
||||
// - 111: 2025-01-14: Client supports a peer having Node.HomeDERP (issue #14636)
|
||||
const CurrentCapabilityVersion CapabilityVersion = 111
|
||||
|
||||
// ID is an integer ID for a user, node, or login allocated by the
|
||||
// control plane.
|
||||
@ -346,15 +347,24 @@ type Node struct {
|
||||
AllowedIPs []netip.Prefix // range of IP addresses to route to this node
|
||||
Endpoints []netip.AddrPort `json:",omitempty"` // IP+port (public via STUN, and local LANs)
|
||||
|
||||
// DERP is this node's home DERP region ID integer, but shoved into an
|
||||
// LegacyDERPString is this node's home LegacyDERPString region ID integer, but shoved into an
|
||||
// IP:port string for legacy reasons. The IP address is always "127.3.3.40"
|
||||
// (a loopback address (127) followed by the digits over the letters DERP on
|
||||
// a QWERTY keyboard (3.3.40)). The "port number" is the home DERP region ID
|
||||
// a QWERTY keyboard (3.3.40)). The "port number" is the home LegacyDERPString region ID
|
||||
// integer.
|
||||
//
|
||||
// TODO(bradfitz): simplify this legacy mess; add a new HomeDERPRegionID int
|
||||
// field behind a new capver bump.
|
||||
DERP string `json:",omitempty"` // DERP-in-IP:port ("127.3.3.40:N") endpoint
|
||||
// Deprecated: HomeDERP has replaced this, but old servers might still send
|
||||
// this field. See tailscale/tailscale#14636. Do not use this field in code
|
||||
// other than in the upgradeNode func, which canonicalizes it to HomeDERP
|
||||
// if it arrives as a LegacyDERPString string on the wire.
|
||||
LegacyDERPString string `json:"DERP,omitempty"` // DERP-in-IP:port ("127.3.3.40:N") endpoint
|
||||
|
||||
// HomeDERP is the modern version of the DERP string field, with just an
|
||||
// integer. The client advertises support for this as of capver 111.
|
||||
//
|
||||
// HomeDERP may be zero if not (yet) known, but ideally always be non-zero
|
||||
// for magicsock connectivity to function normally.
|
||||
HomeDERP int `json:",omitempty"` // DERP region ID of the node's home DERP
|
||||
|
||||
Hostinfo HostinfoView
|
||||
Created time.Time
|
||||
@ -2162,7 +2172,8 @@ func (n *Node) Equal(n2 *Node) bool {
|
||||
slicesx.EqualSameNil(n.AllowedIPs, n2.AllowedIPs) &&
|
||||
slicesx.EqualSameNil(n.PrimaryRoutes, n2.PrimaryRoutes) &&
|
||||
slicesx.EqualSameNil(n.Endpoints, n2.Endpoints) &&
|
||||
n.DERP == n2.DERP &&
|
||||
n.LegacyDERPString == n2.LegacyDERPString &&
|
||||
n.HomeDERP == n2.HomeDERP &&
|
||||
n.Cap == n2.Cap &&
|
||||
n.Hostinfo.Equal(n2.Hostinfo) &&
|
||||
n.Created.Equal(n2.Created) &&
|
||||
|
@ -99,7 +99,8 @@ var _NodeCloneNeedsRegeneration = Node(struct {
|
||||
Addresses []netip.Prefix
|
||||
AllowedIPs []netip.Prefix
|
||||
Endpoints []netip.AddrPort
|
||||
DERP string
|
||||
LegacyDERPString string
|
||||
HomeDERP int
|
||||
Hostinfo HostinfoView
|
||||
Created time.Time
|
||||
Cap CapabilityVersion
|
||||
|
@ -367,7 +367,7 @@ func TestNodeEqual(t *testing.T) {
|
||||
nodeHandles := []string{
|
||||
"ID", "StableID", "Name", "User", "Sharer",
|
||||
"Key", "KeyExpiry", "KeySignature", "Machine", "DiscoKey",
|
||||
"Addresses", "AllowedIPs", "Endpoints", "DERP", "Hostinfo",
|
||||
"Addresses", "AllowedIPs", "Endpoints", "LegacyDERPString", "HomeDERP", "Hostinfo",
|
||||
"Created", "Cap", "Tags", "PrimaryRoutes",
|
||||
"LastSeen", "Online", "MachineAuthorized",
|
||||
"Capabilities", "CapMap",
|
||||
@ -530,8 +530,13 @@ func TestNodeEqual(t *testing.T) {
|
||||
true,
|
||||
},
|
||||
{
|
||||
&Node{DERP: "foo"},
|
||||
&Node{DERP: "bar"},
|
||||
&Node{LegacyDERPString: "foo"},
|
||||
&Node{LegacyDERPString: "bar"},
|
||||
false,
|
||||
},
|
||||
{
|
||||
&Node{HomeDERP: 1},
|
||||
&Node{HomeDERP: 2},
|
||||
false,
|
||||
},
|
||||
{
|
||||
|
@ -139,7 +139,8 @@ func (v NodeView) DiscoKey() key.DiscoPublic { return v.ж.DiscoK
|
||||
func (v NodeView) Addresses() views.Slice[netip.Prefix] { return views.SliceOf(v.ж.Addresses) }
|
||||
func (v NodeView) AllowedIPs() views.Slice[netip.Prefix] { return views.SliceOf(v.ж.AllowedIPs) }
|
||||
func (v NodeView) Endpoints() views.Slice[netip.AddrPort] { return views.SliceOf(v.ж.Endpoints) }
|
||||
func (v NodeView) DERP() string { return v.ж.DERP }
|
||||
func (v NodeView) LegacyDERPString() string { return v.ж.LegacyDERPString }
|
||||
func (v NodeView) HomeDERP() int { return v.ж.HomeDERP }
|
||||
func (v NodeView) Hostinfo() HostinfoView { return v.ж.Hostinfo }
|
||||
func (v NodeView) Created() time.Time { return v.ж.Created }
|
||||
func (v NodeView) Cap() CapabilityVersion { return v.ж.Cap }
|
||||
@ -192,7 +193,8 @@ var _NodeViewNeedsRegeneration = Node(struct {
|
||||
Addresses []netip.Prefix
|
||||
AllowedIPs []netip.Prefix
|
||||
Endpoints []netip.AddrPort
|
||||
DERP string
|
||||
LegacyDERPString string
|
||||
HomeDERP int
|
||||
Hostinfo HostinfoView
|
||||
Created time.Time
|
||||
Cap CapabilityVersion
|
||||
|
@ -805,7 +805,7 @@ func (s *Server) serveMap(w http.ResponseWriter, r *http.Request, mkey key.Machi
|
||||
node.Hostinfo = req.Hostinfo.View()
|
||||
if ni := node.Hostinfo.NetInfo(); ni.Valid() {
|
||||
if ni.PreferredDERP() != 0 {
|
||||
node.DERP = fmt.Sprintf("127.3.3.40:%d", ni.PreferredDERP())
|
||||
node.HomeDERP = ni.PreferredDERP()
|
||||
}
|
||||
}
|
||||
}
|
||||
|
@ -287,11 +287,8 @@ func printPeerConcise(buf *strings.Builder, p tailcfg.NodeView) {
|
||||
epStrs[i] = fmt.Sprintf("%21v", e+strings.Repeat(" ", spaces))
|
||||
}
|
||||
|
||||
derp := p.DERP()
|
||||
const derpPrefix = "127.3.3.40:"
|
||||
if strings.HasPrefix(derp, derpPrefix) {
|
||||
derp = "D" + derp[len(derpPrefix):]
|
||||
}
|
||||
derp := fmt.Sprintf("D%d", p.HomeDERP())
|
||||
|
||||
var discoShort string
|
||||
if !p.DiscoKey().IsZero() {
|
||||
discoShort = p.DiscoKey().ShortString() + " "
|
||||
@ -311,7 +308,7 @@ func printPeerConcise(buf *strings.Builder, p tailcfg.NodeView) {
|
||||
// nodeConciseEqual reports whether a and b are equal for the fields accessed by printPeerConcise.
|
||||
func nodeConciseEqual(a, b tailcfg.NodeView) bool {
|
||||
return a.Key() == b.Key() &&
|
||||
a.DERP() == b.DERP() &&
|
||||
a.HomeDERP() == b.HomeDERP() &&
|
||||
a.DiscoKey() == b.DiscoKey() &&
|
||||
views.SliceEqual(a.AllowedIPs(), b.AllowedIPs()) &&
|
||||
views.SliceEqual(a.Endpoints(), b.Endpoints())
|
||||
|
@ -63,12 +63,12 @@ func TestNetworkMapConcise(t *testing.T) {
|
||||
Peers: nodeViews([]*tailcfg.Node{
|
||||
{
|
||||
Key: testNodeKey(2),
|
||||
DERP: "127.3.3.40:2",
|
||||
HomeDERP: 2,
|
||||
Endpoints: eps("192.168.0.100:12", "192.168.0.100:12354"),
|
||||
},
|
||||
{
|
||||
Key: testNodeKey(3),
|
||||
DERP: "127.3.3.40:4",
|
||||
HomeDERP: 4,
|
||||
Endpoints: eps("10.2.0.100:12", "10.1.0.100:12345"),
|
||||
},
|
||||
}),
|
||||
@ -102,7 +102,7 @@ func TestConciseDiffFrom(t *testing.T) {
|
||||
Peers: nodeViews([]*tailcfg.Node{
|
||||
{
|
||||
Key: testNodeKey(2),
|
||||
DERP: "127.3.3.40:2",
|
||||
HomeDERP: 2,
|
||||
Endpoints: eps("192.168.0.100:12", "192.168.0.100:12354"),
|
||||
},
|
||||
}),
|
||||
@ -112,7 +112,7 @@ func TestConciseDiffFrom(t *testing.T) {
|
||||
Peers: nodeViews([]*tailcfg.Node{
|
||||
{
|
||||
Key: testNodeKey(2),
|
||||
DERP: "127.3.3.40:2",
|
||||
HomeDERP: 2,
|
||||
Endpoints: eps("192.168.0.100:12", "192.168.0.100:12354"),
|
||||
},
|
||||
}),
|
||||
@ -126,7 +126,7 @@ func TestConciseDiffFrom(t *testing.T) {
|
||||
Peers: nodeViews([]*tailcfg.Node{
|
||||
{
|
||||
Key: testNodeKey(2),
|
||||
DERP: "127.3.3.40:2",
|
||||
HomeDERP: 2,
|
||||
Endpoints: eps("192.168.0.100:12", "192.168.0.100:12354"),
|
||||
},
|
||||
}),
|
||||
@ -136,7 +136,7 @@ func TestConciseDiffFrom(t *testing.T) {
|
||||
Peers: nodeViews([]*tailcfg.Node{
|
||||
{
|
||||
Key: testNodeKey(2),
|
||||
DERP: "127.3.3.40:2",
|
||||
HomeDERP: 2,
|
||||
Endpoints: eps("192.168.0.100:12", "192.168.0.100:12354"),
|
||||
},
|
||||
}),
|
||||
@ -151,7 +151,7 @@ func TestConciseDiffFrom(t *testing.T) {
|
||||
{
|
||||
ID: 2,
|
||||
Key: testNodeKey(2),
|
||||
DERP: "127.3.3.40:2",
|
||||
HomeDERP: 2,
|
||||
Endpoints: eps("192.168.0.100:12", "192.168.0.100:12354"),
|
||||
},
|
||||
}),
|
||||
@ -162,19 +162,19 @@ func TestConciseDiffFrom(t *testing.T) {
|
||||
{
|
||||
ID: 1,
|
||||
Key: testNodeKey(1),
|
||||
DERP: "127.3.3.40:1",
|
||||
HomeDERP: 1,
|
||||
Endpoints: eps("192.168.0.100:12", "192.168.0.100:12354"),
|
||||
},
|
||||
{
|
||||
ID: 2,
|
||||
Key: testNodeKey(2),
|
||||
DERP: "127.3.3.40:2",
|
||||
HomeDERP: 2,
|
||||
Endpoints: eps("192.168.0.100:12", "192.168.0.100:12354"),
|
||||
},
|
||||
{
|
||||
ID: 3,
|
||||
Key: testNodeKey(3),
|
||||
DERP: "127.3.3.40:3",
|
||||
HomeDERP: 3,
|
||||
Endpoints: eps("192.168.0.100:12", "192.168.0.100:12354"),
|
||||
},
|
||||
}),
|
||||
@ -189,19 +189,19 @@ func TestConciseDiffFrom(t *testing.T) {
|
||||
{
|
||||
ID: 1,
|
||||
Key: testNodeKey(1),
|
||||
DERP: "127.3.3.40:1",
|
||||
HomeDERP: 1,
|
||||
Endpoints: eps("192.168.0.100:12", "192.168.0.100:12354"),
|
||||
},
|
||||
{
|
||||
ID: 2,
|
||||
Key: testNodeKey(2),
|
||||
DERP: "127.3.3.40:2",
|
||||
HomeDERP: 2,
|
||||
Endpoints: eps("192.168.0.100:12", "192.168.0.100:12354"),
|
||||
},
|
||||
{
|
||||
ID: 3,
|
||||
Key: testNodeKey(3),
|
||||
DERP: "127.3.3.40:3",
|
||||
HomeDERP: 3,
|
||||
Endpoints: eps("192.168.0.100:12", "192.168.0.100:12354"),
|
||||
},
|
||||
}),
|
||||
@ -212,7 +212,7 @@ func TestConciseDiffFrom(t *testing.T) {
|
||||
{
|
||||
ID: 2,
|
||||
Key: testNodeKey(2),
|
||||
DERP: "127.3.3.40:2",
|
||||
HomeDERP: 2,
|
||||
Endpoints: eps("192.168.0.100:12", "192.168.0.100:12354"),
|
||||
},
|
||||
}),
|
||||
@ -227,7 +227,7 @@ func TestConciseDiffFrom(t *testing.T) {
|
||||
{
|
||||
ID: 2,
|
||||
Key: testNodeKey(2),
|
||||
DERP: "127.3.3.40:2",
|
||||
HomeDERP: 2,
|
||||
Endpoints: eps("192.168.0.100:12", "1.1.1.1:1"),
|
||||
},
|
||||
}),
|
||||
@ -238,7 +238,7 @@ func TestConciseDiffFrom(t *testing.T) {
|
||||
{
|
||||
ID: 2,
|
||||
Key: testNodeKey(2),
|
||||
DERP: "127.3.3.40:2",
|
||||
HomeDERP: 2,
|
||||
Endpoints: eps("192.168.0.100:12", "1.1.1.1:2"),
|
||||
},
|
||||
}),
|
||||
@ -253,7 +253,7 @@ func TestConciseDiffFrom(t *testing.T) {
|
||||
{
|
||||
ID: 2,
|
||||
Key: testNodeKey(2),
|
||||
DERP: "127.3.3.40:2",
|
||||
HomeDERP: 2,
|
||||
Endpoints: eps("192.168.0.100:41641", "1.1.1.1:41641"),
|
||||
DiscoKey: testDiscoKey("f00f00f00f"),
|
||||
AllowedIPs: []netip.Prefix{netip.PrefixFrom(netaddr.IPv4(100, 102, 103, 104), 32)},
|
||||
@ -266,7 +266,7 @@ func TestConciseDiffFrom(t *testing.T) {
|
||||
{
|
||||
ID: 2,
|
||||
Key: testNodeKey(2),
|
||||
DERP: "127.3.3.40:2",
|
||||
HomeDERP: 2,
|
||||
Endpoints: eps("192.168.0.100:41641", "1.1.1.1:41641"),
|
||||
DiscoKey: testDiscoKey("ba4ba4ba4b"),
|
||||
AllowedIPs: []netip.Prefix{netip.PrefixFrom(netaddr.IPv4(100, 102, 103, 104), 32)},
|
||||
|
@ -5,7 +5,6 @@ package netmap
|
||||
|
||||
import (
|
||||
"cmp"
|
||||
"fmt"
|
||||
"net/netip"
|
||||
"reflect"
|
||||
"slices"
|
||||
@ -35,7 +34,7 @@ type NodeMutationDERPHome struct {
|
||||
}
|
||||
|
||||
func (m NodeMutationDERPHome) Apply(n *tailcfg.Node) {
|
||||
n.DERP = fmt.Sprintf("127.3.3.40:%v", m.DERPRegion)
|
||||
n.HomeDERP = m.DERPRegion
|
||||
}
|
||||
|
||||
// NodeMutation is a NodeMutation that says a node's endpoints have changed.
|
||||
|
@ -1359,7 +1359,7 @@ func (de *endpoint) updateFromNode(n tailcfg.NodeView, heartbeatDisabled bool, p
|
||||
})
|
||||
de.resetLocked()
|
||||
}
|
||||
if n.DERP() == "" {
|
||||
if n.HomeDERP() == 0 {
|
||||
if de.derpAddr.IsValid() {
|
||||
de.debugUpdates.Add(EndpointChange{
|
||||
When: time.Now(),
|
||||
@ -1369,7 +1369,7 @@ func (de *endpoint) updateFromNode(n tailcfg.NodeView, heartbeatDisabled bool, p
|
||||
}
|
||||
de.derpAddr = netip.AddrPort{}
|
||||
} else {
|
||||
newDerp, _ := netip.ParseAddrPort(n.DERP())
|
||||
newDerp := netip.AddrPortFrom(tailcfg.DerpMagicIPAddr, uint16(n.HomeDERP()))
|
||||
if de.derpAddr != newDerp {
|
||||
de.debugUpdates.Add(EndpointChange{
|
||||
When: time.Now(),
|
||||
|
@ -2337,10 +2337,7 @@ func devPanicf(format string, a ...any) {
|
||||
|
||||
func (c *Conn) logEndpointCreated(n tailcfg.NodeView) {
|
||||
c.logf("magicsock: created endpoint key=%s: disco=%s; %v", n.Key().ShortString(), n.DiscoKey().ShortString(), logger.ArgWriter(func(w *bufio.Writer) {
|
||||
const derpPrefix = "127.3.3.40:"
|
||||
if strings.HasPrefix(n.DERP(), derpPrefix) {
|
||||
ipp, _ := netip.ParseAddrPort(n.DERP())
|
||||
regionID := int(ipp.Port())
|
||||
if regionID := n.HomeDERP(); regionID != 0 {
|
||||
code := c.derpRegionCodeLocked(regionID)
|
||||
if code != "" {
|
||||
code = "(" + code + ")"
|
||||
|
@ -314,7 +314,7 @@ func meshStacks(logf logger.Logf, mutateNetmap func(idx int, nm *netmap.NetworkM
|
||||
Addresses: addrs,
|
||||
AllowedIPs: addrs,
|
||||
Endpoints: epFromTyped(eps[i]),
|
||||
DERP: "127.3.3.40:1",
|
||||
HomeDERP: 1,
|
||||
}
|
||||
nm.Peers = append(nm.Peers, peer.View())
|
||||
}
|
||||
|
@ -198,7 +198,7 @@ func (e *userspaceEngine) onOpenTimeout(flow flowtrack.Tuple) {
|
||||
e.logf("open-conn-track: timeout opening %v; peer node %v running pre-0.100", flow, n.Key().ShortString())
|
||||
return
|
||||
}
|
||||
if n.DERP() == "" {
|
||||
if n.HomeDERP() == 0 {
|
||||
e.logf("open-conn-track: timeout opening %v; peer node %v not connected to any DERP relay", flow, n.Key().ShortString())
|
||||
return
|
||||
}
|
||||
|
@ -85,7 +85,7 @@ func WGCfg(nm *netmap.NetworkMap, logf logger.Logf, flags netmap.WGConfigFlags,
|
||||
skippedSubnets := new(bytes.Buffer)
|
||||
|
||||
for _, peer := range nm.Peers {
|
||||
if peer.DiscoKey().IsZero() && peer.DERP() == "" && !peer.IsWireGuardOnly() {
|
||||
if peer.DiscoKey().IsZero() && peer.HomeDERP() == 0 && !peer.IsWireGuardOnly() {
|
||||
// Peer predates both DERP and active discovery, we cannot
|
||||
// communicate with it.
|
||||
logf("[v1] wgcfg: skipped peer %s, doesn't offer DERP or disco", peer.Key().ShortString())
|
||||
|
Loading…
x
Reference in New Issue
Block a user