diff --git a/scripts/bench-recursive.sh b/scripts/bench-recursive.sh deleted file mode 100755 index 1a1ab71..0000000 --- a/scripts/bench-recursive.sh +++ /dev/null @@ -1,115 +0,0 @@ -#!/usr/bin/env bash -# Bench: Numa cold-cache recursive resolution vs dig (forwarded through system resolver) -# -# Measures cold-cache recursive resolution time for Numa. -# Flushes Numa's cache before each query to ensure cold-cache. -# Compares against dig querying a public recursive resolver (no cache advantage). -# -# Usage: ./scripts/bench-recursive.sh [numa_port] - -set -euo pipefail - -NUMA_ADDR="${NUMA_ADDR:-127.0.0.1}" -NUMA_PORT="${NUMA_PORT:-${1:-53}}" -API_PORT="${API_PORT:-5380}" -ROUNDS=3 - -DOMAINS=( - "example.com" - "rust-lang.org" - "kernel.org" - "signal.org" - "archlinux.org" - "openbsd.org" - "git-scm.com" - "sqlite.org" - "wireguard.com" - "mozilla.org" -) - -GREEN='\033[0;32m' -AMBER='\033[0;33m' -CYAN='\033[0;36m' -DIM='\033[0;90m' -BOLD='\033[1m' -RESET='\033[0m' - -echo -e "${CYAN}${BOLD}Recursive DNS Resolution Benchmark${RESET}" -echo -e "${DIM}Numa (cold cache, recursive from root) vs dig @1.1.1.1 (public resolver)${RESET}" -echo -e "${DIM}Rounds per domain: ${ROUNDS}${RESET}" -echo "" - -# Verify Numa is reachable -if ! dig @${NUMA_ADDR} -p ${NUMA_PORT} +short +time=3 +tries=1 example.com A &>/dev/null; then - echo -e "${AMBER}Numa not responding on ${NUMA_ADDR}:${NUMA_PORT}${RESET}" >&2 - exit 1 -fi - -# Verify we can flush cache -if ! curl -s -X DELETE "http://${NUMA_ADDR}:${API_PORT}/cache" &>/dev/null; then - echo -e "${AMBER}Cannot flush cache via API at ${NUMA_ADDR}:${API_PORT}${RESET}" >&2 - exit 1 -fi - -measure_ms() { - local start end - start=$(python3 -c 'import time; print(time.time())') - eval "$1" &>/dev/null - end=$(python3 -c 'import time; print(time.time())') - python3 -c "print(round(($end - $start) * 1000, 1))" -} - -printf "${BOLD}%-22s %10s %10s %8s${RESET}\n" "Domain" "Numa (ms)" "1.1.1.1" "Delta" -printf "%-22s %10s %10s %8s\n" "----------------------" "----------" "----------" "--------" - -numa_total=0 -dig_total=0 -count=0 - -for domain in "${DOMAINS[@]}"; do - numa_sum=0 - dig_sum=0 - - for ((r=1; r<=ROUNDS; r++)); do - # Flush Numa cache - curl -s -X DELETE "http://${NUMA_ADDR}:${API_PORT}/cache" &>/dev/null - sleep 0.05 - - # Measure Numa (recursive from root, cold cache) - ms=$(measure_ms "dig @${NUMA_ADDR} -p ${NUMA_PORT} +short +time=10 +tries=1 ${domain} A") - numa_sum=$(python3 -c "print(round($numa_sum + $ms, 1))") - - # Measure dig against 1.1.1.1 (Cloudflare — warm cache, but shows baseline) - ms=$(measure_ms "dig @1.1.1.1 +short +time=10 +tries=1 ${domain} A") - dig_sum=$(python3 -c "print(round($dig_sum + $ms, 1))") - done - - numa_avg=$(python3 -c "print(round($numa_sum / $ROUNDS, 1))") - dig_avg=$(python3 -c "print(round($dig_sum / $ROUNDS, 1))") - delta=$(python3 -c "d = round($numa_avg - $dig_avg, 1); print(f'+{d}' if d > 0 else str(d))") - - # Color the delta - delta_color="$GREEN" - if python3 -c "exit(0 if $numa_avg > $dig_avg * 1.5 else 1)" 2>/dev/null; then - delta_color="$AMBER" - fi - - printf "%-22s %8s ms %8s ms ${delta_color}%6s ms${RESET}\n" "$domain" "$numa_avg" "$dig_avg" "$delta" - - numa_total=$(python3 -c "print(round($numa_total + $numa_avg, 1))") - dig_total=$(python3 -c "print(round($dig_total + $dig_avg, 1))") - count=$((count + 1)) -done - -echo "" -numa_mean=$(python3 -c "print(round($numa_total / $count, 1))") -dig_mean=$(python3 -c "print(round($dig_total / $count, 1))") -delta_mean=$(python3 -c "d = round($numa_mean - $dig_mean, 1); print(f'+{d}' if d > 0 else str(d))") - -printf "${BOLD}%-22s %8s ms %8s ms %6s ms${RESET}\n" "AVERAGE" "$numa_mean" "$dig_mean" "$delta_mean" - -echo "" -echo -e "${DIM}Note: Numa resolves recursively from root hints (cold cache).${RESET}" -echo -e "${DIM}1.1.1.1 serves from Cloudflare's global cache (warm). The comparison${RESET}" -echo -e "${DIM}is intentionally unfair — it shows Numa's worst case vs the best case${RESET}" -echo -e "${DIM}of a global anycast resolver. Cached Numa queries resolve in <1ms.${RESET}"