From 921820b26a70de4eac9dc57dd2bf962561dc790f Mon Sep 17 00:00:00 2001 From: TermiNexus Date: Thu, 13 Aug 2026 07:51:33 +0800 Subject: [PATCH] =?UTF-8?q?chore:=20=E7=BA=B3=E5=85=A5=20toast=20=E8=84=9A?= =?UTF-8?q?=E6=9C=AC=E3=80=81Sequential=20=E5=9B=9E=E5=BD=92=E6=B5=8B?= =?UTF-8?q?=E8=AF=95=E4=B8=8E=E8=AF=8A=E6=96=AD=E4=BA=A7=E7=89=A9=E6=96=87?= =?UTF-8?q?=E4=BB=B6?= MIME-Version: 1.0 Content-Type: text/plain; charset=UTF-8 Content-Transfer-Encoding: 8bit _toast_gen.py(完成通知 toast 脚本)、Test/SequentialRegressionTest.py (TPV bootstrap 回归测试脚本)、handles_expr_HEAD.vp 与 output.s (历史诊断/反汇编产物)入库保存。 --- Test/SequentialRegressionTest.py | 282 +++++++ _toast_gen.py | 19 + handles_expr_HEAD.vp | 767 ++++++++++++++++++ output.s | 1281 ++++++++++++++++++++++++++++++ 4 files changed, 2349 insertions(+) create mode 100644 Test/SequentialRegressionTest.py create mode 100644 _toast_gen.py create mode 100644 handles_expr_HEAD.vp create mode 100644 output.s diff --git a/Test/SequentialRegressionTest.py b/Test/SequentialRegressionTest.py new file mode 100644 index 0000000..ab9763e --- /dev/null +++ b/Test/SequentialRegressionTest.py @@ -0,0 +1,282 @@ +#!/usr/bin/env python3 +"""TransPyC 顺序回归测试脚本 + +与 regression_test.py 的区别: +1. 按 Test/TestsOverview.md「建议实现顺序」节(难度升序,68 个项目)逐个编译 +2. 每个项目编译成功后立即运行其可执行文件 +3. 编译或运行失败立刻结束(fail-fast),退出码非 0 +""" +import os +import sys +import json +import time +import re +import subprocess +import argparse + +# 强制 stdout/stderr 使用 UTF-8 编码,避免 Windows GBK 编码在打印含替换字符的输出时崩溃 +try: + sys.stdout.reconfigure(encoding='utf-8', errors='replace') + sys.stderr.reconfigure(encoding='utf-8', errors='replace') +except Exception: + pass + +# ============================================================ +# 路径 +# ============================================================ +TEST_DIR = os.path.dirname(os.path.abspath(__file__)) +# 项目根目录(Projectrans.py 所在位置) +PROJECT_ROOT = os.path.dirname(TEST_DIR) +# Projectrans.py 路径 +PROJECTRANS = os.path.join(PROJECT_ROOT, "Projectrans.py") +# TestsOverview.md 路径(顺序来源) +OVERVIEW = os.path.join(TEST_DIR, "TestsOverview.md") + +# 编译超时(秒) +COMPILE_TIMEOUT = 300 +# 运行超时(秒) +RUN_TIMEOUT = 30 + + +def read_test_order(): + """从 TestsOverview.md「建议实现顺序」节提取项目名(难度升序)""" + with open(OVERVIEW, encoding='utf-8') as f: + text = f.read() + m = re.search(r'##\s*二、\s*建议实现顺序(.*?)##\s*三、', text, re.S) + if not m: + raise SystemExit("TestsOverview.md 中找不到「建议实现顺序」节") + section = m.group(1) + order = [] + for line in section.splitlines(): + mm = re.match(r'\s*\d+\.\s*\*\*(.+?)\*\*', line) + if mm: + order.append(mm.group(1)) + if not order: + raise SystemExit("「建议实现顺序」节中未解析到任何项目名") + return order + + +def build_compile_cmd(args): + """根据 --exe/--compiler 构建编译命令模板({project} 为项目 json 路径占位) + + --exe 指定编译器可执行文件(如 TransPyV.exe),优先于 --compiler; + 两者都未指定时使用 TPC(python Projectrans.py)。 + --rebuild-includes 时追加 --rebuild-includes(全量重编 includes, + 修复 includes.binary 缓存不一致导致的 undefined symbol)。 + """ + suffix = " --rebuild-includes" if args.rebuild_includes else "" + if args.exe: + return f'"{args.exe}" --project {{project}} --clean{suffix}' + if args.compiler: + return args.compiler + return f'D:\\Python312\\python.exe -u "{PROJECTRANS}" --project {{project}} --clean{suffix}' + + +def compile_project(cmd, proj_dir): + """编译单个测试项目,返回 (success, elapsed, combined_output)""" + start = time.time() + result = subprocess.run( + cmd, + shell=True, + capture_output=True, + text=True, + encoding='utf-8', + errors='replace', + cwd=proj_dir, + timeout=COMPILE_TIMEOUT, + ) + elapsed = time.time() - start + + combined = (result.stdout or "") + (result.stderr or "") + return (result.returncode == 0, elapsed, combined) + + +def find_executables(output_dir): + """在 output 目录中查找可执行文件""" + exes = [] + if not os.path.isdir(output_dir): + return exes + for f in os.listdir(output_dir): + fpath = os.path.join(output_dir, f) + if os.path.isfile(fpath) and (f.endswith('.exe') or f.endswith('.bin')): + exes.append(fpath) + return exes + + +def find_output_dirs(proj_dir, proj_config): + """收集候选输出目录(兼容 TPC 与 TPV 布局) + + - project.json 显式 output_dir(TPC 常用) + - project.json build_dir + '/output'(TPV 布局:.tpv_build/output) + - 兜底 ./output + 保序去重返回。 + """ + dirs = [] + od = proj_config.get('output_dir') + if od: + dirs.append(os.path.abspath(os.path.join(proj_dir, od))) + bd = proj_config.get('build_dir') + if bd: + dirs.append(os.path.abspath(os.path.join(proj_dir, bd, 'output'))) + if not dirs: + dirs.append(os.path.abspath(os.path.join(proj_dir, './output'))) + seen = set() + uniq = [] + for d in dirs: + if d not in seen: + seen.add(d) + uniq.append(d) + return uniq + + +def run_executable(exe_path): + """运行单个可执行文件,返回 (returncode, stdout, stderr, timed_out) + + 超时 RUN_TIMEOUT 秒强制结束。 + 使用 CREATE_NO_WINDOW 避免弹出 cmd 窗口,通过管道捕获 stdout/stderr。 + """ + try: + CREATE_NO_WINDOW = 0x08000000 + result = subprocess.run( + [exe_path], + cwd=os.path.dirname(exe_path), + capture_output=True, + text=True, + encoding='utf-8', + errors='replace', + timeout=RUN_TIMEOUT, + creationflags=CREATE_NO_WINDOW, + ) + return (result.returncode, result.stdout or "", result.stderr or "", False) + except subprocess.TimeoutExpired: + return (-1, "", "超时(强制终止)", True) + except Exception as e: + return (-1, "", str(e), False) + + +def print_tail(output, max_lines=40): + """打印输出尾部(编译/运行失败时的诊断信息)""" + lines = output.strip().splitlines() + if len(lines) > max_lines: + print(f" ... (省略前 {len(lines) - max_lines} 行) ...") + lines = lines[-max_lines:] + for line in lines: + print(f" {line}") + + +def main(): + parser = argparse.ArgumentParser( + description="TransPyC 顺序回归测试(按 TestsOverview.md 顺序,失败即停)") + parser.add_argument("--exe", default=None, + help="编译器可执行文件(如 TransPyV.exe),用它编译测试项目(替代 TPC)") + parser.add_argument("--compiler", default=None, + help="自定义编译命令模板,用 {project} 表示项目 json 路径;默认 TPC python") + parser.add_argument("--rebuild-includes", action="store_true", + help="每次编译追加 --rebuild-includes:清空 includes.binary 全量重编(修复缓存不一致)") + parser.add_argument("--number", type=int, default=1, + help="从第几个案例开始(1 开始编号),编译该编号及之后的项目;默认 1") + args = parser.parse_args() + compile_cmd = build_compile_cmd(args) + + print("=" * 70) + print("TransPyC 顺序回归测试(按 TestsOverview.md 顺序,失败即停)") + print("=" * 70) + print() + + order = read_test_order() + total = len(order) + + start = max(1, args.number) + if start > total: + print(f"错误: --number {args.number} 超出总项目数 {total}") + return 1 + print(f"按顺序共 {total} 个项目,从第 {start} 个({order[start - 1]})开始") + print(f"编译命令: {compile_cmd}\n") + + passed = 0 + for idx, name in enumerate(order, 1): + if idx < start: + continue + proj_dir = os.path.join(TEST_DIR, name) + proj_json = os.path.join(proj_dir, "project.json") + + if not os.path.isfile(proj_json): + print(f"[{idx}/{total}] {name}: 缺少 project.json,跳过") + continue + + # ---------- 编译 ---------- + print(f"[{idx}/{total}] 编译 {name} ...", end=" ", flush=True) + cmd = compile_cmd.format(project=proj_json) + try: + compile_ok, elapsed, output = compile_project(cmd, proj_dir) + except subprocess.TimeoutExpired: + print("编译超时(5 分钟)") + print_tail("编译超时(5 分钟)") + print(f"\n在 {name} 编译超时,立即终止。") + return 1 + except Exception as e: + print(f"异常: {e}") + print_tail(str(e)) + print(f"\n在 {name} 编译异常,立即终止。") + return 1 + + if not compile_ok: + print(f"失败 ({elapsed:.1f}s)") + print_tail(output) + print(f"\n在 {name} 编译失败,立即终止。") + return 1 + print(f"通过 ({elapsed:.1f}s)") + + # ---------- 编译成功后立即运行 ---------- + try: + with open(proj_json, 'r', encoding='utf-8') as f: + proj_config = json.load(f) + except Exception: + proj_config = {} + + output_dirs = find_output_dirs(proj_dir, proj_config) + exes = [] + for od in output_dirs: + exes = find_executables(od) + if exes: + break + + if not exes: + print(f" [运行] 未找到可执行文件(候选: {'; '.join(output_dirs)}),视为运行失败") + return 1 + + run_ok = True + for exe_path in exes: + exe_name = os.path.basename(exe_path) + print(f" [运行] {exe_name} ...", end=" ", flush=True) + returncode, stdout, stderr, timed_out = run_executable(exe_path) + + if timed_out: + print("超时") + print_tail(stdout + stderr) + run_ok = False + elif returncode == 0: + print("通过") + else: + print(f"失败(退出码 {returncode})") + print_tail(stdout + stderr) + run_ok = False + + if not run_ok: + break + + if not run_ok: + print(f"\n在 {name} 运行失败,立即终止。") + return 1 + + passed += 1 + + print() + print("=" * 70) + print(f"全部 {passed} 个项目编译并运行通过!") + print("=" * 70) + return 0 + + +if __name__ == "__main__": + sys.exit(main()) diff --git a/_toast_gen.py b/_toast_gen.py new file mode 100644 index 0000000..d843617 --- /dev/null +++ b/_toast_gen.py @@ -0,0 +1,19 @@ +# -*- coding: utf-8 -*- +"""生成并发送 toast 通知""" +import base64, subprocess + +ps = ( + "Add-Type -AssemblyName System.Runtime.WindowsRuntime\n" + "[Windows.UI.Notifications.ToastNotificationManager, Windows.UI.Notifications, ContentType = WindowsRuntime] | Out-Null\n" + "[Windows.Data.Xml.Dom.XmlDocument, Windows.Data.Xml.Dom.XmlDocument, ContentType = WindowsRuntime] | Out-Null\n" + "$t = 'TransPyC 治本修复:联合转换属性访问'\n" + "$b = 'TPC _handle_attr_call_result 现从 (X|t.CPtr)(arg) 提取真实类并 bitcast,修复属性访问被丢弃;已提交 6a67203(TPV 侧 9f7333b 双保险)'\n" + "$xml = [Windows.Data.Xml.Dom.XmlDocument]::new()\n" + "$xml.LoadXml('' + $t + '' + $b + '')\n" + "$toast = [Windows.UI.Notifications.ToastNotification]::new($xml)\n" + "[Windows.UI.Notifications.ToastNotificationManager]::CreateToastNotifier('TraeCode').Show($toast)\n" +) +b64 = base64.b64encode(ps.encode('utf-16-le')).decode() +r = subprocess.run(['powershell', '-NoProfile', '-EncodedCommand', b64], + capture_output=True, text=True) +print('rc=', r.returncode) diff --git a/handles_expr_HEAD.vp b/handles_expr_HEAD.vp new file mode 100644 index 0000000..4819840 --- /dev/null +++ b/handles_expr_HEAD.vp @@ -0,0 +1,767 @@ +import t, c +from stdint import * +import ast +import memhub +import string +import llvmlite +import stdlib +import stdio +import viperlib +import w32.fileio as fileio +import lib.core.Handles.HandlesBase as HandlesBase +import lib.core.Handles.HandlesTranslator as HT +import lib.core.Handles.HandlesVar as HandlesVar +import lib.core.Handles.HandlesExprOps as HandlesExprOps +import lib.core.Handles.HandlesExprCall as HandlesExprCall +import lib.core.Handles.HandlesNonlocal as HandlesNonlocal +import lib.core.Handles.HandlesType as HandlesType +import lib.core.Handles.HandlesStruct as HandlesStruct +import lib.core.Handles.HandlesEnum as HandlesEnum +import lib.core.Handles.HandlesClassDef as HandlesClassDef +import lib.core.Handles.HandlesImports as HandlesImports +import lib.core.StubMerger as StubMerger +import lib.core.VLogger as VLogger +import lib.Projectrans.Config as Config +import lib.Projectrans.Utils as Utils + + +# ============================================================ +# HandlesExpr - 表达式处理(P3 对象化后的委托层) +# +# 全部模块级函数已迁移为 lib.core.Gen.ExprGenMixin 的方法 +# (全局状态迁入 gen 字段),本模块保留同名模块级函数作为 +# "一行委托":延迟 import Gen 取全局单例(BuildPipeline/main +# 创建后 set_global_gen 注册),再调用 gen 的对应方法。签名与 +# 旧函数完全一致,调用方零改动。 +# +# ExprHandle 类及其 NewExprHandle 工厂保留(translator handler 模式)。 +# ============================================================ + + +# ============================================================ +# 全局 gen 单例(模块级镜像,同 HandlesType/HandlesStruct 模式) +# +# 由 BuildPipeline/main 在 gen 创建后调用 set_global_gen 注入。 +# P3 委托函数用本地 _g_gen(cast 成 Generator 类型)调 +# ExprGenMixin 方法,避免函数体 import 包模块与类/模块名歧义。 +# ============================================================ +_g_gen: t.CVoid | t.CPtr = None + + +def set_global_gen(gen: t.CVoid | t.CPtr) -> None: + """注入全局 gen 单例(BuildPipeline/main 调用)""" + global _g_gen + _g_gen = gen + + +# ============================================================ +# 委托函数:延迟 import Gen 取全局单例 → 调 gen 方法 +# (gen 未注册时正常流程不会发生;有返回值函数返回默认值) +# ============================================================ + + +# ============================================================ +# 从 AST 节点提取函数名 +# ============================================================ +def get_func_name(func_node: ast.AST | t.CPtr) -> str: + """从函数节点提取函数名(委托到 gen.get_func_name)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g.get_func_name(func_node) + return None + + +# ============================================================ +# 转义 LLVM IR 字符串字面量 +# ============================================================ +def escape_llvm_string(pool: memhub.MemBuddy | t.CPtr, + src: t.CChar | t.CPtr) -> t.CChar | t.CPtr: + """将字符串转换为 LLVM IR 字符串字面量 c"...\\00"(委托到 gen.escape_llvm_string)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g.escape_llvm_string(pool, src) + return None + + +# ============================================================ +# 获取 LLVM 整数类型的位宽 +# ============================================================ +def get_llvm_type_bits(ty: llvmlite.LLVMType | t.CPtr) -> int: + """获取 LLVM 整数类型的位宽,非整数类型返回 0(委托到 gen.get_llvm_type_bits)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g.get_llvm_type_bits(ty) + return 0 + + +# ============================================================ +# 获取 LLVM 浮点类型的位宽 +# ============================================================ +def get_llvm_float_bits(ty: llvmlite.LLVMType | t.CPtr) -> int: + """获取 LLVM 浮点类型的位宽,非浮点类型返回 0(委托到 gen.get_llvm_float_bits)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g.get_llvm_float_bits(ty) + return 0 + + +# ============================================================ +# is_ptr_type - 检查类型是否为 Ptr +# +# 返回 1=是, 0=否。作为类型检查工具函数被广泛使用(50+ 处调用)。 +# ============================================================ +def is_ptr_type(ty: llvmlite.LLVMType | t.CPtr) -> int: + """检查 ty 是否是 Ptr 类型,返回 1=是, 0=否(委托到 gen.is_ptr_type)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g.is_ptr_type(ty) + return 0 + + +# ============================================================ +# get_ptr_level - 计算指针层级 +# +# 返回值: +# 0 = 非指针(数值/结构体等) +# 1 = 一级指针(如 i8*, Struct*) +# 2 = 二级指针(如 i8**, Struct**) +# 3+ = 更高级指针 +# ============================================================ +def get_ptr_level(ty: llvmlite.LLVMType | t.CPtr) -> int: + """计算指针层级,0=非指针, 1=一级指针, 2=二级指针...(委托到 gen.get_ptr_level)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g.get_ptr_level(ty) + return 0 + + +# ============================================================ +# is_array_type - 检查类型是否为 Array +# +# 返回 1=是, 0=否。类型检查工具函数。 +# ============================================================ +def is_array_type(ty: llvmlite.LLVMType | t.CPtr) -> int: + """检查 ty 是否是 Array 类型,返回 1=是, 0=否(委托到 gen.is_array_type)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g.is_array_type(ty) + return 0 + + +# ============================================================ +# _zext_index_to_i32 - 数组下标索引零扩展 +# +# LLVM GEP 对窄整数索引默认符号扩展:i8 0xE2(226) 会被当成 -30, +# 导致数组下标越界读(字节 >= 128 的乱码根因)。 +# 数组下标语义为非负,<32 位整数索引一律 zext 到 i32。 +# ============================================================ +def _zext_index_to_i32(builder: llvmlite.IRBuilder | t.CPtr, + idx_val: llvmlite.Value | t.CPtr) -> llvmlite.Value | t.CPtr: + """将 <32 位整数下标零扩展到 i32(数组下标非负语义)(委托到 gen._zext_index_to_i32)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g._zext_index_to_i32(builder, idx_val) + return None + + +# ============================================================ +# _get_custom_struct_cls_nm - 检查类型是否为已注册的自定义结构体 +# +# 处理两种情况: +# - ty 直接是 Struct → 检查是否注册 +# - ty 是 Ptr(Struct) → 检查 pointee 是否注册 +# ============================================================ +def _get_custom_struct_cls_nm(pool: memhub.MemBuddy | t.CPtr, + ty: llvmlite.LLVMType | t.CPtr) -> str: + """检查 ty 或 ty 的 pointee 是否是已注册的自定义结构体,返回类名或 None(委托到 gen._get_custom_struct_cls_nm)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g._get_custom_struct_cls_nm(pool, ty) + return None + + +# ============================================================ +# _is_list_subscript_base - 判断下标基座是否为 list[T] 变量 +# ============================================================ +def _is_list_subscript_base(pool: memhub.MemBuddy | t.CPtr, + trans: HT.Translator | t.CPtr, + sub_node: ast.AST | t.CPtr) -> int: + """判断下标基座是否为 list[T] 变量(1=是)(委托到 gen._is_list_subscript_base)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g._is_list_subscript_base(pool, trans, sub_node) + return 0 + + +# ============================================================ +# _sub_base_class_name - 解析下标基座变量的结构体类名 +# ============================================================ +def _sub_base_class_name(pool: memhub.MemBuddy | t.CPtr, + trans: HT.Translator | t.CPtr, + sub_node: ast.AST | t.CPtr) -> str: + """解析下标基座变量的结构体类名(无则 None)(委托到 gen._sub_base_class_name)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g._sub_base_class_name(pool, trans, sub_node) + return None + + +# ============================================================ +# _sub_base_uses_getitem - 下标基座是否应走 __getitem__ 语义 +# ============================================================ +def _sub_base_uses_getitem(pool: memhub.MemBuddy | t.CPtr, + mod: llvmlite.LLVMModule | t.CPtr, + trans: HT.Translator | t.CPtr, + sub_node: ast.AST | t.CPtr) -> int: + """下标基座应走 __getitem__ 语义时返回 1,否则 0(应走 GEP 地址语义)(委托到 gen._sub_base_uses_getitem)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g._sub_base_uses_getitem(pool, mod, trans, sub_node) + return 0 + + +# ============================================================ +# _deref_if_ptr_ptr - 如果 obj_ptr 是 Ptr(Ptr(...)),load 解引用 +# ============================================================ +def _deref_if_ptr_ptr(builder: llvmlite.IRBuilder | t.CPtr, + obj_ptr: llvmlite.Value | t.CPtr) -> llvmlite.Value | t.CPtr: + """如果 obj_ptr 是 Ptr(Ptr(...)),load 解引用获取内层指针(委托到 gen._deref_if_ptr_ptr)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g._deref_if_ptr_ptr(builder, obj_ptr) + return None + + +# ============================================================ +# 类型强制转换:整数 sext/trunc,浮点 fpext/fptrunc,int↔float si2fp/fp2si +# ============================================================ +def coerce_to_type(builder: llvmlite.IRBuilder | t.CPtr, + val: llvmlite.Value | t.CPtr, + target_ty: llvmlite.LLVMType | t.CPtr, + node: ast.AST | t.CPtr = None) -> llvmlite.Value | t.CPtr: + """将 val 强制转换为 target_ty(委托到 gen.coerce_to_type)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g.coerce_to_type(builder, val, target_ty, node) + return None + + +# ============================================================ +# translate_ptr_arith - 指针算术: ptr + int / ptr - int +# +# 用 getelementptr(按 pointee 元素大小缩放索引),对齐 TPC +# ExprGen.emit_binary_op / HandlesAugAssign.py。 +# ============================================================ +def translate_ptr_arith(pool: memhub.MemBuddy | t.CPtr, + builder: llvmlite.IRBuilder | t.CPtr, + ptr_val: llvmlite.Value | t.CPtr, + int_val: llvmlite.Value | t.CPtr, + op: int) -> llvmlite.Value | t.CPtr: + """指针算术: ptr + int / ptr - int → GEP(按元素大小缩放索引)(委托到 gen.translate_ptr_arith)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g.translate_ptr_arith(pool, builder, ptr_val, int_val, op) + return None + + +# ============================================================ +# 创建全局字符串常量 +# ============================================================ +def create_global_string(builder: llvmlite.IRBuilder | t.CPtr, + pool: memhub.MemBuddy | t.CPtr, + mod: llvmlite.LLVMModule | t.CPtr, + str_val: str, + trans: HT.Translator | t.CPtr) -> llvmlite.Value | t.CPtr: + """创建全局字符串常量并返回 i8* bitcast(委托到 gen.create_global_string)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g.create_global_string(builder, pool, mod, str_val, trans) + return None + + +# ============================================================ +# 翻译常量表达式 +# ============================================================ +def translate_constant(builder: llvmlite.IRBuilder | t.CPtr, + pool: memhub.MemBuddy | t.CPtr, + mod: llvmlite.LLVMModule | t.CPtr, + node: ast.AST | t.CPtr, + trans: HT.Translator | t.CPtr = None) -> llvmlite.Value | t.CPtr: + """翻译常量(int/str/bool)(委托到 gen.translate_constant)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g.translate_constant(builder, pool, mod, node, trans) + return None + + +# ============================================================ +# _infer_elem_type_from_value — 从 LLVM Value 推断 list 元素类型名 +# ============================================================ +def _infer_elem_type_from_value(pool: memhub.MemBuddy | t.CPtr, + value: llvmlite.Value | t.CPtr) -> str: + """从 LLVM Value 的类型推断 list 元素类型名(委托到 gen._infer_elem_type_from_value)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g._infer_elem_type_from_value(pool, value) + return None + + +# ============================================================ +# _find_pool_var — 查找上下文中的 pool 变量 +# +# 依次尝试 "pool", "_mbuddy", "mbuddy", "mb" +# ============================================================ +def _find_pool_var(trans: HT.Translator | t.CPtr) -> llvmlite.Value | t.CPtr: + """查找上下文中的 pool 变量,返回 alloca 或 None(委托到 gen._find_pool_var)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g._find_pool_var(trans) + return None + + +# ============================================================ +# translate_list_literal — 翻译 list 字面量 [a, b, c] +# +# 将 list 字面量翻译为 list[T](pool) 构造 + append 调用序列 +# ============================================================ +def translate_list_literal(builder: llvmlite.IRBuilder | t.CPtr, + pool: memhub.MemBuddy | t.CPtr, + mod: llvmlite.LLVMModule | t.CPtr, + node: ast.AST | t.CPtr, + elem_type_name: str, + trans: HT.Translator | t.CPtr) -> llvmlite.Value | t.CPtr: + """翻译 list 字面量 [a, b, c] → list[T](pool) + append 序列(委托到 gen.translate_list_literal)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g.translate_list_literal(builder, pool, mod, node, elem_type_name, trans) + return None + + +# ============================================================ +# 翻译值表达式(RHS 分派)— 模块级版本 +# ============================================================ +def translate_value(builder: llvmlite.IRBuilder | t.CPtr, + pool: memhub.MemBuddy | t.CPtr, + mod: llvmlite.LLVMModule | t.CPtr, + node: ast.AST | t.CPtr, + funcs_ptr: t.CPtr = None, + func_count: int = 0, + trans: HT.Translator | t.CPtr = None) -> llvmlite.Value | t.CPtr: + """翻译值表达式为 LLVM Value(委托到 gen.translate_value)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g.translate_value(builder, pool, mod, node, funcs_ptr, func_count, trans) + return None + + +# ============================================================ +# 翻译三元表达式 IfExp(test, body, orelse) +# ============================================================ +def translate_ifexp(builder: llvmlite.IRBuilder | t.CPtr, + pool: memhub.MemBuddy | t.CPtr, + mod: llvmlite.LLVMModule | t.CPtr, + node: ast.AST | t.CPtr, + trans: HT.Translator | t.CPtr = None) -> llvmlite.Value | t.CPtr: + """翻译三元表达式 (body if test else orelse),返回 phi 结果 Value(委托到 gen.translate_ifexp)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g.translate_ifexp(builder, pool, mod, node, trans) + return None + + +# ============================================================ +# 翻译比较表达式 Compare(left, ops, comparators) +# ============================================================ +def should_zext_widen(pool: memhub.MemBuddy | t.CPtr, + narrow_val: llvmlite.Value | t.CPtr, + wide_val: llvmlite.Value | t.CPtr, + narrow_node: ast.AST | t.CPtr = None) -> int: + """判断整数拓宽方向:1=zext(无符号语义),0=sext(委托到 gen.should_zext_widen)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g.should_zext_widen(pool, narrow_val, wide_val, narrow_node) + return 0 + + +def _node_type_unsigned(pool: memhub.MemBuddy | t.CPtr, + node: ast.AST | t.CPtr, + trans: HT.Translator | t.CPtr = None) -> int: + """轻量判断 AST 节点是否解析为无符号整数类型(1=是,0=否/未知)(委托到 gen._node_type_unsigned)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g._node_type_unsigned(pool, node, trans) + return 0 + + +def _type_name_unsigned(type_name: str) -> int: + """类型名是否为无符号整数类型(精确匹配,避免子串误伤如 nUIntCount)(委托到 gen._type_name_unsigned)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g._type_name_unsigned(type_name) + return 0 + + +def translate_compare(builder: llvmlite.IRBuilder | t.CPtr, + pool: memhub.MemBuddy | t.CPtr, + mod: llvmlite.LLVMModule | t.CPtr, + node: ast.AST | t.CPtr, + trans: HT.Translator | t.CPtr = None) -> llvmlite.Value | t.CPtr: + """翻译比较表达式,返回 i1 结果(委托到 gen.translate_compare)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g.translate_compare(builder, pool, mod, node, trans) + return None + + +# ============================================================ +# 翻译一元运算表达式 UnaryOp(op, operand) +# ============================================================ +def translate_unaryop(builder: llvmlite.IRBuilder | t.CPtr, + pool: memhub.MemBuddy | t.CPtr, + mod: llvmlite.LLVMModule | t.CPtr, + node: ast.AST | t.CPtr, + trans: HT.Translator | t.CPtr = None) -> llvmlite.Value | t.CPtr: + """翻译一元运算(-x, +x, not x, ~x)(委托到 gen.translate_unaryop)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g.translate_unaryop(builder, pool, mod, node, trans) + return None + + +# ============================================================ +# 翻译布尔运算 BoolOp(op, values) — 短路求值,返回 i1 +# ============================================================ +def translate_boolop(builder: llvmlite.IRBuilder | t.CPtr, + pool: memhub.MemBuddy | t.CPtr, + mod: llvmlite.LLVMModule | t.CPtr, + node: ast.AST | t.CPtr, + funcs_ptr: t.CPtr = None, + func_count: int = 0, + trans: HT.Translator | t.CPtr = None) -> llvmlite.Value | t.CPtr: + """翻译布尔运算(and/or)的短路求值,返回 i1(委托到 gen.translate_boolop)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g.translate_boolop(builder, pool, mod, node, funcs_ptr, func_count, trans) + return None + + +# ============================================================ +# _build_source_path_from_sha1 - 通过 SHA1 从存储器构建源 .vp/.py 文件路径 +# ============================================================ +def _build_source_path_from_sha1(sha1: str) -> str: + """通过 SHA1 从全局存储器构建源 .py 文件路径(委托到 gen._build_source_path_from_sha1)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g._build_source_path_from_sha1(sha1) + return None + + +# ============================================================ +# _lookup_cross_module_cdefine - 跨模块查找 CDefine 常量 +# ============================================================ +def _lookup_cross_module_cdefine(pool: memhub.MemBuddy | t.CPtr, + name: str, + from_imports: str, + imported_modules: str = None) -> int: + """跨模块查找 CDefine 常量,返回值或 -1(未找到)(委托到 gen._lookup_cross_module_cdefine)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g._lookup_cross_module_cdefine(pool, name, from_imports, imported_modules) + return 0 + + +# ============================================================ +# _is_cdefine_name_pattern - 检查名字是否符合 CDefine 命名约定 +# ============================================================ +def _is_cdefine_name_pattern(name: str) -> int: + """检查名字是否符合 CDefine 命名约定(全大写+下划线+数字)(委托到 gen._is_cdefine_name_pattern)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g._is_cdefine_name_pattern(name) + return 0 + + +# ============================================================ +# 翻译变量引用(Name 节点)→ load +# ============================================================ +def translate_name_value(builder: llvmlite.IRBuilder | t.CPtr, + pool: memhub.MemBuddy | t.CPtr, + node: ast.AST | t.CPtr, + trans: HT.Translator | t.CPtr = None) -> llvmlite.Value | t.CPtr: + """翻译变量引用(Name 节点)→ load(委托到 gen.translate_name_value)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g.translate_name_value(builder, pool, node, trans) + return None + + +# ============================================================ +# ExprHandle - 表达式处理器(Mixin 继承模式) +# +# HandleValue 提供 trans 接口,委托到模块级 translate_value +# ============================================================ +@t.NoVTable +class ExprHandle(HandlesBase.Mixin): + """表达式处理器:继承 Mixin 获得 Trans 回指针""" + + def __init__(self, trans: HT.Translator | t.CPtr): + self.Trans = trans + + # ============================================================ + # HandleValue - 翻译值表达式为 LLVM Value + # ============================================================ + def HandleValue(self, node: ast.AST | t.CPtr) -> llvmlite.Value | t.CPtr: + """翻译值表达式,从 self.Trans 获取共享状态""" + return translate_value( + self.Trans._cur_builder, self.Trans.Pool, self.Trans.Module, + node, + self.Trans._funcs, self.Trans._func_count, self.Trans) + + +# ============================================================ +# NewExprHandle - 工厂函数 +# ============================================================ +def NewExprHandle(pool: memhub.MemBuddy | t.CPtr, + trans: HT.Translator | t.CPtr) -> ExprHandle | t.CPtr: + h: ExprHandle | t.CPtr = pool.alloc(ExprHandle.__sizeof__()) + if h is None: + return None + string.memset(h, 0, ExprHandle.__sizeof__()) + h.Trans = trans + return h + + +# ============================================================ +# list_getitem_inline — 内联生成 list[T] __getitem__ 逻辑 +# +# list 结构布局 (6 字段 × 8 字节): +# __data__(0) __count__(8) __capacity__(16) __pool__(24) __elem_size__(32) __iter_index__(40) +# 返回元素地址 (i8*),调用方根据元素类型 load 正确的值 +# ============================================================ +def list_getitem_inline(builder: llvmlite.IRBuilder | t.CPtr, + pool: memhub.MemBuddy | t.CPtr, + lm_obj: llvmlite.Value | t.CPtr, + idx_val: llvmlite.Value | t.CPtr, + node: ast.AST | t.CPtr = None) -> llvmlite.Value | t.CPtr: + """内联生成 list __getitem__ 逻辑,返回元素地址 (i8*)(委托到 gen.list_getitem_inline)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g.list_getitem_inline(builder, pool, lm_obj, idx_val, node) + return None + + +# ============================================================ +# _list_elem_type_from_name — 从 list 类型名提取元素 LLVM 类型 +# ============================================================ +def _list_elem_type_from_name(pool: memhub.MemBuddy | t.CPtr, + struct_name: str) -> llvmlite.LLVMType | t.CPtr: + """从 list 类型名提取元素 LLVM 类型(委托到 gen._list_elem_type_from_name)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g._list_elem_type_from_name(pool, struct_name) + return None + + +# ============================================================ +# list_setitem_inline — 内联生成 list[T] __setitem__ 逻辑 +# ============================================================ +def list_setitem_inline(builder: llvmlite.IRBuilder | t.CPtr, + pool: memhub.MemBuddy | t.CPtr, + lm_obj: llvmlite.Value | t.CPtr, + idx_val: llvmlite.Value | t.CPtr, + rhs_val: llvmlite.Value | t.CPtr, + node: ast.AST | t.CPtr = None) -> int: + """内联生成 list __setitem__ 逻辑,返回 0(委托到 gen.list_setitem_inline)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g.list_setitem_inline(builder, pool, lm_obj, idx_val, rhs_val, node) + return 0 + + +# ============================================================ +# is_list_subscript — 检查 Subscript 节点是否是 list[T] 类型 +# +# 返回 list 对象指针 (Ptr(list[T])) 或 None +# ============================================================ +def is_list_subscript(node: ast.AST | t.CPtr, + trans: HT.Translator | t.CPtr) -> llvmlite.Value | t.CPtr: + """检查 Subscript 节点是否是 list[T] 类型,返回 list 对象指针或 None(委托到 gen.is_list_subscript)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g.is_list_subscript(node, trans) + return None + + +# ============================================================ +# 翻译下标表达式 Subscript(value, slice, ctx) — ptr[i] / arr[i] +# ============================================================ +def translate_subscript(builder: llvmlite.IRBuilder | t.CPtr, + pool: memhub.MemBuddy | t.CPtr, + mod: llvmlite.LLVMModule | t.CPtr, + node: ast.AST | t.CPtr, + trans: HT.Translator | t.CPtr = None) -> llvmlite.Value | t.CPtr: + """翻译下标表达式,返回加载的元素值(委托到 gen.translate_subscript)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g.translate_subscript(builder, pool, mod, node, trans) + return None + + +# ============================================================ +# find_global_in_module - 在模块全局变量链表中按名称查找 +# +# 查找策略: +# 1. 精确匹配 (如 "_mbuddy" 匹配 @_mbuddy) +# 2. 后缀匹配 (如 "_mbuddy" 匹配 @"sha1._mbuddy") +# ============================================================ +def find_global_in_module(mod: llvmlite.LLVMModule | t.CPtr, + name: str) -> llvmlite.GlobalVariable | t.CPtr: + """在模块全局变量链表中按名称查找全局变量(委托到 gen.find_global_in_module)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g.find_global_in_module(mod, name) + return None + + +# ============================================================ +# make_global_ref - 创建全局变量引用 (@name,类型为 ty*) +# ============================================================ +def make_global_ref(pool: memhub.MemBuddy | t.CPtr, + name: str, + ty: llvmlite.LLVMType | t.CPtr) -> llvmlite.Value | t.CPtr: + """创建全局变量引用 (类型为 ty*,名称为 @name)(委托到 gen.make_global_ref)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g.make_global_ref(pool, name, ty) + return None + + +# ============================================================ +# _is_t_type_object_name - 检查 name 是否是 t.py 中的类型对象名 +# ============================================================ +def _is_t_type_object_name(name: str) -> int: + """检查 name 是否是 t.py 中的类型对象名(CPtr/CInt/CDouble 等)(委托到 gen._is_t_type_object_name)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g._is_t_type_object_name(name) + return 0 + + +# ============================================================ +# _resolve_module_attribute_global - 解析模块属性访问的全局变量引用 +# ============================================================ +def _resolve_module_attribute_global(pool: memhub.MemBuddy | t.CPtr, + mod: llvmlite.LLVMModule | t.CPtr, + trans: HT.Translator | t.CPtr, + at: ast.Attribute | t.CPtr, + ty_hint: llvmlite.LLVMType | t.CPtr) -> llvmlite.Value | t.CPtr: + """解析模块属性访问,返回全局变量引用 (用于跨模块 global 访问)(委托到 gen._resolve_module_attribute_global)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g._resolve_module_attribute_global(pool, mod, trans, at, ty_hint) + return None + + +# ============================================================ +# _get_cderef_attr_base - c.Deref(ptr).attr 属性访问的 base 指针 +# ============================================================ +def _get_cderef_attr_base(builder: llvmlite.IRBuilder | t.CPtr, + pool: memhub.MemBuddy | t.CPtr, + mod: llvmlite.LLVMModule | t.CPtr, + at_value: ast.AST | t.CPtr, + trans: HT.Translator | t.CPtr = None) -> llvmlite.Value | t.CPtr: + """检测 at.value 是否为 c.Deref(ptr) 调用,返回 ptr 指针(不做 load)(委托到 gen._get_cderef_attr_base)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g._get_cderef_attr_base(builder, pool, mod, at_value, trans) + return None + + +# ============================================================ +# 翻译属性访问 Attribute(value, attr, ctx) — obj.field +# ============================================================ +def translate_attribute(builder: llvmlite.IRBuilder | t.CPtr, + pool: memhub.MemBuddy | t.CPtr, + mod: llvmlite.LLVMModule | t.CPtr, + node: ast.AST | t.CPtr, + trans: HT.Translator | t.CPtr = None) -> llvmlite.Value | t.CPtr: + """翻译属性访问,返回加载的字段值(委托到 gen.translate_attribute)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g.translate_attribute(builder, pool, mod, node, trans) + return None + + +# ============================================================ +# 获取下标表达式的元素指针(不加载值,用于赋值) +# ============================================================ +def get_subscript_ptr(builder: llvmlite.IRBuilder | t.CPtr, + pool: memhub.MemBuddy | t.CPtr, + mod: llvmlite.LLVMModule | t.CPtr, + node: ast.AST | t.CPtr, + trans: HT.Translator | t.CPtr = None) -> llvmlite.Value | t.CPtr: + """获取下标表达式的元素指针(用于赋值 lhs)(委托到 gen.get_subscript_ptr)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g.get_subscript_ptr(builder, pool, mod, node, trans) + return None + + +# ============================================================ +# 获取属性访问的字段指针(不加载值,用于赋值) +# ============================================================ +def get_attribute_ptr(builder: llvmlite.IRBuilder | t.CPtr, + pool: memhub.MemBuddy | t.CPtr, + mod: llvmlite.LLVMModule | t.CPtr, + node: ast.AST | t.CPtr, + trans: HT.Translator | t.CPtr = None) -> llvmlite.Value | t.CPtr: + """获取属性访问的字段指针(用于赋值 lhs)(委托到 gen.get_attribute_ptr)""" + import lib.core.Gen.Generator as Generator + g: Generator.Generator | t.CPtr = (Generator.Generator | t.CPtr)(t.CVoid(_g_gen, t.CPtr)) + if g is not None: + return g.get_attribute_ptr(builder, pool, mod, node, trans) + return None diff --git a/output.s b/output.s new file mode 100644 index 0000000..8f5d814 --- /dev/null +++ b/output.s @@ -0,0 +1,1281 @@ + .def @feat.00; + .scl 3; + .type 0; + .endef + .globl @feat.00 +@feat.00 = 0 + .file "124730a62158dfd3.ll" + .def main; + .scl 2; + .type 32; + .endef + .section .rdata,"dr" + .p2align 3, 0x0 # -- Begin function main +.LCPI0_0: + .quad 0x4008000000000000 # double 3 +.LCPI0_1: + .quad 0x4010000000000000 # double 4 + .text + .globl main + .p2align 4 +main: # @main +.seh_proc main +# %bb.0: # %entry + pushq %rbp + .seh_pushreg %rbp + pushq %rsi + .seh_pushreg %rsi + pushq %rdi + .seh_pushreg %rdi + subq $64, %rsp + .seh_stackalloc 64 + leaq 64(%rsp), %rbp + .seh_setframe %rbp, 64 + .seh_endprologue + callq __main + movl $65001, %ecx # imm = 0xFDE9 + callq SetConsoleCP + movl $65001, %ecx # imm = 0xFDE9 + callq SetConsoleOutputCP + leaq .str.124730a62158dfd3.0(%rip), %rcx + callq 748d0424e8976fa0.begin + movl $256, %ecx # imm = 0x100 + callq malloc + movq %rax, %rsi + leaq .str.124730a62158dfd3.1(%rip), %rcx + callq 748d0424e8976fa0.section + movq $3, 40(%rsp) + movq $2, 32(%rsp) + leaq .str.124730a62158dfd3.2(%rip), %r8 + movl $256, %edx # imm = 0x100 + movl $1, %r9d + movq %rsi, %rcx + callq snprintf + leaq .str.124730a62158dfd3.45(%rip), %rdi + movq %rdi, %rcx + movq %rsi, %rdx + callq printf + leaq .str.124730a62158dfd3.4(%rip), %rdx + leaq .str.124730a62158dfd3.5(%rip), %r8 + movl $1, %ecx + callq 748d0424e8976fa0.check + leaq .str.124730a62158dfd3.6(%rip), %rdx + leaq .str.124730a62158dfd3.7(%rip), %r8 + movl $1, %ecx + callq 748d0424e8976fa0.check + leaq .str.124730a62158dfd3.8(%rip), %rdx + leaq .str.124730a62158dfd3.9(%rip), %r8 + movl $1, %ecx + callq 748d0424e8976fa0.check + leaq .str.124730a62158dfd3.10(%rip), %rdx + leaq .str.124730a62158dfd3.11(%rip), %r8 + movl $1, %ecx + callq 748d0424e8976fa0.check + leaq .str.124730a62158dfd3.12(%rip), %rdx + leaq .str.124730a62158dfd3.13(%rip), %r8 + movl $1, %ecx + callq 748d0424e8976fa0.check + leaq .str.124730a62158dfd3.14(%rip), %rdx + leaq .str.124730a62158dfd3.15(%rip), %r8 + movl $1, %ecx + callq 748d0424e8976fa0.check + leaq .str.124730a62158dfd3.16(%rip), %rcx + callq 748d0424e8976fa0.ok + leaq .str.124730a62158dfd3.17(%rip), %rcx + callq 748d0424e8976fa0.section + movq $100, 40(%rsp) + movq $2, 32(%rsp) + leaq .str.124730a62158dfd3.18(%rip), %r8 + movl $256, %edx # imm = 0x100 + movl $5, %r9d + movq %rsi, %rcx + callq snprintf + movq %rdi, %rcx + movq %rsi, %rdx + callq printf + leaq .str.124730a62158dfd3.20(%rip), %rdx + leaq .str.124730a62158dfd3.21(%rip), %r8 + movl $1, %ecx + callq 748d0424e8976fa0.check + leaq .str.124730a62158dfd3.22(%rip), %rdx + leaq .str.124730a62158dfd3.23(%rip), %r8 + movl $1, %ecx + callq 748d0424e8976fa0.check + leaq .str.124730a62158dfd3.24(%rip), %rdx + leaq .str.124730a62158dfd3.25(%rip), %r8 + movl $1, %ecx + callq 748d0424e8976fa0.check + leaq .str.124730a62158dfd3.26(%rip), %rcx + callq 748d0424e8976fa0.ok + leaq .str.124730a62158dfd3.27(%rip), %rcx + callq 748d0424e8976fa0.section + movabsq $4628651735144066958, %rax # imm = 0x403C463ABE41EF8E + movq %rax, 40(%rsp) + movq $7, 48(%rsp) + movq $7, 32(%rsp) + leaq .str.124730a62158dfd3.28(%rip), %r8 + movq .LCPI0_0(%rip), %xmm3 # xmm3 = [3.0E+0,0.0E+0] + movl $256, %edx # imm = 0x100 + movq %rsi, %rcx + movq %xmm3, %r9 + callq snprintf + movq %rdi, %rcx + movq %rsi, %rdx + callq printf + leaq .str.124730a62158dfd3.30(%rip), %rdx + leaq .str.124730a62158dfd3.31(%rip), %r8 + movl $1, %ecx + callq 748d0424e8976fa0.check + leaq .str.124730a62158dfd3.32(%rip), %rdx + leaq .str.124730a62158dfd3.33(%rip), %r8 + movl $1, %ecx + callq 748d0424e8976fa0.check + leaq .str.124730a62158dfd3.34(%rip), %rdx + leaq .str.124730a62158dfd3.35(%rip), %r8 + movl $1, %ecx + callq 748d0424e8976fa0.check + leaq .str.124730a62158dfd3.36(%rip), %rcx + callq 748d0424e8976fa0.ok + leaq .str.124730a62158dfd3.37(%rip), %rcx + callq 748d0424e8976fa0.section + movabsq $4618441417868443648, %rax # imm = 0x4018000000000000 + movq %rax, 32(%rsp) + leaq .str.124730a62158dfd3.38(%rip), %r8 + movq .LCPI0_1(%rip), %xmm3 # xmm3 = [4.0E+0,0.0E+0] + movl $256, %edx # imm = 0x100 + movq %rsi, %rcx + movq %xmm3, %r9 + callq snprintf + movq %rdi, %rcx + movq %rsi, %rdx + callq printf + leaq .str.124730a62158dfd3.40(%rip), %rdx + leaq .str.124730a62158dfd3.41(%rip), %r8 + movl $1, %ecx + callq 748d0424e8976fa0.check + leaq .str.124730a62158dfd3.42(%rip), %rdx + leaq .str.124730a62158dfd3.43(%rip), %r8 + movl $1, %ecx + callq 748d0424e8976fa0.check + leaq .str.124730a62158dfd3.44(%rip), %r8 + movl $256, %edx # imm = 0x100 + movl $7, %r9d + movq %rsi, %rcx + callq snprintf + movq %rdi, %rcx + movq %rsi, %rdx + callq printf + leaq .str.124730a62158dfd3.46(%rip), %rdx + leaq .str.124730a62158dfd3.47(%rip), %r8 + movl $1, %ecx + callq 748d0424e8976fa0.check + leaq .str.124730a62158dfd3.48(%rip), %rcx + callq 748d0424e8976fa0.ok + movq %rsi, %rcx + callq free + nop + .seh_startepilogue + addq $64, %rsp + popq %rdi + popq %rsi + popq %rbp + .seh_endepilogue + jmp 748d0424e8976fa0.end # TAILCALL + .seh_endproc + # -- End function + .def 124730a62158dfd3.A.__init__; + .scl 2; + .type 32; + .endef + .globl 124730a62158dfd3.A.__init__ # -- Begin function 124730a62158dfd3.A.__init__ + .p2align 4 +124730a62158dfd3.A.__init__: # @"124730a62158dfd3.A.__init__" +# %bb.0: # %entry + movl %edx, (%rcx) + retq + # -- End function + .def 124730a62158dfd3.A.get_a; + .scl 2; + .type 32; + .endef + .globl 124730a62158dfd3.A.get_a # -- Begin function 124730a62158dfd3.A.get_a + .p2align 4 +124730a62158dfd3.A.get_a: # @"124730a62158dfd3.A.get_a" +# %bb.0: # %entry + movl (%rcx), %eax + retq + # -- End function + .def 124730a62158dfd3.A.__before_init__; + .scl 2; + .type 32; + .endef + .globl 124730a62158dfd3.A.__before_init__ # -- Begin function 124730a62158dfd3.A.__before_init__ + .p2align 4 +124730a62158dfd3.A.__before_init__: # @"124730a62158dfd3.A.__before_init__" +# %bb.0: # %entry + movl $0, (%rcx) + retq + # -- End function + .def 124730a62158dfd3.B.__init__; + .scl 2; + .type 32; + .endef + .globl 124730a62158dfd3.B.__init__ # -- Begin function 124730a62158dfd3.B.__init__ + .p2align 4 +124730a62158dfd3.B.__init__: # @"124730a62158dfd3.B.__init__" +# %bb.0: # %entry + movl %edx, (%rcx) + retq + # -- End function + .def 124730a62158dfd3.B.get_b; + .scl 2; + .type 32; + .endef + .globl 124730a62158dfd3.B.get_b # -- Begin function 124730a62158dfd3.B.get_b + .p2align 4 +124730a62158dfd3.B.get_b: # @"124730a62158dfd3.B.get_b" +# %bb.0: # %entry + movl (%rcx), %eax + retq + # -- End function + .def 124730a62158dfd3.B.__before_init__; + .scl 2; + .type 32; + .endef + .globl 124730a62158dfd3.B.__before_init__ # -- Begin function 124730a62158dfd3.B.__before_init__ + .p2align 4 +124730a62158dfd3.B.__before_init__: # @"124730a62158dfd3.B.__before_init__" +# %bb.0: # %entry + movl $0, (%rcx) + retq + # -- End function + .def 124730a62158dfd3.C.__init__; + .scl 2; + .type 32; + .endef + .globl 124730a62158dfd3.C.__init__ # -- Begin function 124730a62158dfd3.C.__init__ + .p2align 4 +124730a62158dfd3.C.__init__: # @"124730a62158dfd3.C.__init__" +# %bb.0: # %entry + movl %edx, (%rcx) + movl %r8d, 4(%rcx) + movl %r9d, 8(%rcx) + retq + # -- End function + .def 124730a62158dfd3.C.get_c; + .scl 2; + .type 32; + .endef + .globl 124730a62158dfd3.C.get_c # -- Begin function 124730a62158dfd3.C.get_c + .p2align 4 +124730a62158dfd3.C.get_c: # @"124730a62158dfd3.C.get_c" +# %bb.0: # %entry + movl 8(%rcx), %eax + retq + # -- End function + .def 124730a62158dfd3.C.__before_init__; + .scl 2; + .type 32; + .endef + .globl 124730a62158dfd3.C.__before_init__ # -- Begin function 124730a62158dfd3.C.__before_init__ + .p2align 4 +124730a62158dfd3.C.__before_init__: # @"124730a62158dfd3.C.__before_init__" +# %bb.0: # %entry + movq $0, (%rcx) + movl $0, 8(%rcx) + retq + # -- End function + .def 124730a62158dfd3.Base.who; + .scl 2; + .type 32; + .endef + .globl 124730a62158dfd3.Base.who # -- Begin function 124730a62158dfd3.Base.who + .p2align 4 +124730a62158dfd3.Base.who: # @"124730a62158dfd3.Base.who" +# %bb.0: # %entry + movl $1, %eax + retq + # -- End function + .def 124730a62158dfd3.Base.base_method; + .scl 2; + .type 32; + .endef + .globl 124730a62158dfd3.Base.base_method # -- Begin function 124730a62158dfd3.Base.base_method + .p2align 4 +124730a62158dfd3.Base.base_method: # @"124730a62158dfd3.Base.base_method" +# %bb.0: # %entry + movl $100, %eax + retq + # -- End function + .def 124730a62158dfd3.Base.__before_init__; + .scl 2; + .type 32; + .endef + .globl 124730a62158dfd3.Base.__before_init__ # -- Begin function 124730a62158dfd3.Base.__before_init__ + .p2align 4 +124730a62158dfd3.Base.__before_init__: # @"124730a62158dfd3.Base.__before_init__" +# %bb.0: # %entry + movl $0, (%rcx) + retq + # -- End function + .def 124730a62158dfd3.Left.who; + .scl 2; + .type 32; + .endef + .globl 124730a62158dfd3.Left.who # -- Begin function 124730a62158dfd3.Left.who + .p2align 4 +124730a62158dfd3.Left.who: # @"124730a62158dfd3.Left.who" +# %bb.0: # %entry + movl $2, %eax + retq + # -- End function + .def 124730a62158dfd3.Left.__before_init__; + .scl 2; + .type 32; + .endef + .globl 124730a62158dfd3.Left.__before_init__ # -- Begin function 124730a62158dfd3.Left.__before_init__ + .p2align 4 +124730a62158dfd3.Left.__before_init__: # @"124730a62158dfd3.Left.__before_init__" +# %bb.0: # %entry + movl $0, (%rcx) + retq + # -- End function + .def 124730a62158dfd3.Right.who; + .scl 2; + .type 32; + .endef + .globl 124730a62158dfd3.Right.who # -- Begin function 124730a62158dfd3.Right.who + .p2align 4 +124730a62158dfd3.Right.who: # @"124730a62158dfd3.Right.who" +# %bb.0: # %entry + movl $3, %eax + retq + # -- End function + .def 124730a62158dfd3.Right.__before_init__; + .scl 2; + .type 32; + .endef + .globl 124730a62158dfd3.Right.__before_init__ # -- Begin function 124730a62158dfd3.Right.__before_init__ + .p2align 4 +124730a62158dfd3.Right.__before_init__: # @"124730a62158dfd3.Right.__before_init__" +# %bb.0: # %entry + movl $0, (%rcx) + retq + # -- End function + .def 124730a62158dfd3.Diamond.__init__; + .scl 2; + .type 32; + .endef + .globl 124730a62158dfd3.Diamond.__init__ # -- Begin function 124730a62158dfd3.Diamond.__init__ + .p2align 4 +124730a62158dfd3.Diamond.__init__: # @"124730a62158dfd3.Diamond.__init__" +# %bb.0: # %entry + movl %edx, (%rcx) + retq + # -- End function + .def 124730a62158dfd3.Diamond.__before_init__; + .scl 2; + .type 32; + .endef + .globl 124730a62158dfd3.Diamond.__before_init__ # -- Begin function 124730a62158dfd3.Diamond.__before_init__ + .p2align 4 +124730a62158dfd3.Diamond.__before_init__: # @"124730a62158dfd3.Diamond.__before_init__" +# %bb.0: # %entry + movl $0, (%rcx) + retq + # -- End function + .def 124730a62158dfd3.ShapeM.area; + .scl 2; + .type 32; + .endef + .globl 124730a62158dfd3.ShapeM.area # -- Begin function 124730a62158dfd3.ShapeM.area + .p2align 4 +124730a62158dfd3.ShapeM.area: # @"124730a62158dfd3.ShapeM.area" +# %bb.0: # %entry + xorps %xmm0, %xmm0 + retq + # -- End function + .def 124730a62158dfd3.ShapeM.__before_init__; + .scl 2; + .type 32; + .endef + .globl 124730a62158dfd3.ShapeM.__before_init__ # -- Begin function 124730a62158dfd3.ShapeM.__before_init__ + .p2align 4 +124730a62158dfd3.ShapeM.__before_init__: # @"124730a62158dfd3.ShapeM.__before_init__" +# %bb.0: # %entry + leaq 124730a62158dfd3.ShapeM.vtable(%rip), %rax + movq %rax, (%rcx) + retq + # -- End function + .def 124730a62158dfd3.ColorM.__init__; + .scl 2; + .type 32; + .endef + .globl 124730a62158dfd3.ColorM.__init__ # -- Begin function 124730a62158dfd3.ColorM.__init__ + .p2align 4 +124730a62158dfd3.ColorM.__init__: # @"124730a62158dfd3.ColorM.__init__" +# %bb.0: # %entry + movl %edx, 8(%rcx) + retq + # -- End function + .def 124730a62158dfd3.ColorM.color_code; + .scl 2; + .type 32; + .endef + .globl 124730a62158dfd3.ColorM.color_code # -- Begin function 124730a62158dfd3.ColorM.color_code + .p2align 4 +124730a62158dfd3.ColorM.color_code: # @"124730a62158dfd3.ColorM.color_code" +# %bb.0: # %entry + movl 8(%rcx), %eax + retq + # -- End function + .def 124730a62158dfd3.ColorM.__before_init__; + .scl 2; + .type 32; + .endef + .globl 124730a62158dfd3.ColorM.__before_init__ # -- Begin function 124730a62158dfd3.ColorM.__before_init__ + .p2align 4 +124730a62158dfd3.ColorM.__before_init__: # @"124730a62158dfd3.ColorM.__before_init__" +# %bb.0: # %entry + movq $0, 8(%rcx) + leaq 124730a62158dfd3.ColorM.vtable(%rip), %rax + movq %rax, (%rcx) + retq + # -- End function + .def 124730a62158dfd3.ColoredCircle.__init__; + .scl 2; + .type 32; + .endef + .globl 124730a62158dfd3.ColoredCircle.__init__ # -- Begin function 124730a62158dfd3.ColoredCircle.__init__ + .p2align 4 +124730a62158dfd3.ColoredCircle.__init__: # @"124730a62158dfd3.ColoredCircle.__init__" +# %bb.0: # %entry + movl %r8d, 8(%rcx) + movsd %xmm1, 16(%rcx) + retq + # -- End function + .def 124730a62158dfd3.ColoredCircle.area; + .scl 2; + .type 32; + .endef + .section .rdata,"dr" + .p2align 3, 0x0 # -- Begin function 124730a62158dfd3.ColoredCircle.area +.LCPI25_0: + .quad 0x400921fb53c8d4f0 # double 3.1415926499999998 + .text + .globl 124730a62158dfd3.ColoredCircle.area + .p2align 4 +124730a62158dfd3.ColoredCircle.area: # @"124730a62158dfd3.ColoredCircle.area" +# %bb.0: # %entry + movsd 16(%rcx), %xmm1 # xmm1 = mem[0],zero + movsd .LCPI25_0(%rip), %xmm0 # xmm0 = [3.1415926499999998E+0,0.0E+0] + mulsd %xmm1, %xmm0 + mulsd %xmm1, %xmm0 + retq + # -- End function + .def 124730a62158dfd3.ColoredCircle.__before_init__; + .scl 2; + .type 32; + .endef + .globl 124730a62158dfd3.ColoredCircle.__before_init__ # -- Begin function 124730a62158dfd3.ColoredCircle.__before_init__ + .p2align 4 +124730a62158dfd3.ColoredCircle.__before_init__: # @"124730a62158dfd3.ColoredCircle.__before_init__" +# %bb.0: # %entry + movq $0, 16(%rcx) + movq $0, 8(%rcx) + leaq 124730a62158dfd3.ColoredCircle.vtable(%rip), %rax + movq %rax, (%rcx) + retq + # -- End function + .def 124730a62158dfd3.Vec2M.__new__; + .scl 2; + .type 32; + .endef + .globl 124730a62158dfd3.Vec2M.__new__ # -- Begin function 124730a62158dfd3.Vec2M.__new__ + .p2align 4 +124730a62158dfd3.Vec2M.__new__: # @"124730a62158dfd3.Vec2M.__new__" +# %bb.0: # %entry + movl $16, %ecx + jmp malloc # TAILCALL + # -- End function + .def 124730a62158dfd3.Vec2M.__init__; + .scl 2; + .type 32; + .endef + .globl 124730a62158dfd3.Vec2M.__init__ # -- Begin function 124730a62158dfd3.Vec2M.__init__ + .p2align 4 +124730a62158dfd3.Vec2M.__init__: # @"124730a62158dfd3.Vec2M.__init__" +# %bb.0: # %entry + movsd %xmm1, (%rcx) + movsd %xmm2, 8(%rcx) + retq + # -- End function + .def 124730a62158dfd3.Vec2M.__add__; + .scl 2; + .type 32; + .endef + .globl 124730a62158dfd3.Vec2M.__add__ # -- Begin function 124730a62158dfd3.Vec2M.__add__ + .p2align 4 +124730a62158dfd3.Vec2M.__add__: # @"124730a62158dfd3.Vec2M.__add__" +# %bb.0: # %entry + pushq %rsi + pushq %rdi + subq $40, %rsp + movq %rdx, %rsi + movq %rcx, %rdi + movl $1, %ecx + movl $16, %edx + callq calloc + movupd (%rsi), %xmm0 + movupd (%rdi), %xmm1 + addpd %xmm0, %xmm1 + movupd %xmm1, (%rax) + addq $40, %rsp + popq %rdi + popq %rsi + retq + # -- End function + .def 124730a62158dfd3.Vec2M.__before_init__; + .scl 2; + .type 32; + .endef + .globl 124730a62158dfd3.Vec2M.__before_init__ # -- Begin function 124730a62158dfd3.Vec2M.__before_init__ + .p2align 4 +124730a62158dfd3.Vec2M.__before_init__: # @"124730a62158dfd3.Vec2M.__before_init__" +# %bb.0: # %entry + movq $0, 8(%rcx) + movq $0, (%rcx) + retq + # -- End function + .def 124730a62158dfd3.Vec2Extra.extra_val; + .scl 2; + .type 32; + .endef + .globl 124730a62158dfd3.Vec2Extra.extra_val # -- Begin function 124730a62158dfd3.Vec2Extra.extra_val + .p2align 4 +124730a62158dfd3.Vec2Extra.extra_val: # @"124730a62158dfd3.Vec2Extra.extra_val" +# %bb.0: # %entry + movl $7, %eax + retq + # -- End function + .def 124730a62158dfd3.Vec2Extra.__before_init__; + .scl 2; + .type 32; + .endef + .globl 124730a62158dfd3.Vec2Extra.__before_init__ # -- Begin function 124730a62158dfd3.Vec2Extra.__before_init__ + .p2align 4 +124730a62158dfd3.Vec2Extra.__before_init__: # @"124730a62158dfd3.Vec2Extra.__before_init__" +# %bb.0: # %entry + retq + # -- End function + .def 124730a62158dfd3.Vec2Both.__new__; + .scl 2; + .type 32; + .endef + .globl 124730a62158dfd3.Vec2Both.__new__ # -- Begin function 124730a62158dfd3.Vec2Both.__new__ + .p2align 4 +124730a62158dfd3.Vec2Both.__new__: # @"124730a62158dfd3.Vec2Both.__new__" +# %bb.0: # %entry + movl $16, %ecx + jmp malloc # TAILCALL + # -- End function + .def 124730a62158dfd3.Vec2Both.__init__; + .scl 2; + .type 32; + .endef + .globl 124730a62158dfd3.Vec2Both.__init__ # -- Begin function 124730a62158dfd3.Vec2Both.__init__ + .p2align 4 +124730a62158dfd3.Vec2Both.__init__: # @"124730a62158dfd3.Vec2Both.__init__" +# %bb.0: # %entry + movsd %xmm1, (%rcx) + movsd %xmm2, 8(%rcx) + retq + # -- End function + .def 124730a62158dfd3.Vec2Both.__before_init__; + .scl 2; + .type 32; + .endef + .globl 124730a62158dfd3.Vec2Both.__before_init__ # -- Begin function 124730a62158dfd3.Vec2Both.__before_init__ + .p2align 4 +124730a62158dfd3.Vec2Both.__before_init__: # @"124730a62158dfd3.Vec2Both.__before_init__" +# %bb.0: # %entry + movq $0, 8(%rcx) + movq $0, (%rcx) + retq + # -- End function + .bss + .globl _pass_count # @_pass_count + .p2align 2, 0x0 +_pass_count: + .long 0 # 0x0 + + .globl _fail_count # @_fail_count + .p2align 2, 0x0 +_fail_count: + .long 0 # 0x0 + + .globl _total_pass # @_total_pass + .p2align 2, 0x0 +_total_pass: + .long 0 # 0x0 + + .globl _total_fail # @_total_fail + .p2align 2, 0x0 +_total_fail: + .long 0 # 0x0 + + .globl INT # @INT + .p2align 2, 0x0 +INT: + .long 0 # 0x0 + + .globl INTPTR # @INTPTR + .p2align 2, 0x0 +INTPTR: + .long 0 # 0x0 + + .globl BOOL # @BOOL + .p2align 2, 0x0 +BOOL: + .long 0 # 0x0 + + .globl UINT # @UINT + .p2align 2, 0x0 +UINT: + .long 0 # 0x0 + + .globl UINTPTR # @UINTPTR + .p2align 2, 0x0 +UINTPTR: + .long 0 # 0x0 + + .globl BYTE # @BYTE + .p2align 2, 0x0 +BYTE: + .long 0 # 0x0 + + .globl BYTEPTR # @BYTEPTR + .p2align 2, 0x0 +BYTEPTR: + .long 0 # 0x0 + + .globl WORD # @WORD + .p2align 2, 0x0 +WORD: + .long 0 # 0x0 + + .globl DWORD # @DWORD + .p2align 2, 0x0 +DWORD: + .long 0 # 0x0 + + .globl QWORD # @QWORD + .p2align 2, 0x0 +QWORD: + .long 0 # 0x0 + + .globl TCHAR # @TCHAR + .p2align 2, 0x0 +TCHAR: + .long 0 # 0x0 + + .globl CHARLIST # @CHARLIST + .p2align 2, 0x0 +CHARLIST: + .long 0 # 0x0 + + .globl VOID # @VOID + .p2align 2, 0x0 +VOID: + .long 0 # 0x0 + + .globl SHORT # @SHORT + .p2align 2, 0x0 +SHORT: + .long 0 # 0x0 + + .globl SHORTPTR # @SHORTPTR + .p2align 2, 0x0 +SHORTPTR: + .long 0 # 0x0 + + .globl USHORT # @USHORT + .p2align 2, 0x0 +USHORT: + .long 0 # 0x0 + + .globl USHORTPTR # @USHORTPTR + .p2align 2, 0x0 +USHORTPTR: + .long 0 # 0x0 + + .globl LONGLONG # @LONGLONG + .p2align 2, 0x0 +LONGLONG: + .long 0 # 0x0 + + .globl ULONGLONG # @ULONGLONG + .p2align 2, 0x0 +ULONGLONG: + .long 0 # 0x0 + + .globl LONG # @LONG + .p2align 2, 0x0 +LONG: + .long 0 # 0x0 + + .globl ULONG # @ULONG + .p2align 2, 0x0 +ULONG: + .long 0 # 0x0 + + .globl WCHAR # @WCHAR + .p2align 2, 0x0 +WCHAR: + .long 0 # 0x0 + + .globl WCHARPTR # @WCHARPTR + .p2align 2, 0x0 +WCHARPTR: + .long 0 # 0x0 + + .globl CHARPTR # @CHARPTR + .p2align 2, 0x0 +CHARPTR: + .long 0 # 0x0 + + .globl FSIZE_t # @FSIZE_t + .p2align 2, 0x0 +FSIZE_t: + .long 0 # 0x0 + + .globl LBA_t # @LBA_t + .p2align 2, 0x0 +LBA_t: + .long 0 # 0x0 + + .globl VOIDPTR # @VOIDPTR + .p2align 2, 0x0 +VOIDPTR: + .long 0 # 0x0 + + .globl FLOAT # @FLOAT + .p2align 2, 0x0 +FLOAT: + .long 0 # 0x0 + + .globl DOUBLE # @DOUBLE + .p2align 2, 0x0 +DOUBLE: + .long 0 # 0x0 + + .globl FLOAT8 # @FLOAT8 + .p2align 2, 0x0 +FLOAT8: + .long 0 # 0x0 + + .globl FLOAT16 # @FLOAT16 + .p2align 2, 0x0 +FLOAT16: + .long 0 # 0x0 + + .globl FLOAT32 # @FLOAT32 + .p2align 2, 0x0 +FLOAT32: + .long 0 # 0x0 + + .globl FLOAT64 # @FLOAT64 + .p2align 2, 0x0 +FLOAT64: + .long 0 # 0x0 + + .globl FLOAT128 # @FLOAT128 + .p2align 2, 0x0 +FLOAT128: + .long 0 # 0x0 + + .globl INT8 # @INT8 + .p2align 2, 0x0 +INT8: + .long 0 # 0x0 + + .globl INT16 # @INT16 + .p2align 2, 0x0 +INT16: + .long 0 # 0x0 + + .globl INT32 # @INT32 + .p2align 2, 0x0 +INT32: + .long 0 # 0x0 + + .globl INT64 # @INT64 + .p2align 2, 0x0 +INT64: + .long 0 # 0x0 + + .globl UINT8 # @UINT8 + .p2align 2, 0x0 +UINT8: + .long 0 # 0x0 + + .globl UINT16 # @UINT16 + .p2align 2, 0x0 +UINT16: + .long 0 # 0x0 + + .globl UINT32 # @UINT32 + .p2align 2, 0x0 +UINT32: + .long 0 # 0x0 + + .globl UINT64 # @UINT64 + .p2align 2, 0x0 +UINT64: + .long 0 # 0x0 + + .globl INT8PTR # @INT8PTR + .p2align 2, 0x0 +INT8PTR: + .long 0 # 0x0 + + .globl INT16PTR # @INT16PTR + .p2align 2, 0x0 +INT16PTR: + .long 0 # 0x0 + + .globl INT32PTR # @INT32PTR + .p2align 2, 0x0 +INT32PTR: + .long 0 # 0x0 + + .globl INT64PTR # @INT64PTR + .p2align 2, 0x0 +INT64PTR: + .long 0 # 0x0 + + .globl UINT8PTR # @UINT8PTR + .p2align 2, 0x0 +UINT8PTR: + .long 0 # 0x0 + + .globl UINT16PTR # @UINT16PTR + .p2align 2, 0x0 +UINT16PTR: + .long 0 # 0x0 + + .globl UINT32PTR # @UINT32PTR + .p2align 2, 0x0 +UINT32PTR: + .long 0 # 0x0 + + .globl UINT64PTR # @UINT64PTR + .p2align 2, 0x0 +UINT64PTR: + .long 0 # 0x0 + + .globl CHAR8 # @CHAR8 + .p2align 2, 0x0 +CHAR8: + .long 0 # 0x0 + + .globl CHAR16 # @CHAR16 + .p2align 2, 0x0 +CHAR16: + .long 0 # 0x0 + + .globl CHAR32 # @CHAR32 + .p2align 2, 0x0 +CHAR32: + .long 0 # 0x0 + + .globl CHAR8PTR # @CHAR8PTR + .p2align 2, 0x0 +CHAR8PTR: + .long 0 # 0x0 + + .globl CHAR16PTR # @CHAR16PTR + .p2align 2, 0x0 +CHAR16PTR: + .long 0 # 0x0 + + .globl CHAR32PTR # @CHAR32PTR + .p2align 2, 0x0 +CHAR32PTR: + .long 0 # 0x0 + + .globl i8 # @i8 + .p2align 2, 0x0 +i8: + .long 0 # 0x0 + + .globl i16 # @i16 + .p2align 2, 0x0 +i16: + .long 0 # 0x0 + + .globl i32 # @i32 + .p2align 2, 0x0 +i32: + .long 0 # 0x0 + + .globl i64 # @i64 + .p2align 2, 0x0 +i64: + .long 0 # 0x0 + + .globl u8 # @u8 + .p2align 2, 0x0 +u8: + .long 0 # 0x0 + + .globl u16 # @u16 + .p2align 2, 0x0 +u16: + .long 0 # 0x0 + + .globl u32 # @u32 + .p2align 2, 0x0 +u32: + .long 0 # 0x0 + + .globl u64 # @u64 + .p2align 2, 0x0 +u64: + .long 0 # 0x0 + + .globl SIZE_T # @SIZE_T + .p2align 2, 0x0 +SIZE_T: + .long 0 # 0x0 + + .globl SSIZE_T # @SSIZE_T + .p2align 2, 0x0 +SSIZE_T: + .long 0 # 0x0 + + .globl PTRDIFF_T # @PTRDIFF_T + .p2align 2, 0x0 +PTRDIFF_T: + .long 0 # 0x0 + + .globl int8_t # @int8_t + .p2align 2, 0x0 +int8_t: + .long 0 # 0x0 + + .globl int16_t # @int16_t + .p2align 2, 0x0 +int16_t: + .long 0 # 0x0 + + .globl int32_t # @int32_t + .p2align 2, 0x0 +int32_t: + .long 0 # 0x0 + + .globl int64_t # @int64_t + .p2align 2, 0x0 +int64_t: + .long 0 # 0x0 + + .globl uint8_t # @uint8_t + .p2align 2, 0x0 +uint8_t: + .long 0 # 0x0 + + .globl uint16_t # @uint16_t + .p2align 2, 0x0 +uint16_t: + .long 0 # 0x0 + + .globl uint32_t # @uint32_t + .p2align 2, 0x0 +uint32_t: + .long 0 # 0x0 + + .globl uint64_t # @uint64_t + .p2align 2, 0x0 +uint64_t: + .long 0 # 0x0 + + .globl size_t # @size_t + .p2align 2, 0x0 +size_t: + .long 0 # 0x0 + + .globl ssize_t # @ssize_t + .p2align 2, 0x0 +ssize_t: + .long 0 # 0x0 + + .globl ptrdiff_t # @ptrdiff_t + .p2align 2, 0x0 +ptrdiff_t: + .long 0 # 0x0 + + .globl intptr_t # @intptr_t + .p2align 2, 0x0 +intptr_t: + .long 0 # 0x0 + + .globl uintptr_t # @uintptr_t + .p2align 2, 0x0 +uintptr_t: + .long 0 # 0x0 + + .globl wchar_t # @wchar_t + .p2align 2, 0x0 +wchar_t: + .long 0 # 0x0 + + .globl char8_t # @char8_t + .p2align 2, 0x0 +char8_t: + .long 0 # 0x0 + + .globl char16_t # @char16_t + .p2align 2, 0x0 +char16_t: + .long 0 # 0x0 + + .globl char32_t # @char32_t + .p2align 2, 0x0 +char32_t: + .long 0 # 0x0 + + .globl float8_t # @float8_t + .p2align 2, 0x0 +float8_t: + .long 0 # 0x0 + + .globl float16_t # @float16_t + .p2align 2, 0x0 +float16_t: + .long 0 # 0x0 + + .globl float32_t # @float32_t + .p2align 2, 0x0 +float32_t: + .long 0 # 0x0 + + .globl float64_t # @float64_t + .p2align 2, 0x0 +float64_t: + .long 0 # 0x0 + + .globl float128_t # @float128_t + .p2align 2, 0x0 +float128_t: + .long 0 # 0x0 + + .globl _Bool # @_Bool + .p2align 2, 0x0 +_Bool: + .long 0 # 0x0 + + .globl HANDLE # @HANDLE + .p2align 2, 0x0 +HANDLE: + .long 0 # 0x0 + + .globl LPCSTR # @LPCSTR + .p2align 2, 0x0 +LPCSTR: + .long 0 # 0x0 + + .globl LPCWSTR # @LPCWSTR + .p2align 2, 0x0 +LPCWSTR: + .long 0 # 0x0 + + .section .rdata,"dr" + .p2align 3, 0x0 # @"124730a62158dfd3.ShapeM.vtable" +124730a62158dfd3.ShapeM.vtable: + .quad 124730a62158dfd3.ShapeM.area + + .p2align 3, 0x0 # @"124730a62158dfd3.ColorM.vtable" +124730a62158dfd3.ColorM.vtable: + .quad 124730a62158dfd3.ColorM.color_code + + .p2align 3, 0x0 # @"124730a62158dfd3.ColoredCircle.vtable" +124730a62158dfd3.ColoredCircle.vtable: + .quad 124730a62158dfd3.ColoredCircle.area + .quad 124730a62158dfd3.ColorM.color_code + + .p2align 4, 0x0 # @.str.124730a62158dfd3.0 +.str.124730a62158dfd3.0: + .asciz "MultiInheritTest: \345\244\232\347\273\247\346\211\277\344\270\223\351\241\271\346\265\213\350\257\225" + + .p2align 4, 0x0 # @.str.124730a62158dfd3.1 +.str.124730a62158dfd3.1: + .asciz "\345\244\232\347\273\247\346\211\277\345\255\227\346\256\265\345\220\210\345\271\266" + + .p2align 4, 0x0 # @.str.124730a62158dfd3.2 +.str.124730a62158dfd3.2: + .asciz "C: a=%d b=%d c=%d" + +.str.124730a62158dfd3.4: # @.str.124730a62158dfd3.4 + .asciz "C.a \345\220\210\345\271\266 OK" + + .p2align 4, 0x0 # @.str.124730a62158dfd3.5 +.str.124730a62158dfd3.5: + .asciz "C.a \345\220\210\345\271\266 FAILED" + +.str.124730a62158dfd3.6: # @.str.124730a62158dfd3.6 + .asciz "C.b \345\220\210\345\271\266 OK" + + .p2align 4, 0x0 # @.str.124730a62158dfd3.7 +.str.124730a62158dfd3.7: + .asciz "C.b \345\220\210\345\271\266 FAILED" + +.str.124730a62158dfd3.8: # @.str.124730a62158dfd3.8 + .asciz "C.c \350\207\252\350\272\253 OK" + + .p2align 4, 0x0 # @.str.124730a62158dfd3.9 +.str.124730a62158dfd3.9: + .asciz "C.c \350\207\252\350\272\253 FAILED" + + .p2align 4, 0x0 # @.str.124730a62158dfd3.10 +.str.124730a62158dfd3.10: + .asciz "C.get_a \347\273\247\346\211\277 OK" + + .p2align 4, 0x0 # @.str.124730a62158dfd3.11 +.str.124730a62158dfd3.11: + .asciz "C.get_a \347\273\247\346\211\277 FAILED" + + .p2align 4, 0x0 # @.str.124730a62158dfd3.12 +.str.124730a62158dfd3.12: + .asciz "C.get_b \347\273\247\346\211\277 OK" + + .p2align 4, 0x0 # @.str.124730a62158dfd3.13 +.str.124730a62158dfd3.13: + .asciz "C.get_b \347\273\247\346\211\277 FAILED" + + .p2align 4, 0x0 # @.str.124730a62158dfd3.14 +.str.124730a62158dfd3.14: + .asciz "C.get_c \350\207\252\350\272\253 OK" + + .p2align 4, 0x0 # @.str.124730a62158dfd3.15 +.str.124730a62158dfd3.15: + .asciz "C.get_c \350\207\252\350\272\253 FAILED" + + .p2align 4, 0x0 # @.str.124730a62158dfd3.16 +.str.124730a62158dfd3.16: + .asciz "\345\255\227\346\256\265\345\220\210\345\271\266\346\265\213\350\257\225\345\256\214\346\210\220" + + .p2align 4, 0x0 # @.str.124730a62158dfd3.17 +.str.124730a62158dfd3.17: + .asciz "\350\217\261\345\275\242\345\216\273\351\207\215 + \346\234\200\345\267\246\344\274\230\345\205\210" + + .p2align 4, 0x0 # @.str.124730a62158dfd3.18 +.str.124730a62158dfd3.18: + .asciz "Diamond: shared=%d who=%d base=%d" + + .p2align 4, 0x0 # @.str.124730a62158dfd3.20 +.str.124730a62158dfd3.20: + .asciz "Diamond.shared \350\217\261\345\275\242\345\216\273\351\207\215 OK" + + .p2align 4, 0x0 # @.str.124730a62158dfd3.21 +.str.124730a62158dfd3.21: + .asciz "Diamond.shared \350\217\261\345\275\242\345\216\273\351\207\215 FAILED" + + .p2align 4, 0x0 # @.str.124730a62158dfd3.22 +.str.124730a62158dfd3.22: + .asciz "who() \346\234\200\345\267\246\344\274\230\345\205\210(Left) OK" + + .p2align 4, 0x0 # @.str.124730a62158dfd3.23 +.str.124730a62158dfd3.23: + .asciz "who() \346\234\200\345\267\246\344\274\230\345\205\210 FAILED" + + .p2align 4, 0x0 # @.str.124730a62158dfd3.24 +.str.124730a62158dfd3.24: + .asciz "Base \346\226\271\346\263\225\347\273\247\346\211\277 OK" + + .p2align 4, 0x0 # @.str.124730a62158dfd3.25 +.str.124730a62158dfd3.25: + .asciz "Base \346\226\271\346\263\225\347\273\247\346\211\277 FAILED" + + .p2align 4, 0x0 # @.str.124730a62158dfd3.26 +.str.124730a62158dfd3.26: + .asciz "\350\217\261\345\275\242\345\216\273\351\207\215\346\265\213\350\257\225\345\256\214\346\210\220" + + .p2align 4, 0x0 # @.str.124730a62158dfd3.27 +.str.124730a62158dfd3.27: + .asciz "\350\231\232\346\226\271\346\263\225\345\244\232\347\273\247\346\211\277 vtable" + + .p2align 4, 0x0 # @.str.124730a62158dfd3.28 +.str.124730a62158dfd3.28: + .asciz "ColoredCircle: r=%.1f color=%d area=%.2f code=%d" + + .p2align 4, 0x0 # @.str.124730a62158dfd3.30 +.str.124730a62158dfd3.30: + .asciz "ColorM.color \345\255\227\346\256\265 OK" + + .p2align 4, 0x0 # @.str.124730a62158dfd3.31 +.str.124730a62158dfd3.31: + .asciz "ColorM.color \345\255\227\346\256\265 FAILED" + + .p2align 4, 0x0 # @.str.124730a62158dfd3.32 +.str.124730a62158dfd3.32: + .asciz "color_code \350\231\232\346\226\271\346\263\225\345\210\206\346\264\276 OK" + + .p2align 4, 0x0 # @.str.124730a62158dfd3.33 +.str.124730a62158dfd3.33: + .asciz "color_code \350\231\232\346\226\271\346\263\225\345\210\206\346\264\276 FAILED" + + .p2align 4, 0x0 # @.str.124730a62158dfd3.34 +.str.124730a62158dfd3.34: + .asciz "area \350\231\232\346\226\271\346\263\225\350\246\206\347\233\226 OK" + + .p2align 4, 0x0 # @.str.124730a62158dfd3.35 +.str.124730a62158dfd3.35: + .asciz "area \350\231\232\346\226\271\346\263\225\350\246\206\347\233\226 FAILED" + + .p2align 4, 0x0 # @.str.124730a62158dfd3.36 +.str.124730a62158dfd3.36: + .asciz "\350\231\232\346\226\271\346\263\225\345\244\232\347\273\247\346\211\277\346\265\213\350\257\225\345\256\214\346\210\220" + + .p2align 4, 0x0 # @.str.124730a62158dfd3.37 +.str.124730a62158dfd3.37: + .asciz "\350\277\220\347\256\227\347\254\246\351\207\215\350\275\275 + \346\226\271\346\263\225\347\273\247\346\211\277\351\223\276" + + .p2align 4, 0x0 # @.str.124730a62158dfd3.38 +.str.124730a62158dfd3.38: + .asciz "Vec2Both add: (%.1f, %.1f)" + + .p2align 4, 0x0 # @.str.124730a62158dfd3.40 +.str.124730a62158dfd3.40: + .asciz "Vec2Both __add__ \347\273\247\346\211\277 OK" + + .p2align 4, 0x0 # @.str.124730a62158dfd3.41 +.str.124730a62158dfd3.41: + .asciz "Vec2Both __add__ \347\273\247\346\211\277 FAILED" + + .p2align 4, 0x0 # @.str.124730a62158dfd3.42 +.str.124730a62158dfd3.42: + .asciz "Vec2Both __add__ y OK" + + .p2align 4, 0x0 # @.str.124730a62158dfd3.43 +.str.124730a62158dfd3.43: + .asciz "Vec2Both __add__ y FAILED" + + .p2align 4, 0x0 # @.str.124730a62158dfd3.44 +.str.124730a62158dfd3.44: + .asciz "Vec2Both extra_val: %d" + +.str.124730a62158dfd3.45: # @.str.124730a62158dfd3.45 + .asciz "%s\n" + + .p2align 4, 0x0 # @.str.124730a62158dfd3.46 +.str.124730a62158dfd3.46: + .asciz "extra_val \347\273\247\346\211\277(Vec2Extra) OK" + + .p2align 4, 0x0 # @.str.124730a62158dfd3.47 +.str.124730a62158dfd3.47: + .asciz "extra_val \347\273\247\346\211\277(Vec2Extra) FAILED" + + .p2align 4, 0x0 # @.str.124730a62158dfd3.48 +.str.124730a62158dfd3.48: + .asciz "\350\277\220\347\256\227\347\254\246\351\207\215\350\275\275\347\273\247\346\211\277\351\223\276\346\265\213\350\257\225\345\256\214\346\210\220" +