You can not select more than 25 topics
Topics must start with a letter or number, can include dashes ('-') and can be up to 35 characters long.
122 lines
3.2 KiB
122 lines
3.2 KiB
#!/usr/bin/env bash
|
|
set -euo pipefail
|
|
|
|
ROOT_DIR="$(cd "$(dirname "${BASH_SOURCE[0]}")/.." && pwd)"
|
|
COMPILER="$ROOT_DIR/build/bin/compiler"
|
|
TMP_DIR="$ROOT_DIR/build/test_compiler"
|
|
TEST_DIRS=("$ROOT_DIR/test/test_case/functional" "$ROOT_DIR/test/test_case/performance")
|
|
|
|
if [[ ! -x "$COMPILER" ]]; then
|
|
echo "未找到编译器: $COMPILER"
|
|
echo "请先构建编译器,例如: mkdir -p build && cd build && cmake .. && make -j"
|
|
exit 1
|
|
fi
|
|
|
|
mkdir -p "$TMP_DIR"
|
|
|
|
ir_total=0
|
|
ir_pass=0
|
|
result_total=0
|
|
result_pass=0
|
|
|
|
ir_failures=()
|
|
result_failures=()
|
|
|
|
function normalize_file() {
|
|
sed 's/\r$//' "$1"
|
|
}
|
|
|
|
for test_dir in "${TEST_DIRS[@]}"; do
|
|
if [[ ! -d "$test_dir" ]]; then
|
|
echo "跳过不存在的测试目录: $test_dir"
|
|
continue
|
|
fi
|
|
|
|
shopt -s nullglob
|
|
for input in "$test_dir"/*.sy; do
|
|
ir_total=$((ir_total+1))
|
|
base=$(basename "$input")
|
|
stem=${base%.sy}
|
|
out_dir="$TMP_DIR/$(basename "$test_dir")"
|
|
mkdir -p "$out_dir"
|
|
ll_file="$out_dir/$stem.ll"
|
|
stdout_file="$out_dir/$stem.stdout"
|
|
expected_file="$test_dir/$stem.out"
|
|
stdin_file="$test_dir/$stem.in"
|
|
|
|
echo "[TEST] $input"
|
|
compiler_status=0
|
|
compiler_output=
|
|
compiler_output=$("$COMPILER" --emit-ir "$input" 2>&1) || compiler_status=$?
|
|
printf '%s\n' "$compiler_output" | sed '/^\[DEBUG/d' > "$ll_file"
|
|
|
|
if [[ $compiler_status -ne 0 ]]; then
|
|
echo " [IR] 编译失败: 返回码 $compiler_status"
|
|
ir_failures+=("$input: compiler failed ($compiler_status)")
|
|
continue
|
|
fi
|
|
|
|
if ! grep -qE '^define ' "$ll_file"; then
|
|
echo " [IR] 失败: 未生成有效函数定义"
|
|
ir_failures+=("$input: invalid IR output")
|
|
continue
|
|
fi
|
|
|
|
ir_pass=$((ir_pass+1))
|
|
echo " [IR] 生成成功"
|
|
|
|
if [[ -f "$expected_file" ]]; then
|
|
result_total=$((result_total+1))
|
|
expected=$(normalize_file "$expected_file")
|
|
run_status=0
|
|
if [[ -f "$stdin_file" ]]; then
|
|
lli "$ll_file" < "$stdin_file" > "$stdout_file" 2>&1 || run_status=$?
|
|
else
|
|
lli "$ll_file" > "$stdout_file" 2>&1 || run_status=$?
|
|
fi
|
|
|
|
if [[ ! -s "$stdout_file" && "$expected" =~ ^-?[0-9]+$ ]]; then
|
|
if [[ "$run_status" -eq "$expected" ]]; then
|
|
result_pass=$((result_pass+1))
|
|
echo " [RUN] 返回码匹配"
|
|
else
|
|
echo " [RUN] 返回码不匹配: got $run_status"
|
|
result_failures+=("$input: exit code mismatch (got $run_status)")
|
|
fi
|
|
else
|
|
if diff -u <(printf '%s\n' "$expected") <(normalize_file "$stdout_file") > "$out_dir/$stem.diff"; then
|
|
result_pass=$((result_pass+1))
|
|
echo " [RUN] 输出匹配"
|
|
else
|
|
echo " [RUN] 输出不匹配"
|
|
result_failures+=("$input: output mismatch")
|
|
fi
|
|
fi
|
|
else
|
|
echo " [RUN] 未找到预期输出 $expected_file,跳过结果验证"
|
|
fi
|
|
done
|
|
shopt -u nullglob
|
|
|
|
done
|
|
|
|
cat <<EOF
|
|
测试完成。
|
|
IR 生成: $ir_pass / $ir_total
|
|
结果匹配: $result_pass / $result_total
|
|
EOF
|
|
|
|
if [[ ${#ir_failures[@]} -gt 0 ]]; then
|
|
echo "\nIR 失败列表:"
|
|
for item in "${ir_failures[@]}"; do
|
|
echo " $item"
|
|
done
|
|
fi
|
|
|
|
if [[ ${#result_failures[@]} -gt 0 ]]; then
|
|
echo "\n结果失败列表:"
|
|
for item in "${result_failures[@]}"; do
|
|
echo " $item"
|
|
done
|
|
fi
|