aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
authorgingerBill <bill@gingerbill.org>2024-09-20 01:29:39 +0100
committergingerBill <bill@gingerbill.org>2024-09-20 01:29:39 +0100
commitb116e8ff55c9250d29f63d7b91cb749bf0766c4f (patch)
treec1c19e4eae13878e20130d4da089a79f93ee4d2f
parenta4dd4892846c73d21793138f518fc4b877aebca8 (diff)
Fix 128-bit integer support for wasm targets
-rw-r--r--base/runtime/procs_wasm.odin60
-rw-r--r--src/llvm_abi.cpp9
-rw-r--r--vendor/wasm/js/events.odin6
3 files changed, 51 insertions, 24 deletions
diff --git a/base/runtime/procs_wasm.odin b/base/runtime/procs_wasm.odin
index 8da1564c6..7e03656ca 100644
--- a/base/runtime/procs_wasm.odin
+++ b/base/runtime/procs_wasm.odin
@@ -14,33 +14,57 @@ ti_uint :: struct #raw_union {
}
@(link_name="__ashlti3", linkage="strong")
-__ashlti3 :: proc "contextless" (la, ha: u64, b_: u32) -> i128 {
- bits_in_dword :: size_of(u32)*8
- b := u32(b_)
+__ashlti3 :: proc "contextless" (a: i128, b: u32) -> i128 {
+ bits :: 64
- input, result: ti_int
- input.lo, input.hi = la, ha
- if b & bits_in_dword != 0 {
+ input: ti_int = ---
+ result: ti_int = ---
+ input.all = a
+ if b & bits != 0 {
result.lo = 0
- result.hi = input.lo << (b-bits_in_dword)
+ result.hi = input.lo << (b-bits)
} else {
if b == 0 {
- return input.all
+ return a
}
result.lo = input.lo<<b
- result.hi = (input.hi<<b) | (input.lo>>(bits_in_dword-b))
+ result.hi = (input.hi<<b) | (input.lo>>(bits-b))
}
return result.all
}
+__ashlti3_unsigned :: proc "contextless" (a: u128, b: u32) -> u128 {
+ return cast(u128)__ashlti3(cast(i128)a, b)
+}
+
+@(link_name="__mulddi3", linkage="strong")
+__mulddi3 :: proc "contextless" (a, b: u64) -> i128 {
+ r: ti_int
+ bits :: 32
+
+ mask :: ~u64(0) >> bits
+ r.lo = (a & mask) * (b & mask)
+ t := r.lo >> bits
+ r.lo &= mask
+ t += (a >> bits) * (b & mask)
+ r.lo += (t & mask) << bits
+ r.hi = t >> bits
+ t = r.lo >> bits
+ r.lo &= mask
+ t += (b >> bits) * (a & mask)
+ r.lo += (t & mask) << bits
+ r.hi += t >> bits
+ r.hi += (a >> bits) * (b >> bits)
+ return r.all
+}
@(link_name="__multi3", linkage="strong")
-__multi3 :: proc "contextless" (la, ha, lb, hb: u64) -> i128 {
+__multi3 :: proc "contextless" (a, b: i128) -> i128 {
x, y, r: ti_int
- x.lo, x.hi = la, ha
- y.lo, y.hi = lb, hb
- r.all = i128(x.lo * y.lo) // TODO this is incorrect
+ x.all = a
+ y.all = b
+ r.all = __mulddi3(x.lo, y.lo)
r.hi += x.hi*y.lo + x.lo*y.hi
return r.all
}
@@ -54,18 +78,16 @@ udivti3 :: proc "c" (la, ha, lb, hb: u64) -> u128 {
}
@(link_name="__lshrti3", linkage="strong")
-__lshrti3 :: proc "c" (la, ha: u64, b: u32) -> i128 {
- bits :: size_of(u32)*8
+__lshrti3 :: proc "c" (a: i128, b: u32) -> i128 {
+ bits :: 64
input, result: ti_int
- input.lo = la
- input.hi = ha
-
+ input.all = a
if b & bits != 0 {
result.hi = 0
result.lo = input.hi >> (b - bits)
} else if b == 0 {
- return input.all
+ return a
} else {
result.hi = input.hi >> b
result.lo = (input.hi << (bits - b)) | (input.lo >> b)
diff --git a/src/llvm_abi.cpp b/src/llvm_abi.cpp
index aa5c4dc60..42086b09d 100644
--- a/src/llvm_abi.cpp
+++ b/src/llvm_abi.cpp
@@ -1257,11 +1257,12 @@ namespace lbAbiWasm {
}
gb_internal lbArgType non_struct(LLVMContextRef c, LLVMTypeRef type, bool is_return) {
- if (!is_return && type == LLVMIntTypeInContext(c, 128)) {
- LLVMTypeRef cast_type = LLVMVectorType(LLVMInt64TypeInContext(c), 2);
+ if (type == LLVMIntTypeInContext(c, 128)) {
+ // LLVMTypeRef cast_type = LLVMVectorType(LLVMInt64TypeInContext(c), 2);
+ LLVMTypeRef cast_type = nullptr;
return lb_arg_type_direct(type, cast_type, nullptr, nullptr);
}
-
+
if (!is_return && lb_sizeof(type) > 8) {
return lb_arg_type_indirect(type, nullptr);
}
@@ -1282,7 +1283,7 @@ namespace lbAbiWasm {
case LLVMPointerTypeKind:
return true;
case LLVMIntegerTypeKind:
- return lb_sizeof(type) <= 8;
+ return lb_sizeof(type) <= 16;
}
return false;
}
diff --git a/vendor/wasm/js/events.odin b/vendor/wasm/js/events.odin
index 442dc50b3..258776fff 100644
--- a/vendor/wasm/js/events.odin
+++ b/vendor/wasm/js/events.odin
@@ -30,6 +30,8 @@ Event_Kind :: enum u32 {
Wheel,
Focus,
+ Focus_In,
+ Focus_Out,
Submit,
Blur,
Change,
@@ -110,6 +112,8 @@ event_kind_string := [Event_Kind]string{
.Wheel = "wheel",
.Focus = "focus",
+ .Focus_In = "focusin",
+ .Focus_Out = "focusout",
.Submit = "submit",
.Blur = "blur",
.Change = "change",
@@ -332,7 +336,7 @@ remove_custom_event_listener :: proc(id: string, name: string, user_data: rawptr
return _remove_event_listener(id, name, user_data, callback)
}
-
+import "core:fmt"
@(export, link_name="odin_dom_do_event_callback")