LLVM  4.0.0
AsmPrinterInlineAsm.cpp
Go to the documentation of this file.
1 //===-- AsmPrinterInlineAsm.cpp - AsmPrinter Inline Asm Handling ----------===//
2 //
3 // The LLVM Compiler Infrastructure
4 //
5 // This file is distributed under the University of Illinois Open Source
6 // License. See LICENSE.TXT for details.
7 //
8 //===----------------------------------------------------------------------===//
9 //
10 // This file implements the inline assembler pieces of the AsmPrinter class.
11 //
12 //===----------------------------------------------------------------------===//
13 
15 #include "llvm/ADT/SmallString.h"
16 #include "llvm/ADT/Twine.h"
20 #include "llvm/IR/Constants.h"
21 #include "llvm/IR/DataLayout.h"
22 #include "llvm/IR/InlineAsm.h"
23 #include "llvm/IR/LLVMContext.h"
24 #include "llvm/IR/Module.h"
25 #include "llvm/MC/MCAsmInfo.h"
27 #include "llvm/MC/MCStreamer.h"
29 #include "llvm/MC/MCSymbol.h"
32 #include "llvm/Support/SourceMgr.h"
39 using namespace llvm;
40 
41 #define DEBUG_TYPE "asm-printer"
42 
43 namespace {
44  struct SrcMgrDiagInfo {
45  const MDNode *LocInfo;
47  void *DiagContext;
48  };
49 }
50 
51 /// srcMgrDiagHandler - This callback is invoked when the SourceMgr for an
52 /// inline asm has an error in it. diagInfo is a pointer to the SrcMgrDiagInfo
53 /// struct above.
54 static void srcMgrDiagHandler(const SMDiagnostic &Diag, void *diagInfo) {
55  SrcMgrDiagInfo *DiagInfo = static_cast<SrcMgrDiagInfo *>(diagInfo);
56  assert(DiagInfo && "Diagnostic context not passed down?");
57 
58  // If the inline asm had metadata associated with it, pull out a location
59  // cookie corresponding to which line the error occurred on.
60  unsigned LocCookie = 0;
61  if (const MDNode *LocInfo = DiagInfo->LocInfo) {
62  unsigned ErrorLine = Diag.getLineNo()-1;
63  if (ErrorLine >= LocInfo->getNumOperands())
64  ErrorLine = 0;
65 
66  if (LocInfo->getNumOperands() != 0)
67  if (const ConstantInt *CI =
68  mdconst::dyn_extract<ConstantInt>(LocInfo->getOperand(ErrorLine)))
69  LocCookie = CI->getZExtValue();
70  }
71 
72  DiagInfo->DiagHandler(Diag, DiagInfo->DiagContext, LocCookie);
73 }
74 
75 /// EmitInlineAsm - Emit a blob of inline asm to the output streamer.
76 void AsmPrinter::EmitInlineAsm(StringRef Str, const MCSubtargetInfo &STI,
77  const MCTargetOptions &MCOptions,
78  const MDNode *LocMDNode,
79  InlineAsm::AsmDialect Dialect) const {
80  assert(!Str.empty() && "Can't emit empty inline asm block");
81 
82  // Remember if the buffer is nul terminated or not so we can avoid a copy.
83  bool isNullTerminated = Str.back() == 0;
84  if (isNullTerminated)
85  Str = Str.substr(0, Str.size()-1);
86 
87  // If the output streamer does not have mature MC support or the integrated
88  // assembler has been disabled, just emit the blob textually.
89  // Otherwise parse the asm and emit it via MC support.
90  // This is useful in case the asm parser doesn't handle something but the
91  // system assembler does.
92  const MCAsmInfo *MCAI = TM.getMCAsmInfo();
93  assert(MCAI && "No MCAsmInfo");
94  if (!MCAI->useIntegratedAssembler() &&
95  !OutStreamer->isIntegratedAssemblerRequired()) {
97  OutStreamer->EmitRawText(Str);
98  emitInlineAsmEnd(STI, nullptr);
99  return;
100  }
101 
103  SrcMgr.setIncludeDirs(MCOptions.IASSearchPaths);
104 
105  SrcMgrDiagInfo DiagInfo;
106 
107  // If the current LLVMContext has an inline asm handler, set it in SourceMgr.
108  LLVMContext &LLVMCtx = MMI->getModule()->getContext();
109  bool HasDiagHandler = false;
110  if (LLVMCtx.getInlineAsmDiagnosticHandler() != nullptr) {
111  // If the source manager has an issue, we arrange for srcMgrDiagHandler
112  // to be invoked, getting DiagInfo passed into it.
113  DiagInfo.LocInfo = LocMDNode;
114  DiagInfo.DiagHandler = LLVMCtx.getInlineAsmDiagnosticHandler();
115  DiagInfo.DiagContext = LLVMCtx.getInlineAsmDiagnosticContext();
116  SrcMgr.setDiagHandler(srcMgrDiagHandler, &DiagInfo);
117  HasDiagHandler = true;
118  }
119 
120  std::unique_ptr<MemoryBuffer> Buffer;
121  if (isNullTerminated)
122  Buffer = MemoryBuffer::getMemBuffer(Str, "<inline asm>");
123  else
124  Buffer = MemoryBuffer::getMemBufferCopy(Str, "<inline asm>");
125 
126  // Tell SrcMgr about this buffer, it takes ownership of the buffer.
127  SrcMgr.AddNewSourceBuffer(std::move(Buffer), SMLoc());
128 
129  std::unique_ptr<MCAsmParser> Parser(
131 
132  // We create a new MCInstrInfo here since we might be at the module level
133  // and not have a MachineFunction to initialize the TargetInstrInfo from and
134  // we only need MCInstrInfo for asm parsing. We create one unconditionally
135  // because it's not subtarget dependent.
136  std::unique_ptr<MCInstrInfo> MII(TM.getTarget().createMCInstrInfo());
137  std::unique_ptr<MCTargetAsmParser> TAP(TM.getTarget().createMCAsmParser(
138  STI, *Parser, *MII, MCOptions));
139  if (!TAP)
140  report_fatal_error("Inline asm not supported by this streamer because"
141  " we don't have an asm parser for this target\n");
142  Parser->setAssemblerDialect(Dialect);
143  Parser->setTargetParser(*TAP.get());
144  if (MF) {
146  TAP->SetFrameRegister(TRI->getFrameRegister(*MF));
147  }
148 
150  // Don't implicitly switch to the text section before the asm.
151  int Res = Parser->Run(/*NoInitialTextSection*/ true,
152  /*NoFinalize*/ true);
153  emitInlineAsmEnd(STI, &TAP->getSTI());
154  if (Res && !HasDiagHandler)
155  report_fatal_error("Error parsing inline asm\n");
156 }
157 
158 static void EmitMSInlineAsmStr(const char *AsmStr, const MachineInstr *MI,
159  MachineModuleInfo *MMI, int InlineAsmVariant,
160  AsmPrinter *AP, unsigned LocCookie,
161  raw_ostream &OS) {
162  // Switch to the inline assembly variant.
163  OS << "\t.intel_syntax\n\t";
164 
165  const char *LastEmitted = AsmStr; // One past the last character emitted.
166  unsigned NumOperands = MI->getNumOperands();
167 
168  while (*LastEmitted) {
169  switch (*LastEmitted) {
170  default: {
171  // Not a special case, emit the string section literally.
172  const char *LiteralEnd = LastEmitted+1;
173  while (*LiteralEnd && *LiteralEnd != '{' && *LiteralEnd != '|' &&
174  *LiteralEnd != '}' && *LiteralEnd != '$' && *LiteralEnd != '\n')
175  ++LiteralEnd;
176 
177  OS.write(LastEmitted, LiteralEnd-LastEmitted);
178  LastEmitted = LiteralEnd;
179  break;
180  }
181  case '\n':
182  ++LastEmitted; // Consume newline character.
183  OS << '\n'; // Indent code with newline.
184  break;
185  case '$': {
186  ++LastEmitted; // Consume '$' character.
187  bool Done = true;
188 
189  // Handle escapes.
190  switch (*LastEmitted) {
191  default: Done = false; break;
192  case '$':
193  ++LastEmitted; // Consume second '$' character.
194  break;
195  }
196  if (Done) break;
197 
198  // If we have ${:foo}, then this is not a real operand reference, it is a
199  // "magic" string reference, just like in .td files. Arrange to call
200  // PrintSpecial.
201  if (LastEmitted[0] == '{' && LastEmitted[1] == ':') {
202  LastEmitted += 2;
203  const char *StrStart = LastEmitted;
204  const char *StrEnd = strchr(StrStart, '}');
205  if (!StrEnd)
206  report_fatal_error("Unterminated ${:foo} operand in inline asm"
207  " string: '" + Twine(AsmStr) + "'");
208 
209  std::string Val(StrStart, StrEnd);
210  AP->PrintSpecial(MI, OS, Val.c_str());
211  LastEmitted = StrEnd+1;
212  break;
213  }
214 
215  const char *IDStart = LastEmitted;
216  const char *IDEnd = IDStart;
217  while (*IDEnd >= '0' && *IDEnd <= '9') ++IDEnd;
218 
219  unsigned Val;
220  if (StringRef(IDStart, IDEnd-IDStart).getAsInteger(10, Val))
221  report_fatal_error("Bad $ operand number in inline asm string: '" +
222  Twine(AsmStr) + "'");
223  LastEmitted = IDEnd;
224 
225  if (Val >= NumOperands-1)
226  report_fatal_error("Invalid $ operand number in inline asm string: '" +
227  Twine(AsmStr) + "'");
228 
229  // Okay, we finally have a value number. Ask the target to print this
230  // operand!
231  unsigned OpNo = InlineAsm::MIOp_FirstOperand;
232 
233  bool Error = false;
234 
235  // Scan to find the machine operand number for the operand.
236  for (; Val; --Val) {
237  if (OpNo >= MI->getNumOperands()) break;
238  unsigned OpFlags = MI->getOperand(OpNo).getImm();
239  OpNo += InlineAsm::getNumOperandRegisters(OpFlags) + 1;
240  }
241 
242  // We may have a location metadata attached to the end of the
243  // instruction, and at no point should see metadata at any
244  // other point while processing. It's an error if so.
245  if (OpNo >= MI->getNumOperands() ||
246  MI->getOperand(OpNo).isMetadata()) {
247  Error = true;
248  } else {
249  unsigned OpFlags = MI->getOperand(OpNo).getImm();
250  ++OpNo; // Skip over the ID number.
251 
252  if (InlineAsm::isMemKind(OpFlags)) {
253  Error = AP->PrintAsmMemoryOperand(MI, OpNo, InlineAsmVariant,
254  /*Modifier*/ nullptr, OS);
255  } else {
256  Error = AP->PrintAsmOperand(MI, OpNo, InlineAsmVariant,
257  /*Modifier*/ nullptr, OS);
258  }
259  }
260  if (Error) {
261  std::string msg;
262  raw_string_ostream Msg(msg);
263  Msg << "invalid operand in inline asm: '" << AsmStr << "'";
264  MMI->getModule()->getContext().emitError(LocCookie, Msg.str());
265  }
266  break;
267  }
268  }
269  }
270  OS << "\n\t.att_syntax\n" << (char)0; // null terminate string.
271 }
272 
273 static void EmitGCCInlineAsmStr(const char *AsmStr, const MachineInstr *MI,
274  MachineModuleInfo *MMI, int InlineAsmVariant,
275  int AsmPrinterVariant, AsmPrinter *AP,
276  unsigned LocCookie, raw_ostream &OS) {
277  int CurVariant = -1; // The number of the {.|.|.} region we are in.
278  const char *LastEmitted = AsmStr; // One past the last character emitted.
279  unsigned NumOperands = MI->getNumOperands();
280 
281  OS << '\t';
282 
283  while (*LastEmitted) {
284  switch (*LastEmitted) {
285  default: {
286  // Not a special case, emit the string section literally.
287  const char *LiteralEnd = LastEmitted+1;
288  while (*LiteralEnd && *LiteralEnd != '{' && *LiteralEnd != '|' &&
289  *LiteralEnd != '}' && *LiteralEnd != '$' && *LiteralEnd != '\n')
290  ++LiteralEnd;
291  if (CurVariant == -1 || CurVariant == AsmPrinterVariant)
292  OS.write(LastEmitted, LiteralEnd-LastEmitted);
293  LastEmitted = LiteralEnd;
294  break;
295  }
296  case '\n':
297  ++LastEmitted; // Consume newline character.
298  OS << '\n'; // Indent code with newline.
299  break;
300  case '$': {
301  ++LastEmitted; // Consume '$' character.
302  bool Done = true;
303 
304  // Handle escapes.
305  switch (*LastEmitted) {
306  default: Done = false; break;
307  case '$': // $$ -> $
308  if (CurVariant == -1 || CurVariant == AsmPrinterVariant)
309  OS << '$';
310  ++LastEmitted; // Consume second '$' character.
311  break;
312  case '(': // $( -> same as GCC's { character.
313  ++LastEmitted; // Consume '(' character.
314  if (CurVariant != -1)
315  report_fatal_error("Nested variants found in inline asm string: '" +
316  Twine(AsmStr) + "'");
317  CurVariant = 0; // We're in the first variant now.
318  break;
319  case '|':
320  ++LastEmitted; // consume '|' character.
321  if (CurVariant == -1)
322  OS << '|'; // this is gcc's behavior for | outside a variant
323  else
324  ++CurVariant; // We're in the next variant.
325  break;
326  case ')': // $) -> same as GCC's } char.
327  ++LastEmitted; // consume ')' character.
328  if (CurVariant == -1)
329  OS << '}'; // this is gcc's behavior for } outside a variant
330  else
331  CurVariant = -1;
332  break;
333  }
334  if (Done) break;
335 
336  bool HasCurlyBraces = false;
337  if (*LastEmitted == '{') { // ${variable}
338  ++LastEmitted; // Consume '{' character.
339  HasCurlyBraces = true;
340  }
341 
342  // If we have ${:foo}, then this is not a real operand reference, it is a
343  // "magic" string reference, just like in .td files. Arrange to call
344  // PrintSpecial.
345  if (HasCurlyBraces && *LastEmitted == ':') {
346  ++LastEmitted;
347  const char *StrStart = LastEmitted;
348  const char *StrEnd = strchr(StrStart, '}');
349  if (!StrEnd)
350  report_fatal_error("Unterminated ${:foo} operand in inline asm"
351  " string: '" + Twine(AsmStr) + "'");
352 
353  std::string Val(StrStart, StrEnd);
354  AP->PrintSpecial(MI, OS, Val.c_str());
355  LastEmitted = StrEnd+1;
356  break;
357  }
358 
359  const char *IDStart = LastEmitted;
360  const char *IDEnd = IDStart;
361  while (*IDEnd >= '0' && *IDEnd <= '9') ++IDEnd;
362 
363  unsigned Val;
364  if (StringRef(IDStart, IDEnd-IDStart).getAsInteger(10, Val))
365  report_fatal_error("Bad $ operand number in inline asm string: '" +
366  Twine(AsmStr) + "'");
367  LastEmitted = IDEnd;
368 
369  char Modifier[2] = { 0, 0 };
370 
371  if (HasCurlyBraces) {
372  // If we have curly braces, check for a modifier character. This
373  // supports syntax like ${0:u}, which correspond to "%u0" in GCC asm.
374  if (*LastEmitted == ':') {
375  ++LastEmitted; // Consume ':' character.
376  if (*LastEmitted == 0)
377  report_fatal_error("Bad ${:} expression in inline asm string: '" +
378  Twine(AsmStr) + "'");
379 
380  Modifier[0] = *LastEmitted;
381  ++LastEmitted; // Consume modifier character.
382  }
383 
384  if (*LastEmitted != '}')
385  report_fatal_error("Bad ${} expression in inline asm string: '" +
386  Twine(AsmStr) + "'");
387  ++LastEmitted; // Consume '}' character.
388  }
389 
390  if (Val >= NumOperands-1)
391  report_fatal_error("Invalid $ operand number in inline asm string: '" +
392  Twine(AsmStr) + "'");
393 
394  // Okay, we finally have a value number. Ask the target to print this
395  // operand!
396  if (CurVariant == -1 || CurVariant == AsmPrinterVariant) {
397  unsigned OpNo = InlineAsm::MIOp_FirstOperand;
398 
399  bool Error = false;
400 
401  // Scan to find the machine operand number for the operand.
402  for (; Val; --Val) {
403  if (OpNo >= MI->getNumOperands()) break;
404  unsigned OpFlags = MI->getOperand(OpNo).getImm();
405  OpNo += InlineAsm::getNumOperandRegisters(OpFlags) + 1;
406  }
407 
408  // We may have a location metadata attached to the end of the
409  // instruction, and at no point should see metadata at any
410  // other point while processing. It's an error if so.
411  if (OpNo >= MI->getNumOperands() ||
412  MI->getOperand(OpNo).isMetadata()) {
413  Error = true;
414  } else {
415  unsigned OpFlags = MI->getOperand(OpNo).getImm();
416  ++OpNo; // Skip over the ID number.
417 
418  if (Modifier[0] == 'l') { // Labels are target independent.
419  // FIXME: What if the operand isn't an MBB, report error?
420  const MCSymbol *Sym = MI->getOperand(OpNo).getMBB()->getSymbol();
421  Sym->print(OS, AP->MAI);
422  } else {
423  if (InlineAsm::isMemKind(OpFlags)) {
424  Error = AP->PrintAsmMemoryOperand(MI, OpNo, InlineAsmVariant,
425  Modifier[0] ? Modifier : nullptr,
426  OS);
427  } else {
428  Error = AP->PrintAsmOperand(MI, OpNo, InlineAsmVariant,
429  Modifier[0] ? Modifier : nullptr, OS);
430  }
431  }
432  }
433  if (Error) {
434  std::string msg;
435  raw_string_ostream Msg(msg);
436  Msg << "invalid operand in inline asm: '" << AsmStr << "'";
437  MMI->getModule()->getContext().emitError(LocCookie, Msg.str());
438  }
439  }
440  break;
441  }
442  }
443  }
444  OS << '\n' << (char)0; // null terminate string.
445 }
446 
447 /// EmitInlineAsm - This method formats and emits the specified machine
448 /// instruction that is an inline asm.
449 void AsmPrinter::EmitInlineAsm(const MachineInstr *MI) const {
450  assert(MI->isInlineAsm() && "printInlineAsm only works on inline asms");
451 
452  // Count the number of register definitions to find the asm string.
453  unsigned NumDefs = 0;
454  for (; MI->getOperand(NumDefs).isReg() && MI->getOperand(NumDefs).isDef();
455  ++NumDefs)
456  assert(NumDefs != MI->getNumOperands()-2 && "No asm string?");
457 
458  assert(MI->getOperand(NumDefs).isSymbol() && "No asm string?");
459 
460  // Disassemble the AsmStr, printing out the literal pieces, the operands, etc.
461  const char *AsmStr = MI->getOperand(NumDefs).getSymbolName();
462 
463  // If this asmstr is empty, just print the #APP/#NOAPP markers.
464  // These are useful to see where empty asm's wound up.
465  if (AsmStr[0] == 0) {
466  OutStreamer->emitRawComment(MAI->getInlineAsmStart());
467  OutStreamer->emitRawComment(MAI->getInlineAsmEnd());
468  return;
469  }
470 
471  // Emit the #APP start marker. This has to happen even if verbose-asm isn't
472  // enabled, so we use emitRawComment.
473  OutStreamer->emitRawComment(MAI->getInlineAsmStart());
474 
475  // Get the !srcloc metadata node if we have it, and decode the loc cookie from
476  // it.
477  unsigned LocCookie = 0;
478  const MDNode *LocMD = nullptr;
479  for (unsigned i = MI->getNumOperands(); i != 0; --i) {
480  if (MI->getOperand(i-1).isMetadata() &&
481  (LocMD = MI->getOperand(i-1).getMetadata()) &&
482  LocMD->getNumOperands() != 0) {
483  if (const ConstantInt *CI =
484  mdconst::dyn_extract<ConstantInt>(LocMD->getOperand(0))) {
485  LocCookie = CI->getZExtValue();
486  break;
487  }
488  }
489  }
490 
491  // Emit the inline asm to a temporary string so we can emit it through
492  // EmitInlineAsm.
493  SmallString<256> StringData;
494  raw_svector_ostream OS(StringData);
495 
496  // The variant of the current asmprinter.
497  int AsmPrinterVariant = MAI->getAssemblerDialect();
498  InlineAsm::AsmDialect InlineAsmVariant = MI->getInlineAsmDialect();
499  AsmPrinter *AP = const_cast<AsmPrinter*>(this);
500  if (InlineAsmVariant == InlineAsm::AD_ATT)
501  EmitGCCInlineAsmStr(AsmStr, MI, MMI, InlineAsmVariant, AsmPrinterVariant,
502  AP, LocCookie, OS);
503  else
504  EmitMSInlineAsmStr(AsmStr, MI, MMI, InlineAsmVariant, AP, LocCookie, OS);
505 
506  // Reset SanitizeAddress based on the function's attribute.
507  MCTargetOptions MCOptions = TM.Options.MCOptions;
508  MCOptions.SanitizeAddress =
509  MF->getFunction()->hasFnAttribute(Attribute::SanitizeAddress);
510 
511  EmitInlineAsm(OS.str(), getSubtargetInfo(), MCOptions, LocMD,
512  MI->getInlineAsmDialect());
513 
514  // Emit the #NOAPP end marker. This has to happen even if verbose-asm isn't
515  // enabled, so we use emitRawComment.
516  OutStreamer->emitRawComment(MAI->getInlineAsmEnd());
517 }
518 
519 
520 /// PrintSpecial - Print information related to the specified machine instr
521 /// that is independent of the operand, and may be independent of the instr
522 /// itself. This can be useful for portably encoding the comment character
523 /// or other bits of target-specific knowledge into the asmstrings. The
524 /// syntax used is ${:comment}. Targets can override this to add support
525 /// for their own strange codes.
527  const char *Code) const {
528  if (!strcmp(Code, "private")) {
529  const DataLayout &DL = MF->getDataLayout();
530  OS << DL.getPrivateGlobalPrefix();
531  } else if (!strcmp(Code, "comment")) {
532  OS << MAI->getCommentString();
533  } else if (!strcmp(Code, "uid")) {
534  // Comparing the address of MI isn't sufficient, because machineinstrs may
535  // be allocated to the same address across functions.
536 
537  // If this is a new LastFn instruction, bump the counter.
538  if (LastMI != MI || LastFn != getFunctionNumber()) {
539  ++Counter;
540  LastMI = MI;
541  LastFn = getFunctionNumber();
542  }
543  OS << Counter;
544  } else {
545  std::string msg;
546  raw_string_ostream Msg(msg);
547  Msg << "Unknown special formatter '" << Code
548  << "' for machine instr: " << *MI;
549  report_fatal_error(Msg.str());
550  }
551 }
552 
553 /// PrintAsmOperand - Print the specified operand of MI, an INLINEASM
554 /// instruction, using the specified assembler variant. Targets should
555 /// override this to format as appropriate.
556 bool AsmPrinter::PrintAsmOperand(const MachineInstr *MI, unsigned OpNo,
557  unsigned AsmVariant, const char *ExtraCode,
558  raw_ostream &O) {
559  // Does this asm operand have a single letter operand modifier?
560  if (ExtraCode && ExtraCode[0]) {
561  if (ExtraCode[1] != 0) return true; // Unknown modifier.
562 
563  const MachineOperand &MO = MI->getOperand(OpNo);
564  switch (ExtraCode[0]) {
565  default:
566  return true; // Unknown modifier.
567  case 'c': // Substitute immediate value without immediate syntax
569  return true;
570  O << MO.getImm();
571  return false;
572  case 'n': // Negate the immediate constant.
574  return true;
575  O << -MO.getImm();
576  return false;
577  case 's': // The GCC deprecated s modifier
579  return true;
580  O << ((32 - MO.getImm()) & 31);
581  return false;
582  }
583  }
584  return true;
585 }
586 
587 bool AsmPrinter::PrintAsmMemoryOperand(const MachineInstr *MI, unsigned OpNo,
588  unsigned AsmVariant,
589  const char *ExtraCode, raw_ostream &O) {
590  // Target doesn't support this yet!
591  return true;
592 }
593 
595 
597  const MCSubtargetInfo *EndInfo) const {}
std::enable_if< std::numeric_limits< T >::is_signed, bool >::type getAsInteger(unsigned Radix, T &Result) const
Parse the current string as an integer of the specified radix.
Definition: StringRef.h:494
A parsed version of the target data layout string in and methods for querying it. ...
Definition: DataLayout.h:102
unsigned getAssemblerDialect() const
Definition: MCAsmInfo.h:491
StringRef getPrivateGlobalPrefix() const
Definition: DataLayout.h:284
std::unique_ptr< MCStreamer > OutStreamer
This is the MCStreamer object for the file we are generating.
Definition: AsmPrinter.h:84
MCTargetOptions MCOptions
Machine level options.
void print(raw_ostream &OS, const MCAsmInfo *MAI) const
print - Print the value to the stream OS.
Definition: MCSymbol.cpp:53
size_t i
LLVM_ATTRIBUTE_NORETURN void report_fatal_error(Error Err, bool gen_crash_diag=true)
Report a serious error, calling any installed error handler.
MachineBasicBlock * getMBB() const
MCSymbol - Instances of this class represent a symbol name in the MC file, and MCSymbols are created ...
Definition: MCSymbol.h:39
InlineAsmDiagHandlerTy getInlineAsmDiagnosticHandler() const
getInlineAsmDiagnosticHandler - Return the diagnostic handler set by setInlineAsmDiagnosticHandler.
std::vector< std::string > IASSearchPaths
Additional paths to search for .include directives when using the integrated assembler.
MCContext & OutContext
This is the context for the output file that we are streaming.
Definition: AsmPrinter.h:79
unsigned getNumOperands() const
Return number of MDNode operands.
Definition: Metadata.h:1040
SourceMgr SrcMgr
static std::unique_ptr< MemoryBuffer > getMemBuffer(StringRef InputData, StringRef BufferName="", bool RequiresNullTerminator=true)
Open the specified memory range as a MemoryBuffer.
bool SanitizeAddress
Enables AddressSanitizer instrumentation at machine level.
const MachineFunction * MF
The current machine function.
Definition: AsmPrinter.h:87
A raw_ostream that writes to an SmallVector or SmallString.
Definition: raw_ostream.h:490
unsigned getFunctionNumber() const
Return a unique ID for the current function.
Definition: AsmPrinter.cpp:140
const char * getSymbolName() const
Metadata node.
Definition: Metadata.h:830
const Function * getFunction() const
getFunction - Return the LLVM function that this machine code represents
virtual void emitInlineAsmStart() const
Let the target do anything it needs to do before emitting inlineasm.
const MCSubtargetInfo & getSubtargetInfo() const
Return information about subtarget.
Definition: AsmPrinter.cpp:156
const MDNode * getMetadata() const
LLVM_NODISCARD char back() const
back - Get the last character in the string.
Definition: StringRef.h:146
Maximum length of the test input libFuzzer tries to guess a good value based on the corpus and reports it always prefer smaller inputs during the corpus shuffle When libFuzzer itself reports a bug this exit code will be used If indicates the maximal total time in seconds to run the fuzzer minimizes the provided crash input Use with strcmp
bool isMetadata() const
isMetadata - Tests if this is a MO_Metadata operand.
StringRef getCommentString() const
Definition: MCAsmInfo.h:471
MCInstrInfo * createMCInstrInfo() const
createMCInstrInfo - Create a MCInstrInfo implementation.
const TargetSubtargetInfo & getSubtarget() const
getSubtarget - Return the subtarget for which this machine code is being compiled.
Twine - A lightweight data structure for efficiently representing the concatenation of temporary valu...
Definition: Twine.h:81
const MCAsmInfo * getMCAsmInfo() const
Return target specific asm information.
bool isReg() const
isReg - Tests if this is a MO_Register operand.
const Module * getModule() const
virtual void PrintSpecial(const MachineInstr *MI, raw_ostream &OS, const char *Code) const
Print information related to the specified machine instr that is independent of the operand...
const char * getInlineAsmEnd() const
Definition: MCAsmInfo.h:487
virtual unsigned getFrameRegister(const MachineFunction &MF) const =0
Debug information queries.
unsigned getNumOperands() const
Access to explicit operands of the instruction.
Definition: MachineInstr.h:277
void emitError(unsigned LocCookie, const Twine &ErrorStr)
emitError - Emit an error message to the currently installed error handler with optional location inf...
MCTargetAsmParser * createMCAsmParser(const MCSubtargetInfo &STI, MCAsmParser &Parser, const MCInstrInfo &MII, const MCTargetOptions &Options) const
createMCAsmParser - Create a target specific assembly parser.
unsigned AddNewSourceBuffer(std::unique_ptr< MemoryBuffer > F, SMLoc IncludeLoc)
Add a new source buffer to this source manager.
Definition: SourceMgr.h:118
virtual bool PrintAsmMemoryOperand(const MachineInstr *MI, unsigned OpNo, unsigned AsmVariant, const char *ExtraCode, raw_ostream &OS)
Print the specified operand of MI, an INLINEASM instruction, using the specified assembler variant as...
int64_t getImm() const
const DataLayout & getDataLayout() const
Return the DataLayout attached to the Module associated to this MF.
LLVM_NODISCARD LLVM_ATTRIBUTE_ALWAYS_INLINE size_t size() const
size - Get the string size.
Definition: StringRef.h:135
MachineModuleInfo * MMI
This is a pointer to the current MachineModuleInfo.
Definition: AsmPrinter.h:90
This class is intended to be used as a base class for asm properties and features specific to the tar...
Definition: MCAsmInfo.h:57
void setDiagHandler(DiagHandlerTy DH, void *Ctx=nullptr)
Specify a diagnostic handler to be invoked every time PrintMessage is called.
Definition: SourceMgr.h:84
const MCAsmInfo * MAI
Target Asm Printer information.
Definition: AsmPrinter.h:75
This is an important class for using LLVM in a threaded context.
Definition: LLVMContext.h:48
This file contains the declarations for the subclasses of Constant, which represent the different fla...
const MachineOperand & getOperand(unsigned i) const
Definition: MachineInstr.h:279
virtual bool PrintAsmOperand(const MachineInstr *MI, unsigned OpNo, unsigned AsmVariant, const char *ExtraCode, raw_ostream &OS)
Print the specified operand of MI, an INLINEASM instruction, using the specified assembler variant...
LLVM_NODISCARD LLVM_ATTRIBUTE_ALWAYS_INLINE StringRef substr(size_t Start, size_t N=npos) const
Return a reference to the substring from [Start, Start + N).
Definition: StringRef.h:587
TargetMachine & TM
Target machine description.
Definition: AsmPrinter.h:71
This class is intended to be used as a driving class for all asm writers.
Definition: AsmPrinter.h:67
static unsigned getNumOperandRegisters(unsigned Flag)
getNumOperandRegisters - Extract the number of registers field from the inline asm operand flag...
Definition: InlineAsm.h:335
bool isSymbol() const
isSymbol - Tests if this is a MO_ExternalSymbol operand.
MCAsmParser * createMCAsmParser(SourceMgr &, MCContext &, MCStreamer &, const MCAsmInfo &)
Create an MCAsmParser instance.
Definition: AsmParser.cpp:5520
static void srcMgrDiagHandler(const SMDiagnostic &Diag, void *diagInfo)
srcMgrDiagHandler - This callback is invoked when the SourceMgr for an inline asm has an error in it...
This owns the files read by a parser, handles include stacks, and handles diagnostic wrangling...
Definition: SourceMgr.h:35
static bool isMemKind(unsigned Flag)
Definition: InlineAsm.h:276
TargetRegisterInfo base class - We assume that the target defines a static array of TargetRegisterDes...
MCSymbol * getSymbol() const
Return the MCSymbol for this basic block.
std::string & str()
Flushes the stream contents to the target string and returns the string's reference.
Definition: raw_ostream.h:479
virtual void emitInlineAsmEnd(const MCSubtargetInfo &StartInfo, const MCSubtargetInfo *EndInfo) const
Let the target do anything it needs to do after emitting inlineasm.
raw_ostream & write(unsigned char C)
const MDOperand & getOperand(unsigned I) const
Definition: Metadata.h:1034
This is the shared class of boolean and integer constants.
Definition: Constants.h:88
MachineOperand class - Representation of each machine instruction operand.
Module.h This file contains the declarations for the Module class.
int getLineNo() const
Definition: SourceMgr.h:257
bool isInlineAsm() const
Definition: MachineInstr.h:789
void(* InlineAsmDiagHandlerTy)(const SMDiagnostic &, void *Context, unsigned LocCookie)
Definition: LLVMContext.h:136
static std::unique_ptr< MemoryBuffer > getMemBufferCopy(StringRef InputData, const Twine &BufferName="")
Open the specified memory range as a MemoryBuffer, copying the contents and taking ownership of it...
LLVM_NODISCARD LLVM_ATTRIBUTE_ALWAYS_INLINE bool empty() const
empty - Check if the string is empty.
Definition: StringRef.h:130
void * getInlineAsmDiagnosticContext() const
getInlineAsmDiagnosticContext - Return the diagnostic context set by setInlineAsmDiagnosticHandler.
Representation of each machine instruction.
Definition: MachineInstr.h:52
MachineOperandType getType() const
getType - Returns the MachineOperandType for this operand.
bool hasFnAttribute(Attribute::AttrKind Kind) const
Return true if the function has the attribute.
Definition: Function.h:226
MCSubtargetInfo - Generic base class for all target subtargets.
assert(ImpDefSCC.getReg()==AMDGPU::SCC &&ImpDefSCC.isDef())
A raw_ostream that writes to an std::string.
Definition: raw_ostream.h:463
static void EmitGCCInlineAsmStr(const char *AsmStr, const MachineInstr *MI, MachineModuleInfo *MMI, int InlineAsmVariant, int AsmPrinterVariant, AsmPrinter *AP, unsigned LocCookie, raw_ostream &OS)
Lightweight error class with error context and mandatory checking.
bool useIntegratedAssembler() const
Return true if assembly (inline or otherwise) should be parsed.
Definition: MCAsmInfo.h:574
This class implements an extremely fast bulk output stream that can only output to a stream...
Definition: raw_ostream.h:44
const Target & getTarget() const
void setIncludeDirs(const std::vector< std::string > &Dirs)
Definition: SourceMgr.h:78
IRTranslator LLVM IR MI
virtual const TargetRegisterInfo * getRegisterInfo() const
getRegisterInfo - If register information is available, return it.
StringRef - Represent a constant reference to a string, i.e.
Definition: StringRef.h:47
static void EmitMSInlineAsmStr(const char *AsmStr, const MachineInstr *MI, MachineModuleInfo *MMI, int InlineAsmVariant, AsmPrinter *AP, unsigned LocCookie, raw_ostream &OS)
const char * getInlineAsmStart() const
Definition: MCAsmInfo.h:486
Represents a location in source code.
Definition: SMLoc.h:24
InlineAsm::AsmDialect getInlineAsmDialect() const
This class contains meta information specific to a module.
LLVMContext & getContext() const
Get the global data context.
Definition: Module.h:222
Instances of this class encapsulate one diagnostic report, allowing printing to a raw_ostream as a ca...
Definition: SourceMgr.h:228