diag_perm update
authorThomas Walker Lynch <eknp9n@reasoningtechnology.com>
Wed, 24 Sep 2025 16:06:49 +0000 (16:06 +0000)
committerThomas Walker Lynch <eknp9n@reasoningtechnology.com>
Wed, 24 Sep 2025 16:06:49 +0000 (16:06 +0000)
developer/diag_perm [deleted file]
developer/source/diag_perm
release/shell/diag_perm

diff --git a/developer/diag_perm b/developer/diag_perm
deleted file mode 100644 (file)
index d40f495..0000000
+++ /dev/null
@@ -1,105 +0,0 @@
-#!/usr/bin/env bash
-# Diagnose Man_In_Grey privilege flow: user -> setuid gasket -> python inner
-set -euo pipefail
-
-# --- locate release base from this script's real path ---
-_this="$(readlink -f "$0")"
-_shell_dir="$(cd -- "$(dirname -- "$_this")" && pwd -P)"   # .../release/shell
-_relbase="$(dirname "$_shell_dir")"                        # .../release
-
-# --- arch normalize ---
-_arch_raw=$(uname -m | tr '[:upper:]' '[:lower:]')
-case "$_arch_raw" in
-  amd64|x64)       _arch="x86_64" ;;
-  x86_64)          _arch="x86_64" ;;
-  i386|i486|i586|i686) _arch="i686" ;;
-  arm64|aarch64)   _arch="aarch64" ;;
-  armv7l)          _arch="armv7l" ;;
-  armv6l)          _arch="armv6l" ;;
-  riscv64)         _arch="riscv64" ;;
-  ppc64le|powerpc64le) _arch="ppc64le" ;;
-  s390x)           _arch="s390x" ;;
-  *)               _arch="$_arch_raw" ;;
-esac
-
-# Allow explicit overrides via args
-GASKET="${1:-"${_relbase}/${_arch}/man_in_grey_apply"}"
-WRAP="${2:-"${_relbase}/shell/Man_In_Grey"}"
-
-echo "== who/where =="
-echo "user: $(id -un) (uid=$(id -u))  groups: $(id -nG)"
-echo "pwd : $(pwd)"
-echo
-
-echo "== paths =="
-echo "wrapper: $WRAP"
-echo "gasket : $GASKET"
-echo
-
-echo "== wrapper sanity =="
-if [[ -x "$WRAP" ]]; then
-  head -n 1 "$WRAP" | sed 's/^/shebang: /'
-  echo "exec path: $(command -v "$WRAP" || echo '(not in PATH)')"
-else
-  echo "!! wrapper missing/non-exec"
-fi
-echo
-
-echo "== gasket file sanity =="
-if [[ -e "$GASKET" ]]; then
-  ls -l "$GASKET"
-  if [[ -u "$GASKET" ]]; then echo "setuid: YES"; else echo "setuid: NO"; fi
-  mp="$(dirname "$(readlink -f "$GASKET")")"
-  echo "mount: $(findmnt -no TARGET,FSTYPE,OPTIONS "$mp" 2>/dev/null || echo 'findmnt not available')"
-else
-  echo "!! gasket not found"
-fi
-echo
-
-echo "== gasket self-report (--print-flags) =="
-if [[ -x "$GASKET" ]]; then
-  "$GASKET" --print-flags || true
-else
-  echo "skip (no gasket)"
-fi
-echo
-
-echo "== python inner EUID test =="
-PYTEST="/tmp/mig_ids_$$.py"
-cat >"$PYTEST"<<'PY'
-import os, pwd
-u = os.getuid(); e = os.geteuid()
-name = pwd.getpwuid(u).pw_name if u>=0 else "?"
-print(f"py.real_uid={u} ({name})")
-print(f"py.effective_uid={e}")
-print("py.groups=", os.getgroups())
-PY
-chmod 0644 "$PYTEST"
-
-if [[ -x "$GASKET" ]]; then
-  echo "running: $GASKET --inner $PYTEST"
-  "$GASKET" --inner "$PYTEST" || true
-else
-  echo "skip (no gasket)"
-fi
-rm -f "$PYTEST"
-echo
-
-echo "== wrapper execution trace (dry) =="
-if [[ -x "$WRAP" ]]; then
-  echo "+ bash -x \"$WRAP\" --phase-2-sanity2-then-stop --stage dummy  (trace only)"
-  set +e
-  bash -x "$WRAP" --phase-2-sanity2-then-stop --stage dummy 1>/dev/null 2>&1 | sed 's/^/TRACE: /' || true
-  set -e
-else
-  echo "skip (no wrapper)"
-fi
-
-echo
-echo "== verdict (rules of thumb) =="
-cat <<'EOT'
-- If --print-flags shows flag.this_process_privileged=0: setuid isn’t taking effect (check nosuid mount, bit not set, or wrong binary).
-- If that flag is 1 and the Python test shows euid=0: privileges flow is OK; if you still get EPERM to /etc, the wrapper may bypass the gasket sometimes.
-- If the wrapper trace never execs the gasket: replace the wrapper so it always runs the gasket.
-- If root is refused for “not in sudo”, update gasket policy to allow UID 0 (you already have that patch).
-EOT
index f73f61d..d40f495 100644 (file)
@@ -1,31 +1,30 @@
 #!/usr/bin/env bash
-# Diagnose Man_In_Grey privilege flow: user → gasket (setuid) → python inner
+# Diagnose Man_In_Grey privilege flow: user -> setuid gasket -> python inner
 set -euo pipefail
 
-# --- locate repo root (best effort) ---
-script_afp="$(realpath "${BASH_SOURCE[0]}")"
-REPO_HOME="$(cd "$(dirname "$script_afp")/.." && pwd -P 2>/dev/null || pwd -P)"
+# --- locate release base from this script's real path ---
+_this="$(readlink -f "$0")"
+_shell_dir="$(cd -- "$(dirname -- "$_this")" && pwd -P)"   # .../release/shell
+_relbase="$(dirname "$_shell_dir")"                        # .../release
 
-# --- arch normalizer (same mapping we use elsewhere) ---
+# --- arch normalize ---
 _arch_raw=$(uname -m | tr '[:upper:]' '[:lower:]')
 case "$_arch_raw" in
-  amd64|x64) _arch="x86_64" ;;
-  x86_64)    _arch="x86_64" ;;
+  amd64|x64)       _arch="x86_64" ;;
+  x86_64)          _arch="x86_64" ;;
   i386|i486|i586|i686) _arch="i686" ;;
-  arm64|aarch64) _arch="aarch64" ;;
-  armv7l)    _arch="armv7l" ;;
-  armv6l)    _arch="armv6l" ;;
-  riscv64)   _arch="riscv64" ;;
+  arm64|aarch64)   _arch="aarch64" ;;
+  armv7l)          _arch="armv7l" ;;
+  armv6l)          _arch="armv6l" ;;
+  riscv64)         _arch="riscv64" ;;
   ppc64le|powerpc64le) _arch="ppc64le" ;;
-  s390x)     _arch="s390x" ;;
-  *)         _arch="$_arch_raw" ;;
+  s390x)           _arch="s390x" ;;
+  *)               _arch="$_arch_raw" ;;
 esac
 
-# Allow overriding via env/args
-REL_BASE="${REPO_HOME}/tool_shared/third_party/Man_In_Grey/release"
-REL_BASE="${REL_BASE:-${REPO_HOME}/release}"
-GASKET="${1:-${REL_BASE}/${_arch}/man_in_grey_apply}"
-WRAP="${2:-${REL_BASE}/shell/Man_In_Grey}"
+# Allow explicit overrides via args
+GASKET="${1:-"${_relbase}/${_arch}/man_in_grey_apply"}"
+WRAP="${2:-"${_relbase}/shell/Man_In_Grey"}"
 
 echo "== who/where =="
 echo "user: $(id -un) (uid=$(id -u))  groups: $(id -nG)"
@@ -49,9 +48,7 @@ echo
 echo "== gasket file sanity =="
 if [[ -e "$GASKET" ]]; then
   ls -l "$GASKET"
-  # setuid bit present?
   if [[ -u "$GASKET" ]]; then echo "setuid: YES"; else echo "setuid: NO"; fi
-  # mount options
   mp="$(dirname "$(readlink -f "$GASKET")")"
   echo "mount: $(findmnt -no TARGET,FSTYPE,OPTIONS "$mp" 2>/dev/null || echo 'findmnt not available')"
 else
@@ -70,13 +67,12 @@ echo
 echo "== python inner EUID test =="
 PYTEST="/tmp/mig_ids_$$.py"
 cat >"$PYTEST"<<'PY'
-import os, sys, grp, pwd
+import os, pwd
 u = os.getuid(); e = os.geteuid()
 name = pwd.getpwuid(u).pw_name if u>=0 else "?"
 print(f"py.real_uid={u} ({name})")
 print(f"py.effective_uid={e}")
 print("py.groups=", os.getgroups())
-sys.exit(0)
 PY
 chmod 0644 "$PYTEST"
 
@@ -102,9 +98,8 @@ fi
 echo
 echo "== verdict (rules of thumb) =="
 cat <<'EOT'
-- If --print-flags shows "flag.this_process_privileged=0": the setuid bit is not taking effect (check mount nosuid, file perms, or wrong gasket path).
-- If --print-flags is 1 but python euid is 0: privileges are flowing OK; problems are likely in the shell wrapper bypassing the gasket.
-- If --print-flags is 1 but python euid is NOT 0: something is stripping EUID across exec (rare: no_new_privs or an LSM). Check `grep NoNewPrivs /proc/$$/status` from the caller shell and try running outside wrappers.
-- If wrapper trace never execs the gasket: fix the wrapper to always call the gasket.
-- If you are root and see a 'not in sudo' refusal: update gasket policy to allow root (special-case UID 0).
+- If --print-flags shows flag.this_process_privileged=0: setuid isn’t taking effect (check nosuid mount, bit not set, or wrong binary).
+- If that flag is 1 and the Python test shows euid=0: privileges flow is OK; if you still get EPERM to /etc, the wrapper may bypass the gasket sometimes.
+- If the wrapper trace never execs the gasket: replace the wrapper so it always runs the gasket.
+- If root is refused for “not in sudo”, update gasket policy to allow UID 0 (you already have that patch).
 EOT
index f73f61d..d40f495 100755 (executable)
@@ -1,31 +1,30 @@
 #!/usr/bin/env bash
-# Diagnose Man_In_Grey privilege flow: user → gasket (setuid) → python inner
+# Diagnose Man_In_Grey privilege flow: user -> setuid gasket -> python inner
 set -euo pipefail
 
-# --- locate repo root (best effort) ---
-script_afp="$(realpath "${BASH_SOURCE[0]}")"
-REPO_HOME="$(cd "$(dirname "$script_afp")/.." && pwd -P 2>/dev/null || pwd -P)"
+# --- locate release base from this script's real path ---
+_this="$(readlink -f "$0")"
+_shell_dir="$(cd -- "$(dirname -- "$_this")" && pwd -P)"   # .../release/shell
+_relbase="$(dirname "$_shell_dir")"                        # .../release
 
-# --- arch normalizer (same mapping we use elsewhere) ---
+# --- arch normalize ---
 _arch_raw=$(uname -m | tr '[:upper:]' '[:lower:]')
 case "$_arch_raw" in
-  amd64|x64) _arch="x86_64" ;;
-  x86_64)    _arch="x86_64" ;;
+  amd64|x64)       _arch="x86_64" ;;
+  x86_64)          _arch="x86_64" ;;
   i386|i486|i586|i686) _arch="i686" ;;
-  arm64|aarch64) _arch="aarch64" ;;
-  armv7l)    _arch="armv7l" ;;
-  armv6l)    _arch="armv6l" ;;
-  riscv64)   _arch="riscv64" ;;
+  arm64|aarch64)   _arch="aarch64" ;;
+  armv7l)          _arch="armv7l" ;;
+  armv6l)          _arch="armv6l" ;;
+  riscv64)         _arch="riscv64" ;;
   ppc64le|powerpc64le) _arch="ppc64le" ;;
-  s390x)     _arch="s390x" ;;
-  *)         _arch="$_arch_raw" ;;
+  s390x)           _arch="s390x" ;;
+  *)               _arch="$_arch_raw" ;;
 esac
 
-# Allow overriding via env/args
-REL_BASE="${REPO_HOME}/tool_shared/third_party/Man_In_Grey/release"
-REL_BASE="${REL_BASE:-${REPO_HOME}/release}"
-GASKET="${1:-${REL_BASE}/${_arch}/man_in_grey_apply}"
-WRAP="${2:-${REL_BASE}/shell/Man_In_Grey}"
+# Allow explicit overrides via args
+GASKET="${1:-"${_relbase}/${_arch}/man_in_grey_apply"}"
+WRAP="${2:-"${_relbase}/shell/Man_In_Grey"}"
 
 echo "== who/where =="
 echo "user: $(id -un) (uid=$(id -u))  groups: $(id -nG)"
@@ -49,9 +48,7 @@ echo
 echo "== gasket file sanity =="
 if [[ -e "$GASKET" ]]; then
   ls -l "$GASKET"
-  # setuid bit present?
   if [[ -u "$GASKET" ]]; then echo "setuid: YES"; else echo "setuid: NO"; fi
-  # mount options
   mp="$(dirname "$(readlink -f "$GASKET")")"
   echo "mount: $(findmnt -no TARGET,FSTYPE,OPTIONS "$mp" 2>/dev/null || echo 'findmnt not available')"
 else
@@ -70,13 +67,12 @@ echo
 echo "== python inner EUID test =="
 PYTEST="/tmp/mig_ids_$$.py"
 cat >"$PYTEST"<<'PY'
-import os, sys, grp, pwd
+import os, pwd
 u = os.getuid(); e = os.geteuid()
 name = pwd.getpwuid(u).pw_name if u>=0 else "?"
 print(f"py.real_uid={u} ({name})")
 print(f"py.effective_uid={e}")
 print("py.groups=", os.getgroups())
-sys.exit(0)
 PY
 chmod 0644 "$PYTEST"
 
@@ -102,9 +98,8 @@ fi
 echo
 echo "== verdict (rules of thumb) =="
 cat <<'EOT'
-- If --print-flags shows "flag.this_process_privileged=0": the setuid bit is not taking effect (check mount nosuid, file perms, or wrong gasket path).
-- If --print-flags is 1 but python euid is 0: privileges are flowing OK; problems are likely in the shell wrapper bypassing the gasket.
-- If --print-flags is 1 but python euid is NOT 0: something is stripping EUID across exec (rare: no_new_privs or an LSM). Check `grep NoNewPrivs /proc/$$/status` from the caller shell and try running outside wrappers.
-- If wrapper trace never execs the gasket: fix the wrapper to always call the gasket.
-- If you are root and see a 'not in sudo' refusal: update gasket policy to allow root (special-case UID 0).
+- If --print-flags shows flag.this_process_privileged=0: setuid isn’t taking effect (check nosuid mount, bit not set, or wrong binary).
+- If that flag is 1 and the Python test shows euid=0: privileges flow is OK; if you still get EPERM to /etc, the wrapper may bypass the gasket sometimes.
+- If the wrapper trace never execs the gasket: replace the wrapper so it always runs the gasket.
+- If root is refused for “not in sudo”, update gasket policy to allow UID 0 (you already have that patch).
 EOT