================
@@ -111,6 +111,26 @@ static RValue emitBuiltinBitOpWithFallback(CIRGenFunction 
&cgf,
   return RValue::get(builder.createSelect(loc, isZero, fallbackValue, result));
 }
 
+static RValue emitStdcBitWidth(CIRGenFunction &cfg, const CallExpr *e) {
+  CIRGenBuilderTy &builder = cfg.getBuilder();
+  mlir::Location loc = cfg.getLoc(e->getSourceRange());
+
+  mlir::Value arg = cfg.emitScalarExpr(e->getArg(0));
+  auto argTy = mlir::cast<cir::IntType>(arg.getType());
+
+  mlir::Value lz =
+      createBuiltinBitOp<cir::BitClzOp>(cfg, e, arg, /*poisonZero=*/false);
----------------
bcardosolopes wrote:

I believe this will hit verifier failure for every type except `unsigned int`.

`createBuiltinBitOp` already casts its result to `convertType(e->getType())`, 
and that type is always `unsigned int` here (SemaChecking.cpp:4142 for the 
generic form, the stdbit.h prototypes for the typed ones). So `lz` comes back 
`!u32i` while `width` on the next line is built in `argTy`, and `cir.sub` is 
`SameOperandsAndResultType`. `stdc_bit_width_uc` gives you `cir.sub` of `!u32i` 
and `!u8i`, `ul`/`ull` give `!u32i` and `!u64i`. `unsigned int` is the only one 
that lines up and it is the only one in the test.

OG does the subtract in the argument type and casts once at the end 
(`emitStdcBitWidthMinus`, CGBuiltin.cpp:2565). Do the same: create the 
`cir::BitClzOp` directly instead of going through `createBuiltinBitOp`, 
subtract in `argTy`, and the cast you already have at the bottom finishes it. 
Keeps the IR matching OGCG too.

`cfg` -> `cgf` while you are in here.

https://github.com/llvm/llvm-project/pull/214931
_______________________________________________
cfe-commits mailing list
[email protected]
https://lists.llvm.org/cgi-bin/mailman/listinfo/cfe-commits

Reply via email to