summaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
authorjonsykkel <jonrevold@gmail.com>2021-09-27 05:19:40 +0200
committerjonsykkel <jonrevold@gmail.com>2021-09-27 05:19:40 +0200
commitbc893e54863617ebd4b87e4f1fc27104c2bfc871 (patch)
tree580777f6257e0cca9ae4e55ba7cb93fa573a27eb
parentf2913d3bfd468398b474b90cabbbc0b80bc115eb (diff)
downloadokeffa-bc893e54863617ebd4b87e4f1fc27104c2bfc871.tar.gz
v_mul
-rw-r--r--inc/okeffa/iron.h8
-rw-r--r--inc/okeffa/w_mul.h69
-rw-r--r--inc/okeffa/word.h19
-rw-r--r--makefile4
-rw-r--r--src/w_mul.c8
5 files changed, 94 insertions, 14 deletions
diff --git a/inc/okeffa/iron.h b/inc/okeffa/iron.h
index 71b3aa5..e31b680 100644
--- a/inc/okeffa/iron.h
+++ b/inc/okeffa/iron.h
@@ -1,11 +1,9 @@
#ifndef OKEFFA_IRON_H
#define OKEFFA_IRON_H
-//32bit system
-//#define IRON_MACHINEBITNESSLOG2 5
-
-//64bit system
-#define IRON_MACHINEBITNESSLOG2 6
+//#define IRON_MACHINEBITNESSLOG2 4 //16bit system
+//#define IRON_MACHINEBITNESSLOG2 5 //32bit system
+#define IRON_MACHINEBITNESSLOG2 6 //64bit system
#define IRON_MACHINEBITNESS (1<<IRON_MACHINEBITNESSLOG2)
#define IRON_BYTEBITS 8
diff --git a/inc/okeffa/w_mul.h b/inc/okeffa/w_mul.h
new file mode 100644
index 0000000..b5dfe4f
--- /dev/null
+++ b/inc/okeffa/w_mul.h
@@ -0,0 +1,69 @@
+#ifndef OKEFFA_W_MUL_H
+#define OKEFFA_W_MUL_H
+
+#include <okeffa/word.h>
+
+inline word_t hw_mul (hword_t a,hword_t b);
+
+inline hword_t w_lo (word_t a);
+inline hword_t w_hi (word_t a);
+inline void w_mul (word_t a,word_t b,word_t *o_lo,word_t *o_hi);
+
+////////////////////////////////////////////////////////////////
+
+#ifdef HW_MUL_IRON
+inline word_t hw_mul(hword_t a,hword_t b){
+ return (word_t)a*(word_t)b;
+}
+#else
+
+#define _HW_MUL_BIT \
+ gm = -(bs & 1); \
+ ab += as & gm; \
+ bs >>= 1; \
+ as <<= 1;
+
+inline word_t hw_mul(hword_t a,hword_t b){
+ word_t as = a;
+ word_t bs = b;
+ word_t gm;
+ word_t ab = 0;
+ for(size_t x = 0;x < HWORD_BYTENESS;x++){
+ _HW_MUL_BIT;
+ _HW_MUL_BIT;
+ _HW_MUL_BIT;
+ _HW_MUL_BIT;
+ _HW_MUL_BIT;
+ _HW_MUL_BIT;
+ _HW_MUL_BIT;
+ _HW_MUL_BIT;
+ }
+ return ab;
+}
+#undef _HW_MUL_BIT
+#endif
+
+inline hword_t w_lo(word_t a){
+ return (hword_t)a;
+}
+
+inline hword_t w_hi(word_t a){
+ return (hword_t)(a>>HWORD_BITNESS);
+}
+
+inline void w_mul(word_t a,word_t b,word_t *o_lo,word_t *o_hi){
+ hword_t al = w_lo(a);
+ hword_t ah = w_hi(a);
+ hword_t bl = w_lo(b);
+ hword_t bh = w_hi(b);
+ word_t ll = hw_mul(al,bl);
+ word_t lh = hw_mul(al,bh);
+ word_t hl = hw_mul(ah,bl);
+ word_t hh = hw_mul(ah,bh);
+ word_t cl = w_hi(w_hi(ll)+w_lo(lh)+w_lo(hl));
+ *o_lo = ll+((lh+hl)<<HWORD_BITNESS);
+ *o_hi = hh+w_hi(hl)+w_hi(lh)+cl;
+}
+
+#endif
+
diff --git a/inc/okeffa/word.h b/inc/okeffa/word.h
index dc8bdbf..1083061 100644
--- a/inc/okeffa/word.h
+++ b/inc/okeffa/word.h
@@ -9,18 +9,23 @@
#define WORD_BITNESSLOG2 IRON_MACHINEBITNESSLOG2
#define WORD_BYTENESS (WORD_BITNESS/IRON_BYTEBITS)
-#if WORD_BITNESS == 8
-typedef uint8_t word_t;
-#elif WORD_BITNESS == 16
-typedef uint16_t word_t;
+#define HWORD_BITNESS (WORD_BITNESS/2)
+#define HWORD_BITNESSLOG2 (WORD_BITNESSLOG2/2)
+#define HWORD_BYTENESS (WORD_BYTENESS/2)
+
+#if WORD_BITNESS == 16
+typedef uint16_t word_t;
+typedef uint8_t hword_t;
#elif WORD_BITNESS == 32
-typedef uint32_t word_t;
+typedef uint32_t word_t;
+typedef uint16_t hword_t;
#elif WORD_BITNESS == 64
-typedef uint64_t word_t;
+typedef uint64_t word_t;
+typedef uint32_t hword_t;
#else
#error cant into this bitness
#endif
-typedef word_t wbool_t;
+typedef word_t wbool_t;
#endif
diff --git a/makefile b/makefile
index d38dd30..0a5fbbd 100644
--- a/makefile
+++ b/makefile
@@ -65,9 +65,9 @@ out := $(bin_dir)/$(out)
ifneq ($(run),)
run_cmd := @echo "run $(out)" 1>&2
- #run_cmd += && ./$(out) 256 16
+ run_cmd += && ./$(out) 256 16
#run_cmd += && time $(out) 2048 16 < prog/ch7
- run_cmd += && prog/ch8.sh $(out)
+ #run_cmd += && prog/ch8.sh $(out)
endif
ifneq ($(debug),)
diff --git a/src/w_mul.c b/src/w_mul.c
new file mode 100644
index 0000000..fb2715e
--- /dev/null
+++ b/src/w_mul.c
@@ -0,0 +1,8 @@
+#include <okeffa/w_mul.h>
+
+extern word_t hw_mul (hword_t a,hword_t b);
+
+extern hword_t w_lo (word_t a);
+extern hword_t w_hi (word_t a);
+extern void w_mul (word_t a,word_t b,word_t *o_lo,word_t *o_hi);
+