Lantunnel
Install Lantunnel Client on each participating device to access your whole LAN from anywhere with P2P-first low-latency routing, encrypted transport, and relay fallback without port forwarding.
翻譯準備中
offline is a Linux sandbox wrapper that executes another program with its network access completely isolated.
翻譯準備中
取自儲存庫 README
正在載入完整 README。 以下為已儲存的摘錄。
offline is a Linux sandbox wrapper that executes another program with its
network access completely isolated: user/net/mount/IPC/UTS namespaces,
capability dropping, and a seccomp filter blocking network syscalls.
Linux only, and it isolates the network — nothing else. The wrapped
program keeps your filesystem and your environment; what it cannot do is
reach anything off the machine. Unprivileged user namespaces must be
enabled on the host.
The wrapped process runs inside a restricted environment where it cannot
access the internet.檢視完整 README ↗offline is a Linux sandbox wrapper that executes another program with its
network access completely isolated: user/net/mount/IPC/UTS namespaces,
capability dropping, and a seccomp filter blocking network syscalls.
Linux only, and it isolates the network — nothing else. The wrapped program keeps your filesystem and your environment; what it cannot do is reach anything off the machine. Unprivileged user namespaces must be enabled on the host.
./offline curl https://example.com
The wrapped process runs inside a restricted environment where it cannot access the internet.
One binary, two stages. The first cannot isolate itself — a running Go program
is multithreaded, and unshare(CLONE_NEWUSER) refuses a multithreaded caller —
so it re-executes itself and passes the flags through the environment:
offline [flags] <program> [args...]
│
│ stage 1 — on the host
├─ parse flags
└─ clone(CLONE_NEWUSER|NEWNET|NEWNS|NEWIPC|NEWUTS)
uid/gid mapped 1:1, setgroups off
_AIRGAP_STAGE=1 in the environment
│
▼
re-exec of the same binary
│
│ stage 2 — inside the namespaces
├─ prctl(PR_SET_NO_NEW_PRIVS) no setuid escape hatch
├─ --keep-loopback ? ifup "lo" before the filter, it needs socket(2)
├─ PR_CAPBSET_DROP 0..63 bounding set emptied
├─ PR_CAP_AMBIENT_CLEAR_ALL ambient set emptied
├─ seccomp: allow by default, deny
│ socket(AF_INET|AF_INET6|AF_PACKET)
│ connect bind listen accept accept4 send* recv*
└─ exec <program> [args...]
Three layers, so a gap in one is not a gap in the sandbox: the namespace leaves nothing to route to, the empty capability set leaves nothing to reconfigure it with, and the filter refuses the syscalls anyway.
offline ip route prints nothing./proc, which
breaks runtimes that look themselves up there, and it never blocked the
network anyway.EPERM.--keep-loopback for the local case — 127.0.0.1 works, external
addresses still fail at the routing layer. Caveat: with loopback up the
connect/bind family has to be allowed, so the filter is thinner here;
AF_PACKET stays blocked either way.--log-external routes denials through a userspace notifier and prints
them. Caveat: it logs the syscall name and pid, not the destination address.Linux kernel with support for user, network, mount, and IPC namespaces, plus seccomp.
Ubuntu/Debian dependencies:
sudo apt install pkg-config libseccomp-dev
Go dependencies are pinned in go.mod (github.com/seccomp/libseccomp-golang,
golang.org/x/sys) and resolved automatically by go build/go mod tidy.
One-liner (clones/updates a checkout under ~/.local/share/offline and
runs make install):
curl -fsSL https://raw.githubusercontent.com/fabiocicerchia/offline/main/install.sh | bash
Build from source:
go build -o offline offline.go
# or
make build
make install # drops the binary in ~/.local/bin (on your PATH)
make install BINDIR=/usr/local/bin # ...or anywhere else
$ offline --help
usage: offline [--keep-loopback] [--log-external] <program> [args...]
Runs <program> with its network access fully isolated: private user, network,
mount, IPC and UTS namespaces, an emptied capability set, and a seccomp
filter refusing the network syscalls.
Flags:
-keep-loopback
keep the loopback interface (127.0.0.1) up and reachable
-log-external
log blocked network syscalls to stderr
A real run — the wrapped curl gets no further than the filter:
$ offline --log-external curl -s -m 3 https://example.com
offline: blocked connect (pid 9)
offline: blocked connect (pid 9)
offline: blocked socket (pid 9)
offline: blocked socket (pid 9)
$ echo $?
7
offline curl https://example.com # fails: no network in the sandbox
offline bash # an offline shell
More in docs/getting-started.md.
Package libseccomp was not found in the pkg-config search path.
The cgo binding needs the development headers, not just the runtime library:
sudo apt install pkg-config libseccomp-dev (or libseccomp-devel on
Fedora/RHEL).
fork/exec /usr/local/bin/offline: operation not permitted
The host refuses unprivileged user namespaces. Check
sysctl kernel.unprivileged_userns_clone and, on Ubuntu,
sysctl kernel.apparmor_restrict_unprivileged_userns; a container runtime can
also block the clone flags through its own seccomp profile.
A non-zero exit with nothing on stderr
Not an offline failure — that is the wrapped program's own status, passed
through untouched. curl returning 7 ("failed to connect") is the sandbox
working. offline writes to stderr only when it is itself the thing that
failed, so anything on there is worth reading.
Full docs live in docs/ (mkdocs). Runnable examples live in
examples/.
The design is a straight reading of the manual pages; they are the reference, not this file.
user_namespaces(7)
— why the uid/gid map is a single entry and why setgroups stays off.network_namespaces(7)
— what a fresh netns contains (a down lo, and nothing else).capabilities(7)
— the bounding and ambient sets, and why both have to be emptied.seccomp(2) and the
kernel's seccomp filter documentation
— including SECCOMP_RET_USER_NOTIF, which --log-external uses.libseccomp-golang — the
binding, and the reason there is a cgo dependency at all.Semantic Versioning. Releases are cut by release-please from Conventional Commits, and the tag is the only source of truth for a version.
Every change to the namespace flags, the capability sweep or the seccomp filter is security-sensitive by definition and is treated as such, whatever the version number says.
See CONTRIBUTING.md. By participating you agree to the Code of Conduct.
Found a vulnerability, especially a network-isolation bypass? See SECURITY.md — please don't open a public issue.
Need help implementing this? Get in touch.
MIT © Fabio Cicerchia