#!/bin/bash
#
# i86pc-audit.sh — Find all remaining i86pc references in the hammerhead tree
#
# Categorizes references as:
#   BUILD-PATH  — Source directory names, Makefile SRCDIR/PLATFORM paths (expected)
#   RUNTIME     — Strings that appear in compiled output or runtime behavior (fix needed)
#   COMMENT     — In comments or documentation only (cosmetic)
#   UNKNOWN     — Needs manual review
#
# Usage: ./i86pc-audit.sh [root_dir]
#

set -o pipefail

ROOT="${1:-$(cd "$(dirname "$0")/../../.." && pwd)}"
SRCDIR="$ROOT/usr/src"

if [ ! -d "$SRCDIR" ]; then
    echo "ERROR: Cannot find usr/src under $ROOT" >&2
    exit 1
fi

# Temp files
HITS=$(mktemp)
CATEGORIZED=$(mktemp)
trap 'rm -f "$HITS" "$CATEGORIZED"' EXIT

echo "============================================================"
echo "i86pc Reference Audit — $(date '+%Y-%m-%d %H:%M')"
echo "Root: $ROOT"
echo "============================================================"
echo ""

#
# Step 1: Find ALL i86pc references (excluding .git, binaries, .o files)
#
echo "Scanning for 'i86pc' references..."
/usr/bin/grep -rn --include='*.c' --include='*.h' --include='*.s' --include='*.S' \
    --include='*.sh' --include='*.ksh' --include='*.pl' --include='*.py' \
    --include='*.xml' --include='*.dtd' --include='*.dtd.1' \
    --include='*.conf' --include='*.toml' --include='*.json' --include='*.yaml' \
    --include='*.4th' --include='*.msg' --include='*.ld' \
    --include='*.mf' --include='*.p5m' --include='*.rc' \
    --include='*.properties' \
    --include='Makefile' --include='Makefile.*' --include='mapfile*' \
    --include='loader.conf*' --include='Targetdirs' \
    'i86pc' "$SRCDIR" 2>/dev/null > "$HITS"

TOTAL=$(wc -l < "$HITS")
echo "Found $TOTAL total references."
echo ""

#
# Step 2: Categorize each reference
#

# Build-path patterns: directory names, SRCDIR, include paths referencing source tree
BUILD_PATH_PATTERNS=(
    'SRCDIR.*i86pc'
    'PLATFORM.*=.*i86pc'       # PLATFORM = i86pc (build variable)
    '/uts/i86pc'               # Source tree path
    '/modules/i86pc'           # Source tree path
    '/maps/i86pc'              # Source tree path (topo map source dir, now maps/amd64)
    '-I.*i86pc'                # Include path
    'MACH_DIR.*i86pc'
    'PLATFORM_DIR.*i86pc'
    'i86pc/Makefile'           # Makefile in i86pc source dir
    'CONF_SRCDIR.*i86pc'
    'CLOSED_SRCDIR.*i86pc'
    'SRC/uts/i86pc'
    'usr/src.*i86pc'           # Source path reference
    'pci_i86pc'                # Source file name reference
)

# Comment patterns
COMMENT_PATTERNS=(
    '^\s*[#*]'                 # Line starts with # or *
    '^\s*//'                   # Line starts with //
    '^\s*/\*'                  # Line starts with /*
    '\*/'                      # End of block comment
    '^\s*\*\s'                 # Continuation of block comment
    'Copyright'
    'CDDL'
    'XXX'
    'TODO'
    'NOTE'
    'FIXME'
    'formerly'
    'was i86pc'
    'example'
    'e\.g\.'
    '<!--'
)

# Known runtime patterns that need fixing
RUNTIME_PATTERNS=(
    'strcmp.*"i86pc"'
    'strncmp.*"i86pc"'
    'strstr.*"i86pc"'
    '"i86pc"'
    'i86pc.*root.*nexus'
    'platform.*i86pc.*lib'     # Runtime library path
    'platform.*i86pc.*boot'    # Runtime boot path
    'platform.*i86pc.*kernel'  # Runtime kernel path
    '/platform/i86pc/'         # Absolute runtime path (NOT in source tree context)
    'ARCH.*=.*i86pc'           # Install arch variable
    'uname.*i86pc'
    'i86pc.*topology'
    'mfg-name.*i86pc'
    'impl-arch-name.*i86pc'
)

categorize_line() {
    local file="$1"
    local line="$2"
    local content="$3"

    # Strip to relative path
    local relpath="${file#$SRCDIR/}"

    # Check if it's a Makefile or build file
    local is_makefile=0
    case "$file" in
        */Makefile*|*/Makefile) is_makefile=1 ;;
    esac

    # Check comment patterns first
    for pat in "${COMMENT_PATTERNS[@]}"; do
        if printf '%s\n' "$content" | grep -qE -- "$pat"; then
            echo "COMMENT|$relpath:$line|$content"
            return
        fi
    done

    # Check build-path patterns
    for pat in "${BUILD_PATH_PATTERNS[@]}"; do
        if printf '%s\n' "$content" | grep -qE -- "$pat"; then
            echo "BUILD-PATH|$relpath:$line|$content"
            return
        fi
    done

    # Check known runtime patterns
    for pat in "${RUNTIME_PATTERNS[@]}"; do
        if printf '%s\n' "$content" | grep -qiE -- "$pat"; then
            echo "RUNTIME|$relpath:$line|$content"
            return
        fi
    done

    # If it's in a source directory path, it's a build path
    if printf '%s\n' "$relpath" | grep -qE -- '(uts|lib|cmd)/.*i86pc'; then
        # But the content itself might be runtime
        if printf '%s\n' "$content" | grep -qE -- '"i86pc"|i86pc[^/]'; then
            echo "UNKNOWN|$relpath:$line|$content"
        else
            echo "BUILD-PATH|$relpath:$line|$content"
        fi
        return
    fi

    echo "UNKNOWN|$relpath:$line|$content"
}

echo "Categorizing references..."

while IFS= read -r hitline; do
    # Parse rg output: /path/to/file:LINENUM:content
    file="${hitline%%:*}"
    rest="${hitline#*:}"
    line="${rest%%:*}"
    content="${rest#*:}"
    [ -z "$file" ] && continue
    categorize_line "$file" "$line" "$content" >> "$CATEGORIZED"
done < "$HITS"

#
# Step 3: Report by category
#

echo ""
echo "============================================================"
echo "CATEGORY SUMMARY"
echo "============================================================"
echo ""

for category in RUNTIME UNKNOWN BUILD-PATH COMMENT; do
    count=$(grep -c "^$category|" "$CATEGORIZED" 2>/dev/null || echo 0)
    echo "  $category: $count"
done

echo ""

#
# Step 4: Detail — RUNTIME references (these likely need fixing)
#
RUNTIME_COUNT=$(grep -c "^RUNTIME|" "$CATEGORIZED" 2>/dev/null || echo 0)
if [ "$RUNTIME_COUNT" -gt 0 ]; then
    echo "============================================================"
    echo "RUNTIME REFERENCES ($RUNTIME_COUNT) — Likely need fixing"
    echo "============================================================"
    echo ""
    grep "^RUNTIME|" "$CATEGORIZED" | while IFS='|' read -r cat loc content; do
        echo "  $loc"
        echo "    $content"
        echo ""
    done
fi

#
# Step 5: Detail — UNKNOWN references (need manual review)
#
UNKNOWN_COUNT=$(grep -c "^UNKNOWN|" "$CATEGORIZED" 2>/dev/null || echo 0)
if [ "$UNKNOWN_COUNT" -gt 0 ]; then
    echo "============================================================"
    echo "UNKNOWN REFERENCES ($UNKNOWN_COUNT) — Need manual review"
    echo "============================================================"
    echo ""
    grep "^UNKNOWN|" "$CATEGORIZED" | while IFS='|' read -r cat loc content; do
        echo "  $loc"
        echo "    $content"
        echo ""
    done
fi

#
# Step 6: Detail — BUILD-PATH references (expected, informational)
#
BUILD_COUNT=$(grep -c "^BUILD-PATH|" "$CATEGORIZED" 2>/dev/null || echo 0)
if [ "$BUILD_COUNT" -gt 0 ]; then
    echo "============================================================"
    echo "BUILD-PATH REFERENCES ($BUILD_COUNT) — Expected (source dirs)"
    echo "============================================================"
    echo ""
    # Group by directory for readability
    grep "^BUILD-PATH|" "$CATEGORIZED" | while IFS='|' read -r cat loc content; do
        echo "  $loc"
    done | sort
fi

echo ""

#
# Step 7: Detail — COMMENT references (cosmetic only)
#
COMMENT_COUNT=$(grep -c "^COMMENT|" "$CATEGORIZED" 2>/dev/null || echo 0)
if [ "$COMMENT_COUNT" -gt 0 ]; then
    echo ""
    echo "============================================================"
    echo "COMMENT REFERENCES ($COMMENT_COUNT) — Cosmetic only"
    echo "============================================================"
    echo ""
    grep "^COMMENT|" "$CATEGORIZED" | while IFS='|' read -r cat loc content; do
        echo "  $loc"
    done | sort
fi

echo ""
echo "============================================================"
echo "AUDIT COMPLETE"
echo "============================================================"
echo ""
echo "Action items:"
echo "  - RUNTIME: These reference i86pc in code that executes at runtime."
echo "    Review each one — should it accept 'amd64' instead/also?"
echo "  - UNKNOWN: Could not auto-categorize. Manual review needed."
echo "  - BUILD-PATH: Expected. Source directory names stay as i86pc."
echo "  - COMMENT: Informational only. Update if desired."
