327 StringRef key, ModuleFlagProfileSummaryAttr summaryAttr,
329 llvm::LLVMContext &context = builder.getContext();
330 llvm::MDBuilder mdb(context);
332 auto getIntTuple = [&](StringRef key, uint64_t val) -> llvm::MDTuple * {
334 mdb.createString(key), mdb.createConstant(llvm::ConstantInt::get(
335 llvm::Type::getInt64Ty(context), val))};
336 return llvm::MDTuple::get(context, tupleNodes);
340 mdb.createString(
"ProfileFormat"),
342 stringifyProfileSummaryFormatKind(summaryAttr.getFormat()))};
345 llvm::MDTuple::get(context, fmtNode),
346 getIntTuple(
"TotalCount", summaryAttr.getTotalCount()),
347 getIntTuple(
"MaxCount", summaryAttr.getMaxCount()),
348 getIntTuple(
"MaxInternalCount", summaryAttr.getMaxInternalCount()),
349 getIntTuple(
"MaxFunctionCount", summaryAttr.getMaxFunctionCount()),
350 getIntTuple(
"NumCounts", summaryAttr.getNumCounts()),
351 getIntTuple(
"NumFunctions", summaryAttr.getNumFunctions()),
354 if (summaryAttr.getIsPartialProfile())
356 getIntTuple(
"IsPartialProfile", *summaryAttr.getIsPartialProfile()));
358 if (summaryAttr.getPartialProfileRatio()) {
360 mdb.createString(
"PartialProfileRatio"),
361 mdb.createConstant(llvm::ConstantFP::get(
362 llvm::Type::getDoubleTy(context),
363 summaryAttr.getPartialProfileRatio().getValue()))};
364 vals.push_back(llvm::MDTuple::get(context, tupleNodes));
368 llvm::Type *llvmInt64Type = llvm::Type::getInt64Ty(context);
369 for (ModuleFlagProfileSummaryDetailedAttr detailedEntry :
370 summaryAttr.getDetailedSummary()) {
373 llvm::ConstantInt::get(llvmInt64Type, detailedEntry.getCutOff())),
375 llvm::ConstantInt::get(llvmInt64Type, detailedEntry.getMinCount())),
376 mdb.createConstant(llvm::ConstantInt::get(
377 llvmInt64Type, detailedEntry.getNumCounts()))};
378 detailedEntries.push_back(llvm::MDTuple::get(context, tupleNodes));
381 mdb.createString(
"DetailedSummary"),
382 llvm::MDTuple::get(context, detailedEntries)};
383 vals.push_back(llvm::MDTuple::get(context, detailedSummary));
385 return llvm::MDNode::get(context, vals);
457 llvm::IRBuilder<>::FastMathFlagGuard fmfGuard(builder);
458 if (
auto fmf = dyn_cast<FastmathFlagsInterface>(opInst))
461#include "mlir/Dialect/LLVMIR/LLVMConversions.inc"
462#include "mlir/Dialect/LLVMIR/LLVMIntrinsicConversions.inc"
468 if (
auto callOp = dyn_cast<LLVM::CallOp>(opInst)) {
469 auto operands = moduleTranslation.
lookupValues(callOp.getCalleeOperands());
472 callOp.getOpBundleTags(), moduleTranslation);
474 llvm::CallInst *call;
475 if (
auto attr = callOp.getCalleeAttr()) {
476 if (llvm::Function *function =
478 call = builder.CreateCall(function, operandsRef, opBundles);
481 attr, callOp.getCalleeFunctionType(), opInst, moduleTranslation);
482 call = builder.CreateCall(calleeType, calleeGV, operandsRef, opBundles);
485 llvm::FunctionType *calleeType = llvm::cast<llvm::FunctionType>(
486 moduleTranslation.
convertType(callOp.getCalleeFunctionType()));
487 call = builder.CreateCall(calleeType, operandsRef.front(),
488 operandsRef.drop_front(), opBundles);
490 call->setCallingConv(convertCConvToLLVM(callOp.getCConv()));
491 call->setTailCallKind(convertTailCallKindToLLVM(callOp.getTailCallKind()));
492 if (callOp.getConvergentAttr())
493 call->addFnAttr(llvm::Attribute::Convergent);
494 if (callOp.getNoUnwindAttr())
495 call->addFnAttr(llvm::Attribute::NoUnwind);
496 if (callOp.getWillReturnAttr())
497 call->addFnAttr(llvm::Attribute::WillReturn);
498 if (callOp.getNoreturnAttr())
499 call->addFnAttr(llvm::Attribute::NoReturn);
500 if (callOp.getOptsizeAttr())
501 call->addFnAttr(llvm::Attribute::OptimizeForSize);
502 if (callOp.getMinsizeAttr())
503 call->addFnAttr(llvm::Attribute::MinSize);
504 if (callOp.getSaveRegParamsAttr())
505 call->addFnAttr(llvm::Attribute::get(moduleTranslation.
getLLVMContext(),
507 if (callOp.getBuiltinAttr())
508 call->addFnAttr(llvm::Attribute::Builtin);
509 if (callOp.getNobuiltinAttr())
510 call->addFnAttr(llvm::Attribute::NoBuiltin);
511 if (callOp.getReturnsTwiceAttr())
512 call->addFnAttr(llvm::Attribute::ReturnsTwice);
513 if (callOp.getColdAttr())
514 call->addFnAttr(llvm::Attribute::Cold);
515 if (callOp.getHotAttr())
516 call->addFnAttr(llvm::Attribute::Hot);
517 if (callOp.getNoduplicateAttr())
518 call->addFnAttr(llvm::Attribute::NoDuplicate);
519 if (callOp.getNoInlineAttr())
520 call->addFnAttr(llvm::Attribute::NoInline);
521 if (callOp.getAlwaysInlineAttr())
522 call->addFnAttr(llvm::Attribute::AlwaysInline);
523 if (callOp.getInlineHintAttr())
524 call->addFnAttr(llvm::Attribute::InlineHint);
525 if (callOp.getNoCallerSavedRegistersAttr())
526 call->addFnAttr(llvm::Attribute::get(moduleTranslation.
getLLVMContext(),
527 "no_caller_saved_registers"));
528 if (callOp.getNocallbackAttr())
529 call->addFnAttr(llvm::Attribute::NoCallback);
530 if (StringAttr modFormat = callOp.getModularFormatAttr())
531 call->addFnAttr(llvm::Attribute::get(moduleTranslation.
getLLVMContext(),
533 modFormat.getValue()));
534 if (StringAttr zcsr = callOp.getZeroCallUsedRegsAttr())
535 call->addFnAttr(llvm::Attribute::get(moduleTranslation.
getLLVMContext(),
536 "zero-call-used-regs",
538 if (StringAttr trapFunc = callOp.getTrapFuncNameAttr())
539 call->addFnAttr(llvm::Attribute::get(moduleTranslation.
getLLVMContext(),
541 trapFunc.getValue()));
543 if (
ArrayAttr noBuiltins = callOp.getNobuiltinsAttr()) {
544 if (noBuiltins.empty())
545 call->addFnAttr(llvm::Attribute::get(moduleTranslation.
getLLVMContext(),
553 callOp.getDefaultFuncAttrsAttr(), call,
556 if (llvm::Attribute attr =
559 call->addFnAttr(attr);
564 if (MemoryEffectsAttr memAttr = callOp.getMemoryEffectsAttr()) {
565 llvm::MemoryEffects memEffects =
566 llvm::MemoryEffects(llvm::MemoryEffects::Location::ArgMem,
567 convertModRefInfoToLLVM(memAttr.getArgMem())) |
569 llvm::MemoryEffects::Location::InaccessibleMem,
570 convertModRefInfoToLLVM(memAttr.getInaccessibleMem())) |
571 llvm::MemoryEffects(llvm::MemoryEffects::Location::Other,
572 convertModRefInfoToLLVM(memAttr.getOther())) |
573 llvm::MemoryEffects(llvm::MemoryEffects::Location::ErrnoMem,
574 convertModRefInfoToLLVM(memAttr.getErrnoMem())) |
576 llvm::MemoryEffects::Location::TargetMem0,
577 convertModRefInfoToLLVM(memAttr.getTargetMem0())) |
578 llvm::MemoryEffects(llvm::MemoryEffects::Location::TargetMem1,
579 convertModRefInfoToLLVM(memAttr.getTargetMem1()));
580 call->setMemoryEffects(memEffects);
591 else if (!call->getType()->isVoidTy())
593 moduleTranslation.
mapCall(callOp, call);
597 if (
auto inlineAsmOp = dyn_cast<LLVM::InlineAsmOp>(opInst)) {
601 llvm::append_range(operandTypes, inlineAsmOp.getOperands().getTypes());
604 if (inlineAsmOp.getNumResults() == 0) {
605 resultType = LLVM::LLVMVoidType::get(&moduleTranslation.
getContext());
607 assert(inlineAsmOp.getNumResults() == 1);
608 resultType = inlineAsmOp.getResultTypes()[0];
610 auto ft = LLVM::LLVMFunctionType::get(resultType, operandTypes);
611 llvm::InlineAsm *inlineAsmInst =
612 inlineAsmOp.getAsmDialect()
613 ? llvm::InlineAsm::get(
614 static_cast<llvm::FunctionType *
>(
616 inlineAsmOp.getAsmString(), inlineAsmOp.getConstraints(),
617 inlineAsmOp.getHasSideEffects(),
618 inlineAsmOp.getIsAlignStack(),
619 convertAsmDialectToLLVM(*inlineAsmOp.getAsmDialect()))
620 : llvm::InlineAsm::get(
static_cast<llvm::FunctionType *
>(
622 inlineAsmOp.getAsmString(),
623 inlineAsmOp.getConstraints(),
624 inlineAsmOp.getHasSideEffects(),
625 inlineAsmOp.getIsAlignStack());
626 llvm::CallInst *inst = builder.CreateCall(
628 moduleTranslation.
lookupValues(inlineAsmOp.getOperands()));
629 inst->setTailCallKind(convertTailCallKindToLLVM(
630 inlineAsmOp.getTailCallKindAttr().getTailCallKind()));
631 if (
auto maybeOperandAttrs = inlineAsmOp.getOperandAttrs()) {
632 llvm::AttributeList attrList;
633 for (
const auto &it : llvm::enumerate(*maybeOperandAttrs)) {
637 DictionaryAttr dAttr = cast<DictionaryAttr>(attr);
641 cast<TypeAttr>(dAttr.get(InlineAsmOp::getElementTypeAttrName()));
643 llvm::Type *ty = moduleTranslation.
convertType(tAttr.getValue());
644 b.addTypeAttr(llvm::Attribute::ElementType, ty);
648 attrList = attrList.addAttributesAtIndex(
651 inst->setAttributes(attrList);
659 if (
auto invOp = dyn_cast<LLVM::InvokeOp>(opInst)) {
660 auto operands = moduleTranslation.
lookupValues(invOp.getCalleeOperands());
663 invOp.getOpBundleTags(), moduleTranslation);
667 if (llvm::Function *function =
669 result = builder.CreateInvoke(
670 function, moduleTranslation.
lookupBlock(invOp.getSuccessor(0)),
671 moduleTranslation.
lookupBlock(invOp.getSuccessor(1)), operandsRef,
675 attr, invOp.getCalleeFunctionType(), opInst, moduleTranslation);
676 result = builder.CreateInvoke(
677 calleeType, calleeGV,
678 moduleTranslation.
lookupBlock(invOp.getSuccessor(0)),
679 moduleTranslation.
lookupBlock(invOp.getSuccessor(1)), operandsRef,
683 llvm::FunctionType *calleeType = llvm::cast<llvm::FunctionType>(
684 moduleTranslation.
convertType(invOp.getCalleeFunctionType()));
685 result = builder.CreateInvoke(
686 calleeType, operandsRef.front(),
687 moduleTranslation.
lookupBlock(invOp.getSuccessor(0)),
688 moduleTranslation.
lookupBlock(invOp.getSuccessor(1)),
689 operandsRef.drop_front(), opBundles);
691 result->setCallingConv(convertCConvToLLVM(invOp.getCConv()));
696 if (invOp->getNumResults() != 0) {
703 if (
auto lpOp = dyn_cast<LLVM::LandingpadOp>(opInst)) {
704 llvm::Type *ty = moduleTranslation.
convertType(lpOp.getType());
705 llvm::LandingPadInst *lpi =
706 builder.CreateLandingPad(ty, lpOp.getNumOperands());
707 lpi->setCleanup(lpOp.getCleanup());
710 for (llvm::Value *operand :
713 if (
auto *constOperand = dyn_cast<llvm::Constant>(operand))
714 lpi->addClause(constOperand);
716 moduleTranslation.
mapValue(lpOp.getResult(), lpi);
722 if (
auto brOp = dyn_cast<LLVM::BrOp>(opInst)) {
723 llvm::UncondBrInst *branch =
724 builder.CreateBr(moduleTranslation.
lookupBlock(brOp.getSuccessor()));
725 moduleTranslation.
mapBranch(&opInst, branch);
729 if (
auto condbrOp = dyn_cast<LLVM::CondBrOp>(opInst)) {
730 llvm::CondBrInst *branch = builder.CreateCondBr(
731 moduleTranslation.
lookupValue(condbrOp.getOperand(0)),
732 moduleTranslation.
lookupBlock(condbrOp.getSuccessor(0)),
733 moduleTranslation.
lookupBlock(condbrOp.getSuccessor(1)));
734 moduleTranslation.
mapBranch(&opInst, branch);
738 if (
auto switchOp = dyn_cast<LLVM::SwitchOp>(opInst)) {
739 llvm::SwitchInst *switchInst = builder.CreateSwitch(
740 moduleTranslation.
lookupValue(switchOp.getValue()),
741 moduleTranslation.
lookupBlock(switchOp.getDefaultDestination()),
742 switchOp.getCaseDestinations().size());
745 if (!switchOp.getCaseValues())
748 auto *ty = llvm::cast<llvm::IntegerType>(
749 moduleTranslation.
convertType(switchOp.getValue().getType()));
751 llvm::zip(llvm::cast<DenseIntElementsAttr>(*switchOp.getCaseValues()),
752 switchOp.getCaseDestinations()))
754 llvm::ConstantInt::get(ty, std::get<0>(i).getLimitedValue()),
757 moduleTranslation.
mapBranch(&opInst, switchInst);
760 if (
auto indBrOp = dyn_cast<LLVM::IndirectBrOp>(opInst)) {
761 llvm::IndirectBrInst *indBr = builder.CreateIndirectBr(
763 indBrOp->getNumSuccessors());
764 for (
auto *succ : indBrOp.getSuccessors())
765 indBr->addDestination(moduleTranslation.
lookupBlock(succ));
766 moduleTranslation.
mapBranch(&opInst, indBr);
773 if (
auto addressOfOp = dyn_cast<LLVM::AddressOfOp>(opInst)) {
774 LLVM::GlobalOp global =
775 addressOfOp.getGlobal(moduleTranslation.
symbolTable());
776 LLVM::LLVMFuncOp function =
777 addressOfOp.getFunction(moduleTranslation.
symbolTable());
778 LLVM::AliasOp alias = addressOfOp.getAlias(moduleTranslation.
symbolTable());
779 LLVM::IFuncOp ifunc = addressOfOp.getIFunc(moduleTranslation.
symbolTable());
782 assert((global || function || alias || ifunc) &&
783 "referencing an undefined global, function, alias, or ifunc");
785 llvm::Value *llvmValue =
nullptr;
795 moduleTranslation.
mapValue(addressOfOp.getResult(), llvmValue);
801 if (
auto dsoLocalEquivalentOp =
802 dyn_cast<LLVM::DSOLocalEquivalentOp>(opInst)) {
803 LLVM::LLVMFuncOp function =
804 dsoLocalEquivalentOp.getFunction(moduleTranslation.
symbolTable());
805 LLVM::AliasOp alias =
806 dsoLocalEquivalentOp.getAlias(moduleTranslation.
symbolTable());
809 assert((function || alias) &&
810 "referencing an undefined function, or alias");
812 llvm::Value *llvmValue =
nullptr;
819 dsoLocalEquivalentOp.getResult(),
820 llvm::DSOLocalEquivalent::get(cast<llvm::GlobalValue>(llvmValue)));
826 if (
auto blockAddressOp = dyn_cast<LLVM::BlockAddressOp>(opInst)) {
827 BlockAddressAttr blockAddressAttr = blockAddressOp.getBlockAddr();
828 llvm::BasicBlock *llvmBlock =
831 llvm::Value *llvmValue =
nullptr;
832 StringRef fnName = blockAddressAttr.getFunction().getValue();
834 llvm::Function *llvmFn = moduleTranslation.
lookupFunction(fnName);
835 llvmValue = llvm::BlockAddress::get(llvmFn, llvmBlock);
843 llvmValue =
new llvm::GlobalVariable(
846 true, llvm::GlobalValue::LinkageTypes::ExternalLinkage,
848 Twine(
"__mlir_block_address_")
849 .concat(Twine(fnName))
850 .concat(Twine((uint64_t)blockAddressOp.getOperation())));
854 moduleTranslation.
mapValue(blockAddressOp.getResult(), llvmValue);
860 if (
auto blockTagOp = dyn_cast<LLVM::BlockTagOp>(opInst)) {
861 auto funcOp = blockTagOp->getParentOfType<LLVMFuncOp>();
862 BlockAddressAttr blockAddressAttr = BlockAddressAttr::get(
866 blockTagOp.getTag());
868 builder.GetInsertBlock());