import stdio
import t, c
import string


# ============================================================
# deco_test - t/c 装饰器测试
#
# 测试 t.CDefine / t.CExport / t.CInline / t.CExtern / t.State
# ============================================================


# Test 1: t.CDefine - 常量定义
MAX_VALUE: t.CDefine = 256
PI_APPROX: t.CDefine = 314
# Test 10: t.CDefine 作为 t.CArray 的 count
ARR_SIZE: t.CDefine = 8


# Test 2: t.CExport - 导出函数标记
def ExportedAdd(a: t.CInt, b: t.CInt) -> t.CInt | t.CExport:
    return a + b


# Test 3: t.CInline - 内联函数标记
def InlineSquare(x: t.CInt) -> t.CInt | t.CInline:
    return x * x


# Test 4: 普通函数（无装饰器，作为对照）
def NormalSub(a: t.CInt, b: t.CInt) -> t.CInt:
    return a - b


# Test 5: t.CExport 与 t.CInline 组合
def ExportedInlineCube(x: t.CInt) -> t.CInt | t.CExport | t.CInline:
    return x * x * x


# Test 6: t.CExport 返回指针
def ExportedFindChar(s: str, ch: t.CInt) -> str | t.CExport:
    return string.strchr(s, ch)


def test_cdefine():
    stdio.printf("--- Test 1: t.CDefine ---\n")
    stdio.printf("MAX_VALUE=%d (expect 256)\n", MAX_VALUE)
    stdio.printf("PI_APPROX=%d (expect 314)\n", PI_APPROX)
    if MAX_VALUE == 256:
        stdio.printf("MAX_VALUE OK\n")
    else:
        stdio.printf("MAX_VALUE FAIL\n")
    if PI_APPROX == 314:
        stdio.printf("PI_APPROX OK\n")
    else:
        stdio.printf("PI_APPROX FAIL\n")


def test_cexport():
    stdio.printf("--- Test 2: t.CExport ---\n")
    r: t.CInt = ExportedAdd(3, 4)
    stdio.printf("ExportedAdd(3,4)=%d (expect 7)\n", r)
    if r == 7:
        stdio.printf("ExportedAdd OK\n")
    else:
        stdio.printf("ExportedAdd FAIL\n")


def test_cinline():
    stdio.printf("--- Test 3: t.CInline ---\n")
    r: t.CInt = InlineSquare(5)
    stdio.printf("InlineSquare(5)=%d (expect 25)\n", r)
    if r == 25:
        stdio.printf("InlineSquare OK\n")
    else:
        stdio.printf("InlineSquare FAIL\n")


def test_deco_normal():
    stdio.printf("--- Test 4: normal function ---\n")
    r: t.CInt = NormalSub(10, 3)
    stdio.printf("NormalSub(10,3)=%d (expect 7)\n", r)
    if r == 7:
        stdio.printf("NormalSub OK\n")
    else:
        stdio.printf("NormalSub FAIL\n")


def test_export_inline():
    stdio.printf("--- Test 5: t.CExport | t.CInline ---\n")
    r: t.CInt = ExportedInlineCube(3)
    stdio.printf("ExportedInlineCube(3)=%d (expect 27)\n", r)
    if r == 27:
        stdio.printf("ExportedInlineCube OK\n")
    else:
        stdio.printf("ExportedInlineCube FAIL\n")


def test_export_ptr():
    stdio.printf("--- Test 6: t.CExport return ptr ---\n")
    p: str = ExportedFindChar("Hello", 108)  # 'l' = 108
    if p is not None:
        stdio.printf("ExportedFindChar found, char=%d (expect 108)\n", c.Deref(p))
        if c.Deref(p) == 108:
            stdio.printf("ExportedFindChar OK\n")
        else:
            stdio.printf("ExportedFindChar FAIL\n")
    else:
        stdio.printf("ExportedFindChar NOT FOUND (FAIL)\n")


# Test 7: t.CExtern | t.CExport - 外部声明函数（pass 体）
# 声明一个外部函数，翻译器应生成 declare 而非 define
def ExternalDecl(x: t.CInt) -> t.CInt | t.CExtern | t.CExport: pass


# Test 8: t.State - 状态声明（等价于 CExtern | CExport）
def StateDecl(x: t.CInt) -> t.CInt | t.State: pass


# Test 9: t.State 返回 void
def StateVoidDecl() -> t.State: pass


def test_extern_decl():
    stdio.printf("--- Test 7: t.CExtern | t.CExport ---\n")
    # 外部声明函数，不调用（应由链接器解析符号）
    stdio.printf("ExternalDecl declared (not called)\n")
    stdio.printf("ExternalDecl OK\n")


def test_state_decl():
    stdio.printf("--- Test 8: t.State ---\n")
    stdio.printf("StateDecl declared (not called)\n")
    stdio.printf("StateDecl OK\n")


def test_state_void_decl():
    stdio.printf("--- Test 9: t.State (void) ---\n")
    stdio.printf("StateVoidDecl declared (not called)\n")
    stdio.printf("StateVoidDecl OK\n")


# Test 10: t.CDefine 作为 t.CArray count
# ARR_SIZE: t.CDefine = 8 已在文件顶部定义
def test_cdefine_array_count():
    stdio.printf("--- Test 10: t.CArray[elem, CDefine] ---\n")
    # 使用 CDefine 常量名作为数组 count
    arr: t.CArray[t.CInt, ARR_SIZE]
    i: t.CInt
    # 初始化: arr[i] = i * 10
    for i in range(ARR_SIZE):
        arr[i] = i * 10
    # 求和验证: 0+10+20+...+70 = 280
    total: t.CInt = 0
    for i in range(ARR_SIZE):
        total += arr[i]
    stdio.printf("ARR_SIZE=%d (expect 8)\n", ARR_SIZE)
    stdio.printf("arr sum=%d (expect 280)\n", total)
    stdio.printf("arr[0]=%d (expect 0)\n", arr[0])
    stdio.printf("arr[7]=%d (expect 70)\n", arr[7])
    if ARR_SIZE == 8 and total == 280 and arr[0] == 0 and arr[7] == 70:
        stdio.printf("CArray CDefine count OK\n")
    else:
        stdio.printf("CArray CDefine count FAIL\n")


def deco_test() -> int:
    stdio.printf("=== deco_test: t/c 装饰器测试 ===\n\n")

    test_cdefine()
    test_cexport()
    test_cinline()
    test_deco_normal()
    test_export_inline()
    test_export_ptr()
    test_extern_decl()
    test_state_decl()
    test_state_void_decl()
    test_cdefine_array_count()

    stdio.printf("\n=== deco_test 完成 ===\n")
    return 0
