---
title: "Installing groundSwXtch"
slug: "installing-groundswxtch-1"
updated: 2026-07-24T19:47:25Z
published: 2026-07-24T19:47:25Z
canonical: "docs.swxtch.io/installing-groundswxtch-1"
---

> ## Documentation Index
> Fetch the complete documentation index at: https://docs.swxtch.io/llms.txt
> Use this file to discover all available pages before exploring further.

# Installing groundSwXtch

**WHAT TO EXPECT**

**In this article**, users will learn how to install a groundSwXtch on an existing Ubuntu 24.04 machine. For more information about VM or hardware prerequisites, please see the [groundSwXtch System Requirements](/v2/docs/groundswxtch-system-requirements)

### Pre-Installation Step: Create the environment

What is needed:

- For prerequisites, see [groundSwXtch System Requirements](/v2/docs/groundswxtch-system-requirements)
- VM must be Ubuntu 24.04
- The VM needs an internet connection.
- The user must be able to log into the VM or physical machine (each agent)

#### Prerequisites

Currently, users **must** install and enable **Docker** on their Ubuntu VM. Please see ["How to Install Docker on RHEL and Ubuntu"](/v2/docs/how-to-install-docker-on-rhel-and-ubuntu).

> [!TIP]
> NOTE
> 
> The installation script will also install all dependencies.

### STEP ONE: Prepare the installation by updating the OS

1. Update all of the currently installed OS packages

```shell
sudo apt update && sudo apt upgrade -y
```
2. Reboot VM

```shell
sudo reboot now
```

### STEP TWO: Install groundSwXtch

In this step, users will execute commands in their VMs or hardware devices to manually install a groundSwXtch.

1. Connect to the VM instance or hardware device that will be used as a groundSwXtch.
  1. Download the package onto the groundSwXtch
2. Enter the following commands to download and install the **groundSwXtch installer script**:

```shell
curl -fL "https://swxrkdistribution.blob.core.windows.net/swxcontainer01/install-groundswxtch.sh?sp=rl&st=2026-05-21T21:40:09Z&se=2027-05-23T05:55:09Z&spr=https&sv=2026-02-06&sr=c&sig=HA9RA9sUQwLBKfePWwB3UhLKGlvtJgoT6z2bCU1Kb6k%3D" -o install-groundswxtch.sh && chmod +x install-groundswxtch.sh
```

[](https://cdn.document360.io/84c5db44-f675-4f33-a980-5d3fc63073ca/Images/Documentation/install-groundswxtch.sh)install-groundswxtch63.98 KB[](https://cdn.document360.io/84c5db44-f675-4f33-a980-5d3fc63073ca/Images/Documentation/install-groundswxtch.sh)
3. The recommended method will install with dependencies:

Shell

```shell
 chmod +x install-groundswxtch.sh
 sudo ~/install-groundswxtch.sh install --image-tag groundswxtch:dev-2494302c
```
  1. NIC selection for wan and lan interfaces can be added with these arguments: `--lan-iface enp2s0 --wan-iface enp2s0`

`Example:`

```shell
sudo ~/install-groundswxtch.sh install --image-tag groundswxtch:dev-2494302c  --lan-iface enp2s0 --wan-iface enp2s0
```

> [!NOTE]
> **Configuration and Log files for a groundSwXtch:**
> 
> 
> 
> - **Configuration files can be found in /var/lib/groundswxtch.**
> - **Logs can be viewed using** `docker logs -f gswx`

1. After the installation, run the following command to see if the container is running:

```shell
docker ps
```

There should be a line with the name gswx. For example:

```shell
ubuntu@drs-ground-swxtch-001:~$ docker ps
CONTAINER ID   IMAGE                       COMMAND            CREATED       STATUS        PORTS     NAMES
d50428d6b201   groundswxtch:dev-70d1fc5c   "groundswxtchd"    5 hours ago   Up 5 hours              gswx
95d07c68d75e   swx-tools:1.0.0             "sleep infinity"   5 days ago    Up 29 hours             swx-tools
ubuntu@drs-ground-swxtch-001:~$
```

## Air-Gapped Deployment

For groundSwXtch without GHCR or Azure Blob access (emergency fallback — the `install-groundswxtch.sh` path is preferred):

```bash
# On a connected host:
docker pull ghcr.io/swxtchio/groundswxtch:v1.1.0-spp.7dbc218
docker save ghcr.io/swxtchio/groundswxtch:v1.1.0-spp.7dbc218 \
  | gzip > groundswxtch-v1.1.0.tar.gz
scp groundswxtch-v1.1.0.tar.gz nuc-2:/tmp/
# On the air-gapped NUC:
docker load < /tmp/groundswxtch-v1.1.0.tar.gz
docker image ls ghcr.io/swxtchio/groundswxtch
```

Then follow the following steps:

#### Help Arguments

1. To get a list of arguments that can be used during the installation, use the help command -h:

```shell
$ ./install-groundswxtch.sh -h
```

1. A list of installation arguments will display as shown below:

```shell
ubuntu@drs-ground-swxtch-006:~$ sudo ./install-groundswxtch.sh tools -h
[install-groundswxtch] WARN: 'tools' is a deprecated alias for 'swx-tools' — please switch (the alias still works for now).
Usage: install-groundswxtch.sh <subcommand> [flags]

═══ SIMPLEST INSTALL (recommended for customer deployments) ═══

  sudo ./install-groundswxtch.sh install --image-tag groundswxtch:v1.1

Defaults to host networking — container shares the host's network namespace,
no IP/subnet/gateway flags needed. Daemon auto-detects its gateway.

═══ FIRST-RUN ON UNLICENSED HARDWARE ═══

License is OPTIONAL at boot — the container starts in degraded mode (daemon
+ REST API up; no traffic processing). First-run flow on a new machine:

  1. sudo ./install-groundswxtch.sh install --image-tag groundswxtch:v1.1
     → boots unlicensed, logs a banner explaining the degraded state.
  2. curl http://127.0.0.1/api/v1/license/fingerprint
     → returns the machine's fingerprint hash; send it to swxtch.
  3. Receive your fingerprint-bound license.key, drop it at
     /var/lib/groundswxtch/license.key (sudo cp ...).
  4. curl -X POST http://127.0.0.1/api/v1/license/reload
     → daemon hot-reloads the new license — no container restart needed.

═══ Subcommands ═══

  gswx-fetch    Download + verify + docker-load the gswx image. No launch.
                Use this to pre-stage a new release before bring-up, or to
                stage an upgrade (combine with --force-fetch). Idempotent.
                Alias: 'fetch' (legacy).
  network       Create the gswx-wan macvlan network. Only required when
                --network-mode=macvlan. Skip in host mode.
  gswx-run      Launch the gswx container (image must already be loaded).
                Replaces any existing gswx container with the same name —
                use this to bring up a new tag after gswx-fetch (upgrade).
                Alias: 'run' (legacy).
  install       gswx-fetch + gswx-run (host mode), or gswx-fetch + network
                + gswx-run (macvlan mode). DEFAULT when no subcommand is
                given.

  swx-tools-fetch  Download + verify + docker-load the swx-tools image. No launch.
                Use to upgrade the tools image independently of running.
                Alias: 'tools-fetch' (legacy, deprecated).
  swx-tools-run Launch the swx-tools container (image must already be loaded).
                Replaces any existing swx-tools container with the same name.
                Alias: 'tools-run' (legacy, deprecated).
  swx-tools     swx-tools-fetch + swx-tools-run convenience.
                Alias: 'tools' (legacy, deprecated).

  teardown      Stop + remove gswx and swx-tools containers (preserves state,
                images, and network so reinstall is fast). Pass --full to also
                remove the gswx-wan network, /var/lib/groundswxtch state, and
                both loaded images.

  restart       Recreate the gswx container with the current flag values
                (e.g. after changing --name). Inherits the running container's
                --image-tag so you don't have to remember which version is
                loaded — pass --image-tag only to also upgrade in-place.

═══ Flags ═══

Required by 'fetch', 'run', 'install':
  --image-tag <ref>       Image to fetch + run. Accepts:
                            latest-prod   newest blessed prod release (channel
                                          alias; auto-resolved by this script)
                            latest-dev    newest blessed dev build (channel alias)
                            groundswxtch:v1.2            newest patch of a minor
                            groundswxtch:v1.2.0          exact immutable build
                          No implicit default — the blob carries multiple
                          versions in parallel. The channel aliases resolve to a
                          concrete build via a pointer in the blob (logged as
                          'channel latest-X → ...'); a channel with nothing
                          promoted yet fails with a distinct "not currently
                          published" error. Exact tags + moving minors fetch
                          directly with no pointer lookup.

Network mode (drives which other flags are needed):
  --network-mode <mode>   host (default) | macvlan.
                          host    — share host's network namespace; no
                                    IP/subnet/gateway needed.
                          macvlan — dedicated container IP on a macvlan over
                                    a host NIC; needs --ip --subnet --gateway
                                    --parent-iface. Use for multi-instance
                                    on the same host.

Required by 'run' and 'install' only when --network-mode=macvlan:
  --ip <addr>             Container IP on gswx-wan (e.g. 192.168.1.10).
  --subnet <cidr>         macvlan subnet (e.g. 192.168.1.0/24).
  --gateway <addr>        macvlan gateway (e.g. 192.168.1.1).
  --parent-iface <nic>    Host NIC for macvlan parent (e.g. enp2s0).

Optional (all modes):
  --name <name>           Instance display name. Surfaces on /api/v1/stats as
                          `instance`, rendered in the SPA as "this instance",
                          and reported to peers via peer-health. Default = the
                          host's short hostname (e.g. groundswxtch-1) so each
                          peer in a fleet shows up distinctly in the UI.
                          NOTE: this is the daemon's self-identity, NOT the
                          docker container name (docker --name stays 'gswx'
                          for muscle-memory portability — `docker exec gswx`
                          works identically on every host).
  --role boundary|leaf    PTP grandmaster (boundary) or PTP2 client (leaf).
                          Default: leaf. Drives TIMEBEAT_PTP2_CONCURRENT.
  --wan-gateway <addr>    GROUNDSWXTCH_WAN_GATEWAY. Optional — daemon falls
                          back to rtnetlink (CFG-13) when unset. Pass only
                          if auto-detect picks the wrong gateway.
  --wan-iface <nic>       GROUNDSWXTCH_WAN_DEV (issue #1004). WAN NIC the daemon
                          binds. Optional — daemon auto-detects when unset.
  --lan-iface <nic>       GROUNDSWXTCH_LAN_DEV (issue #1004). LAN NIC for
                          local-multicast. INDEPENDENT of --wan-iface (dual-NIC).
                          Optional — omit for the default virtual LAN (swx0-lan);
                          set to the WAN NIC for same-NIC mode, or a distinct NIC
                          for dual-NIC mode.
                          NOTE (both --wan-iface/--lan-iface): these are
                          FIRST-BOOT config SEEDS. yaml-trumps-env — once the
                          daemon has persisted groundswxtch.yaml the persisted
                          value wins and these are IGNORED (the installer WARNs
                          when a persisted config already exists). Change a
                          running install via the SPA / PUT /api/v1/config, or
                          'teardown --full' then re-seed. Env vars accepted too.
  --veth-instance <N>     GROUNDSWXTCH_VETH_INSTANCE (1..=255). PINS the
                          per-host swx0-lan veth /30:
                          N=1 → 169.254.1.{1,2}, N=221 → 169.254.221.{1,2}.
                          DEFAULT (omit this flag): the daemon AUTO-derives
                          the instance from network.address' last octet and
                          OWNS it — a VLAN move recomputes it automatically
                          (#170). Pass --veth-instance ONLY to pin a fixed
                          value the daemon must never recompute (e.g. two
                          hosts on different /24s with the same last octet,
                          or multiple gswx on a single host).
  --peer-id <fp>          Boundary clock libp2p fingerprint (leaf clients).
  --peer-ip <addr>        Boundary clock IP (leaf clients).
  --peer-port <port>      Boundary clock DHT port (default: 65107).
  --state-root <dir>      Persistent state root (default: /var/lib/groundswxtch).
                          Mounted inside the container at /etc/groundswxtch.
  --license-dir <dir>     Convenience: seeds <dir>/license.key into --state-root
                          when the state-root has none. Checked every run (so a
                          re-install after 'teardown --full' re-seeds); never
                          overwrites an existing key; warns if <dir>/license.key
                          is missing/empty rather than booting unlicensed silently.
  --force-fetch           Re-download + reload even if image is already present.
  --skip-docker-install   Don't auto-install Docker if it's missing. By default
                          a missing Docker engine is auto-installed (issue #77)
                          via https://get.docker.com so a fresh host runs the
                          full setup end-to-end; pass this (or set
                          SKIP_DOCKER_INSTALL=true) to get a clear actionable
                          error instead — e.g. for air-gapped / managed hosts.
  --ptp2-concurrent <int> Override role-derived TIMEBEAT_PTP2_CONCURRENT.
  --extra-mount <triple>  Extra docker -v mount, e.g.
                          /tmp/19.1-spa:/opt/groundswxtch/ui/spa.
                          Repeatable. Phase 19.1 plan 04 codex HIGH-2 dev
                          knob — production installs leave this unset.
  --extra-daemon-arg <a>  Extra CLI flag forwarded to the daemon, e.g.
                          --ui-dev=/opt/groundswxtch/ui/spa. Repeatable.
                          Phase 19.1 plan 04 codex HIGH-2 dev knob —
                          production installs leave this unset.
  -h, --help              Show this help.

'swx-tools-fetch', 'swx-tools-run', 'swx-tools' flags (legacy aliases: 'tools*'):
  --tools-version <ver>   swx-tools version to pull. Default: 1.0.0. Pass
                          'latest' to auto-resolve the current prod-blessed
                          swx-tools build via the channel pointer (prod ONLY —
                          swx-tools has no latest-dev). Pass an exact version
                          when a specific tools release is needed.
  --network <name>        Docker network for the swx-tools container.
                          Default: host (shares the host's net namespace
                          with spp). This is the only mode where round-
                          trip mcast testing works end-to-end today —
                          send + receive both flow correctly through
                          spp's tunnel. Avoid UDP 5000 + 6000 (spp reserves
                          them at boot via KernelSocketClaim).
                          Pass 'bridge' for SEND-only tests on the docker0
                          bridge (receive is broken on docker0 due to
                          source-IP collisions + bridge IGMP forwarding
                          quirks). Pass 'gswx-wan' when gswx was installed
                          with --network-mode=macvlan.
  --tools-ip <addr>       Container IP — required only when --network is a
                          macvlan. Pick an unused IP in the macvlan subnet.
  --tools-container-name <name>  Docker container name. Default: <hostname>-tools.

'teardown' flags:
  --full                  Also remove the gswx-wan network, /var/lib/groundswxtch
                          state directory, and both loaded images. Without
                          --full, only the containers are removed (state, images,
                          and network are preserved so a re-install is fast).

The script is idempotent: fetch / swx-tools-fetch skip curl+load if the image is
already present (unless --force-fetch); network skips create if gswx-wan
already exists; run / swx-tools-run remove any pre-existing container with the
same name before launching.
```

files are located in /var/lib/groundswxtch/

timebeat logs are in /var/log/timebeat

swx tools can be installed using the following commands after the download for groundSwXtch:

```bash
sudo ./install-groundswxtch.sh tools
```

swx-tools are used to test the system. Refer to [Tools and Testing](/v2/docs/testing) for more information on the tools provided.

The swx tools run in docker, therefore to access them and run swx commands:

sudo docker exec -it swx-tools bash

### STEP THREE: License the groundSwXtch

For more information, see [How to license the groundSwXtch](/v2/docs/how-to-license-the-groundswxtch).

**NEXT STEPS**

**The groundSwXtch is ready to use**. The next step is to install at least one more groundSwXtch to connect one on-prem network to another.

A software-based network switch that adds multicast to your physical networks as a softwared defined overlay. Link your facilities into a reliable multicast fabric.
