mirror of
https://github.com/rcourtman/Pulse.git
synced 2026-10-23 20:25:56 +00:00
Keep same-RC secure-runtime canary inside isolated lab
Create the non-loopback veth canary only inside the no-network disposable systemd container before running the immutable release lab. Preserve packet authentication and fail closed when the local interface or no-default-route assertion is absent. Bind the workflow, source contract and installtests guard in one reviewed candidate. Change-source: pulse-maintainer
This commit is contained in:
@@ -224,7 +224,7 @@ jobs:
|
||||
COPY --from=dind /usr/local/bin/ /usr/local/bin/
|
||||
COPY pulse-qualification-docker.service /etc/systemd/system/pulse-qualification-docker.service
|
||||
RUN apt-get update && DEBIAN_FRONTEND=noninteractive apt-get install -y --no-install-recommends \
|
||||
ca-certificates curl dbus systemd systemd-sysv util-linux && \
|
||||
ca-certificates curl dbus systemd systemd-sysv util-linux iproute2 && \
|
||||
apt-get clean && \
|
||||
systemctl mask dev-hugepages.mount sys-fs-fuse-connections.mount systemd-remount-fs.service docker.service docker.socket && \
|
||||
systemctl enable pulse-qualification-docker.service
|
||||
@@ -269,7 +269,19 @@ jobs:
|
||||
sleep 2
|
||||
done
|
||||
docker exec "${container}" sh -c \
|
||||
'for command in curl docker dockerd id nsenter runuser systemctl; do command -v "$command" >/dev/null || exit 1; done'
|
||||
'for command in curl docker dockerd id ip nsenter runuser systemctl; do command -v "$command" >/dev/null || exit 1; done'
|
||||
# The immutable RC test needs a reachable non-loopback host-interface
|
||||
# canary to prove that the helper's private network cannot reach it.
|
||||
# Both veth ends stay inside this --network none namespace; neither
|
||||
# endpoint is attached to the runner or an egress bridge.
|
||||
docker exec "${container}" sh -ceu '
|
||||
ip link add pulse-can0 type veth peer name pulse-can1
|
||||
ip address add 192.0.2.1/32 dev pulse-can0
|
||||
ip link set pulse-can1 up
|
||||
ip link set pulse-can0 up
|
||||
test -z "$(ip -4 route show default)"
|
||||
ip -4 address show dev pulse-can0 | grep -F "192.0.2.1/32"
|
||||
'
|
||||
docker exec "${container}" systemctl start pulse-qualification-docker.service
|
||||
for attempt in $(seq 1 60); do
|
||||
if docker exec "${container}" docker info >/dev/null 2>&1; then
|
||||
|
||||
@@ -1239,6 +1239,14 @@ artifact-selection behaviour.
|
||||
privileged systemd container must mount that exact snapshot read-only and
|
||||
must never execute directly from the download directory. The post-run
|
||||
attester must consume the same snapshot paths.
|
||||
The outer systemd qualification container must retain `--network none`:
|
||||
it may create a non-loopback host-interface canary only as a veth pair
|
||||
wholly inside that container's network namespace, with no runner bridge,
|
||||
egress attachment, or default IPv4 route. The immutable RC lab uses this
|
||||
reachable local canary to distinguish host-network access from the typed
|
||||
helper's private network isolation. Canary setup and the no-default-route
|
||||
check must fail qualification before that lab if the boundary is absent;
|
||||
they must not skip the lab or change the release packet under test.
|
||||
PVE jobs must consume their runner users' persistent local Go and npm caches
|
||||
directly; disposable-runner Actions cache restore/save phases must remain
|
||||
disabled because archiving those same caches adds network work after the
|
||||
|
||||
@@ -2847,12 +2847,15 @@ func TestSecureRuntimeQualificationPacketIsHostedAndReleaseBound(t *testing.T) {
|
||||
`git remote set-url origin https://github.com/rcourtman/Pulse.git`,
|
||||
"ca-certificates curl dbus systemd systemd-sysv util-linux",
|
||||
`docker:27.5.1-dind@sha256:f649ef046008ca7f926a2571c32b0ac22e5c59eb61b959617f9acc2a4c638cf5`,
|
||||
`for command in curl docker dockerd id nsenter runuser systemctl`,
|
||||
`for command in curl docker dockerd id ip nsenter runuser systemctl`,
|
||||
`--host=unix:///var/run/docker.sock`,
|
||||
`--storage-driver=vfs`,
|
||||
`--bridge=none`,
|
||||
`--iptables=false`,
|
||||
`--network none`,
|
||||
`ip link add pulse-can0 type veth peer name pulse-can1`,
|
||||
`ip address add 192.0.2.1/32 dev pulse-can0`,
|
||||
`test -z "$(ip -4 route show default)"`,
|
||||
`pulse-secure-runtime-fixture:v7`,
|
||||
"--verify-release-packet-only",
|
||||
"--verified-packet-dir",
|
||||
@@ -2870,6 +2873,16 @@ func TestSecureRuntimeQualificationPacketIsHostedAndReleaseBound(t *testing.T) {
|
||||
t.Fatalf("post-publication secure-runtime qualification missing %q", required)
|
||||
}
|
||||
}
|
||||
canaryIndex := strings.Index(qualificationWorkflow, `ip link add pulse-can0 type veth peer name pulse-can1`)
|
||||
labIndex := strings.Index(qualificationWorkflow, `--env PULSE_SECURE_RUNTIME_SYSTEMD_LAB=1`)
|
||||
if canaryIndex <= privilegedExecutionIndex || labIndex <= canaryIndex {
|
||||
t.Fatal("the isolated host-interface canary must be configured before running the immutable RC lab")
|
||||
}
|
||||
if !strings.Contains(qualificationWorkflow, `--privileged \
|
||||
--network none \
|
||||
--cgroupns=host`) {
|
||||
t.Fatal("the outer systemd lab must retain its no-network namespace")
|
||||
}
|
||||
for _, forbidden := range []string{
|
||||
`/var/run/docker.sock:/var/run/docker.sock`,
|
||||
`--host=tcp://`,
|
||||
|
||||
Reference in New Issue
Block a user