authorgravatar for techatrix@mailbox.orgTechatrix <techatrix@mailbox.org> 2025-01-29 19:59:24+01:00
committergravatar for paul.verigo@gmail.comPavel Verigo <paul.verigo@gmail.com> 2026-07-05 19:22:27+02:00
log002f324dfcd4f70d98cbfb7df57cee27bdf3db9f
tree51c1b47c40323176d5214eaf5c0342a6b964eb00
parent59a628c6d98d52aec394a7d270999c6349f7ec82

wasm: implement `@abs` on f16, f80 and f128 without compiler_rt


1 files changed, 30 insertions(+), 19 deletions(-)

src/codegen/wasm/CodeGen.zig+30-19
......@@ -4482,21 +4482,7 @@ fn floatNeg(cg: *CodeGen, ty: FloatType, arg: WValue) InnerError!WValue {
44824482 try cg.addTag(.f64_neg);
44834483 return .stack;
44844484 },
4485 .f80 => {
4486 const result = try cg.allocStack(Type.f80);
4487 try cg.emitWValue(result);
4488 try cg.emitWValue(arg);
4489 try cg.addMemArg(.i64_load, .{ .offset = 0 + arg.offset(), .alignment = 2 });
4490 try cg.addMemArg(.i64_store, .{ .offset = 0 + result.offset(), .alignment = 2 });
4491 try cg.emitWValue(result);
4492 try cg.emitWValue(arg);
4493 try cg.addMemArg(.i64_load, .{ .offset = 8 + arg.offset(), .alignment = 2 });
4494 try cg.addImm64(0x8000);
4495 try cg.addTag(.i64_xor);
4496 try cg.addMemArg(.i64_store, .{ .offset = 8 + result.offset(), .alignment = 2 });
4497 return result;
4498 },
4499 .f128 => {
4485 .f80, .f128 => {
45004486 const result = try cg.allocStack(Type.f128);
45014487 try cg.emitWValue(result);
45024488 try cg.emitWValue(arg);
......@@ -4505,7 +4491,11 @@ fn floatNeg(cg: *CodeGen, ty: FloatType, arg: WValue) InnerError!WValue {
45054491 try cg.emitWValue(result);
45064492 try cg.emitWValue(arg);
45074493 try cg.addMemArg(.i64_load, .{ .offset = 8 + arg.offset(), .alignment = 2 });
4508 try cg.addImm64(0x8000000000000000);
4494 if (ty == .f80) {
4495 try cg.addImm64(0x8000);
4496 } else {
4497 try cg.addImm64(0x8000000000000000);
4498 }
45094499 try cg.addTag(.i64_xor);
45104500 try cg.addMemArg(.i64_store, .{ .offset = 8 + result.offset(), .alignment = 2 });
45114501 return result;
......@@ -4515,7 +4505,12 @@ fn floatNeg(cg: *CodeGen, ty: FloatType, arg: WValue) InnerError!WValue {
45154505
45164506fn floatAbs(cg: *CodeGen, ty: FloatType, arg: WValue) InnerError!WValue {
45174507 switch (ty) {
4518 .f16 => return cg.callIntrinsic(.__fabsh, &.{.f16_type}, Type.f16, &.{arg}),
4508 .f16 => {
4509 try cg.emitWValue(arg);
4510 try cg.addImm32(0x7FFF);
4511 try cg.addTag(.i32_and);
4512 return .stack;
4513 },
45194514 .f32 => {
45204515 try cg.emitWValue(arg);
45214516 try cg.addTag(.f32_abs);
......@@ -4526,8 +4521,24 @@ fn floatAbs(cg: *CodeGen, ty: FloatType, arg: WValue) InnerError!WValue {
45264521 try cg.addTag(.f64_abs);
45274522 return .stack;
45284523 },
4529 .f80 => return cg.callIntrinsic(.__fabsx, &.{.f80_type}, Type.f80, &.{arg}),
4530 .f128 => return cg.callIntrinsic(.fabsq, &.{.f128_type}, Type.f128, &.{arg}),
4524 .f80, .f128 => {
4525 const result = try cg.allocStack(Type.f128);
4526 try cg.emitWValue(result);
4527 try cg.emitWValue(arg);
4528 try cg.addMemArg(.i64_load, .{ .offset = 0 + arg.offset(), .alignment = 2 });
4529 try cg.addMemArg(.i64_store, .{ .offset = 0 + result.offset(), .alignment = 2 });
4530 try cg.emitWValue(result);
4531 try cg.emitWValue(arg);
4532 try cg.addMemArg(.i64_load, .{ .offset = 8 + arg.offset(), .alignment = 2 });
4533 if (ty == .f80) {
4534 try cg.addImm64(0x7FFF);
4535 } else {
4536 try cg.addImm64(0x7FFFFFFFFFFFFFFF);
4537 }
4538 try cg.addTag(.i64_and);
4539 try cg.addMemArg(.i64_store, .{ .offset = 8 + result.offset(), .alignment = 2 });
4540 return result;
4541 },
45314542 }
45324543}
45334544