18#include "mlir/IR/Operation.h"
20#include "clang/AST/Attrs.inc"
30#include "llvm/Support/Casting.h"
31#include "llvm/Support/MemoryBuffer.h"
32#include "llvm/Support/VirtualFileSystem.h"
46 llvm::StringMap<mlir::Operation *> kernelHandles;
49 llvm::DenseMap<mlir::Operation *, mlir::Operation *> kernelStubs;
54 cir::CUDADeviceVarKind flags;
56 llvm::SmallVector<VarInfo, 16> deviceVars;
59 std::unique_ptr<MangleContext> deviceMC;
62 void emitDeviceStubBodyNew(CIRGenFunction &cgf, cir::FuncOp fn,
63 FunctionArgList &args);
64 void recordDeviceBinary();
65 void transformManagedVars();
66 mlir::Value prepareKernelArgs(CIRGenFunction &cgf, mlir::Location loc,
67 FunctionArgList &args);
68 mlir::Operation *getKernelHandle(cir::FuncOp fn, GlobalDecl gd)
override;
70 mlir::Operation *getKernelStub(mlir::Operation *handle)
override {
71 auto it = kernelStubs.find(handle);
72 assert(it != kernelStubs.end());
75 std::string addPrefixToName(StringRef funcName)
const;
76 std::string addUnderscoredPrefixToName(StringRef funcName)
const;
79 CIRGenNVCUDARuntime(CIRGenModule &cgm);
80 ~CIRGenNVCUDARuntime();
82 void emitDeviceStub(CIRGenFunction &cgf, cir::FuncOp fn,
83 FunctionArgList &args)
override;
85 void handleVarRegistration(
const VarDecl *vd, cir::GlobalOp var)
override;
86 void finalizeModule()
override;
87 void handleGlobalReplace(cir::GlobalOp oldGV, cir::GlobalOp newGV)
override;
89 void internalizeDeviceSideVar(
const VarDecl *d,
90 cir::GlobalLinkageKind &linkage)
override;
92 std::string getDeviceSideName(
const NamedDecl *nd)
override;
94 void registerDeviceVar(
const VarDecl *vd, cir::GlobalOp &var,
bool isExtern,
97 auto &builder = cgm.getBuilder();
98 var->setAttr(cir::CUDAVarRegistrationInfoAttr::getMnemonic(),
99 cir::CUDAVarRegistrationInfoAttr::get(
100 builder.getContext(),
102 cir::CUDADeviceVarKind::Variable, isExtern, isConstant,
105 deviceVars.push_back({
108 cir::CUDADeviceVarKind::Variable,
112 void registerDeviceSurf(
const VarDecl *vd, cir::GlobalOp &var,
bool isExtern,
114 auto &builder = cgm.getBuilder();
116 var->setAttr(cir::CUDAVarRegistrationInfoAttr::getMnemonic(),
117 cir::CUDAVarRegistrationInfoAttr::get(
118 builder.getContext(),
120 cir::CUDADeviceVarKind::Surface, isExtern,
122 false, surfaceType));
124 deviceVars.push_back({
127 cir::CUDADeviceVarKind::Surface,
131 void registerDeviceTex(
const VarDecl *vd, cir::GlobalOp &var,
bool isExtern) {
132 auto &builder = cgm.getBuilder();
134 var->setAttr(cir::CUDAVarRegistrationInfoAttr::getMnemonic(),
135 cir::CUDAVarRegistrationInfoAttr::get(
136 builder.getContext(),
138 cir::CUDADeviceVarKind::Texture, isExtern,
143 deviceVars.push_back({
146 cir::CUDADeviceVarKind::Texture,
153std::string CIRGenNVCUDARuntime::addPrefixToName(StringRef funcName)
const {
154 return (prefix + funcName).str();
158CIRGenNVCUDARuntime::addUnderscoredPrefixToName(StringRef funcName)
const {
159 return (
"__" + prefix + funcName).str();
162CIRGenNVCUDARuntime::CIRGenNVCUDARuntime(CIRGenModule &cgm)
163 : CIRGenCUDARuntime(cgm),
164 deviceMC(cgm.getASTContext().cudaNVInitDeviceMC()) {
166 cgm.
errorNYI(
"CIRGenNVCUDARuntime: Offload via LLVM");
173mlir::Value CIRGenNVCUDARuntime::prepareKernelArgs(
CIRGenFunction &cgf,
179 auto voidPtrArrayTy = cir::ArrayType::get(cgm.
voidPtrTy, args.size());
180 mlir::Value kernelArgs =
181 builder.
createAlloca(loc, cir::PointerType::get(voidPtrArrayTy),
184 mlir::Value kernelArgsDecayed =
185 builder.
createCast(cir::CastKind::array_to_ptrdecay, kernelArgs,
188 for (
const auto &[i, arg] : llvm::enumerate(args)) {
191 mlir::Value storePos =
196 builder.CIRBaseBuilderTy::createStore(loc, argAsVoid, storePos);
199 return kernelArgsDecayed;
204void CIRGenNVCUDARuntime::emitDeviceStubBodyNew(CIRGenFunction &cgf,
206 FunctionArgList &args) {
210 cgm.
errorNYI(
"CIRGenNVCUDARuntime: Offload via LLVM");
213 mlir::Location loc = fn.getLoc();
218 mlir::Value kernelArgs = prepareKernelArgs(cgf, loc, args);
235 std::string kernelLaunchAPI =
"LaunchKernel";
237 LangOptions::GPUDefaultStreamKind::PerThread) {
239 kernelLaunchAPI +=
"_spt";
241 kernelLaunchAPI +=
"_ptsz";
244 std::string launchKernelName = addPrefixToName(kernelLaunchAPI);
245 const IdentifierInfo &launchII =
247 FunctionDecl *cudaLaunchKernelFD =
nullptr;
248 for (NamedDecl *result : dc->
lookup(&launchII)) {
249 if (FunctionDecl *fd = dyn_cast<FunctionDecl>(result))
250 cudaLaunchKernelFD = fd;
253 if (cudaLaunchKernelFD ==
nullptr) {
255 "Can't find declaration for " + launchKernelName);
272 builder.
createAlloca(loc, cir::PointerType::get(dim3Ty),
"grid_dim",
275 builder.
createAlloca(loc, cir::PointerType::get(dim3Ty),
"block_dim",
280 loc, cir::PointerType::get(streamTy),
"stream", cgm.
getPointerAlign());
284 sharedMem.getType(), stream.getType()},
286 addUnderscoredPrefixToName(
"PopCallConfiguration"));
297 mlir::Value kernel = [&]() -> mlir::Value {
298 if (cir::GlobalOp globalOp = llvm::dyn_cast_or_null<cir::GlobalOp>(
299 kernelHandles[fn.getSymName()])) {
300 cir::PointerType kernelTy = cir::PointerType::get(globalOp.getSymType());
301 mlir::Value kernelVal = cir::GetGlobalOp::create(builder, loc, kernelTy,
302 globalOp.getSymName());
306 if (cir::FuncOp funcOp = llvm::dyn_cast_or_null<cir::FuncOp>(
307 kernelHandles[fn.getSymName()])) {
308 cir::PointerType kernelTy =
309 cir::PointerType::get(funcOp.getFunctionType());
310 mlir::Value kernelVal =
311 cir::GetGlobalOp::create(builder, loc, kernelTy, funcOp.getSymName());
315 llvm_unreachable(
"Expected stub handle to be cir::GlobalOp or FuncOp");
318 CallArgList launchArgs;
330 RValue::get(builder.CIRBaseBuilderTy::createLoad(loc, sharedMem)),
332 launchArgs.
add(
RValue::get(builder.CIRBaseBuilderTy::createLoad(loc, stream)),
335 mlir::Type launchTy =
339 const CIRGenFunctionInfo &callInfo =
342 ReturnValueSlot(), launchArgs,
false);
346 cgm.
errorNYI(
"MSVC CUDA stub handling");
349void CIRGenNVCUDARuntime::emitDeviceStub(CIRGenFunction &cgf, cir::FuncOp fn,
350 FunctionArgList &args) {
354 auto kernelNameAttr = cir::CUDAKernelNameAttr::get(
355 builder.getContext(), builder.getStringAttr(kernelName));
356 fn->setDiscardableAttr(cir::CUDAKernelNameAttr::getMnemonic(),
360 llvm::dyn_cast<cir::GlobalOp>(kernelHandles[fn.getSymName()])) {
361 mlir::Type fnPtrTy = globalOp.getSymType();
362 auto sym = mlir::FlatSymbolRefAttr::get(fn.getSymNameAttr());
363 auto gv = cir::GlobalViewAttr::get(fnPtrTy, sym);
365 globalOp->setAttr(
"initial_value", gv);
366 globalOp->setAttr(
"alignment", builder.getI64IntegerAttr(
371 globalOp.setLinkage(fn.getLinkage());
372 mlir::SymbolTable::setSymbolVisibility(
374 cgm.
setDSOLocal(
static_cast<mlir::Operation *
>(globalOp));
379 CudaFeature::CUDA_USES_NEW_LAUNCH) ||
382 emitDeviceStubBodyNew(cgf, fn, args);
384 cgm.
errorNYI(
"Emit Stub Body Legacy");
388 return new CIRGenNVCUDARuntime(cgm);
391CIRGenNVCUDARuntime::~CIRGenNVCUDARuntime() {}
393mlir::Operation *CIRGenNVCUDARuntime::getKernelHandle(cir::FuncOp fn,
397 auto it = kernelHandles.find(fn.getSymName());
398 if (it != kernelHandles.end()) {
399 mlir::Operation *oldHandle = it->second;
401 if (kernelStubs[oldHandle] == fn)
409 kernelStubs[oldHandle] = fn;
414 kernelStubs.erase(oldHandle);
419 kernelHandles[fn.getSymName()] = fn;
420 kernelStubs[fn] = fn;
428 cir::PointerType fnPtrTy = builder.
getPointerTo(fn.getFunctionType());
429 cir::GlobalOp globalOp =
432 globalOp->setAttr(
"alignment", builder.getI64IntegerAttr(
438 FunctionTemplateDecl *ft = fd->getPrimaryTemplate();
443 kernelHandles[fn.getSymName()] = globalOp;
444 kernelStubs[globalOp] = fn;
449void CIRGenNVCUDARuntime::internalizeDeviceSideVar(
450 const VarDecl *d, cir::GlobalLinkageKind &linkage) {
453 "internalizeDeviceSideVar: GPU Relocatable Device Code (RDC)");
460 if (d->
hasAttr<CUDADeviceAttr>() || d->
hasAttr<CUDAConstantAttr>() ||
461 d->
hasAttr<CUDASharedAttr>() ||
464 linkage = cir::GlobalLinkageKind::InternalLinkage;
469 "internalizeDeviceSideVar: CUDA Texture support");
472std::string CIRGenNVCUDARuntime::getDeviceSideName(
const NamedDecl *nd) {
475 if (
auto *fd = dyn_cast<FunctionDecl>(nd))
476 gd = GlobalDecl(fd, KernelReferenceKind::Kernel);
479 std::string deviceSideName;
486 SmallString<256> buffer;
487 llvm::raw_svector_ostream
out(buffer);
489 deviceSideName = std::string(
out.str());
496 SmallString<256> buffer;
497 llvm::raw_svector_ostream
out(buffer);
498 out << deviceSideName;
500 deviceSideName = std::string(
out.str());
502 return deviceSideName;
505void CIRGenNVCUDARuntime::handleVarRegistration(
const VarDecl *vd,
507 if (vd->
hasAttr<CUDADeviceAttr>() || vd->
hasAttr<CUDAConstantAttr>()) {
523 vd->
hasAttr<HIPManagedAttr>()) {
525 vd->
hasAttr<CUDAConstantAttr>());
532 const TemplateArgumentList &args = td->getTemplateArgs();
534 assert(args.
size() == 2 &&
535 "Unexpected number of template arguments of CUDA device "
536 "builtin surface type.");
538 llvm::APSInt surfaceType = args[1].getAsIntegral();
542 surfaceType.getSExtValue());
552void CIRGenNVCUDARuntime::handleGlobalReplace(cir::GlobalOp oldGV,
553 cir::GlobalOp newGV) {
554 for (
auto &info : deviceVars) {
555 if (
info.var == oldGV)
568 ->walk([](mlir::Operation *op) {
569 if (auto fn = mlir::dyn_cast<cir::FuncOp>(op);
570 fn && !fn.isDeclaration() &&
571 fn->hasAttr(cir::CUDAKernelNameAttr::getMnemonic()))
572 return mlir::WalkResult::interrupt();
573 if (op->hasAttr(cir::CUDAVarRegistrationInfoAttr::getMnemonic()))
574 return mlir::WalkResult::interrupt();
575 return mlir::WalkResult::advance();
586void CIRGenNVCUDARuntime::recordDeviceBinary() {
588 if (binaryName.empty())
592 if ((langOpts.HIP || !langOpts.GPURelocatableDeviceCode) &&
600 llvm::ErrorOr<std::unique_ptr<llvm::MemoryBuffer>> binaryOrErr =
601 fs.getBufferForFile(binaryName, -1,
603 if (std::error_code ec = binaryOrErr.getError()) {
605 << binaryName << ec.message();
613 StringRef
bytes = binaryOrErr.get()->getBuffer();
617 auto fatbinTy = cir::ArrayType::get(charTy,
bytes.size());
618 cgm.
getModule()->setAttr(cir::CIRDialect::getCUDADeviceBinaryAttrName(),
619 mlir::StringAttr::get(
bytes, fatbinTy));
623void CIRGenNVCUDARuntime::transformManagedVars() {
626 for (
auto &&info : deviceVars) {
628 if (
info.flags != cir::CUDADeviceVarKind::Variable ||
629 !
info.d->hasAttr<HIPManagedAttr>())
632 cir::PointerType varPtrTy =
636 cgm.
getLangOpts().CUDAIsDevice ? LangAS::cuda_device : LangAS::Default);
637 std::optional<mlir::SymbolTable::UseRange> uses =
var.getSymbolUses(module);
639 std::string
name =
var.getSymName().str();
641 std::optional<llvm::StringRef> comdat =
var.getComdat();
642 if (comdat && comdat->empty())
643 var.setComdat(llvm::StringRef(name));
645 var.setSymName(name +
".managed");
648 cir::GlobalOp managedVar =
651 managedVar.setLinkage(
var.getLinkage());
652 if (!
var.isDeclaration())
654 managedVar.setDsoLocal(
var.getDsoLocal());
655 managedVar.setGlobalVisibility(
var.getGlobalVisibility());
656 mlir::SymbolTable::setSymbolVisibility(
657 managedVar, mlir::SymbolTable::getSymbolVisibility(var));
659 cir::CUDAExternallyInitializedAttr::getMnemonic(),
663 cir::PointerType managedPtrTy =
664 builder.
getPointerTo(varPtrTy, managedVar.getAddrSpaceAttr());
665 for (mlir::SymbolTable::SymbolUse use : *uses) {
666 auto getGlobalOp = dyn_cast<cir::GetGlobalOp>(use.getUser());
669 "transformManagedVars: non-instruction use");
672 mlir::Value addr = getGlobalOp.getAddr();
673 addr.setType(managedPtrTy);
674 mlir::OpBuilder::InsertionGuard guard(builder);
675 builder.setInsertionPointAfter(getGlobalOp);
677 getGlobalOp.getLoc(), varPtrTy, addr,
679 addr.replaceAllUsesExcept(ld, ld.getDefiningOp());
690void CIRGenNVCUDARuntime::finalizeModule() {
691 transformManagedVars();
693 recordDeviceBinary();
707 for (
auto &&info : deviceVars) {
709 bool isDecl =
info.var.isDeclaration();
711 bool isVarOrSurfaceOrTexture = (
kind == cir::CUDADeviceVarKind::Variable ||
712 kind == cir::CUDADeviceVarKind::Surface ||
713 kind == cir::CUDADeviceVarKind::Texture);
714 bool isUsed =
info.d->isUsed();
715 bool hasUsedAttr =
info.d->hasAttr<UsedAttr>();
716 if (!isDecl && !isLocalLinkage && isVarOrSurfaceOrTexture && isUsed &&
718 if (
auto globalValue = mlir::dyn_cast<cir::CIRGlobalValueInterface>(
719 info.var.getOperation())) {
Defines the clang::ASTContext interface.
static StringRef bytes(const std::vector< T, Allocator > &v)
Provides definitions for the various language-specific address spaces.
static bool hasEntitiesToRegister(mlir::ModuleOp module)
Whether this translation unit has anything for the CUDA runtime to register.
Defines the clang::FileManager interface and associated types.
*collection of selector each with an associated kind and an ordered *collection of selectors A selector has a kind
Defines the SourceManager interface.
__CUDA_BUILTIN_VAR __cuda_builtin_blockDim_t blockDim
__CUDA_BUILTIN_VAR __cuda_builtin_gridDim_t gridDim
mlir::TypedAttr getConstNullPtrAttr(mlir::Type t)
mlir::Value createCast(mlir::Location loc, cir::CastKind kind, mlir::Value src, mlir::Type newTy)
cir::PtrStrideOp createPtrStride(mlir::Location loc, mlir::Value base, mlir::Value stride)
cir::PointerType getPointerTo(mlir::Type ty)
mlir::Value createAlloca(mlir::Location loc, cir::PointerType addrType, llvm::StringRef name, mlir::IntegerAttr alignment, mlir::Value dynAllocSize)
mlir::Value createBitcast(mlir::Value src, mlir::Type newTy)
SourceManager & getSourceManager()
TranslationUnitDecl * getTranslationUnitDecl() const
bool shouldExternalize(const Decl *D) const
Whether a C++ static variable or CUDA/HIP kernel should be externalized.
llvm::SetVector< const VarDecl * > CUDADeviceVarODRUsedByHost
Keep track of CUDA/HIP device-side variables ODR-used by host code.
const TargetInfo & getTargetInfo() const
mlir::Value getPointer() const
cir::LoadOp createAlignedLoad(mlir::Location loc, mlir::Type ty, mlir::Value ptr, llvm::MaybeAlign align)
cir::ConstantOp getConstInt(mlir::Location loc, llvm::APSInt intVal)
clang::MangleContext & getMangleContext()
Gets the mangle context.
static CIRGenCallee forDirect(mlir::Operation *funcPtr, const CIRGenCalleeInfo &abstractInfo=CIRGenCalleeInfo())
clang::GlobalDecl curGD
The GlobalDecl for the current function being compiled or the global variable currently being initial...
CIRGenTypes & getTypes() const
const clang::LangOptions & getLangOpts() const
const clang::Decl * curFuncDecl
Address getAddrOfLocalVar(const clang::VarDecl *vd)
Return the address of a local variable.
mlir::Value emitRuntimeCall(mlir::Location loc, cir::FuncOp callee, llvm::ArrayRef< mlir::Value > args={}, mlir::NamedAttrList attrs={})
RValue emitCall(const CIRGenFunctionInfo &funcInfo, const CIRGenCallee &callee, ReturnValueSlot returnValue, const CallArgList &args, cir::CIRCallOpInterface *callOp, bool isMustTail, SourceRange clangLoc)
This class organizes the cross-function state that is used while generating CIR code.
llvm::StringRef getMangledName(clang::GlobalDecl gd)
DiagnosticBuilder errorNYI(SourceLocation, llvm::StringRef)
Helpers to emit "not yet implemented" error diagnostics.
clang::ASTContext & getASTContext() const
void insertGlobalSymbol(mlir::Operation *op)
CIRGenBuilderTy & getBuilder()
void setDSOLocal(mlir::Operation *op) const
void setGVProperties(mlir::Operation *op, const NamedDecl *d) const
Set visibility, dllimport/dllexport and dso_local.
clang::DiagnosticsEngine & getDiags() const
static mlir::SymbolTable::Visibility getMLIRVisibilityFromCIRLinkage(cir::GlobalLinkageKind GLK)
const clang::TargetInfo & getTarget() const
void error(SourceLocation loc, llvm::StringRef error)
Emit a general error that something can't be done.
cir::FuncOp createRuntimeFunction(cir::FuncType ty, llvm::StringRef name, mlir::NamedAttrList extraAttrs={}, bool isLocal=false, bool assumeConvergent=false)
void eraseGlobalSymbol(mlir::Operation *op)
const clang::CodeGenOptions & getCodeGenOpts() const
const clang::LangOptions & getLangOpts() const
void printPostfixForExternalizedDecl(llvm::raw_ostream &os, const Decl *d)
Print the postfix for externalized static variable or kernels for single source offloading languages ...
cir::GlobalOp createGlobalOp(mlir::Location loc, llvm::StringRef name, mlir::Type t, bool isConstant=false, mlir::ptr::MemorySpaceAttrInterface addrSpace={}, mlir::Operation *insertPoint=nullptr)
mlir::ModuleOp getModule() const
void addCompilerUsedGlobal(cir::CIRGlobalValueInterface gv)
Add a global value to the llvmCompilerUsed list.
mlir::MLIRContext & getMLIRContext()
void maybeSetTrivialComdat(const clang::Decl &d, mlir::Operation *op)
CIRGenCXXABI & getCXXABI() const
const CIRGenFunctionInfo & arrangeFunctionDeclaration(const clang::FunctionDecl *fd)
Free functions are functions that are compatible with an ordinary C function pointer type.
mlir::Type convertType(clang::QualType type)
Convert a Clang type into a mlir::Type.
void add(RValue rvalue, clang::QualType type)
Type for representing both the decl and type of parameters to a function.
static RValue get(mlir::Value v)
static RValue getAggregate(Address addr, bool isVolatile=false)
Convert an Address to an RValue.
QuantityType getQuantity() const
Get the raw integer representation of this quantity.
static CharUnits fromQuantity(QuantityType Quantity)
Construct a CharUnits quantity from a raw integer type.
std::string OffloadBinaryToEmbedFile
Name of file passed with -foffload-include-binary option to forward to offloading runtime back-end fo...
lookup_result lookup(DeclarationName Name) const
lookup - Find the declarations (if any) with the given Name in this context.
SourceLocation getLocation() const
DiagnosticBuilder Report(SourceLocation Loc, unsigned DiagID)
Issue the message to the client.
llvm::vfs::FileSystem & getVirtualFileSystem() const
const ParmVarDecl * getParamDecl(unsigned i) const
bool isThisDeclarationADefinition() const
Returns whether this template declaration defines the primary pattern.
GlobalDecl - represents a global declaration.
GlobalDecl getWithKernelReferenceKind(KernelReferenceKind Kind)
const Decl * getDecl() const
StringRef getName() const
Return the actual identifier string.
IdentifierInfo & get(StringRef Name)
Return the identifier token info for the specified named identifier.
GPUDefaultStreamKind GPUDefaultStream
The default stream kind used for HIP kernel launching.
bool shouldMangleDeclName(const NamedDecl *D)
void mangleName(GlobalDecl GD, raw_ostream &)
IdentifierInfo * getIdentifier() const
Get the identifier that names this declaration, if there is one.
FileManager & getFileManager() const
bool isMicrosoft() const
Is this ABI an MSVC-compatible ABI?
TargetCXXABI getCXXABI() const
Get the C++ ABI currently in use.
unsigned getCharWidth() const
const llvm::VersionTuple & getSDKVersion() const
unsigned size() const
Retrieve the number of template arguments in this template argument list.
static DeclContext * castToDeclContext(const TranslationUnitDecl *D)
CXXRecordDecl * castAsCXXRecordDecl() const
bool isCUDADeviceBuiltinSurfaceType() const
Check if the type is the CUDA device builtin surface type.
bool isCUDADeviceBuiltinTextureType() const
Check if the type is the CUDA device builtin texture type.
SourceRange getSourceRange() const override LLVM_READONLY
Source range that this declaration covers.
bool isInline() const
Whether this variable is (C++1z) inline.
bool hasExternalStorage() const
Returns true if a variable has extern or private_extern storage.
DefinitionKind hasDefinition(ASTContext &) const
Check whether this variable is defined in this translation unit.
static bool isLocalLinkage(GlobalLinkageKind linkage)
mlir::ptr::MemorySpaceAttrInterface toCIRAddressSpaceAttr(mlir::MLIRContext &ctx, clang::LangAS langAS)
Convert an AST LangAS to the appropriate CIR address space attribute interface.
CIRGenCUDARuntime * createNVCUDARuntime(CIRGenModule &cgm)
constexpr Variable var(Literal L)
Returns the variable of L.
@ Address
A pointer to a ValueDecl.
void info(bool Verbose, unsigned Level, const char *Fmt, Ts &&...Args)
Prints an indented note to stderr when Verbose is set.
Top level wrappers for InstallAPI frontend operations.
if(T->getSizeExpr()) TRY_TO(TraverseStmt(const_cast< Expr * >(T -> getSizeExpr())))
bool CudaFeatureEnabled(llvm::VersionTuple, CudaFeature)
U cast(CodeGen::Address addr)
__builtin_bitreverse32 uint32_t __builtin_riscv_aaddu_u32 __builtin_riscv_asubu_u32 __builtin_elementwise_add_sat __builtin_elementwise_sub_sat int32_t
clang::CharUnits getPointerAlign() const
clang::CharUnits getSizeAlign() const
cir::PointerType voidPtrTy
void* in address space 0