diff options
author | Tom Smeding <tom@tomsmeding.com> | 2024-05-26 14:57:34 +0200 |
---|---|---|
committer | Tom Smeding <tom@tomsmeding.com> | 2024-05-26 14:57:34 +0200 |
commit | e80b2593edc3d216905279ebcfa797593a1efbfc (patch) | |
tree | 5e5057e03f35369983f6600efc59c438c0cf2366 /cbits | |
parent | 2ac16efe59051e0cdeb37422ab579c8d354d562a (diff) |
Fast Fractional ops via C code
Diffstat (limited to 'cbits')
-rw-r--r-- | cbits/arith.c | 60 | ||||
-rw-r--r-- | cbits/arith_lists.h | 4 |
2 files changed, 61 insertions, 3 deletions
diff --git a/cbits/arith.c b/cbits/arith.c index 65cdb41..a71c1b9 100644 --- a/cbits/arith.c +++ b/cbits/arith.c @@ -8,7 +8,9 @@ // These are the wrapper macros used in arith_lists.h. Preset them to empty to // avoid having to touch macros unrelated to the particular operation set below. #define LIST_BINOP(name, id, hsop) +#define LIST_FBINOP(name, id, hsop) #define LIST_UNOP(name, id, _) +#define LIST_FUNOP(name, id, _) #define LIST_REDOP(name, id, _) @@ -147,6 +149,34 @@ enum binop_tag_t { } \ } +enum fbinop_tag_t { +#undef LIST_FBINOP +#define LIST_FBINOP(name, id, hsop) name = id, +#include "arith_lists.h" +#undef LIST_FBINOP +#define LIST_FBINOP(name, id, hsop) +}; + +#define ENTRY_FBINARY_OPS(typ) \ + void oxarop_fbinary_ ## typ ## _sv(enum binop_tag_t tag, i64 n, typ *out, typ x, const typ *y) { \ + switch (tag) { \ + case FB_DIV: oxarop_op_fdiv_ ## typ ## _sv(n, out, x, y); break; \ + default: wrong_op("binary_sv", tag); \ + } \ + } \ + void oxarop_fbinary_ ## typ ## _vs(enum binop_tag_t tag, i64 n, typ *out, const typ *x, typ y) { \ + switch (tag) { \ + case FB_DIV: oxarop_op_fdiv_ ## typ ## _vs(n, out, x, y); break; \ + default: wrong_op("binary_vs", tag); \ + } \ + } \ + void oxarop_fbinary_ ## typ ## _vv(enum binop_tag_t tag, i64 n, typ *out, const typ *x, const typ *y) { \ + switch (tag) { \ + case FB_DIV: oxarop_op_fdiv_ ## typ ## _vv(n, out, x, y); break; \ + default: wrong_op("binary_vv", tag); \ + } \ + } + enum unop_tag_t { #undef LIST_UNOP #define LIST_UNOP(name, id, _) name = id, @@ -165,6 +195,22 @@ enum unop_tag_t { } \ } +enum funop_tag_t { +#undef LIST_FUNOP +#define LIST_FUNOP(name, id, _) name = id, +#include "arith_lists.h" +#undef LIST_FUNOP +#define LIST_FUNOP(name, id, _) +}; + +#define ENTRY_FUNARY_OPS(typ) \ + void oxarop_funary_ ## typ(enum unop_tag_t tag, i64 n, typ *out, const typ *x) { \ + switch (tag) { \ + case FU_RECIP: oxarop_op_recip_ ## typ(n, out, x); break; \ + default: wrong_op("unary", tag); \ + } \ + } + enum redop_tag_t { #undef LIST_REDOP #define LIST_REDOP(name, id, _) name = id, @@ -187,8 +233,8 @@ enum redop_tag_t { * Generate all the functions * *****************************************************************************/ -#define NUM_TYPES_LOOP_XLIST \ - X(i32) X(i64) X(double) X(float) +#define FLOAT_TYPES_XLIST X(double) X(float) +#define NUM_TYPES_XLIST X(i32) X(i64) FLOAT_TYPES_XLIST #define X(typ) \ COMM_OP(add, +, typ) \ @@ -202,5 +248,13 @@ enum redop_tag_t { ENTRY_BINARY_OPS(typ) \ ENTRY_UNARY_OPS(typ) \ ENTRY_REDUCE_OPS(typ) -NUM_TYPES_LOOP_XLIST +NUM_TYPES_XLIST +#undef X + +#define X(typ) \ + NONCOMM_OP(fdiv, /, typ) \ + UNARY_OP(recip, 1.0/, typ) \ + ENTRY_FBINARY_OPS(typ) \ + ENTRY_FUNARY_OPS(typ) +FLOAT_TYPES_XLIST #undef X diff --git a/cbits/arith_lists.h b/cbits/arith_lists.h index c7495e8..1137c18 100644 --- a/cbits/arith_lists.h +++ b/cbits/arith_lists.h @@ -2,9 +2,13 @@ LIST_BINOP(BO_ADD, 1, +) LIST_BINOP(BO_SUB, 2, -) LIST_BINOP(BO_MUL, 3, *) +LIST_FBINOP(FB_DIV, 1, /) + LIST_UNOP(UO_NEG, 1,) LIST_UNOP(UO_ABS, 2,) LIST_UNOP(UO_SIGNUM, 3,) +LIST_FUNOP(FU_RECIP, 1,) + LIST_REDOP(RO_SUM1, 1,) LIST_REDOP(RO_PRODUCT1, 2,) |