#include "MCTargetDesc/NVPTXMCAsmInfo.h"
#include "NVPTX.h"
#include "NVPTXInstrInfo.h"
+#include "NVPTXMachineFunctionInfo.h"
#include "NVPTXMCExpr.h"
#include "NVPTXRegisterInfo.h"
#include "NVPTXTargetMachine.h"
#include "llvm/CodeGen/MachineFrameInfo.h"
#include "llvm/CodeGen/MachineModuleInfo.h"
#include "llvm/CodeGen/MachineRegisterInfo.h"
-#include "llvm/DebugInfo.h"
+#include "llvm/IR/DebugInfo.h"
#include "llvm/IR/DerivedTypes.h"
#include "llvm/IR/Function.h"
#include "llvm/IR/GlobalVariable.h"
return MCSymbolRefExpr::Create(AP.GetBlockAddressSymbol(BA), Ctx);
const ConstantExpr *CE = dyn_cast<ConstantExpr>(CV);
- if (CE == 0)
+ if (!CE)
llvm_unreachable("Unknown constant value to lower!");
switch (CE->getOpcode()) {
raw_string_ostream OS(S);
OS << "Unsupported expression in static initializer: ";
CE->printAsOperand(OS, /*PrintType=*/ false,
- !AP.MF ? 0 : AP.MF->getFunction()->getParent());
+ !AP.MF ? nullptr : AP.MF->getFunction()->getParent());
report_fatal_error(OS.str());
}
+ case Instruction::AddrSpaceCast: {
+ // Strip any addrspace(1)->addrspace(0) addrspace casts. These will be
+ // handled by the generic() logic in the MCExpr printer
+ PointerType *DstTy = cast<PointerType>(CE->getType());
+ PointerType *SrcTy = cast<PointerType>(CE->getOperand(0)->getType());
+ if (SrcTy->getAddressSpace() == 1 && DstTy->getAddressSpace() == 0) {
+ return LowerConstant(cast<const Constant>(CE->getOperand(0)), AP);
+ }
+ std::string S;
+ raw_string_ostream OS(S);
+ OS << "Unsupported expression in static initializer: ";
+ CE->printAsOperand(OS, /*PrintType=*/ false,
+ !AP.MF ? nullptr : AP.MF->getFunction()->getParent());
+ report_fatal_error(OS.str());
+ }
case Instruction::GetElementPtr: {
const DataLayout &TD = *AP.TM.getDataLayout();
// Generate a symbolic expression for the byte address
MCInst Inst;
lowerToMCInst(MI, Inst);
- OutStreamer.EmitInstruction(Inst);
+ EmitToStreamer(OutStreamer, Inst);
+}
+
+// Handle symbol backtracking for targets that do not support image handles
+bool NVPTXAsmPrinter::lowerImageHandleOperand(const MachineInstr *MI,
+ unsigned OpNo, MCOperand &MCOp) {
+ const MachineOperand &MO = MI->getOperand(OpNo);
+
+ switch (MI->getOpcode()) {
+ default: return false;
+ case NVPTX::TEX_1D_F32_I32:
+ case NVPTX::TEX_1D_F32_F32:
+ case NVPTX::TEX_1D_F32_F32_LEVEL:
+ case NVPTX::TEX_1D_F32_F32_GRAD:
+ case NVPTX::TEX_1D_I32_I32:
+ case NVPTX::TEX_1D_I32_F32:
+ case NVPTX::TEX_1D_I32_F32_LEVEL:
+ case NVPTX::TEX_1D_I32_F32_GRAD:
+ case NVPTX::TEX_1D_ARRAY_F32_I32:
+ case NVPTX::TEX_1D_ARRAY_F32_F32:
+ case NVPTX::TEX_1D_ARRAY_F32_F32_LEVEL:
+ case NVPTX::TEX_1D_ARRAY_F32_F32_GRAD:
+ case NVPTX::TEX_1D_ARRAY_I32_I32:
+ case NVPTX::TEX_1D_ARRAY_I32_F32:
+ case NVPTX::TEX_1D_ARRAY_I32_F32_LEVEL:
+ case NVPTX::TEX_1D_ARRAY_I32_F32_GRAD:
+ case NVPTX::TEX_2D_F32_I32:
+ case NVPTX::TEX_2D_F32_F32:
+ case NVPTX::TEX_2D_F32_F32_LEVEL:
+ case NVPTX::TEX_2D_F32_F32_GRAD:
+ case NVPTX::TEX_2D_I32_I32:
+ case NVPTX::TEX_2D_I32_F32:
+ case NVPTX::TEX_2D_I32_F32_LEVEL:
+ case NVPTX::TEX_2D_I32_F32_GRAD:
+ case NVPTX::TEX_2D_ARRAY_F32_I32:
+ case NVPTX::TEX_2D_ARRAY_F32_F32:
+ case NVPTX::TEX_2D_ARRAY_F32_F32_LEVEL:
+ case NVPTX::TEX_2D_ARRAY_F32_F32_GRAD:
+ case NVPTX::TEX_2D_ARRAY_I32_I32:
+ case NVPTX::TEX_2D_ARRAY_I32_F32:
+ case NVPTX::TEX_2D_ARRAY_I32_F32_LEVEL:
+ case NVPTX::TEX_2D_ARRAY_I32_F32_GRAD:
+ case NVPTX::TEX_3D_F32_I32:
+ case NVPTX::TEX_3D_F32_F32:
+ case NVPTX::TEX_3D_F32_F32_LEVEL:
+ case NVPTX::TEX_3D_F32_F32_GRAD:
+ case NVPTX::TEX_3D_I32_I32:
+ case NVPTX::TEX_3D_I32_F32:
+ case NVPTX::TEX_3D_I32_F32_LEVEL:
+ case NVPTX::TEX_3D_I32_F32_GRAD:
+ {
+ // This is a texture fetch, so operand 4 is a texref and operand 5 is
+ // a samplerref
+ if (OpNo == 4) {
+ lowerImageHandleSymbol(MO.getImm(), MCOp);
+ return true;
+ }
+ if (OpNo == 5) {
+ lowerImageHandleSymbol(MO.getImm(), MCOp);
+ return true;
+ }
+
+ return false;
+ }
+ case NVPTX::SULD_1D_I8_TRAP:
+ case NVPTX::SULD_1D_I16_TRAP:
+ case NVPTX::SULD_1D_I32_TRAP:
+ case NVPTX::SULD_1D_ARRAY_I8_TRAP:
+ case NVPTX::SULD_1D_ARRAY_I16_TRAP:
+ case NVPTX::SULD_1D_ARRAY_I32_TRAP:
+ case NVPTX::SULD_2D_I8_TRAP:
+ case NVPTX::SULD_2D_I16_TRAP:
+ case NVPTX::SULD_2D_I32_TRAP:
+ case NVPTX::SULD_2D_ARRAY_I8_TRAP:
+ case NVPTX::SULD_2D_ARRAY_I16_TRAP:
+ case NVPTX::SULD_2D_ARRAY_I32_TRAP:
+ case NVPTX::SULD_3D_I8_TRAP:
+ case NVPTX::SULD_3D_I16_TRAP:
+ case NVPTX::SULD_3D_I32_TRAP: {
+ // This is a V1 surface load, so operand 1 is a surfref
+ if (OpNo == 1) {
+ lowerImageHandleSymbol(MO.getImm(), MCOp);
+ return true;
+ }
+
+ return false;
+ }
+ case NVPTX::SULD_1D_V2I8_TRAP:
+ case NVPTX::SULD_1D_V2I16_TRAP:
+ case NVPTX::SULD_1D_V2I32_TRAP:
+ case NVPTX::SULD_1D_ARRAY_V2I8_TRAP:
+ case NVPTX::SULD_1D_ARRAY_V2I16_TRAP:
+ case NVPTX::SULD_1D_ARRAY_V2I32_TRAP:
+ case NVPTX::SULD_2D_V2I8_TRAP:
+ case NVPTX::SULD_2D_V2I16_TRAP:
+ case NVPTX::SULD_2D_V2I32_TRAP:
+ case NVPTX::SULD_2D_ARRAY_V2I8_TRAP:
+ case NVPTX::SULD_2D_ARRAY_V2I16_TRAP:
+ case NVPTX::SULD_2D_ARRAY_V2I32_TRAP:
+ case NVPTX::SULD_3D_V2I8_TRAP:
+ case NVPTX::SULD_3D_V2I16_TRAP:
+ case NVPTX::SULD_3D_V2I32_TRAP: {
+ // This is a V2 surface load, so operand 2 is a surfref
+ if (OpNo == 2) {
+ lowerImageHandleSymbol(MO.getImm(), MCOp);
+ return true;
+ }
+
+ return false;
+ }
+ case NVPTX::SULD_1D_V4I8_TRAP:
+ case NVPTX::SULD_1D_V4I16_TRAP:
+ case NVPTX::SULD_1D_V4I32_TRAP:
+ case NVPTX::SULD_1D_ARRAY_V4I8_TRAP:
+ case NVPTX::SULD_1D_ARRAY_V4I16_TRAP:
+ case NVPTX::SULD_1D_ARRAY_V4I32_TRAP:
+ case NVPTX::SULD_2D_V4I8_TRAP:
+ case NVPTX::SULD_2D_V4I16_TRAP:
+ case NVPTX::SULD_2D_V4I32_TRAP:
+ case NVPTX::SULD_2D_ARRAY_V4I8_TRAP:
+ case NVPTX::SULD_2D_ARRAY_V4I16_TRAP:
+ case NVPTX::SULD_2D_ARRAY_V4I32_TRAP:
+ case NVPTX::SULD_3D_V4I8_TRAP:
+ case NVPTX::SULD_3D_V4I16_TRAP:
+ case NVPTX::SULD_3D_V4I32_TRAP: {
+ // This is a V4 surface load, so operand 4 is a surfref
+ if (OpNo == 4) {
+ lowerImageHandleSymbol(MO.getImm(), MCOp);
+ return true;
+ }
+
+ return false;
+ }
+ case NVPTX::SUST_B_1D_B8_TRAP:
+ case NVPTX::SUST_B_1D_B16_TRAP:
+ case NVPTX::SUST_B_1D_B32_TRAP:
+ case NVPTX::SUST_B_1D_V2B8_TRAP:
+ case NVPTX::SUST_B_1D_V2B16_TRAP:
+ case NVPTX::SUST_B_1D_V2B32_TRAP:
+ case NVPTX::SUST_B_1D_V4B8_TRAP:
+ case NVPTX::SUST_B_1D_V4B16_TRAP:
+ case NVPTX::SUST_B_1D_V4B32_TRAP:
+ case NVPTX::SUST_B_1D_ARRAY_B8_TRAP:
+ case NVPTX::SUST_B_1D_ARRAY_B16_TRAP:
+ case NVPTX::SUST_B_1D_ARRAY_B32_TRAP:
+ case NVPTX::SUST_B_1D_ARRAY_V2B8_TRAP:
+ case NVPTX::SUST_B_1D_ARRAY_V2B16_TRAP:
+ case NVPTX::SUST_B_1D_ARRAY_V2B32_TRAP:
+ case NVPTX::SUST_B_1D_ARRAY_V4B8_TRAP:
+ case NVPTX::SUST_B_1D_ARRAY_V4B16_TRAP:
+ case NVPTX::SUST_B_1D_ARRAY_V4B32_TRAP:
+ case NVPTX::SUST_B_2D_B8_TRAP:
+ case NVPTX::SUST_B_2D_B16_TRAP:
+ case NVPTX::SUST_B_2D_B32_TRAP:
+ case NVPTX::SUST_B_2D_V2B8_TRAP:
+ case NVPTX::SUST_B_2D_V2B16_TRAP:
+ case NVPTX::SUST_B_2D_V2B32_TRAP:
+ case NVPTX::SUST_B_2D_V4B8_TRAP:
+ case NVPTX::SUST_B_2D_V4B16_TRAP:
+ case NVPTX::SUST_B_2D_V4B32_TRAP:
+ case NVPTX::SUST_B_2D_ARRAY_B8_TRAP:
+ case NVPTX::SUST_B_2D_ARRAY_B16_TRAP:
+ case NVPTX::SUST_B_2D_ARRAY_B32_TRAP:
+ case NVPTX::SUST_B_2D_ARRAY_V2B8_TRAP:
+ case NVPTX::SUST_B_2D_ARRAY_V2B16_TRAP:
+ case NVPTX::SUST_B_2D_ARRAY_V2B32_TRAP:
+ case NVPTX::SUST_B_2D_ARRAY_V4B8_TRAP:
+ case NVPTX::SUST_B_2D_ARRAY_V4B16_TRAP:
+ case NVPTX::SUST_B_2D_ARRAY_V4B32_TRAP:
+ case NVPTX::SUST_B_3D_B8_TRAP:
+ case NVPTX::SUST_B_3D_B16_TRAP:
+ case NVPTX::SUST_B_3D_B32_TRAP:
+ case NVPTX::SUST_B_3D_V2B8_TRAP:
+ case NVPTX::SUST_B_3D_V2B16_TRAP:
+ case NVPTX::SUST_B_3D_V2B32_TRAP:
+ case NVPTX::SUST_B_3D_V4B8_TRAP:
+ case NVPTX::SUST_B_3D_V4B16_TRAP:
+ case NVPTX::SUST_B_3D_V4B32_TRAP:
+ case NVPTX::SUST_P_1D_B8_TRAP:
+ case NVPTX::SUST_P_1D_B16_TRAP:
+ case NVPTX::SUST_P_1D_B32_TRAP:
+ case NVPTX::SUST_P_1D_V2B8_TRAP:
+ case NVPTX::SUST_P_1D_V2B16_TRAP:
+ case NVPTX::SUST_P_1D_V2B32_TRAP:
+ case NVPTX::SUST_P_1D_V4B8_TRAP:
+ case NVPTX::SUST_P_1D_V4B16_TRAP:
+ case NVPTX::SUST_P_1D_V4B32_TRAP:
+ case NVPTX::SUST_P_1D_ARRAY_B8_TRAP:
+ case NVPTX::SUST_P_1D_ARRAY_B16_TRAP:
+ case NVPTX::SUST_P_1D_ARRAY_B32_TRAP:
+ case NVPTX::SUST_P_1D_ARRAY_V2B8_TRAP:
+ case NVPTX::SUST_P_1D_ARRAY_V2B16_TRAP:
+ case NVPTX::SUST_P_1D_ARRAY_V2B32_TRAP:
+ case NVPTX::SUST_P_1D_ARRAY_V4B8_TRAP:
+ case NVPTX::SUST_P_1D_ARRAY_V4B16_TRAP:
+ case NVPTX::SUST_P_1D_ARRAY_V4B32_TRAP:
+ case NVPTX::SUST_P_2D_B8_TRAP:
+ case NVPTX::SUST_P_2D_B16_TRAP:
+ case NVPTX::SUST_P_2D_B32_TRAP:
+ case NVPTX::SUST_P_2D_V2B8_TRAP:
+ case NVPTX::SUST_P_2D_V2B16_TRAP:
+ case NVPTX::SUST_P_2D_V2B32_TRAP:
+ case NVPTX::SUST_P_2D_V4B8_TRAP:
+ case NVPTX::SUST_P_2D_V4B16_TRAP:
+ case NVPTX::SUST_P_2D_V4B32_TRAP:
+ case NVPTX::SUST_P_2D_ARRAY_B8_TRAP:
+ case NVPTX::SUST_P_2D_ARRAY_B16_TRAP:
+ case NVPTX::SUST_P_2D_ARRAY_B32_TRAP:
+ case NVPTX::SUST_P_2D_ARRAY_V2B8_TRAP:
+ case NVPTX::SUST_P_2D_ARRAY_V2B16_TRAP:
+ case NVPTX::SUST_P_2D_ARRAY_V2B32_TRAP:
+ case NVPTX::SUST_P_2D_ARRAY_V4B8_TRAP:
+ case NVPTX::SUST_P_2D_ARRAY_V4B16_TRAP:
+ case NVPTX::SUST_P_2D_ARRAY_V4B32_TRAP:
+ case NVPTX::SUST_P_3D_B8_TRAP:
+ case NVPTX::SUST_P_3D_B16_TRAP:
+ case NVPTX::SUST_P_3D_B32_TRAP:
+ case NVPTX::SUST_P_3D_V2B8_TRAP:
+ case NVPTX::SUST_P_3D_V2B16_TRAP:
+ case NVPTX::SUST_P_3D_V2B32_TRAP:
+ case NVPTX::SUST_P_3D_V4B8_TRAP:
+ case NVPTX::SUST_P_3D_V4B16_TRAP:
+ case NVPTX::SUST_P_3D_V4B32_TRAP: {
+ // This is a surface store, so operand 0 is a surfref
+ if (OpNo == 0) {
+ lowerImageHandleSymbol(MO.getImm(), MCOp);
+ return true;
+ }
+
+ return false;
+ }
+ case NVPTX::TXQ_CHANNEL_ORDER:
+ case NVPTX::TXQ_CHANNEL_DATA_TYPE:
+ case NVPTX::TXQ_WIDTH:
+ case NVPTX::TXQ_HEIGHT:
+ case NVPTX::TXQ_DEPTH:
+ case NVPTX::TXQ_ARRAY_SIZE:
+ case NVPTX::TXQ_NUM_SAMPLES:
+ case NVPTX::TXQ_NUM_MIPMAP_LEVELS:
+ case NVPTX::SUQ_CHANNEL_ORDER:
+ case NVPTX::SUQ_CHANNEL_DATA_TYPE:
+ case NVPTX::SUQ_WIDTH:
+ case NVPTX::SUQ_HEIGHT:
+ case NVPTX::SUQ_DEPTH:
+ case NVPTX::SUQ_ARRAY_SIZE: {
+ // This is a query, so operand 1 is a surfref/texref
+ if (OpNo == 1) {
+ lowerImageHandleSymbol(MO.getImm(), MCOp);
+ return true;
+ }
+
+ return false;
+ }
+ }
+}
+
+void NVPTXAsmPrinter::lowerImageHandleSymbol(unsigned Index, MCOperand &MCOp) {
+ // Ewwww
+ TargetMachine &TM = const_cast<TargetMachine&>(MF->getTarget());
+ NVPTXTargetMachine &nvTM = static_cast<NVPTXTargetMachine&>(TM);
+ const NVPTXMachineFunctionInfo *MFI = MF->getInfo<NVPTXMachineFunctionInfo>();
+ const char *Sym = MFI->getImageHandleSymbol(Index);
+ std::string *SymNamePtr =
+ nvTM.getManagedStrPool()->getManagedString(Sym);
+ MCOp = GetSymbolRef(OutContext.GetOrCreateSymbol(
+ StringRef(SymNamePtr->c_str())));
}
void NVPTXAsmPrinter::lowerToMCInst(const MachineInstr *MI, MCInst &OutMI) {
OutMI.setOpcode(MI->getOpcode());
+ const NVPTXSubtarget &ST = TM.getSubtarget<NVPTXSubtarget>();
// Special: Do not mangle symbol operand of CALL_PROTOTYPE
if (MI->getOpcode() == NVPTX::CALL_PROTOTYPE) {
const MachineOperand &MO = MI->getOperand(0);
- OutMI.addOperand(GetSymbolRef(MO,
+ OutMI.addOperand(GetSymbolRef(
OutContext.GetOrCreateSymbol(Twine(MO.getSymbolName()))));
return;
}
const MachineOperand &MO = MI->getOperand(i);
MCOperand MCOp;
+ if (!ST.hasImageHandles()) {
+ if (lowerImageHandleOperand(MI, i, MCOp)) {
+ OutMI.addOperand(MCOp);
+ continue;
+ }
+ }
+
if (lowerOperand(MO, MCOp))
OutMI.addOperand(MCOp);
}
MO.getMBB()->getSymbol(), OutContext));
break;
case MachineOperand::MO_ExternalSymbol:
- MCOp = GetSymbolRef(MO, GetExternalSymbolSymbol(MO.getSymbolName()));
+ MCOp = GetSymbolRef(GetExternalSymbolSymbol(MO.getSymbolName()));
break;
case MachineOperand::MO_GlobalAddress:
- MCOp = GetSymbolRef(MO, getSymbol(MO.getGlobal()));
+ MCOp = GetSymbolRef(getSymbol(MO.getGlobal()));
break;
case MachineOperand::MO_FPImmediate: {
const ConstantFP *Cnt = MO.getFPImm();
}
}
-MCOperand NVPTXAsmPrinter::GetSymbolRef(const MachineOperand &MO,
- const MCSymbol *Symbol) {
+MCOperand NVPTXAsmPrinter::GetSymbolRef(const MCSymbol *Symbol) {
const MCExpr *Expr;
Expr = MCSymbolRefExpr::Create(Symbol, MCSymbolRefExpr::VK_None,
OutContext);
<< " func_retval0";
} else {
if ((Ty->getTypeID() == Type::StructTyID) || isa<VectorType>(Ty)) {
- SmallVector<EVT, 16> vtparts;
- ComputeValueVTs(*TLI, Ty, vtparts);
- unsigned totalsz = 0;
- for (unsigned i = 0, e = vtparts.size(); i != e; ++i) {
- unsigned elems = 1;
- EVT elemtype = vtparts[i];
- if (vtparts[i].isVector()) {
- elems = vtparts[i].getVectorNumElements();
- elemtype = vtparts[i].getVectorElementType();
- }
- for (unsigned j = 0, je = elems; j != je; ++j) {
- unsigned sz = elemtype.getSizeInBits();
- if (elemtype.isInteger() && (sz < 8))
- sz = 8;
- totalsz += sz / 8;
- }
- }
+ unsigned totalsz = TD->getTypeAllocSize(Ty);
unsigned retAlignment = 0;
if (!llvm::getAlign(*F, 0, retAlignment))
retAlignment = TD->getABITypeAlignment(Ty);
return true;
}
- for (Value::const_use_iterator ui = C->use_begin(), ue = C->use_end();
- ui != ue; ++ui) {
- const Constant *C = dyn_cast<Constant>(*ui);
- if (usedInGlobalVarDef(C))
- return true;
- }
+ for (const User *U : C->users())
+ if (const Constant *C = dyn_cast<Constant>(U))
+ if (usedInGlobalVarDef(C))
+ return true;
+
return false;
}
(md->getName().str() == "llvm.dbg.sp")))
return true;
- for (User::const_use_iterator ui = U->use_begin(), ue = U->use_end();
- ui != ue; ++ui) {
- if (usedInOneFunc(*ui, oneFunc) == false)
+ for (const User *UU : U->users())
+ if (usedInOneFunc(UU, oneFunc) == false)
return false;
- }
+
return true;
}
if (Pty->getAddressSpace() != llvm::ADDRESS_SPACE_SHARED)
return false;
- const Function *oneFunc = 0;
+ const Function *oneFunc = nullptr;
bool flag = usedInOneFunc(gv, oneFunc);
if (flag == false)
static bool useFuncSeen(const Constant *C,
llvm::DenseMap<const Function *, bool> &seenMap) {
- for (Value::const_use_iterator ui = C->use_begin(), ue = C->use_end();
- ui != ue; ++ui) {
- if (const Constant *cu = dyn_cast<Constant>(*ui)) {
+ for (const User *U : C->users()) {
+ if (const Constant *cu = dyn_cast<Constant>(U)) {
if (useFuncSeen(cu, seenMap))
return true;
- } else if (const Instruction *I = dyn_cast<Instruction>(*ui)) {
+ } else if (const Instruction *I = dyn_cast<Instruction>(U)) {
const BasicBlock *bb = I->getParent();
if (!bb)
continue;
emitDeclaration(F, O);
continue;
}
- for (Value::const_use_iterator iter = F->use_begin(),
- iterEnd = F->use_end();
- iter != iterEnd; ++iter) {
- if (const Constant *C = dyn_cast<Constant>(*iter)) {
+ for (const User *U : F->users()) {
+ if (const Constant *C = dyn_cast<Constant>(U)) {
if (usedInGlobalVarDef(C)) {
// The use is in the initialization of a global variable
// that is a function pointer, so print a declaration
}
}
- if (!isa<Instruction>(*iter))
+ if (!isa<Instruction>(U))
continue;
- const Instruction *instr = cast<Instruction>(*iter);
+ const Instruction *instr = cast<Instruction>(U);
const BasicBlock *bb = instr->getParent();
if (!bb)
continue;
DbgFinder.processModule(M);
unsigned i = 1;
- for (DebugInfoFinder::iterator I = DbgFinder.compile_unit_begin(),
- E = DbgFinder.compile_unit_end();
- I != E; ++I) {
- DICompileUnit DIUnit(*I);
+ for (DICompileUnit DIUnit : DbgFinder.compile_units()) {
StringRef Filename(DIUnit.getFilename());
StringRef Dirname(DIUnit.getDirectory());
SmallString<128> FullPathName = Dirname;
++i;
}
- for (DebugInfoFinder::iterator I = DbgFinder.subprogram_begin(),
- E = DbgFinder.subprogram_end();
- I != E; ++I) {
- DISubprogram SP(*I);
+ for (DISubprogram SP : DbgFinder.subprograms()) {
StringRef Filename(SP.getFilename());
StringRef Dirname(SP.getDirectory());
SmallString<128> FullPathName = Dirname;
for (i = 0; i < n; i++)
global_list.insert(global_list.end(), gv_array[i]);
+ clearAnnotationCache(&M);
+
delete[] gv_array;
return ret;
// external global variable with init -> .visible
// external without init -> .extern
// appending -> not allowed, assert.
+// for any linkage other than
+// internal, private, linker_private,
+// linker_private_weak, linker_private_weak_def_auto,
+// we emit -> .weak.
void NVPTXAsmPrinter::emitLinkageDirective(const GlobalValue *V,
raw_ostream &O) {
msg.append(V->getName().str());
msg.append("has unsupported appending linkage type");
llvm_unreachable(msg.c_str());
+ } else if (!V->hasInternalLinkage() &&
+ !V->hasPrivateLinkage()) {
+ O << ".weak ";
}
}
}
// Skip meta data
if (GVar->hasSection()) {
- if (GVar->getSection() == "llvm.metadata")
+ if (GVar->getSection() == StringRef("llvm.metadata"))
return;
}
+ // Skip LLVM intrinsic global variables
+ if (GVar->getName().startswith("llvm.") ||
+ GVar->getName().startswith("nvvm."))
+ return;
+
const DataLayout *TD = TM.getDataLayout();
// GlobalVariables are always constant pointers themselves.
O << ".visible ";
else
O << ".extern ";
+ } else if (GVar->hasLinkOnceLinkage() || GVar->hasWeakLinkage() ||
+ GVar->hasAvailableExternallyLinkage() ||
+ GVar->hasCommonLinkage()) {
+ O << ".weak ";
}
if (llvm::isTexture(*GVar)) {
if (llvm::isSampler(*GVar)) {
O << ".global .samplerref " << llvm::getSamplerName(*GVar);
- const Constant *Initializer = NULL;
+ const Constant *Initializer = nullptr;
if (GVar->hasInitializer())
Initializer = GVar->getInitializer();
- const ConstantInt *CI = NULL;
+ const ConstantInt *CI = nullptr;
if (Initializer)
CI = dyn_cast<ConstantInt>(Initializer);
if (CI) {
O << "linear";
break;
case 2:
- assert(0 && "Anisotropic filtering is not supported");
+ llvm_unreachable("Anisotropic filtering is not supported");
default:
O << "nearest";
break;
return;
}
- const Function *demotedFunc = 0;
+ const Function *demotedFunc = nullptr;
if (!processDemoted && canDemoteGlobalVar(GVar, demotedFunc)) {
O << "// " << GVar->getName().str() << " has been demoted\n";
if (localDecls.find(demotedFunc) != localDecls.end())
O << ".";
emitPTXAddressSpace(PTy->getAddressSpace(), O);
+
+ if (isManaged(*GVar)) {
+ O << " .attribute(.managed)";
+ }
+
if (GVar->getAlignment() == 0)
O << " .align " << (int) TD->getPrefTypeAlignment(ETy);
else
// Ptx allows variable initilization only for constant and global state
// spaces.
- if (((PTy->getAddressSpace() == llvm::ADDRESS_SPACE_GLOBAL) ||
- (PTy->getAddressSpace() == llvm::ADDRESS_SPACE_CONST)) &&
- GVar->hasInitializer()) {
- const Constant *Initializer = GVar->getInitializer();
- if (!Initializer->isNullValue()) {
- O << " = ";
- printScalarConstant(Initializer, O);
+ if (GVar->hasInitializer()) {
+ if ((PTy->getAddressSpace() == llvm::ADDRESS_SPACE_GLOBAL) ||
+ (PTy->getAddressSpace() == llvm::ADDRESS_SPACE_CONST)) {
+ const Constant *Initializer = GVar->getInitializer();
+ // 'undef' is treated as there is no value spefied.
+ if (!Initializer->isNullValue() && !isa<UndefValue>(Initializer)) {
+ O << " = ";
+ printScalarConstant(Initializer, O);
+ }
+ } else {
+ // The frontend adds zero-initializer to variables that don't have an
+ // initial value, so skip warning for this case.
+ if (!GVar->getInitializer()->isNullValue()) {
+ std::string warnMsg = "initial value of '" + GVar->getName().str() +
+ "' is not allowed in addrspace(" +
+ llvm::utostr_32(PTy->getAddressSpace()) + ")";
+ report_fatal_error(warnMsg.c_str());
+ }
}
}
} else {
}
break;
default:
- assert(0 && "type not supported yet");
+ llvm_unreachable("type not supported yet");
}
}
return "u32";
}
llvm_unreachable("unexpected type");
- return NULL;
+ return nullptr;
}
void NVPTXAsmPrinter::emitPTXGlobalVariable(const GlobalVariable *GVar,
O << "]";
break;
default:
- assert(0 && "type not supported yet");
+ llvm_unreachable("type not supported yet");
}
return;
}
first = false;
// Handle image/sampler parameters
- if (llvm::isSampler(*I) || llvm::isImage(*I)) {
- if (llvm::isImage(*I)) {
- std::string sname = I->getName();
- if (llvm::isImageWriteOnly(*I))
- O << "\t.param .surfref " << *getSymbol(F) << "_param_"
- << paramIndex;
- else // Default image is read_only
- O << "\t.param .texref " << *getSymbol(F) << "_param_"
- << paramIndex;
- } else // Should be llvm::isSampler(*I)
- O << "\t.param .samplerref " << *getSymbol(F) << "_param_"
- << paramIndex;
- continue;
+ if (isKernelFunction(*F)) {
+ if (isSampler(*I) || isImage(*I)) {
+ if (isImage(*I)) {
+ std::string sname = I->getName();
+ if (isImageWriteOnly(*I) || isImageReadWrite(*I)) {
+ if (nvptxSubtarget.hasImageHandles())
+ O << "\t.param .u64 .ptr .surfref ";
+ else
+ O << "\t.param .surfref ";
+ O << *CurrentFnSym << "_param_" << paramIndex;
+ }
+ else { // Default image is read_only
+ if (nvptxSubtarget.hasImageHandles())
+ O << "\t.param .u64 .ptr .texref ";
+ else
+ O << "\t.param .texref ";
+ O << *CurrentFnSym << "_param_" << paramIndex;
+ }
+ } else {
+ if (nvptxSubtarget.hasImageHandles())
+ O << "\t.param .u64 .ptr .samplerref ";
+ else
+ O << "\t.param .samplerref ";
+ O << *CurrentFnSym << "_param_" << paramIndex;
+ }
+ continue;
+ }
}
if (PAL.hasAttribute(paramIndex + 1, Attribute::ByVal) == false) {
return;
}
if (const GlobalValue *GVar = dyn_cast<GlobalValue>(CPV)) {
- O << *getSymbol(GVar);
+ PointerType *PTy = dyn_cast<PointerType>(GVar->getType());
+ bool IsNonGenericPointer = false;
+ if (PTy && PTy->getAddressSpace() != 0) {
+ IsNonGenericPointer = true;
+ }
+ if (EmitGeneric && !isa<Function>(CPV) && !IsNonGenericPointer) {
+ O << "generic(";
+ O << *getSymbol(GVar);
+ O << ")";
+ } else {
+ O << *getSymbol(GVar);
+ }
return;
}
if (const ConstantExpr *Cexpr = dyn_cast<ConstantExpr>(CPV)) {
const Value *v = Cexpr->stripPointerCasts();
+ PointerType *PTy = dyn_cast<PointerType>(Cexpr->getType());
+ bool IsNonGenericPointer = false;
+ if (PTy && PTy->getAddressSpace() != 0) {
+ IsNonGenericPointer = true;
+ }
if (const GlobalValue *GVar = dyn_cast<GlobalValue>(v)) {
- O << *getSymbol(GVar);
+ if (EmitGeneric && !isa<Function>(v) && !IsNonGenericPointer) {
+ O << "generic(";
+ O << *getSymbol(GVar);
+ O << ")";
+ } else {
+ O << *getSymbol(GVar);
+ }
return;
} else {
O << *LowerConstant(CPV, *this);
}
LineReader *NVPTXAsmPrinter::getReader(std::string filename) {
- if (reader == NULL) {
+ if (!reader) {
reader = new LineReader(filename);
}