diff options
Diffstat (limited to 'test_runner.sh')
| -rwxr-xr-x | test_runner.sh | 334 |
1 files changed, 334 insertions, 0 deletions
diff --git a/test_runner.sh b/test_runner.sh new file mode 100755 index 0000000..d478f55 --- /dev/null +++ b/test_runner.sh @@ -0,0 +1,334 @@ +#!/bin/bash + +# CCDJIT Comprehensive Test Runner +# This script provides a more advanced testing interface with better organization + +# Colors for pretty output +RED='\033[0;31m' +GREEN='\033[0;32m' +YELLOW='\033[1;33m' +BLUE='\033[0;34m' +PURPLE='\033[0;35m' +CYAN='\033[0;36m' +WHITE='\033[1;37m' +GRAY='\033[0;37m' +NC='\033[0m' # No Color + +# Test configuration +declare -A test_map +test_map["./tests/add2.c"]=3 +test_map["./tests/arithmetic.c"]=28 +test_map["./tests/comparison.c"]=5 +test_map["./tests/logical.c"]=3 +test_map["./tests/if_else.c"]=12 +test_map["./tests/while_loop.c"]=10 +test_map["./tests/for_loop.c"]=6 +test_map["./tests/function_call.c"]=17 +test_map["./tests/recursive.c"]=24 +test_map["./tests/bitwise.c"]=58 +test_map["./tests/pointers.c"]=184 +test_map["./tests/arrays.c"]=150 +test_map["./tests/strings.c"]=5 +test_map["./tests/edge_cases.c"]=12 + +# Error tests (expected to fail with non-zero exit code) +declare -A error_test_map +error_test_map["./tests/error_syntax.c"]="syntax" +error_test_map["./tests/error_undefined_var.c"]="undefined" +error_test_map["./tests/error_type_mismatch.c"]="type" + +# Test categories +declare -A test_categories +test_categories["./tests/add2.c"]="Basic" +test_categories["./tests/arithmetic.c"]="Arithmetic" +test_categories["./tests/comparison.c"]="Comparison" +test_categories["./tests/logical.c"]="Logical" +test_categories["./tests/if_else.c"]="Control Flow" +test_categories["./tests/while_loop.c"]="Control Flow" +test_categories["./tests/for_loop.c"]="Control Flow" +test_categories["./tests/function_call.c"]="Functions" +test_categories["./tests/recursive.c"]="Functions" +test_categories["./tests/bitwise.c"]="Bitwise" +test_categories["./tests/pointers.c"]="Pointers" +test_categories["./tests/arrays.c"]="Arrays" +test_categories["./tests/strings.c"]="Strings" +test_categories["./tests/edge_cases.c"]="Edge Cases" +test_categories["./tests/error_syntax.c"]="Error Tests" +test_categories["./tests/error_undefined_var.c"]="Error Tests" +test_categories["./tests/error_type_mismatch.c"]="Error Tests" + +print_header() { + echo -e "${CYAN}╔══════════════════════════════════════════════════════════════════════════════╗${NC}" + echo -e "${CYAN}║${WHITE} CCDJIT Comprehensive Test Suite ${CYAN}║${NC}" + echo -e "${CYAN}╚══════════════════════════════════════════════════════════════════════════════╝${NC}" + echo +} + +print_test_header() { + local test_file="$1" + local category="${test_categories[$test_file]}" + local test_name=$(basename "$test_file" .c) + echo -e "${BLUE}┌─ ${WHITE}$test_name${BLUE} (${YELLOW}$category${BLUE})${NC}" + echo -e "${BLUE}│${NC} File: $test_file" + + if [ -n "${test_map[$test_file]}" ]; then + echo -e "${BLUE}│${NC} Expected: ${test_map[$test_file]}" + elif [ -n "${error_test_map[$test_file]}" ]; then + echo -e "${BLUE}│${NC} Expected: ${RED}ERROR${NC} (${error_test_map[$test_file]})" + fi +} + +print_test_result() { + local test_file="$1" + local expected="$2" + local actual="$3" + local status="$4" + local is_error="$5" + + if [ "$status" == "PASS" ]; then + if [ "$is_error" == "true" ]; then + echo -e "${BLUE}│${NC} Result: ${GREEN}✓ PASSED${NC} (correctly failed with exit code $actual)" + else + echo -e "${BLUE}│${NC} Result: ${GREEN}✓ PASSED${NC} (got $actual)" + fi + echo -e "${BLUE}└─${GREEN} SUCCESS${NC}" + else + if [ "$is_error" == "true" ]; then + echo -e "${BLUE}│${NC} Result: ${RED}✗ FAILED${NC} (expected error, got exit code $actual)" + else + echo -e "${BLUE}│${NC} Result: ${RED}✗ FAILED${NC} (expected $expected, got $actual)" + fi + echo -e "${BLUE}└─${RED} FAILURE${NC}" + fi + echo +} + +print_summary() { + local passed="$1" + local failed="$2" + local total="$3" + local error_passed="$4" + local error_failed="$5" + local error_total="$6" + + echo -e "${CYAN}╔══════════════════════════════════════════════════════════════════════════════╗${NC}" + echo -e "${CYAN}║${WHITE} Test Summary ${CYAN}║${NC}" + echo -e "${CYAN}╠══════════════════════════════════════════════════════════════════════════════╣${NC}" + + if [ "$failed" -eq 0 ] && [ "$error_failed" -eq 0 ]; then + echo -e "${CYAN}║${GREEN} All tests passed! ${WHITE}(${passed}/${total} functional, ${error_passed}/${error_total} error)${CYAN} ║${NC}" + else + echo -e "${CYAN}║${GREEN} Functional Tests: ${passed}/${total}${CYAN} │ ${RED}Failed: ${failed}${CYAN} ║${NC}" + echo -e "${CYAN}║${GREEN} Error Tests: ${error_passed}/${error_total}${CYAN} │ ${RED}Failed: ${error_failed}${CYAN} ║${NC}" + fi + + echo -e "${CYAN}╚══════════════════════════════════════════════════════════════════════════════╝${NC}" +} + +run_functional_tests() { + local count=0 + local passed=0 + local failed=0 + + echo -e "${PURPLE}Running Functional Tests...${NC}" >&2 + echo >&2 + + for key in "${!test_map[@]}"; do + print_test_header "$key" >&2 + + local output + local exit_code + local actual_result + output=$(./bin/ccdjit "$key" 2>&1) + exit_code=$? + + # Extract the actual result from "JIT returned: X" line + actual_result=$(echo "$output" | grep "JIT returned:" | sed 's/.*JIT returned: //' | tail -1) + if [ -z "$actual_result" ]; then + actual_result=$exit_code + fi + + if [ "${test_map[$key]}" = "$actual_result" ]; then + print_test_result "$key" "${test_map[$key]}" "$actual_result" "PASS" "false" >&2 + passed=$((passed+1)) + else + print_test_result "$key" "${test_map[$key]}" "$actual_result" "FAIL" "false" >&2 + failed=$((failed+1)) + fi + count=$((count+1)) + done + + echo "$passed $failed $count" +} + +run_error_tests() { + local count=0 + local passed=0 + local failed=0 + + echo -e "${PURPLE}Running Error Tests...${NC}" >&2 + echo >&2 + + for key in "${!error_test_map[@]}"; do + print_test_header "$key" >&2 + + local output + local exit_code + output=$(./bin/ccdjit "$key" 2>&1) + exit_code=$? + + if [ $exit_code -ne 0 ]; then + print_test_result "$key" "ERROR" "$exit_code" "PASS" "true" >&2 + passed=$((passed+1)) + else + print_test_result "$key" "ERROR" "$exit_code" "FAIL" "true" >&2 + failed=$((failed+1)) + fi + count=$((count+1)) + done + + echo "$passed $failed $count" +} + +run_all_tests() { + print_header + + local func_results + local error_results + + func_results=($(run_functional_tests)) + error_results=($(run_error_tests)) + + # Ensure all stderr output is flushed before showing summary + sleep 0.1 + + local func_passed=${func_results[0]} + local func_failed=${func_results[1]} + local func_total=${func_results[2]} + + local error_passed=${error_results[0]} + local error_failed=${error_results[1]} + local error_total=${error_results[2]} + + print_summary $func_passed $func_failed $func_total $error_passed $error_failed $error_total +} + +run_single_test() { + local test_file="$1" + + if [ -z "${test_map[$test_file]}" ] && [ -z "${error_test_map[$test_file]}" ]; then + echo -e "${RED}Error: Test file '$test_file' not found in test suite${NC}" + exit 1 + fi + + print_header + print_test_header "$test_file" + + local output + local exit_code + local actual_result + output=$(./bin/ccdjit "$test_file" 2>&1) + exit_code=$? + + # Extract the actual result from "JIT returned: X" line + actual_result=$(echo "$output" | grep "JIT returned:" | sed 's/.*JIT returned: //' | tail -1) + if [ -z "$actual_result" ]; then + actual_result=$exit_code + fi + + if [ -n "${test_map[$test_file]}" ]; then + # Functional test + if [ "${test_map[$test_file]}" = "$actual_result" ]; then + print_test_result "$test_file" "${test_map[$test_file]}" "$actual_result" "PASS" "false" + else + print_test_result "$test_file" "${test_map[$test_file]}" "$actual_result" "FAIL" "false" + fi + else + # Error test + if [ $exit_code -ne 0 ]; then + print_test_result "$test_file" "ERROR" "$exit_code" "PASS" "true" + else + print_test_result "$test_file" "ERROR" "$exit_code" "FAIL" "true" + fi + fi +} + +list_tests() { + echo -e "${CYAN}Available Tests:${NC}" + echo + + echo -e "${GREEN}Functional Tests:${NC}" + for key in "${!test_map[@]}"; do + local category="${test_categories[$key]}" + local test_name=$(basename "$key" .c) + echo -e " ${WHITE}$test_name${NC} (${YELLOW}$category${NC}) - Expected: ${test_map[$key]}" + done + + echo + echo -e "${RED}Error Tests:${NC}" + for key in "${!error_test_map[@]}"; do + local category="${test_categories[$key]}" + local test_name=$(basename "$key" .c) + echo -e " ${WHITE}$test_name${NC} (${YELLOW}$category${NC}) - Expected: ERROR" + done +} + +show_help() { + echo -e "${CYAN}CCDJIT Test Runner${NC}" + echo + echo "Usage: $0 [COMMAND] [OPTIONS]" + echo + echo "Commands:" + echo " all Run all tests (functional + error)" + echo " functional Run only functional tests" + echo " error Run only error tests" + echo " test <file> Run a specific test file" + echo " list List all available tests" + echo " help Show this help message" + echo + echo "Examples:" + echo " $0 all" + echo " $0 functional" + echo " $0 test ./tests/arithmetic.c" + echo " $0 list" +} + +# Main script logic +case "$1" in + "all") + run_all_tests + ;; + "functional") + print_header + func_results=($(run_functional_tests)) + sleep 0.1 + print_summary ${func_results[0]} ${func_results[1]} ${func_results[2]} 0 0 0 + ;; + "error") + print_header + error_results=($(run_error_tests)) + sleep 0.1 + print_summary 0 0 0 ${error_results[0]} ${error_results[1]} ${error_results[2]} + ;; + "test") + if [ -z "$2" ]; then + echo -e "${RED}Error: Please specify a test file${NC}" + exit 1 + fi + run_single_test "$2" + ;; + "list") + list_tests + ;; + "help"|"-h"|"--help") + show_help + ;; + "") + show_help + ;; + *) + echo -e "${RED}Error: Unknown command '$1'${NC}" + echo "Use '$0 help' for usage information" + exit 1 + ;; +esac |
