From 47375a2f3c10124ef75f6fa7b3133669cb868f57 Mon Sep 17 00:00:00 2001 From: Nicolas Kruse Date: Sat, 18 Oct 2025 23:26:35 +0200 Subject: [PATCH] pow and cast partially implemented --- src/copapy/__init__.py | 7 ++++--- src/coparun/runmem.c | 4 ++++ src/coparun/runmem.h | 1 + tools/generate_stencils.py | 29 +++++++++++++++++++++++++++-- 4 files changed, 36 insertions(+), 5 deletions(-) diff --git a/src/copapy/__init__.py b/src/copapy/__init__.py index 57cf8b0..acf7155 100644 --- a/src/copapy/__init__.py +++ b/src/copapy/__init__.py @@ -295,9 +295,11 @@ class cpint(CPNumber): class cpfloat(CPNumber): - def __init__(self, source: float | Node): + def __init__(self, source: float | Node | CPNumber): if isinstance(source, Node): self.source = source + elif isinstance(source, CPNumber): + self.source = _add_op('cast_float', [source]).source else: self.source = InitVar(float(source)) self.dtype = 'float' @@ -373,7 +375,7 @@ def _add_op(op: str, args: list[CPNumber | int | float], commutative: bool = Fal @overload -def cpvalue(value: bool) -> cpbool: +def cpvalue(value: bool) -> cpbool: # pyright: ignore[reportOverlappingOverload] ... @@ -653,7 +655,6 @@ def compile_to_instruction_list(node_list: Iterable[Node], sdb: stencil_database data = sdb.get_function_code('entry_function_shell', 'end') data_list.append(data) offset += len(data) - # print('function_end', offset, data) # allocate program data dw.write_com(binw.Command.ALLOCATE_CODE) diff --git a/src/coparun/runmem.c b/src/coparun/runmem.c index 2020c33..74173e1 100644 --- a/src/coparun/runmem.c +++ b/src/coparun/runmem.c @@ -1,6 +1,7 @@ #include #include #include +#include #include "runmem.h" #include "mem_man.h" @@ -116,6 +117,9 @@ int parse_commands(uint8_t *bytes) { patch(executable_memory + offs, reloc_type, value + data_offs); break; + case PATCH_MATH_POW: + break; + case ENTRY_POINT: LOG("ENTRY_POINT rel_entr_point=%i\n", rel_entr_point); rel_entr_point = *(uint32_t*)bytes; bytes += 4; diff --git a/src/coparun/runmem.h b/src/coparun/runmem.h index af9b61c..faed240 100644 --- a/src/coparun/runmem.h +++ b/src/coparun/runmem.h @@ -15,6 +15,7 @@ #define READ_DATA 65 #define END_COM 256 #define FREE_MEMORY 257 +#define PATCH_MATH_POW 512 /* Relocation types */ #define PATCH_RELATIVE_32 0 diff --git a/tools/generate_stencils.py b/tools/generate_stencils.py index caff4af..d9ef772 100644 --- a/tools/generate_stencils.py +++ b/tools/generate_stencils.py @@ -1,7 +1,7 @@ from typing import Generator import argparse -op_signs = {'add': '+', 'sub': '-', 'mul': '*', 'div': '/', +op_signs = {'add': '+', 'sub': '-', 'mul': '*', 'div': '/', 'pow': '**', 'gt': '>', 'eq': '==', 'ne': '!=', 'mod': '%'} entry_func_prefix = '' @@ -37,6 +37,14 @@ def get_op_code(op: str, type1: str, type2: str, type_out: str) -> str: """ +def get_cast(type1: str, type2: str, type_out: str) -> str: + return f""" + {stencil_func_prefix}void cast_{type_out}_{type1}_{type2}({type1} arg1, {type2} arg2) {{ + result_{type_out}_{type2}(({type1})arg1, arg2); + }} + """ + + def get_conv_code(type1: str, type2: str, type_out: str) -> str: return f""" {stencil_func_prefix}void conv_{type1}_{type2}({type1} arg1, {type2} arg2) {{ @@ -53,6 +61,15 @@ def get_op_code_float(op: str, type1: str, type2: str) -> str: """ +def get_pow(type1: str, type2: str) -> str: + return f""" + {stencil_func_prefix}void pow_{type1}_{type2}({type1} arg1, {type2} arg2) {{ + ret = math_pow((double)arg1, (double)arg2); + result_float_{type2}((float)ret); + }} + """ + + def get_floordiv(op: str, type1: str, type2: str) -> str: if type1 == 'int' and type2 == 'int': return f""" @@ -128,17 +145,23 @@ if __name__ == "__main__": // Auto-generated stencils for copapy // Do not edit manually + void math_pow(double arg1, double arg2); + volatile int dummy_int = 1337; volatile float dummy_float = 1337; """ # Scalar arithmetic: types = ['int', 'float'] - ops = ['add', 'sub', 'mul', 'div', 'floordiv', 'gt', 'eq', 'ne'] + ops = ['add', 'sub', 'mul', 'div', 'floordiv', 'gt', 'eq', 'ne', 'pow'] for t1 in types: code += get_result_stubs1(t1) + for t1, t2 in permutate(types, types): + t_out = 'int' if t1 == 'float' else 'float' + code += get_cast(t1, t2, t_out) + for t1, t2 in permutate(types, types): code += get_result_stubs2(t1, t2) @@ -150,6 +173,8 @@ if __name__ == "__main__": code += get_floordiv('floordiv', t1, t2) elif op == 'div': code += get_op_code_float(op, t1, t2) + elif op == 'pow': + code += get_pow(t1, t2) elif op == 'gt' or op == 'eq' or op == 'ne': code += get_op_code(op, t1, t2, 'int') else: