diff options
| author | Andrew Kelley <andrew@ziglang.org> | 2022-02-12 20:44:30 -0700 |
|---|---|---|
| committer | Andrew Kelley <andrew@ziglang.org> | 2022-02-12 20:44:30 -0700 |
| commit | a005ac9d3c884c6254074ec150fe536881fe31b5 (patch) | |
| tree | 6c7d2016362d441ad77d77abbf76f5116b329c73 /src/codegen | |
| parent | 16ec848d2ab5702ad3794d30ed5d776b5abb60ce (diff) | |
| download | zig-a005ac9d3c884c6254074ec150fe536881fe31b5.tar.gz zig-a005ac9d3c884c6254074ec150fe536881fe31b5.zip | |
stage2: implement `@popCount` for SIMD vectors
Diffstat (limited to 'src/codegen')
| -rw-r--r-- | src/codegen/llvm.zig | 15 |
1 files changed, 10 insertions, 5 deletions
diff --git a/src/codegen/llvm.zig b/src/codegen/llvm.zig index 3b9bac09ec..493b895d5d 100644 --- a/src/codegen/llvm.zig +++ b/src/codegen/llvm.zig @@ -2205,7 +2205,7 @@ pub const FuncGen = struct { .get_union_tag => try self.airGetUnionTag(inst), .clz => try self.airClzCtz(inst, "ctlz"), .ctz => try self.airClzCtz(inst, "cttz"), - .popcount => try self.airPopCount(inst, "ctpop"), + .popcount => try self.airPopCount(inst), .tag_name => try self.airTagName(inst), .error_name => try self.airErrorName(inst), .splat => try self.airSplat(inst), @@ -4364,7 +4364,7 @@ pub const FuncGen = struct { } } - fn airPopCount(self: *FuncGen, inst: Air.Inst.Index, prefix: [*:0]const u8) !?*const llvm.Value { + fn airPopCount(self: *FuncGen, inst: Air.Inst.Index) !?*const llvm.Value { if (self.liveness.isUnused(inst)) return null; const ty_op = self.air.instructions.items(.data)[inst].ty_op; @@ -4372,11 +4372,16 @@ pub const FuncGen = struct { const operand = try self.resolveInst(ty_op.operand); const target = self.dg.module.getTarget(); const bits = operand_ty.intInfo(target).bits; + const vec_len: ?u32 = switch (operand_ty.zigTypeTag()) { + .Vector => operand_ty.vectorLen(), + else => null, + }; var fn_name_buf: [100]u8 = undefined; - const llvm_fn_name = std.fmt.bufPrintZ(&fn_name_buf, "llvm.{s}.i{d}", .{ - prefix, bits, - }) catch unreachable; + const llvm_fn_name = if (vec_len) |len| + std.fmt.bufPrintZ(&fn_name_buf, "llvm.ctpop.v{d}i{d}", .{ len, bits }) catch unreachable + else + std.fmt.bufPrintZ(&fn_name_buf, "llvm.ctpop.i{d}", .{bits}) catch unreachable; const fn_val = self.dg.object.llvm_module.getNamedFunction(llvm_fn_name) orelse blk: { const operand_llvm_ty = try self.dg.llvmType(operand_ty); const param_types = [_]*const llvm.Type{operand_llvm_ty}; |
