tailscale/tailscale · error

unimplemented on this GOOS

Error message

unimplemented on this GOOS

What it means

derp/xdp provides an eBPF/XDP-accelerated STUN server only on Linux (xdp_linux.go); xdp_default.go is the stub compiled for every other GOOS. Its NewSTUNServer (and Close, SetDropSTUN) return 'unimplemented on this GOOS' so platform-agnostic code fails loudly instead of silently misbehaving.

Source

Thrown at derp/xdp/xdp_default.go:19

// Copyright (c) Tailscale Inc & contributors
// SPDX-License-Identifier: BSD-3-Clause

//go:build !linux

package xdp

import (
	"errors"

	"github.com/prometheus/client_golang/prometheus"
)

// STUNServer is unimplemented on these platforms, see xdp_linux.go.
type STUNServer struct {
}

func NewSTUNServer(config *STUNServerConfig, opts ...STUNServerOption) (*STUNServer, error) {
	return nil, errors.New("unimplemented on this GOOS")
}

func (s *STUNServer) Close() error {
	return errors.New("unimplemented on this GOOS")
}

func (s *STUNServer) Describe(descCh chan<- *prometheus.Desc) {}

func (s *STUNServer) Collect(metricCh chan<- prometheus.Metric) {}

func (s *STUNServer) SetDropSTUN(v bool) error {
	return errors.New("unimplemented on this GOOS")
}

func (s *STUNServer) GetDropSTUN() bool {
	return true
}

View on GitHub (pinned to 6e0912f979)

Solutions

  1. Gate the code with a //go:build linux constraint or a runtime.GOOS check that falls back to the userspace STUN implementation.
  2. Build and deploy the XDP component only on Linux hosts with a kernel/dependencies that support XDP.

Example fix

// before (fails on darwin/windows: "unimplemented on this GOOS")
srv, err := xdp.NewSTUNServer(cfg)

// after
//go:build linux
srv, err := xdp.NewSTUNServer(cfg)
Defensive patterns

Strategy: validation

Validate before calling

if runtime.GOOS != "linux" {
	return fmt.Errorf("xdp STUN server requires linux; build this binary for linux or use the userspace STUN implementation")
}
srv, err := xdp.NewSTUNServer(cfg)

Type guard

// compile-time guard: only allow compilation of XDP paths on linux
//go:build linux

func newXDPSTUNServer(cfg *xdp.STUNServerConfig) (*xdp.STUNServer, error) {
	return xdp.NewSTUNServer(cfg)
}

Prevention

When it happens

Trigger: Constructing xdp.STUNServer on darwin, windows, freebsd, etc. — either directly in cross-platform code or via tests that aren't gated by build tags when run on a non-Linux host.

Common situations: Developing on a Mac against Linux production; CI build/test matrices that run the package on all GOOS; referencing derp/xdp without platform guards in shared packages.

Understand the failure class

Background: "unsupported platform" / "not supported on this platform" errors: what they mean and how to fix them — this error's family across 47 libraries.

Related errors


AI-assisted analysis of tailscale/tailscale@6e0912f979 (2026-08-18). Data as JSON: /api/errors/4ded23da0d42a523. Report an issue: GitHub.