Skip to content
quarry Artifact [b4d352033d]
Login

Artifact [b4d352033d]

Artifact b4d352033dd5f3ba8aef9fa3e294afcd78783e6d5dc0a95bf14bd72801eef9c4:


#!/bin/sh
# race.sh — the race detector over the packages whose invariants only a
# data race can break (make race).
#
# On a branch, only the packages the branch changed run. The CI runner
# sets QUARRY_CHANGED to a file listing the paths the branch changed
# since its fork point; a package runs when one of those paths is in it
# (its own files, or a subdirectory that is not a package of its own),
# and every package runs when a path is a build input. With no list —
# trunk, a local run, a lookup that failed — every package runs, so a
# race a branch reaches only through a dependency is still caught on
# trunk.
#
# The cheap packages repeat; internal/web and internal/index take over
# a minute a pass, so they run COUNT times, once by default.
set -eu
COUNT=${COUNT:-1}
list=${QUARRY_CHANGED:-}
if [ -n "$list" ] && [ ! -r "$list" ]; then
	echo "race: QUARRY_CHANGED names $list, which cannot be read; running every package" >&2
	list=
fi
if [ -n "$list" ] && grep -qxE 'go\.(mod|sum)|Makefile|scripts/(race|ci-zit|build-linux)\.sh' "$list"; then
	echo "race: the branch changed a build input; running every package" >&2
	list=
fi

# changed PKG: did the branch change PKG? (sh has no locals, so these
# names are its own: pick's loop variable must survive the call.)
changed() {
	[ -z "$list" ] && return 0
	while IFS= read -r changed_path; do
		d=$(dirname "$changed_path")
		while [ "$d" != . ] && [ "$d" != "$1" ]; do
			# A directory between the path and PKG with Go files of its
			# own is another package.
			if ls "$d"/*.go >/dev/null 2>&1; then
				break
			fi
			d=$(dirname "$d")
		done
		[ "$d" = "$1" ] && return 0
	done <"$list"
	return 1
}

# pick PKG...: the packages of these the branch changed, as ./PKG/.
pick() {
	out=
	for pkg in "$@"; do
		if changed "$pkg"; then out="$out ./$pkg/"; fi
	done
	echo "$out"
}

ran=
pkgs=$(pick internal/children internal/xfer)
if [ -n "$pkgs" ]; then
	go test -race -count=3 $pkgs
	ran="$ran$pkgs"
fi
if [ -n "$(pick cmd/quarry)" ]; then
	go test -race -count=3 -run '^(TestTheForgeStopsInOrder|TestAnAPIStreamEndsWhenTheForgeStops|TestTeardownWaitsForHandlersThatIgnoredTheStop|TestAStopWaitsForALiveZitChildAndLogsIt|TestAQuietStopStillRefusesNewChildren|TestTheDrainBoundIsKept)$' ./cmd/quarry/
	ran="$ran ./cmd/quarry/"
fi
pkgs=$(pick internal/web internal/index)
if [ -n "$pkgs" ]; then
	go test -race -count="$COUNT" -timeout 20m $pkgs
	ran="$ran$pkgs"
fi
if [ -z "$ran" ]; then
	echo "race: the branch changed none of the raced packages; trunk runs them all"
fi