LLVM: lib/MC/MCParser/AsmParser.cpp Source File (original) (raw)

1

2

3

4

5

6

7

8

9

10

11

12

59#include

60#include

61#include

62#include

63#include

64#include

65#include

66#include

67#include

68#include

69#include

70#include

71#include

72#include

73

74using namespace llvm;

75

77

78namespace {

79

80

81typedef std::vector MCAsmMacroArgument;

82typedef std::vector MCAsmMacroArguments;

83

84

85

86struct MacroInstantiation {

87

88 SMLoc InstantiationLoc;

89

90

91 unsigned ExitBuffer;

92

93

94 SMLoc ExitLoc;

95

96

97 size_t CondStackDepth;

98};

99

100struct ParseStatementInfo {

101

103

104

105 unsigned Opcode = ~0U;

106

107

108 bool ParseError = false;

109

110 SmallVectorImpl *AsmRewrites = nullptr;

111

112 ParseStatementInfo() = delete;

113 ParseStatementInfo(SmallVectorImpl *rewrites)

114 : AsmRewrites(rewrites) {}

115};

116

117

119private:

121 void *SavedDiagContext;

122 std::unique_ptr PlatformParser;

123 SMLoc StartTokLoc;

124 std::optional CFIStartProcLoc;

125

126

127

128 unsigned CurBuffer;

129

130 AsmCond TheCondState;

131 std::vector TheCondStack;

132

133

134

135

136 StringMap ExtensionDirectiveMap;

137

138

139 std::vector<MacroInstantiation*> ActiveMacros;

140

141

142 std::deque MacroLikeBodies;

143

144

145 unsigned MacrosEnabledFlag : 1;

146

147

148 unsigned NumOfMacroInstantiations = 0;

149

150

151 struct CppHashInfoTy {

152 StringRef Filename;

153 int64_t LineNumber;

154 SMLoc Loc;

155 unsigned Buf;

156 CppHashInfoTy() : LineNumber(0), Buf(0) {}

157 };

158 CppHashInfoTy CppHashInfo;

159

160

161 bool HadCppHashFilename = false;

162

163

165

166 SmallSet<StringRef, 2> LTODiscardSymbols;

167

168

169 unsigned AssemblerDialect = ~0U;

170

171

172 bool IsDarwin = false;

173

174

175 bool ParsingMSInlineAsm = false;

176

177

178 bool ReportedInconsistentMD5 = false;

179

180

181 bool AltMacroMode = false;

182

183protected:

184 virtual bool parseStatement(ParseStatementInfo &Info,

185 MCAsmParserSemaCallback *SI);

186

187

188

189

190 bool parseAndMatchAndEmitTargetInstruction(ParseStatementInfo &Info,

191 StringRef IDVal, AsmToken ID,

192 SMLoc IDLoc);

193

194

195

196

197 bool enabledGenDwarfForAssembly();

198

199public:

200 AsmParser(SourceMgr &SM, MCContext &Ctx, MCStreamer &Out,

201 const MCAsmInfo &MAI, unsigned CB);

202 AsmParser(const AsmParser &) = delete;

203 AsmParser &operator=(const AsmParser &) = delete;

204 ~AsmParser() override;

205

206 bool Run(bool NoInitialTextSection, bool NoFinalize = false) override;

207

208 void addDirectiveHandler(StringRef Directive,

209 ExtensionDirectiveHandler Handler) override {

210 ExtensionDirectiveMap[Directive] = Handler;

211 }

212

213 void addAliasForDirective(StringRef Directive, StringRef Alias) override {

214 DirectiveKindMap[Directive.lower()] = DirectiveKindMap[Alias.lower()];

215 }

216

217

218

219

220 CodeViewContext &getCVContext() { return Ctx.getCVContext(); }

221

222 unsigned getAssemblerDialect() override {

223 if (AssemblerDialect == ~0U)

224 return MAI.getAssemblerDialect();

225 else

226 return AssemblerDialect;

227 }

228 void setAssemblerDialect(unsigned i) override {

229 AssemblerDialect = i;

230 }

231

232 void Note(SMLoc L, const Twine &Msg, SMRange Range = {}) override;

233 bool Warning(SMLoc L, const Twine &Msg, SMRange Range = {}) override;

234 bool printError(SMLoc L, const Twine &Msg, SMRange Range = {}) override;

235

236 const AsmToken &Lex() override;

237

238 void setParsingMSInlineAsm(bool V) override {

239 ParsingMSInlineAsm = V;

240

241

242 Lexer.setLexMasmIntegers(V);

243 }

244 bool isParsingMSInlineAsm() override { return ParsingMSInlineAsm; }

245

246 bool discardLTOSymbol(StringRef Name) const override {

247 return LTODiscardSymbols.contains(Name);

248 }

249

250 bool parseMSInlineAsm(std::string &AsmString, unsigned &NumOutputs,

251 unsigned &NumInputs,

252 SmallVectorImpl<std::pair<void *, bool>> &OpDecls,

253 SmallVectorImplstd::string &Constraints,

254 SmallVectorImplstd::string &Clobbers,

255 const MCInstrInfo *MII, MCInstPrinter *IP,

256 MCAsmParserSemaCallback &SI) override;

257

258 bool parseExpression(const MCExpr *&Res);

259 bool parseExpression(const MCExpr *&Res, SMLoc &EndLoc) override;

260 bool parsePrimaryExpr(const MCExpr *&Res, SMLoc &EndLoc,

261 AsmTypeInfo *TypeInfo) override;

262 bool parseParenExpression(const MCExpr *&Res, SMLoc &EndLoc) override;

263 bool parseAbsoluteExpression(int64_t &Res) override;

264

265

266

267 bool parseRealValue(const fltSemantics &Semantics, APInt &Res);

268

269

270

271 bool parseIdentifier(StringRef &Res) override;

272 void eatToEndOfStatement() override;

273

274 bool checkForValidSection() override;

275

276

277

278private:

279 bool parseCurlyBlockScope(SmallVectorImpl& AsmStrRewrites);

280 bool parseCppHashLineFilenameComment(SMLoc L, bool SaveLocInfo = true);

281

282 void checkForBadMacro(SMLoc DirectiveLoc, StringRef Name, StringRef Body,

284 bool expandMacro(raw_svector_ostream &OS, MCAsmMacro &Macro,

287

288

289 bool areMacrosEnabled() {return MacrosEnabledFlag;}

290

291

292 void setMacrosEnabled(bool Flag) {MacrosEnabledFlag = Flag;}

293

294

295 bool isInsideMacroInstantiation() {return !ActiveMacros.empty();}

296

297

298

299

300

301 bool handleMacroEntry(MCAsmMacro *M, SMLoc NameLoc);

302

303

304 void handleMacroExit();

305

306

307 bool parseMacroArgument(MCAsmMacroArgument &MA, bool Vararg);

308

309

310 bool parseMacroArguments(const MCAsmMacro *M, MCAsmMacroArguments &A);

311

312 void printMacroInstantiations();

314 SMRange Range = {}) const {

317 }

319

320

321 bool enterIncludeFile(const std::string &Filename);

322

323

324

325 bool processIncbinFile(const std::string &Filename, int64_t Skip = 0,

326 const MCExpr *Count = nullptr, SMLoc Loc = SMLoc());

327

328

329

330

331

332

333

334 void jumpToLoc(SMLoc Loc, unsigned InBuffer = 0);

335

336

337

338

339 StringRef parseStringToEndOfStatement() override;

340

341

342

343 StringRef parseStringToComma();

344

345 enum class AssignmentKind {

347 Equiv,

349 LTOSetConditional,

350 };

351

352 bool parseAssignment(StringRef Name, AssignmentKind Kind);

353

356

357 bool parseBinOpRHS(unsigned Precedence, const MCExpr *&Res, SMLoc &EndLoc);

358 bool parseParenExpr(const MCExpr *&Res, SMLoc &EndLoc);

359 bool parseBracketExpr(const MCExpr *&Res, SMLoc &EndLoc);

360

361 bool parseRegisterOrRegisterNumber(int64_t &Register, SMLoc DirectiveLoc);

362

363 bool parseCVFunctionId(int64_t &FunctionId, StringRef DirectiveName);

364 bool parseCVFileId(int64_t &FileId, StringRef DirectiveName);

365

366

367 enum DirectiveKind {

368 DK_NO_DIRECTIVE,

369 DK_SET,

370 DK_EQU,

371 DK_EQUIV,

372 DK_ASCII,

373 DK_ASCIZ,

374 DK_STRING,

375 DK_BYTE,

376 DK_SHORT,

377 DK_RELOC,

378 DK_VALUE,

379 DK_2BYTE,

380 DK_LONG,

381 DK_INT,

382 DK_4BYTE,

383 DK_QUAD,

384 DK_8BYTE,

385 DK_OCTA,

386 DK_DC,

387 DK_DC_A,

388 DK_DC_B,

389 DK_DC_D,

390 DK_DC_L,

391 DK_DC_S,

392 DK_DC_W,

393 DK_DC_X,

394 DK_DCB,

395 DK_DCB_B,

396 DK_DCB_D,

397 DK_DCB_L,

398 DK_DCB_S,

399 DK_DCB_W,

400 DK_DCB_X,

401 DK_DS,

402 DK_DS_B,

403 DK_DS_D,

404 DK_DS_L,

405 DK_DS_P,

406 DK_DS_S,

407 DK_DS_W,

408 DK_DS_X,

409 DK_SINGLE,

410 DK_FLOAT,

411 DK_DOUBLE,

412 DK_ALIGN,

413 DK_ALIGN32,

414 DK_BALIGN,

415 DK_BALIGNW,

416 DK_BALIGNL,

417 DK_P2ALIGN,

418 DK_P2ALIGNW,

419 DK_P2ALIGNL,

420 DK_ORG,

421 DK_FILL,

422 DK_ENDR,

423 DK_ZERO,

424 DK_EXTERN,

425 DK_GLOBL,

426 DK_GLOBAL,

427 DK_LAZY_REFERENCE,

428 DK_NO_DEAD_STRIP,

429 DK_SYMBOL_RESOLVER,

430 DK_PRIVATE_EXTERN,

431 DK_REFERENCE,

432 DK_WEAK_DEFINITION,

433 DK_WEAK_REFERENCE,

434 DK_WEAK_DEF_CAN_BE_HIDDEN,

435 DK_COLD,

436 DK_COMM,

437 DK_COMMON,

438 DK_LCOMM,

439 DK_ABORT,

440 DK_INCLUDE,

441 DK_INCBIN,

442 DK_CODE16,

443 DK_CODE16GCC,

444 DK_REPT,

445 DK_IRP,

446 DK_IRPC,

447 DK_IF,

448 DK_IFEQ,

449 DK_IFGE,

450 DK_IFGT,

451 DK_IFLE,

452 DK_IFLT,

453 DK_IFNE,

454 DK_IFB,

455 DK_IFNB,

456 DK_IFC,

457 DK_IFEQS,

458 DK_IFNC,

459 DK_IFNES,

460 DK_IFDEF,

461 DK_IFNDEF,

462 DK_IFNOTDEF,

463 DK_ELSEIF,

464 DK_ELSE,

465 DK_ENDIF,

466 DK_SPACE,

467 DK_SKIP,

468 DK_FILE,

469 DK_LINE,

470 DK_LOC,

471 DK_LOC_LABEL,

472 DK_STABS,

473 DK_CV_FILE,

474 DK_CV_FUNC_ID,

475 DK_CV_INLINE_SITE_ID,

476 DK_CV_LOC,

477 DK_CV_LINETABLE,

478 DK_CV_INLINE_LINETABLE,

479 DK_CV_DEF_RANGE,

480 DK_CV_STRINGTABLE,

481 DK_CV_STRING,

482 DK_CV_FILECHECKSUMS,

483 DK_CV_FILECHECKSUM_OFFSET,

484 DK_CV_FPO_DATA,

485 DK_CFI_SECTIONS,

486 DK_CFI_STARTPROC,

487 DK_CFI_ENDPROC,

488 DK_CFI_DEF_CFA,

489 DK_CFI_DEF_CFA_OFFSET,

490 DK_CFI_ADJUST_CFA_OFFSET,

491 DK_CFI_DEF_CFA_REGISTER,

492 DK_CFI_LLVM_DEF_ASPACE_CFA,

493 DK_CFI_OFFSET,

494 DK_CFI_REL_OFFSET,

495 DK_CFI_PERSONALITY,

496 DK_CFI_LSDA,

497 DK_CFI_REMEMBER_STATE,

498 DK_CFI_RESTORE_STATE,

499 DK_CFI_SAME_VALUE,

500 DK_CFI_RESTORE,

501 DK_CFI_ESCAPE,

502 DK_CFI_RETURN_COLUMN,

503 DK_CFI_SIGNAL_FRAME,

504 DK_CFI_UNDEFINED,

505 DK_CFI_REGISTER,

506 DK_CFI_WINDOW_SAVE,

507 DK_CFI_LABEL,

508 DK_CFI_B_KEY_FRAME,

509 DK_CFI_VAL_OFFSET,

510 DK_MACROS_ON,

511 DK_MACROS_OFF,

512 DK_ALTMACRO,

513 DK_NOALTMACRO,

514 DK_MACRO,

515 DK_EXITM,

516 DK_ENDM,

517 DK_ENDMACRO,

518 DK_PURGEM,

519 DK_SLEB128,

520 DK_ULEB128,

521 DK_ERR,

522 DK_ERROR,

523 DK_WARNING,

524 DK_PRINT,

525 DK_ADDRSIG,

526 DK_ADDRSIG_SYM,

527 DK_PSEUDO_PROBE,

528 DK_LTO_DISCARD,

529 DK_LTO_SET_CONDITIONAL,

530 DK_CFI_MTE_TAGGED_FRAME,

531 DK_MEMTAG,

532 DK_BASE64,

533 DK_END

534 };

535

536

537

538 StringMap DirectiveKindMap;

539

540

541 enum CVDefRangeType {

542 CVDR_DEFRANGE = 0,

543 CVDR_DEFRANGE_REGISTER,

544 CVDR_DEFRANGE_FRAMEPOINTER_REL,

545 CVDR_DEFRANGE_SUBFIELD_REGISTER,

546 CVDR_DEFRANGE_REGISTER_REL

547 };

548

549

550

551 StringMap CVDefRangeTypeMap;

552

553

554 bool parseDirectiveAscii(StringRef IDVal, bool ZeroTerminated);

555 bool parseDirectiveBase64();

556 bool parseDirectiveReloc(SMLoc DirectiveLoc);

557 bool parseDirectiveValue(StringRef IDVal,

558 unsigned Size);

559 bool parseDirectiveOctaValue(StringRef IDVal);

560 bool parseDirectiveRealValue(StringRef IDVal,

561 const fltSemantics &);

562 bool parseDirectiveFill();

563 bool parseDirectiveZero();

564

565 bool parseDirectiveSet(StringRef IDVal, AssignmentKind Kind);

566 bool parseDirectiveOrg();

567

568 bool parseDirectiveAlign(bool IsPow2, uint8_t ValueSize);

569

570

571 bool parseDirectiveFile(SMLoc DirectiveLoc);

572 bool parseDirectiveLine();

573 bool parseDirectiveLoc();

574 bool parseDirectiveLocLabel(SMLoc DirectiveLoc);

575 bool parseDirectiveStabs();

576

577

578

579 bool parseDirectiveCVFile();

580 bool parseDirectiveCVFuncId();

581 bool parseDirectiveCVInlineSiteId();

582 bool parseDirectiveCVLoc();

583 bool parseDirectiveCVLinetable();

584 bool parseDirectiveCVInlineLinetable();

585 bool parseDirectiveCVDefRange();

586 bool parseDirectiveCVString();

587 bool parseDirectiveCVStringTable();

588 bool parseDirectiveCVFileChecksums();

589 bool parseDirectiveCVFileChecksumOffset();

590 bool parseDirectiveCVFPOData();

591

592

593 bool parseDirectiveCFIRegister(SMLoc DirectiveLoc);

594 bool parseDirectiveCFIWindowSave(SMLoc DirectiveLoc);

595 bool parseDirectiveCFISections();

596 bool parseDirectiveCFIStartProc();

597 bool parseDirectiveCFIEndProc();

598 bool parseDirectiveCFIDefCfaOffset(SMLoc DirectiveLoc);

599 bool parseDirectiveCFIDefCfa(SMLoc DirectiveLoc);

600 bool parseDirectiveCFIAdjustCfaOffset(SMLoc DirectiveLoc);

601 bool parseDirectiveCFIDefCfaRegister(SMLoc DirectiveLoc);

602 bool parseDirectiveCFILLVMDefAspaceCfa(SMLoc DirectiveLoc);

603 bool parseDirectiveCFIOffset(SMLoc DirectiveLoc);

604 bool parseDirectiveCFIRelOffset(SMLoc DirectiveLoc);

605 bool parseDirectiveCFIPersonalityOrLsda(bool IsPersonality);

606 bool parseDirectiveCFIRememberState(SMLoc DirectiveLoc);

607 bool parseDirectiveCFIRestoreState(SMLoc DirectiveLoc);

608 bool parseDirectiveCFISameValue(SMLoc DirectiveLoc);

609 bool parseDirectiveCFIRestore(SMLoc DirectiveLoc);

610 bool parseDirectiveCFIEscape(SMLoc DirectiveLoc);

611 bool parseDirectiveCFIReturnColumn(SMLoc DirectiveLoc);

612 bool parseDirectiveCFISignalFrame(SMLoc DirectiveLoc);

613 bool parseDirectiveCFIUndefined(SMLoc DirectiveLoc);

614 bool parseDirectiveCFILabel(SMLoc DirectiveLoc);

615 bool parseDirectiveCFIValOffset(SMLoc DirectiveLoc);

616

617

618 bool parseDirectivePurgeMacro(SMLoc DirectiveLoc);

619 bool parseDirectiveExitMacro(StringRef Directive);

620 bool parseDirectiveEndMacro(StringRef Directive);

621 bool parseDirectiveMacro(SMLoc DirectiveLoc);

622 bool parseDirectiveMacrosOnOff(StringRef Directive);

623

624 bool parseDirectiveAltmacro(StringRef Directive);

625

626

627 bool parseDirectiveSpace(StringRef IDVal);

628

629

630 bool parseDirectiveDCB(StringRef IDVal, unsigned Size);

631 bool parseDirectiveRealDCB(StringRef IDVal, const fltSemantics &);

632

633 bool parseDirectiveDS(StringRef IDVal, unsigned Size);

634

635

636 bool parseDirectiveLEB128(bool Signed);

637

638

639

640 bool parseDirectiveSymbolAttribute(MCSymbolAttr Attr);

641

642 bool parseDirectiveComm(bool IsLocal);

643

644 bool parseDirectiveAbort(SMLoc DirectiveLoc);

645 bool parseDirectiveInclude();

646 bool parseDirectiveIncbin();

647

648

649 bool parseDirectiveIf(SMLoc DirectiveLoc, DirectiveKind DirKind);

650

651 bool parseDirectiveIfb(SMLoc DirectiveLoc, bool ExpectBlank);

652

653 bool parseDirectiveIfc(SMLoc DirectiveLoc, bool ExpectEqual);

654

655 bool parseDirectiveIfeqs(SMLoc DirectiveLoc, bool ExpectEqual);

656

657 bool parseDirectiveIfdef(SMLoc DirectiveLoc, bool expect_defined);

658 bool parseDirectiveElseIf(SMLoc DirectiveLoc);

659 bool parseDirectiveElse(SMLoc DirectiveLoc);

660 bool parseDirectiveEndIf(SMLoc DirectiveLoc);

661 bool parseEscapedString(std::string &Data) override;

662 bool parseAngleBracketString(std::string &Data) override;

663

664

665 MCAsmMacro *parseMacroLikeBody(SMLoc DirectiveLoc);

666 void instantiateMacroLikeBody(MCAsmMacro *M, SMLoc DirectiveLoc,

667 raw_svector_ostream &OS);

668 bool parseDirectiveRept(SMLoc DirectiveLoc, StringRef Directive);

669 bool parseDirectiveIrp(SMLoc DirectiveLoc);

670 bool parseDirectiveIrpc(SMLoc DirectiveLoc);

671 bool parseDirectiveEndr(SMLoc DirectiveLoc);

672

673

674 bool parseDirectiveMSEmit(SMLoc DirectiveLoc, ParseStatementInfo &Info,

675 size_t Len);

676

677

678 bool parseDirectiveMSAlign(SMLoc DirectiveLoc, ParseStatementInfo &Info);

679

680

681 bool parseDirectiveEnd(SMLoc DirectiveLoc);

682

683

684 bool parseDirectiveError(SMLoc DirectiveLoc, bool WithMessage);

685

686

687 bool parseDirectiveWarning(SMLoc DirectiveLoc);

688

689

690 bool parseDirectivePrint(SMLoc DirectiveLoc);

691

692

693 bool parseDirectivePseudoProbe();

694

695

696 bool parseDirectiveLTODiscard();

697

698

699 bool parseDirectiveAddrsig();

700 bool parseDirectiveAddrsigSym();

701

702 void initializeDirectiveKindMap();

703 void initializeCVDefRangeTypeMap();

704};

705

706class HLASMAsmParser final : public AsmParser {

707private:

708 AsmLexer &Lexer;

709 MCStreamer &Out;

710

711 void lexLeadingSpaces() {

713 Lexer.Lex();

714 }

715

716 bool parseAsHLASMLabel(ParseStatementInfo &Info, MCAsmParserSemaCallback *SI);

717 bool parseAsMachineInstruction(ParseStatementInfo &Info,

718 MCAsmParserSemaCallback *SI);

719

720public:

721 HLASMAsmParser(SourceMgr &SM, MCContext &Ctx, MCStreamer &Out,

722 const MCAsmInfo &MAI, unsigned CB = 0)

723 : AsmParser(SM, Ctx, Out, MAI, CB), Lexer(getLexer()), Out(Out) {

724 Lexer.setSkipSpace(false);

725 Lexer.setAllowHashInIdentifier(true);

726 Lexer.setLexHLASMIntegers(true);

727 Lexer.setLexHLASMStrings(true);

728 }

729

730 ~HLASMAsmParser() override { Lexer.setSkipSpace(true); }

731

732 bool parseStatement(ParseStatementInfo &Info,

733 MCAsmParserSemaCallback *SI) override;

734};

735

736}

737

738namespace llvm {

739

741

742}

743

745 const MCAsmInfo &MAI, unsigned CB = 0)

746 : MCAsmParser(Ctx, Out, SM, MAI), CurBuffer(CB ? CB : SM.getMainFileID()),

747 MacrosEnabledFlag(true) {

748 HadError = false;

749

750 SavedDiagHandler = SrcMgr.getDiagHandler();

751 SavedDiagContext = SrcMgr.getDiagContext();

752

754 Lexer.setBuffer(SrcMgr.getMemoryBuffer(CurBuffer)->getBuffer());

755

757

758

759 switch (Ctx.getObjectFileType()) {

760 case MCContext::IsCOFF:

761 PlatformParser.reset(createCOFFAsmParser());

762 break;

763 case MCContext::IsMachO:

764 PlatformParser.reset(createDarwinAsmParser());

765 IsDarwin = true;

766 break;

767 case MCContext::IsELF:

768 PlatformParser.reset(createELFAsmParser());

769 break;

770 case MCContext::IsGOFF:

771 PlatformParser.reset(createGOFFAsmParser());

772 break;

773 case MCContext::IsSPIRV:

774 report_fatal_error(

775 "Need to implement createSPIRVAsmParser for SPIRV format.");

776 break;

777 case MCContext::IsWasm:

778 PlatformParser.reset(createWasmAsmParser());

779 break;

780 case MCContext::IsXCOFF:

781 PlatformParser.reset(createXCOFFAsmParser());

782 break;

783 case MCContext::IsDXContainer:

784 report_fatal_error("DXContainer is not supported yet");

785 break;

786 }

787

788 PlatformParser->Initialize(*this);

789 initializeDirectiveKindMap();

790 initializeCVDefRangeTypeMap();

791}

792

793AsmParser::~AsmParser() {

794 assert((HadError || ActiveMacros.empty()) &&

795 "Unexpected active macro instantiation!");

796

797

799

800

802}

803

804void AsmParser::printMacroInstantiations() {

805

806 for (MacroInstantiation *M : reverse(ActiveMacros))

808 "while in macro instantiation");

809}

810

811void AsmParser::Note(SMLoc L, const Twine &Msg, SMRange Range) {

812 printPendingErrors();

814 printMacroInstantiations();

815}

816

817bool AsmParser::Warning(SMLoc L, const Twine &Msg, SMRange Range) {

818 if(getTargetParser().getTargetOptions().MCNoWarn)

819 return false;

820 if (getTargetParser().getTargetOptions().MCFatalWarnings)

823 printMacroInstantiations();

824 return false;

825}

826

827bool AsmParser::printError(SMLoc L, const Twine &Msg, SMRange Range) {

828 HadError = true;

830 printMacroInstantiations();

831 return true;

832}

833

834bool AsmParser::enterIncludeFile(const std::string &Filename) {

835 std::string IncludedFile;

836 unsigned NewBuf =

838 if (!NewBuf)

839 return true;

840

841 CurBuffer = NewBuf;

843 return false;

844}

845

846

847

848

849bool AsmParser::processIncbinFile(const std::string &Filename, int64_t Skip,

850 const MCExpr *Count, SMLoc Loc) {

851 std::string IncludedFile;

852 unsigned NewBuf =

854 if (!NewBuf)

855 return true;

856

857

861 int64_t Res;

862 if (Count->evaluateAsAbsolute(Res, getStreamer().getAssemblerPtr()))

863 return Error(Loc, "expected absolute expression");

864 if (Res < 0)

865 return Warning(Loc, "negative count has no effect");

867 }

868 getStreamer().emitBytes(Bytes);

869 return false;

870}

871

872void AsmParser::jumpToLoc(SMLoc Loc, unsigned InBuffer) {

876}

877

878const AsmToken &AsmParser::Lex() {

881

882

884

885 if (!getTok().getString().empty() && getTok().getString().front() != '\n' &&

888 }

889

890 const AsmToken *tok = &Lexer.Lex();

891

892

896 tok = &Lexer.Lex();

897 }

898

900

901

903 if (ParentIncludeLoc != SMLoc()) {

904 jumpToLoc(ParentIncludeLoc);

905 return Lex();

906 }

907 }

908

909 return *tok;

910}

911

912bool AsmParser::enabledGenDwarfForAssembly() {

913

914 if (getContext().getGenDwarfForAssembly())

915 return false;

916

917

918

919 if (getContext().getGenDwarfFileNumber() == 0) {

920 const MCDwarfFile &RootFile =

921 getContext().getMCDwarfLineTable(0).getRootFile();

922 getContext().setGenDwarfFileNumber(getStreamer().emitDwarfFileDirective(

923 0, getContext().getCompilationDir(), RootFile.Name,

925 }

926 return true;

927}

928

929bool AsmParser::Run(bool NoInitialTextSection, bool NoFinalize) {

930 LTODiscardSymbols.clear();

931

932

933 if (!NoInitialTextSection)

934 Out.initSections(false, getTargetParser().getSTI());

935

936

937 Lex();

938

939 HadError = false;

940 AsmCond StartingCondState = TheCondState;

942

943

944

945

946

947 if (getContext().getGenDwarfForAssembly()) {

948 MCSection *Sec = getStreamer().getCurrentSectionOnly();

951 getStreamer().emitLabel(SectionStartSym);

953 }

954 bool InsertResult = getContext().addGenDwarfSection(Sec);

955 assert(InsertResult && ".text section should not have debug info yet");

956 (void)InsertResult;

957 }

958

959 getTargetParser().onBeginOfFile();

960

961

963 ParseStatementInfo Info(&AsmStrRewrites);

964 bool HasError = parseStatement(Info, nullptr);

965

966

967

968

970 Lex();

971

972

973 printPendingErrors();

974

975

976 if (HasError && !getLexer().justConsumedEOL())

977 eatToEndOfStatement();

978 }

979

980 getTargetParser().onEndOfFile();

981 printPendingErrors();

982

983

984 assert(!hasPendingError() && "unexpected error from parseStatement");

985

986 if (TheCondState.TheCond != StartingCondState.TheCond ||

987 TheCondState.Ignore != StartingCondState.Ignore)

988 printError(getTok().getLoc(), "unmatched .ifs or .elses");

989

990 const auto &LineTables = getContext().getMCDwarfLineTables();

991 if (!LineTables.empty()) {

992 unsigned Index = 0;

993 for (const auto &File : LineTables.begin()->second.getMCDwarfFiles()) {

994 if (File.Name.empty() && Index != 0)

995 printError(getTok().getLoc(), "unassigned file number: " +

996 Twine(Index) +

997 " for .file directives");

999 }

1000 }

1001

1002

1003

1004

1005

1006 if (!NoFinalize) {

1009 MCSymbol *Sym = TableEntry.getValue().Symbol;

1010

1011

1012

1015

1016

1017

1018 printError(getTok().getLoc(), "assembler local symbol '" +

1019 Sym->getName() + "' not defined");

1020 }

1021 }

1022

1023

1024

1025 for (std::tuple<SMLoc, CppHashInfoTy, MCSymbol *> &LocSym : DirLabels) {

1026 if (std::get<2>(LocSym)->isUndefined()) {

1027

1028

1029 CppHashInfo = std::get<1>(LocSym);

1030 printError(std::get<0>(LocSym), "directional label undefined");

1031 }

1032 }

1033 }

1034

1035

1036 if (!HadError && !NoFinalize) {

1038 TS->emitConstantPools();

1039

1041 }

1042

1043 return HadError || getContext().hadError();

1044}

1045

1046bool AsmParser::checkForValidSection() {

1047 if (!ParsingMSInlineAsm && !getStreamer().getCurrentFragment()) {

1048 Out.initSections(false, getTargetParser().getSTI());

1049 return Error(getTok().getLoc(),

1050 "expected section directive before assembly directive");

1051 }

1052 return false;

1053}

1054

1055

1056void AsmParser::eatToEndOfStatement() {

1058 Lexer.Lex();

1059

1060

1062 Lexer.Lex();

1063}

1064

1065StringRef AsmParser::parseStringToEndOfStatement() {

1066 const char *Start = getTok().getLoc().getPointer();

1067

1069 Lexer.Lex();

1070

1072 return StringRef(Start, End - Start);

1073}

1074

1075StringRef AsmParser::parseStringToComma() {

1076 const char *Start = getTok().getLoc().getPointer();

1077

1080 Lexer.Lex();

1081

1082 const char *End = getTok().getLoc().getPointer();

1083 return StringRef(Start, End - Start);

1084}

1085

1086

1087

1088

1089

1090

1091bool AsmParser::parseParenExpr(const MCExpr *&Res, SMLoc &EndLoc) {

1092 if (parseExpression(Res))

1093 return true;

1095 return parseRParen();

1096}

1097

1098

1099

1100

1101

1102

1103bool AsmParser::parseBracketExpr(const MCExpr *&Res, SMLoc &EndLoc) {

1104 if (parseExpression(Res))

1105 return true;

1106 EndLoc = getTok().getEndLoc();

1107 if (parseToken(AsmToken::RBrac, "expected ']' in brackets expression"))

1108 return true;

1109 return false;

1110}

1111

1112

1113

1114

1115

1116

1117

1118bool AsmParser::parsePrimaryExpr(const MCExpr *&Res, SMLoc &EndLoc,

1119 AsmTypeInfo *TypeInfo) {

1120 SMLoc FirstTokenLoc = getLexer().getLoc();

1122 switch (FirstTokenKind) {

1123 default:

1124 return TokError("unknown token in expression");

1125

1127 return true;

1129 Lex();

1130 if (parsePrimaryExpr(Res, EndLoc, TypeInfo))

1131 return true;

1133 return false;

1140 if (parseIdentifier(Identifier)) {

1141

1142

1144 bool ShouldGenerateTempSymbol = false;

1147 ShouldGenerateTempSymbol = true;

1148

1149 if (!ShouldGenerateTempSymbol)

1150 return Error(FirstTokenLoc, "invalid token in expression");

1151

1152

1153 Lex();

1154

1155

1159 EndLoc = FirstTokenLoc;

1160 return false;

1161 }

1162 }

1163

1164 std::pair<StringRef, StringRef> Split;

1168 Lex();

1169 SMLoc AtLoc = getLexer().getLoc();

1170 StringRef VName;

1171 if (parseIdentifier(VName))

1172 return Error(AtLoc, "expected symbol variant after '@'");

1173

1174 Split = std::make_pair(Identifier, VName);

1175 }

1178 }

1181 StringRef VName;

1182 parseIdentifier(VName);

1183 if (parseRParen())

1184 return true;

1185 Split = std::make_pair(Identifier, VName);

1186 }

1187

1189

1190

1193 return Error(getLexer().getLoc(), "expected a symbol reference");

1194

1195

1196 uint16_t Spec = 0;

1197 if (Split.second.empty()) {

1199 if (MaybeSpecifier) {

1201 Spec = *MaybeSpecifier;

1204 "invalid variant '" + Split.second + "'");

1205 }

1206 }

1207

1209 if (!Sym)

1211 : SymbolName);

1212

1213

1214

1219 DoInline = TV->inlineAssignedExpr();

1220 if (DoInline) {

1221 if (Spec)

1222 return Error(EndLoc, "unexpected modifier on variable reference");

1224 return false;

1225 }

1226 }

1227

1228

1230 return false;

1231 }

1233 return TokError("literal value out of range for directive");

1235 SMLoc Loc = getTok().getLoc();

1236 int64_t IntVal = getTok().getIntVal();

1239 Lex();

1240

1242 StringRef IDVal = getTok().getString();

1243

1244 std::pair<StringRef, StringRef> Split = IDVal.split('@');

1245 uint16_t Spec = 0;

1246 if (Split.first.size() != IDVal.size()) {

1248 if (!MaybeSpec)

1249 return TokError("invalid variant '" + Split.second + "'");

1250 IDVal = Split.first;

1251 Spec = *MaybeSpec;

1252 }

1253 if (IDVal == "f" || IDVal == "b") {

1258 return Error(Loc, "directional label undefined");

1259 DirLabels.push_back(std::make_tuple(Loc, CppHashInfo, Sym));

1261 Lex();

1262 }

1263 }

1264 return false;

1265 }

1267 APFloat RealVal(APFloat::IEEEdouble(), getTok().getString());

1268 uint64_t IntVal = RealVal.bitcastToAPInt().getZExtValue();

1271 Lex();

1272 return false;

1273 }

1276 return TokError("cannot use . as current PC");

1277

1278

1279

1284 Lex();

1285 return false;

1286 }

1288 Lex();

1289 return parseParenExpr(Res, EndLoc);

1291 if (!PlatformParser->HasBracketExpressions())

1292 return TokError("brackets expression not supported on this target");

1293 Lex();

1294 return parseBracketExpr(Res, EndLoc);

1296 Lex();

1297 if (parsePrimaryExpr(Res, EndLoc, TypeInfo))

1298 return true;

1300 return false;

1302 Lex();

1303 if (parsePrimaryExpr(Res, EndLoc, TypeInfo))

1304 return true;

1306 return false;

1308 Lex();

1309 if (parsePrimaryExpr(Res, EndLoc, TypeInfo))

1310 return true;

1312 return false;

1313 }

1314}

1315

1316bool AsmParser::parseExpression(const MCExpr *&Res) {

1317 SMLoc EndLoc;

1318 return parseExpression(Res, EndLoc);

1319}

1320

1322

1324 if (NewE)

1325 return NewE;

1326

1327

1328 switch (E->getKind()) {

1330 llvm_unreachable("cannot apply another specifier to MCSpecifierExpr");

1333 return nullptr;

1334

1337

1339 TokError("invalid variant on expression '" + getTok().getIdentifier() +

1340 "' (already modified)");

1341 return E;

1342 }

1343

1346 }

1347

1351 if (Sub)

1352 return nullptr;

1355 }

1356

1361

1362 if (!LHS && !RHS)

1363 return nullptr;

1364

1365 if (!LHS)

1367 if (!RHS)

1369

1372 }

1373 }

1374

1376}

1377

1378

1379

1380

1381

1382

1383

1384

1385

1386

1387

1388

1391 "Argument to the function cannot be a NULL value");

1392 const char *CharPtr = StrLoc.getPointer();

1393 while ((*CharPtr != '>') && (*CharPtr != '\n') && (*CharPtr != '\r') &&

1394 (*CharPtr != '\0')) {

1395 if (*CharPtr == '!')

1396 CharPtr++;

1397 CharPtr++;

1398 }

1399 if (*CharPtr == '>') {

1401 return true;

1402 }

1403 return false;

1404}

1405

1406

1408 std::string Res;

1409 for (size_t Pos = 0; Pos < AltMacroStr.size(); Pos++) {

1410 if (AltMacroStr[Pos] == '!')

1411 Pos++;

1412 Res += AltMacroStr[Pos];

1413 }

1414 return Res;

1415}

1416

1420 return TokError("expected specifier following '@'");

1421

1422 auto Spec = MAI.getSpecifierForName(getTok().getIdentifier());

1424 return TokError("invalid specifier '@" + getTok().getIdentifier() + "'");

1425

1427 if (ModifiedRes)

1428 Res = ModifiedRes;

1430 }

1431 return false;

1432}

1433

1434

1435

1436

1437

1438

1439

1440

1441

1442

1443

1444bool AsmParser::parseExpression(const MCExpr *&Res, SMLoc &EndLoc) {

1445

1446 Res = nullptr;

1447 auto &TS = getTargetParser();

1448 if (TS.parsePrimaryExpr(Res, EndLoc) || parseBinOpRHS(1, Res, EndLoc))

1449 return true;

1450

1451

1452

1453

1456 return TokError("unexpected symbol modifier following '@'");

1457

1460 return TokError("invalid variant '" + getTok().getIdentifier() + "'");

1461

1462 const MCExpr *ModifiedRes = applySpecifier(Res, *Spec);

1463 if (!ModifiedRes) {

1464 return TokError("invalid modifier '" + getTok().getIdentifier() +

1465 "' (no symbols present)");

1466 }

1467

1468 Res = ModifiedRes;

1469 Lex();

1470 }

1471

1472

1473

1475 if (Res->evaluateAsAbsolute(Value))

1477

1478 return false;

1479}

1480

1481bool AsmParser::parseParenExpression(const MCExpr *&Res, SMLoc &EndLoc) {

1482 Res = nullptr;

1483 return parseParenExpr(Res, EndLoc) || parseBinOpRHS(1, Res, EndLoc);

1484}

1485

1486bool AsmParser::parseAbsoluteExpression(int64_t &Res) {

1487 const MCExpr *Expr;

1488

1489 SMLoc StartLoc = Lexer.getLoc();

1490 if (parseExpression(Expr))

1491 return true;

1492

1493 if (!Expr->evaluateAsAbsolute(Res, getStreamer().getAssemblerPtr()))

1494 return Error(StartLoc, "expected absolute expression");

1495

1496 return false;

1497}

1498

1501 bool ShouldUseLogicalShr) {

1502 switch (K) {

1503 default:

1504 return 0;

1505

1506

1509 return 1;

1512 return 1;

1513

1514

1517 return 2;

1520 return 2;

1523 return 2;

1524

1525

1528 return 3;

1532 return 3;

1535 return 3;

1538 return 3;

1541 return 3;

1544 return 3;

1545

1546

1549 return 4;

1552 return 4;

1553

1554

1557 return 5;

1560 return 5;

1561

1562

1565 return 6;

1568 return 6;

1571 return 6;

1572 }

1573}

1574

1578 bool ShouldUseLogicalShr) {

1579 switch (K) {

1580 default:

1581 return 0;

1582

1583

1586 return 2;

1589 return 1;

1590

1591

1594 return 3;

1598 return 3;

1601 return 3;

1604 return 3;

1607 return 3;

1610 return 3;

1611

1612

1615 return 4;

1618 return 4;

1619

1620

1621

1624 return 5;

1626

1627

1629 return 0;

1631 return 5;

1634 return 5;

1637 return 5;

1638

1639

1642 return 6;

1645 return 6;

1648 return 6;

1651 return 6;

1654 return 6;

1655 }

1656}

1657

1663}

1664

1665

1666

1667bool AsmParser::parseBinOpRHS(unsigned Precedence, const MCExpr *&Res,

1668 SMLoc &EndLoc) {

1669 SMLoc StartLoc = Lexer.getLoc();

1670 while (true) {

1672 unsigned TokPrec = getBinOpPrecedence(Lexer.getKind(), Kind);

1673

1674

1675

1676 if (TokPrec < Precedence)

1677 return false;

1678

1679 Lex();

1680

1681

1682 const MCExpr *RHS;

1683 if (getTargetParser().parsePrimaryExpr(RHS, EndLoc))

1684 return true;

1685

1686

1687

1689 unsigned NextTokPrec = getBinOpPrecedence(Lexer.getKind(), Dummy);

1690 if (TokPrec < NextTokPrec && parseBinOpRHS(TokPrec + 1, RHS, EndLoc))

1691 return true;

1692

1693

1695 }

1696}

1697

1698

1699

1700

1701

1702bool AsmParser::parseStatement(ParseStatementInfo &Info,

1703 MCAsmParserSemaCallback *SI) {

1704 assert(!hasPendingError() && "parseStatement started with pending error");

1705

1707 Lex();

1709

1710 if (getTok().getString().empty() || getTok().getString().front() == '\r' ||

1711 getTok().getString().front() == '\n')

1713 Lex();

1714 return false;

1715 }

1716

1717 AsmToken ID = getTok();

1718 SMLoc IDLoc = ID.getLoc();

1719 StringRef IDVal;

1720 int64_t LocalLabelVal = -1;

1721 StartTokLoc = ID.getLoc();

1723 return parseCppHashLineFilenameComment(IDLoc,

1724 !isInsideMacroInstantiation());

1725

1726

1728 LocalLabelVal = getTok().getIntVal();

1729 if (LocalLabelVal < 0) {

1730 if (!TheCondState.Ignore) {

1731 Lex();

1732 return Error(IDLoc, "unexpected token at start of statement");

1733 }

1734 IDVal = "";

1735 } else {

1736 IDVal = getTok().getString();

1737 Lex();

1739 if (!TheCondState.Ignore) {

1740 Lex();

1741 return Error(IDLoc, "unexpected token at start of statement");

1742 }

1743 }

1744 }

1746

1747 Lex();

1748 IDVal = ".";

1749 } else if (getTargetParser().tokenIsStartOfStatement(ID.getKind())) {

1750 Lex();

1751 IDVal = ID.getString();

1752 } else if (parseIdentifier(IDVal)) {

1753 if (!TheCondState.Ignore) {

1754 Lex();

1755 return Error(IDLoc, "unexpected token at start of statement");

1756 }

1757 IDVal = "";

1758 }

1759

1760

1761

1762

1764 DirectiveKindMap.find(IDVal.lower());

1765 DirectiveKind DirKind = (DirKindIt == DirectiveKindMap.end())

1766 ? DK_NO_DIRECTIVE

1767 : DirKindIt->getValue();

1768 switch (DirKind) {

1769 default:

1770 break;

1771 case DK_IF:

1772 case DK_IFEQ:

1773 case DK_IFGE:

1774 case DK_IFGT:

1775 case DK_IFLE:

1776 case DK_IFLT:

1777 case DK_IFNE:

1778 return parseDirectiveIf(IDLoc, DirKind);

1779 case DK_IFB:

1780 return parseDirectiveIfb(IDLoc, true);

1781 case DK_IFNB:

1782 return parseDirectiveIfb(IDLoc, false);

1783 case DK_IFC:

1784 return parseDirectiveIfc(IDLoc, true);

1785 case DK_IFEQS:

1786 return parseDirectiveIfeqs(IDLoc, true);

1787 case DK_IFNC:

1788 return parseDirectiveIfc(IDLoc, false);

1789 case DK_IFNES:

1790 return parseDirectiveIfeqs(IDLoc, false);

1791 case DK_IFDEF:

1792 return parseDirectiveIfdef(IDLoc, true);

1793 case DK_IFNDEF:

1794 case DK_IFNOTDEF:

1795 return parseDirectiveIfdef(IDLoc, false);

1796 case DK_ELSEIF:

1797 return parseDirectiveElseIf(IDLoc);

1798 case DK_ELSE:

1799 return parseDirectiveElse(IDLoc);

1800 case DK_ENDIF:

1801 return parseDirectiveEndIf(IDLoc);

1802 }

1803

1804

1805

1806 if (TheCondState.Ignore) {

1807 eatToEndOfStatement();

1808 return false;

1809 }

1810

1811

1812

1813

1814

1815

1817 if (checkForValidSection())

1818 return true;

1819

1820 Lex();

1821

1822

1823 if (IDVal == ".")

1824 return Error(IDLoc, "invalid use of pseudo-symbol '.' as a label");

1825

1826

1827

1828

1829

1830

1832 if (LocalLabelVal == -1) {

1833 if (ParsingMSInlineAsm && SI) {

1834 StringRef RewrittenLabel =

1835 SI->LookupInlineAsmLabel(IDVal, getSourceManager(), IDLoc, true);

1837 "We should have an internal name here.");

1839 RewrittenLabel);

1840 IDVal = RewrittenLabel;

1841 }

1842 Sym = getContext().parseSymbol(IDVal);

1843 } else

1845

1846

1847

1848

1850 StringRef CommentStr = parseStringToEndOfStatement();

1851 Lexer.Lex();

1853 }

1854

1855

1856

1858 Lex();

1859 }

1860

1861 if (MAI.isMachO() && CFIStartProcLoc) {

1862 auto *SymM = static_cast<MCSymbolMachO *>(Sym);

1863 if (SymM->isExternal() && !SymM->isAltEntry())

1864 return Error(StartTokLoc, "non-private labels cannot appear between "

1865 ".cfi_startproc / .cfi_endproc pairs") &&

1866 Error(*CFIStartProcLoc, "previous .cfi_startproc was here");

1867 }

1868

1869 if (discardLTOSymbol(IDVal))

1870 return false;

1871

1872 getTargetParser().doBeforeLabelEmit(Sym, IDLoc);

1873

1874

1875 if (!getTargetParser().isParsingMSInlineAsm())

1877

1878

1879

1880 if (enabledGenDwarfForAssembly())

1882 IDLoc);

1883

1884 getTargetParser().onLabelParsed(Sym);

1885

1886 return false;

1887 }

1888

1889

1890

1891 if (Lexer.is(AsmToken::Equal) && getTargetParser().equalIsAsmAssignment()) {

1892 Lex();

1893 return parseAssignment(IDVal, AssignmentKind::Equal);

1894 }

1895

1896

1897 if (areMacrosEnabled())

1898 if (MCAsmMacro *M = getContext().lookupMacro(IDVal))

1899 return handleMacroEntry(M, IDLoc);

1900

1901

1902

1903

1904 if (IDVal.starts_with(".") && IDVal != ".") {

1905

1906

1907

1908

1909

1910

1911

1912

1913

1914

1915

1916 getTargetParser().flushPendingInstructions(getStreamer());

1917

1918 ParseStatus TPDirectiveReturn = getTargetParser().parseDirective(ID);

1919 assert(TPDirectiveReturn.isFailure() == hasPendingError() &&

1920 "Should only return Failure iff there was an error");

1921 if (TPDirectiveReturn.isFailure())

1922 return true;

1923 if (TPDirectiveReturn.isSuccess())

1924 return false;

1925

1926

1927

1928 std::pair<MCAsmParserExtension *, DirectiveHandler> Handler =

1929 ExtensionDirectiveMap.lookup(IDVal);

1930 if (Handler.first)

1931 return (*Handler.second)(Handler.first, IDVal, IDLoc);

1932

1933

1934

1935 switch (DirKind) {

1936 default:

1937 break;

1938 case DK_SET:

1939 case DK_EQU:

1940 return parseDirectiveSet(IDVal, AssignmentKind::Set);

1941 case DK_EQUIV:

1942 return parseDirectiveSet(IDVal, AssignmentKind::Equiv);

1943 case DK_LTO_SET_CONDITIONAL:

1944 return parseDirectiveSet(IDVal, AssignmentKind::LTOSetConditional);

1945 case DK_ASCII:

1946 return parseDirectiveAscii(IDVal, false);

1947 case DK_ASCIZ:

1948 case DK_STRING:

1949 return parseDirectiveAscii(IDVal, true);

1950 case DK_BASE64:

1951 return parseDirectiveBase64();

1952 case DK_BYTE:

1953 case DK_DC_B:

1954 return parseDirectiveValue(IDVal, 1);

1955 case DK_DC:

1956 case DK_DC_W:

1957 case DK_SHORT:

1958 case DK_VALUE:

1959 case DK_2BYTE:

1960 return parseDirectiveValue(IDVal, 2);

1961 case DK_LONG:

1962 case DK_INT:

1963 case DK_4BYTE:

1964 case DK_DC_L:

1965 return parseDirectiveValue(IDVal, 4);

1966 case DK_QUAD:

1967 case DK_8BYTE:

1968 return parseDirectiveValue(IDVal, 8);

1969 case DK_DC_A:

1970 return parseDirectiveValue(

1971 IDVal, getContext().getAsmInfo()->getCodePointerSize());

1972 case DK_OCTA:

1973 return parseDirectiveOctaValue(IDVal);

1974 case DK_SINGLE:

1975 case DK_FLOAT:

1976 case DK_DC_S:

1977 return parseDirectiveRealValue(IDVal, APFloat::IEEEsingle());

1978 case DK_DOUBLE:

1979 case DK_DC_D:

1980 return parseDirectiveRealValue(IDVal, APFloat::IEEEdouble());

1981 case DK_ALIGN: {

1982 bool IsPow2 = getContext().getAsmInfo()->getAlignmentIsInBytes();

1983 return parseDirectiveAlign(IsPow2, 1);

1984 }

1985 case DK_ALIGN32: {

1986 bool IsPow2 = getContext().getAsmInfo()->getAlignmentIsInBytes();

1987 return parseDirectiveAlign(IsPow2, 4);

1988 }

1989 case DK_BALIGN:

1990 return parseDirectiveAlign(false, 1);

1991 case DK_BALIGNW:

1992 return parseDirectiveAlign(false, 2);

1993 case DK_BALIGNL:

1994 return parseDirectiveAlign(false, 4);

1995 case DK_P2ALIGN:

1996 return parseDirectiveAlign(true, 1);

1997 case DK_P2ALIGNW:

1998 return parseDirectiveAlign(true, 2);

1999 case DK_P2ALIGNL:

2000 return parseDirectiveAlign(true, 4);

2001 case DK_ORG:

2002 return parseDirectiveOrg();

2003 case DK_FILL:

2004 return parseDirectiveFill();

2005 case DK_ZERO:

2006 return parseDirectiveZero();

2007 case DK_EXTERN:

2008 eatToEndOfStatement();

2009 return false;

2010 case DK_GLOBL:

2011 case DK_GLOBAL:

2012 return parseDirectiveSymbolAttribute(MCSA_Global);

2013 case DK_LAZY_REFERENCE:

2015 case DK_NO_DEAD_STRIP:

2017 case DK_SYMBOL_RESOLVER:

2019 case DK_PRIVATE_EXTERN:

2021 case DK_REFERENCE:

2022 return parseDirectiveSymbolAttribute(MCSA_Reference);

2023 case DK_WEAK_DEFINITION:

2025 case DK_WEAK_REFERENCE:

2027 case DK_WEAK_DEF_CAN_BE_HIDDEN:

2029 case DK_COLD:

2030 return parseDirectiveSymbolAttribute(MCSA_Cold);

2031 case DK_COMM:

2032 case DK_COMMON:

2033 return parseDirectiveComm(false);

2034 case DK_LCOMM:

2035 return parseDirectiveComm(true);

2036 case DK_ABORT:

2037 return parseDirectiveAbort(IDLoc);

2038 case DK_INCLUDE:

2039 return parseDirectiveInclude();

2040 case DK_INCBIN:

2041 return parseDirectiveIncbin();

2042 case DK_CODE16:

2043 case DK_CODE16GCC:

2044 return TokError(Twine(IDVal) +

2045 " not currently supported for this target");

2046 case DK_REPT:

2047 return parseDirectiveRept(IDLoc, IDVal);

2048 case DK_IRP:

2049 return parseDirectiveIrp(IDLoc);

2050 case DK_IRPC:

2051 return parseDirectiveIrpc(IDLoc);

2052 case DK_ENDR:

2053 return parseDirectiveEndr(IDLoc);

2054 case DK_SLEB128:

2055 return parseDirectiveLEB128(true);

2056 case DK_ULEB128:

2057 return parseDirectiveLEB128(false);

2058 case DK_SPACE:

2059 case DK_SKIP:

2060 return parseDirectiveSpace(IDVal);

2061 case DK_FILE:

2062 return parseDirectiveFile(IDLoc);

2063 case DK_LINE:

2064 return parseDirectiveLine();

2065 case DK_LOC:

2066 return parseDirectiveLoc();

2067 case DK_LOC_LABEL:

2068 return parseDirectiveLocLabel(IDLoc);

2069 case DK_STABS:

2070 return parseDirectiveStabs();

2071 case DK_CV_FILE:

2072 return parseDirectiveCVFile();

2073 case DK_CV_FUNC_ID:

2074 return parseDirectiveCVFuncId();

2075 case DK_CV_INLINE_SITE_ID:

2076 return parseDirectiveCVInlineSiteId();

2077 case DK_CV_LOC:

2078 return parseDirectiveCVLoc();

2079 case DK_CV_LINETABLE:

2080 return parseDirectiveCVLinetable();

2081 case DK_CV_INLINE_LINETABLE:

2082 return parseDirectiveCVInlineLinetable();

2083 case DK_CV_DEF_RANGE:

2084 return parseDirectiveCVDefRange();

2085 case DK_CV_STRING:

2086 return parseDirectiveCVString();

2087 case DK_CV_STRINGTABLE:

2088 return parseDirectiveCVStringTable();

2089 case DK_CV_FILECHECKSUMS:

2090 return parseDirectiveCVFileChecksums();

2091 case DK_CV_FILECHECKSUM_OFFSET:

2092 return parseDirectiveCVFileChecksumOffset();

2093 case DK_CV_FPO_DATA:

2094 return parseDirectiveCVFPOData();

2095 case DK_CFI_SECTIONS:

2096 return parseDirectiveCFISections();

2097 case DK_CFI_STARTPROC:

2098 return parseDirectiveCFIStartProc();

2099 case DK_CFI_ENDPROC:

2100 return parseDirectiveCFIEndProc();

2101 case DK_CFI_DEF_CFA:

2102 return parseDirectiveCFIDefCfa(IDLoc);

2103 case DK_CFI_DEF_CFA_OFFSET:

2104 return parseDirectiveCFIDefCfaOffset(IDLoc);

2105 case DK_CFI_ADJUST_CFA_OFFSET:

2106 return parseDirectiveCFIAdjustCfaOffset(IDLoc);

2107 case DK_CFI_DEF_CFA_REGISTER:

2108 return parseDirectiveCFIDefCfaRegister(IDLoc);

2109 case DK_CFI_LLVM_DEF_ASPACE_CFA:

2110 return parseDirectiveCFILLVMDefAspaceCfa(IDLoc);

2111 case DK_CFI_OFFSET:

2112 return parseDirectiveCFIOffset(IDLoc);

2113 case DK_CFI_REL_OFFSET:

2114 return parseDirectiveCFIRelOffset(IDLoc);

2115 case DK_CFI_PERSONALITY:

2116 return parseDirectiveCFIPersonalityOrLsda(true);

2117 case DK_CFI_LSDA:

2118 return parseDirectiveCFIPersonalityOrLsda(false);

2119 case DK_CFI_REMEMBER_STATE:

2120 return parseDirectiveCFIRememberState(IDLoc);

2121 case DK_CFI_RESTORE_STATE:

2122 return parseDirectiveCFIRestoreState(IDLoc);

2123 case DK_CFI_SAME_VALUE:

2124 return parseDirectiveCFISameValue(IDLoc);

2125 case DK_CFI_RESTORE:

2126 return parseDirectiveCFIRestore(IDLoc);

2127 case DK_CFI_ESCAPE:

2128 return parseDirectiveCFIEscape(IDLoc);

2129 case DK_CFI_RETURN_COLUMN:

2130 return parseDirectiveCFIReturnColumn(IDLoc);

2131 case DK_CFI_SIGNAL_FRAME:

2132 return parseDirectiveCFISignalFrame(IDLoc);

2133 case DK_CFI_UNDEFINED:

2134 return parseDirectiveCFIUndefined(IDLoc);

2135 case DK_CFI_REGISTER:

2136 return parseDirectiveCFIRegister(IDLoc);

2137 case DK_CFI_WINDOW_SAVE:

2138 return parseDirectiveCFIWindowSave(IDLoc);

2139 case DK_CFI_LABEL:

2140 return parseDirectiveCFILabel(IDLoc);

2141 case DK_CFI_VAL_OFFSET:

2142 return parseDirectiveCFIValOffset(IDLoc);

2143 case DK_MACROS_ON:

2144 case DK_MACROS_OFF:

2145 return parseDirectiveMacrosOnOff(IDVal);

2146 case DK_MACRO:

2147 return parseDirectiveMacro(IDLoc);

2148 case DK_ALTMACRO:

2149 case DK_NOALTMACRO:

2150 return parseDirectiveAltmacro(IDVal);

2151 case DK_EXITM:

2152 return parseDirectiveExitMacro(IDVal);

2153 case DK_ENDM:

2154 case DK_ENDMACRO:

2155 return parseDirectiveEndMacro(IDVal);

2156 case DK_PURGEM:

2157 return parseDirectivePurgeMacro(IDLoc);

2158 case DK_END:

2159 return parseDirectiveEnd(IDLoc);

2160 case DK_ERR:

2161 return parseDirectiveError(IDLoc, false);

2162 case DK_ERROR:

2163 return parseDirectiveError(IDLoc, true);

2164 case DK_WARNING:

2165 return parseDirectiveWarning(IDLoc);

2166 case DK_RELOC:

2167 return parseDirectiveReloc(IDLoc);

2168 case DK_DCB:

2169 case DK_DCB_W:

2170 return parseDirectiveDCB(IDVal, 2);

2171 case DK_DCB_B:

2172 return parseDirectiveDCB(IDVal, 1);

2173 case DK_DCB_D:

2174 return parseDirectiveRealDCB(IDVal, APFloat::IEEEdouble());

2175 case DK_DCB_L:

2176 return parseDirectiveDCB(IDVal, 4);

2177 case DK_DCB_S:

2178 return parseDirectiveRealDCB(IDVal, APFloat::IEEEsingle());

2179 case DK_DC_X:

2180 case DK_DCB_X:

2181 return TokError(Twine(IDVal) +

2182 " not currently supported for this target");

2183 case DK_DS:

2184 case DK_DS_W:

2185 return parseDirectiveDS(IDVal, 2);

2186 case DK_DS_B:

2187 return parseDirectiveDS(IDVal, 1);

2188 case DK_DS_D:

2189 return parseDirectiveDS(IDVal, 8);

2190 case DK_DS_L:

2191 case DK_DS_S:

2192 return parseDirectiveDS(IDVal, 4);

2193 case DK_DS_P:

2194 case DK_DS_X:

2195 return parseDirectiveDS(IDVal, 12);

2196 case DK_PRINT:

2197 return parseDirectivePrint(IDLoc);

2198 case DK_ADDRSIG:

2199 return parseDirectiveAddrsig();

2200 case DK_ADDRSIG_SYM:

2201 return parseDirectiveAddrsigSym();

2202 case DK_PSEUDO_PROBE:

2203 return parseDirectivePseudoProbe();

2204 case DK_LTO_DISCARD:

2205 return parseDirectiveLTODiscard();

2206 case DK_MEMTAG:

2207 return parseDirectiveSymbolAttribute(MCSA_Memtag);

2208 }

2209

2210 return Error(IDLoc, "unknown directive");

2211 }

2212

2213

2214 if (ParsingMSInlineAsm && (IDVal == "_emit" || IDVal == "__emit" ||

2215 IDVal == "_EMIT" || IDVal == "__EMIT"))

2216 return parseDirectiveMSEmit(IDLoc, Info, IDVal.size());

2217

2218

2219 if (ParsingMSInlineAsm && (IDVal == "align" || IDVal == "ALIGN"))

2220 return parseDirectiveMSAlign(IDLoc, Info);

2221

2222 if (ParsingMSInlineAsm && (IDVal == "even" || IDVal == "EVEN"))

2223 Info.AsmRewrites->emplace_back(AOK_EVEN, IDLoc, 4);

2224 if (checkForValidSection())

2225 return true;

2226

2227 return parseAndMatchAndEmitTargetInstruction(Info, IDVal, ID, IDLoc);

2228}

2229

2230bool AsmParser::parseAndMatchAndEmitTargetInstruction(ParseStatementInfo &Info,

2231 StringRef IDVal,

2232 AsmToken ID,

2233 SMLoc IDLoc) {

2234

2235 std::string OpcodeStr = IDVal.lower();

2236 ParseInstructionInfo IInfo(Info.AsmRewrites);

2237 bool ParseHadError = getTargetParser().parseInstruction(IInfo, OpcodeStr, ID,

2238 Info.ParsedOperands);

2239 Info.ParseError = ParseHadError;

2240

2241

2242 if (getShowParsedOperands()) {

2243 SmallString<256> Str;

2244 raw_svector_ostream OS(Str);

2245 OS << "parsed instruction: [";

2246 for (unsigned i = 0; i != Info.ParsedOperands.size(); ++i) {

2247 if (i != 0)

2248 OS << ", ";

2249 Info.ParsedOperands[i]->print(OS, MAI);

2250 }

2251 OS << "]";

2252

2254 }

2255

2256

2257 if (hasPendingError() || ParseHadError)

2258 return true;

2259

2260

2261

2262 if (!ParseHadError && enabledGenDwarfForAssembly() &&

2264 getStreamer().getCurrentSectionOnly())) {

2265 unsigned Line;

2266 if (ActiveMacros.empty())

2268 else

2270 ActiveMacros.front()->ExitBuffer);

2271

2272

2273

2274

2275 if (!CppHashInfo.Filename.empty()) {

2276 unsigned FileNumber = getStreamer().emitDwarfFileDirective(

2277 0, StringRef(), CppHashInfo.Filename);

2278 getContext().setGenDwarfFileNumber(FileNumber);

2279

2280 unsigned CppHashLocLineNo =

2282 Line = CppHashInfo.LineNumber - 1 + (Line - CppHashLocLineNo);

2283 }

2284

2285 getStreamer().emitDwarfLocDirective(

2286 getContext().getGenDwarfFileNumber(), Line, 0,

2288 StringRef());

2289 }

2290

2291

2292 if (!ParseHadError) {

2293 uint64_t ErrorInfo;

2294 if (getTargetParser().matchAndEmitInstruction(

2295 IDLoc, Info.Opcode, Info.ParsedOperands, Out, ErrorInfo,

2296 getTargetParser().isParsingMSInlineAsm()))

2297 return true;

2298 }

2299 return false;

2300}

2301

2302

2303bool

2304AsmParser::parseCurlyBlockScope(SmallVectorImpl &AsmStrRewrites) {

2305

2307 return false;

2308

2309 SMLoc StartLoc = Lexer.getLoc();

2310 Lex();

2312 Lex();

2313

2314

2317 return true;

2318}

2319

2320

2321

2322bool AsmParser::parseCppHashLineFilenameComment(SMLoc L, bool SaveLocInfo) {

2323 Lex();

2324

2325

2327 "Lexing Cpp line comment: Expected Integer");

2328 int64_t LineNumber = getTok().getIntVal();

2329 Lex();

2331 "Lexing Cpp line comment: Expected String");

2332 StringRef Filename = getTok().getString();

2333 Lex();

2334

2335 if (!SaveLocInfo)

2336 return false;

2337

2338

2340

2341

2342

2343 CppHashInfo.Loc = L;

2344 CppHashInfo.Filename = Filename;

2345 CppHashInfo.LineNumber = LineNumber;

2346 CppHashInfo.Buf = CurBuffer;

2347 if (!HadCppHashFilename) {

2348 HadCppHashFilename = true;

2349

2350

2351

2352 if (getContext().getGenDwarfForAssembly() &&

2353 getContext().getGenDwarfFileNumber() == 0) {

2354

2355

2356 getContext().setMCLineTableRootFile(

2357 0, getContext().getCompilationDir(), Filename,

2358 std::nullopt, std::nullopt);

2359 }

2360 }

2361 return false;

2362}

2363

2364

2365

2366void AsmParser::DiagHandler(const SMDiagnostic &Diag, void *Context) {

2367 auto *Parser = static_cast<AsmParser *>(Context);

2368 raw_ostream &OS = errs();

2369

2370 const SourceMgr &DiagSrcMgr = *Diag.getSourceMgr();

2371 SMLoc DiagLoc = Diag.getLoc();

2373 unsigned CppHashBuf =

2374 Parser->SrcMgr.FindBufferContainingLoc(Parser->CppHashInfo.Loc);

2375

2376

2377

2379 if (!Parser->SavedDiagHandler && DiagCurBuffer &&

2383 }

2384

2385

2386

2387

2388 if (!Parser->CppHashInfo.LineNumber || DiagBuf != CppHashBuf) {

2389 if (Parser->SavedDiagHandler)

2390 Parser->SavedDiagHandler(Diag, Parser->SavedDiagContext);

2391 else

2392 Parser->getContext().diagnose(Diag);

2393 return;

2394 }

2395

2396

2397

2398

2399 const std::string &Filename = std::string(Parser->CppHashInfo.Filename);

2400

2401 int DiagLocLineNo = DiagSrcMgr.FindLineNumber(DiagLoc, DiagBuf);

2402 int CppHashLocLineNo =

2403 Parser->SrcMgr.FindLineNumber(Parser->CppHashInfo.Loc, CppHashBuf);

2404 int LineNo =

2405 Parser->CppHashInfo.LineNumber - 1 + (DiagLocLineNo - CppHashLocLineNo);

2406

2407 SMDiagnostic NewDiag(*Diag.getSourceMgr(), Diag.getLoc(), Filename, LineNo,

2410

2411 if (Parser->SavedDiagHandler)

2412 Parser->SavedDiagHandler(Diag, Parser->SavedDiagContext);

2413 else

2414 Parser->getContext().diagnose(NewDiag);

2415}

2416

2417

2418

2419

2420

2422 return isalnum(static_cast<unsigned char>(c)) || c == '_' || c == '$' ||

2423 c == '.';

2424}

2425

2426bool AsmParser::expandMacro(raw_svector_ostream &OS, MCAsmMacro &Macro,

2429 bool EnableAtPseudoVariable) {

2430 unsigned NParameters = Parameters.size();

2431 auto expandArg = [&](unsigned Index) {

2432 bool HasVararg = NParameters ? Parameters.back().Vararg : false;

2433 bool VarargParameter = HasVararg && Index == (NParameters - 1);

2434 for (const AsmToken &Token : A[Index])

2435

2436

2437

2438

2439

2440

2441

2442 if (AltMacroMode && Token.getString().front() == '%' &&

2444

2445 OS << Token.getIntVal();

2446

2447

2448 else if (AltMacroMode && Token.getString().front() == '<' &&

2451 }

2452

2453

2455 OS << Token.getString();

2456 else

2457 OS << Token.getStringContents();

2458 };

2459

2460

2461

2462 StringRef Body = Macro.Body;

2463 size_t I = 0, End = Body.size();

2464 while (I != End) {

2465 if (Body[I] == '\\' && I + 1 != End) {

2466

2467 if (EnableAtPseudoVariable && Body[I + 1] == '@') {

2468 OS << NumOfMacroInstantiations;

2469 I += 2;

2470 continue;

2471 }

2472 if (Body[I + 1] == '+') {

2473 OS << Macro.Count;

2474 I += 2;

2475 continue;

2476 }

2477 if (Body[I + 1] == '(' && Body[I + 2] == ')') {

2478 I += 3;

2479 continue;

2480 }

2481

2482 size_t Pos = ++I;

2484 ++I;

2486 if (AltMacroMode && I != End && Body[I] == '&')

2487 ++I;

2488 unsigned Index = 0;

2489 for (; Index < NParameters; ++Index)

2490 if (Parameters[Index].Name == Argument)

2491 break;

2492 if (Index == NParameters)

2494 else

2495 expandArg(Index);

2496 continue;

2497 }

2498

2499

2500

2501 if (Body[I] == '$' && I + 1 != End && IsDarwin && !NParameters) {

2502

2503 switch (Body[I + 1]) {

2504

2505 case '$':

2506 OS << '$';

2507 I += 2;

2508 continue;

2509

2510 case 'n':

2511 OS << A.size();

2512 I += 2;

2513 continue;

2514 default: {

2516 break;

2517

2518

2519 unsigned Index = Body[I + 1] - '0';

2520 if (Index < A.size())

2521 for (const AsmToken &Token : A[Index])

2522 OS << Token.getString();

2523 I += 2;

2524 continue;

2525 }

2526 }

2527 }

2528

2530 OS << Body[I++];

2531 continue;

2532 }

2533

2534 const size_t Start = I;

2536 }

2537 StringRef Token(Body.data() + Start, I - Start);

2538 if (AltMacroMode) {

2539 unsigned Index = 0;

2540 for (; Index != NParameters; ++Index)

2541 if (Parameters[Index].Name == Token)

2542 break;

2543 if (Index != NParameters) {

2544 expandArg(Index);

2545 if (I != End && Body[I] == '&')

2546 ++I;

2547 continue;

2548 }

2549 }

2550 OS << Token;

2551 }

2552

2554 return false;

2555}

2556

2558 switch (kind) {

2559 default:

2560 return false;

2583 return true;

2584 }

2585}

2586

2587namespace {

2588

2589class AsmLexerSkipSpaceRAII {

2590public:

2591 AsmLexerSkipSpaceRAII(AsmLexer &Lexer, bool SkipSpace) : Lexer(Lexer) {

2593 }

2594

2595 ~AsmLexerSkipSpaceRAII() {

2597 }

2598

2599private:

2600 AsmLexer &Lexer;

2601};

2602

2603}

2604

2605bool AsmParser::parseMacroArgument(MCAsmMacroArgument &MA, bool Vararg) {

2606

2607 if (Vararg) {

2609 StringRef Str = parseStringToEndOfStatement();

2611 }

2612 return false;

2613 }

2614

2615 unsigned ParenLevel = 0;

2616

2617

2618 AsmLexerSkipSpaceRAII ScopedSkipSpace(Lexer, IsDarwin);

2619

2620 bool SpaceEaten;

2621

2622 while (true) {

2623 SpaceEaten = false;

2625 return TokError("unexpected token in macro instantiation");

2626

2627 if (ParenLevel == 0) {

2628

2630 break;

2631

2633 SpaceEaten = true;

2634

2635

2636

2637

2638 if (!IsDarwin) {

2640 MA.push_back(getTok());

2641 Lexer.Lex();

2642

2643

2645 continue;

2646 }

2647 }

2648 if (SpaceEaten)

2649 break;

2650 }

2651

2652

2653

2655 break;

2656

2657

2659 ++ParenLevel;

2661 --ParenLevel;

2662

2663

2664 MA.push_back(getTok());

2665 Lexer.Lex();

2666 }

2667

2668 if (ParenLevel != 0)

2669 return TokError("unbalanced parentheses in macro argument");

2670 return false;

2671}

2672

2673

2674bool AsmParser::parseMacroArguments(const MCAsmMacro *M,

2675 MCAsmMacroArguments &A) {

2676 const unsigned NParameters = M ? M->Parameters.size() : 0;

2677 bool NamedParametersFound = false;

2678 SmallVector<SMLoc, 4> FALocs;

2679

2680 A.resize(NParameters);

2681 FALocs.resize(NParameters);

2682

2683

2684

2685

2686 bool HasVararg = NParameters ? M->Parameters.back().Vararg : false;

2687 for (unsigned Parameter = 0; !NParameters || Parameter < NParameters;

2689 SMLoc IDLoc = Lexer.getLoc();

2690 MCAsmMacroParameter FA;

2691

2693 if (parseIdentifier(FA.Name))

2694 return Error(IDLoc, "invalid argument identifier for formal argument");

2695

2697 return TokError("expected '=' after formal parameter identifier");

2698

2699 Lex();

2700

2701 NamedParametersFound = true;

2702 }

2703 bool Vararg = HasVararg && Parameter == (NParameters - 1);

2704

2705 if (NamedParametersFound && FA.Name.empty())

2706 return Error(IDLoc, "cannot mix positional and keyword arguments");

2707

2708 SMLoc StrLoc = Lexer.getLoc();

2709 SMLoc EndLoc;

2711 const MCExpr *AbsoluteExp;

2713

2714 Lex();

2715 if (parseExpression(AbsoluteExp, EndLoc))

2716 return false;

2717 if (!AbsoluteExp->evaluateAsAbsolute(Value,

2718 getStreamer().getAssemblerPtr()))

2719 return Error(StrLoc, "expected absolute expression");

2720 const char *StrChar = StrLoc.getPointer();

2721 const char *EndChar = EndLoc.getPointer();

2723 StringRef(StrChar, EndChar - StrChar), Value);

2724 FA.Value.push_back(newToken);

2727 const char *StrChar = StrLoc.getPointer();

2728 const char *EndChar = EndLoc.getPointer();

2729 jumpToLoc(EndLoc, CurBuffer);

2730

2731 Lex();

2733 StringRef(StrChar, EndChar - StrChar));

2734 FA.Value.push_back(newToken);

2735 } else if(parseMacroArgument(FA.Value, Vararg))

2736 return true;

2737

2740 unsigned FAI = 0;

2741 for (FAI = 0; FAI < NParameters; ++FAI)

2742 if (M->Parameters[FAI].Name == FA.Name)

2743 break;

2744

2745 if (FAI >= NParameters) {

2746 assert(M && "expected macro to be defined");

2747 return Error(IDLoc, "parameter named '" + FA.Name +

2748 "' does not exist for macro '" + M->Name + "'");

2749 }

2750 PI = FAI;

2751 }

2752

2753 if (!FA.Value.empty()) {

2754 if (A.size() <= PI)

2755 A.resize(PI + 1);

2757

2758 if (FALocs.size() <= PI)

2759 FALocs.resize(PI + 1);

2760

2761 FALocs[PI] = Lexer.getLoc();

2762 }

2763

2764

2765

2766

2769 for (unsigned FAI = 0; FAI < NParameters; ++FAI) {

2770 if (A[FAI].empty()) {

2771 if (M->Parameters[FAI].Required) {

2773 "missing value for required parameter "

2774 "'" + M->Parameters[FAI].Name + "' in macro '" + M->Name + "'");

2776 }

2777

2778 if (M->Parameters[FAI].Value.empty())

2779 A[FAI] = M->Parameters[FAI].Value;

2780 }

2781 }

2783 }

2784

2786 }

2787

2788 return TokError("too many positional arguments");

2789}

2790

2791bool AsmParser::handleMacroEntry(MCAsmMacro *M, SMLoc NameLoc) {

2792

2793

2795 if (ActiveMacros.size() == MaxNestingDepth) {

2796 std::ostringstream MaxNestingDepthError;

2797 MaxNestingDepthError << "macros cannot be nested more than "

2798 << MaxNestingDepth << " levels deep."

2799 << " Use -asm-macro-max-nesting-depth to increase "

2800 "this limit.";

2801 return TokError(MaxNestingDepthError.str());

2802 }

2803

2804 MCAsmMacroArguments A;

2805 if (parseMacroArguments(M, A))

2806 return true;

2807

2808

2809

2810 SmallString<256> Buf;

2811 raw_svector_ostream OS(Buf);

2812

2813 if ((!IsDarwin || M->Parameters.size()) && M->Parameters.size() != A.size())

2814 return Error(getTok().getLoc(), "Wrong number of arguments");

2815 if (expandMacro(OS, *M, M->Parameters, A, true))

2816 return true;

2817

2818

2819

2820 OS << ".endmacro\n";

2821

2822 std::unique_ptr Instantiation =

2824

2825

2826

2827 MacroInstantiation *MI = new MacroInstantiation{

2828 NameLoc, CurBuffer, getTok().getLoc(), TheCondStack.size()};

2829 ActiveMacros.push_back(MI);

2830

2831 ++NumOfMacroInstantiations;

2832

2833

2836 Lex();

2837

2838 return false;

2839}

2840

2841void AsmParser::handleMacroExit() {

2842

2843 jumpToLoc(ActiveMacros.back()->ExitLoc, ActiveMacros.back()->ExitBuffer);

2844 Lex();

2845

2846

2848 Lex();

2849

2850

2851 delete ActiveMacros.back();

2852 ActiveMacros.pop_back();

2853}

2854

2855bool AsmParser::parseAssignment(StringRef Name, AssignmentKind Kind) {

2857 const MCExpr *Value;

2858 SMLoc ExprLoc = getTok().getLoc();

2859 bool AllowRedef =

2860 Kind == AssignmentKind::Set || Kind == AssignmentKind::Equal;

2863 return true;

2864

2865 if (!Sym) {

2866

2867

2868

2869 return false;

2870 }

2871

2872 if (discardLTOSymbol(Name))

2873 return false;

2874

2875

2876 switch (Kind) {

2877 case AssignmentKind::Equal:

2879 break;

2880 case AssignmentKind::Set:

2881 case AssignmentKind::Equiv:

2884 break;

2885 case AssignmentKind::LTOSetConditional:

2887 return Error(ExprLoc, "expected identifier");

2888

2890 break;

2891 }

2892

2893 return false;

2894}

2895

2896

2897

2898

2899bool AsmParser::parseIdentifier(StringRef &Res) {

2900

2901

2902

2903

2904

2906 SMLoc PrefixLoc = getLexer().getLoc();

2907

2908

2909

2910 AsmToken Buf[1];

2912

2914 return true;

2915

2916

2917

2918 if (PrefixLoc.getPointer() + 1 != Buf[0].getLoc().getPointer())

2919 return true;

2920

2921

2922 Lexer.Lex();

2923

2924 Res = StringRef(PrefixLoc.getPointer(), getTok().getString().size() + 1);

2925 Lex();

2926 return false;

2927 }

2928

2930 return true;

2931

2932 Res = getTok().getIdentifier();

2933

2934 Lex();

2935

2936 return false;

2937}

2938

2939

2940

2941

2942

2943

2944bool AsmParser::parseDirectiveSet(StringRef IDVal, AssignmentKind Kind) {

2945 StringRef Name;

2946 if (check(parseIdentifier(Name), "expected identifier") || parseComma() ||

2947 parseAssignment(Name, Kind))

2948 return true;

2949 return false;

2950}

2951

2952bool AsmParser::parseEscapedString(std::string &Data) {

2954 return true;

2955

2957 StringRef Str = getTok().getStringContents();

2958 for (unsigned i = 0, e = Str.size(); i != e; ++i) {

2959 if (Str[i] != '\\') {

2960 if ((Str[i] == '\n') || (Str[i] == '\r')) {

2961

2962 if ((Str[i] == '\n') && (i > 0) && (Str[i - 1] == '\r'))

2963 continue;

2964

2966 if (Warning(NewlineLoc, "unterminated string; newline inserted"))

2967 return true;

2968 }

2969 Data += Str[i];

2970 continue;

2971 }

2972

2973

2974

2975 ++i;

2976 if (i == e)

2977 return TokError("unexpected backslash at end of string");

2978

2979

2980 if (Str[i] == 'x' || Str[i] == 'X') {

2981 size_t length = Str.size();

2982 if (i + 1 >= length || isHexDigit(Str[i + 1]))

2983 return TokError("invalid hexadecimal escape sequence");

2984

2985

2986

2987 unsigned Value = 0;

2988 while (i + 1 < length && isHexDigit(Str[i + 1]))

2990

2991 Data += (unsigned char)(Value & 0xFF);

2992 continue;

2993 }

2994

2995

2996 if ((unsigned)(Str[i] - '0') <= 7) {

2997

2998 unsigned Value = Str[i] - '0';

2999

3000 if (i + 1 != e && ((unsigned)(Str[i + 1] - '0')) <= 7) {

3001 ++i;

3003

3004 if (i + 1 != e && ((unsigned)(Str[i + 1] - '0')) <= 7) {

3005 ++i;

3007 }

3008 }

3009

3010 if (Value > 255)

3011 return TokError("invalid octal escape sequence (out of range)");

3012

3014 continue;

3015 }

3016

3017

3018 switch (Str[i]) {

3019 default:

3020

3021 return TokError("invalid escape sequence (unrecognized character)");

3022

3023 case 'b': Data += '\b'; break;

3024 case 'f': Data += '\f'; break;

3025 case 'n': Data += '\n'; break;

3026 case 'r': Data += '\r'; break;

3027 case 't': Data += '\t'; break;

3028 case '"': Data += '"'; break;

3029 case '\\': Data += '\\'; break;

3030 }

3031 }

3032

3033 Lex();

3034 return false;

3035}

3036

3037bool AsmParser::parseAngleBracketString(std::string &Data) {

3038 SMLoc EndLoc, StartLoc = getTok().getLoc();

3040 const char *StartChar = StartLoc.getPointer() + 1;

3041 const char *EndChar = EndLoc.getPointer() - 1;

3042 jumpToLoc(EndLoc, CurBuffer);

3043

3044 Lex();

3045

3047 return false;

3048 }

3049 return true;

3050}

3051

3052

3053

3054

3055bool AsmParser::parseDirectiveAscii(StringRef IDVal, bool ZeroTerminated) {

3056 auto parseOp = [&]() -> bool {

3057 std::string Data;

3058 if (checkForValidSection())

3059 return true;

3060

3061

3062 do {

3063 if (parseEscapedString(Data))

3064 return true;

3065 getStreamer().emitBytes(Data);

3067 if (ZeroTerminated)

3068 getStreamer().emitBytes(StringRef("\0", 1));

3069 return false;

3070 };

3071

3072 return parseMany(parseOp);

3073}

3074

3075

3076

3077bool AsmParser::parseDirectiveBase64() {

3078 auto parseOp = [&]() -> bool {

3079 if (checkForValidSection())

3080 return true;

3081

3083 return true;

3084 }

3085

3086 std::vector Decoded;

3087 std::string const str = getTok().getStringContents().str();

3088 if (check(str.empty(), "expected nonempty string")) {

3089 return true;

3090 }

3091

3093 if (e) {

3095 return Error(Lexer.getLoc(), "failed to base64 decode string data");

3096 }

3097

3098 getStreamer().emitBytes(std::string(Decoded.begin(), Decoded.end()));

3099 Lex();

3100 return false;

3101 };

3102

3103 return check(parseMany(parseOp), "expected string");

3104}

3105

3106

3107

3108bool AsmParser::parseDirectiveReloc(SMLoc DirectiveLoc) {

3109 const MCExpr *Offset;

3110 const MCExpr *Expr = nullptr;

3111

3112 if (parseExpression(Offset))

3113 return true;

3114 if (parseComma() ||

3116 return true;

3117

3120 Lex();

3121

3123 Lex();

3124 SMLoc ExprLoc = Lexer.getLoc();

3125 if (parseExpression(Expr))

3126 return true;

3127

3130 return Error(ExprLoc, "expression must be relocatable");

3131 }

3132

3133 if (parseEOL())

3134 return true;

3135

3136 getStreamer().emitRelocDirective(*Offset, Name, Expr, NameLoc);

3137 return false;

3138}

3139

3140

3141

3142bool AsmParser::parseDirectiveValue(StringRef IDVal, unsigned Size) {

3143 auto parseOp = [&]() -> bool {

3144 const MCExpr *Value;

3145 SMLoc ExprLoc = getLexer().getLoc();

3146 if (checkForValidSection() || getTargetParser().parseDataExpr(Value))

3147 return true;

3148

3150 assert(Size <= 8 && "Invalid size");

3151 uint64_t IntValue = MCE->getValue();

3153 return Error(ExprLoc, "out of range literal value");

3154 getStreamer().emitIntValue(IntValue, Size);

3155 } else

3156 getStreamer().emitValue(Value, Size, ExprLoc);

3157 return false;

3158 };

3159

3160 return parseMany(parseOp);

3161}

3162

3166 return Asm.TokError("unknown token in expression");

3167 SMLoc ExprLoc = Asm.getTok().getLoc();

3168 APInt IntValue = Asm.getTok().getAPIntVal();

3169 Asm.Lex();

3170 if (!IntValue.isIntN(128))

3171 return Asm.Error(ExprLoc, "out of range literal value");

3172 if (!IntValue.isIntN(64)) {

3175 } else {

3176 hi = 0;

3178 }

3179 return false;

3180}

3181

3182

3183

3184

3185bool AsmParser::parseDirectiveOctaValue(StringRef IDVal) {

3186 auto parseOp = [&]() -> bool {

3187 if (checkForValidSection())

3188 return true;

3189 uint64_t hi, lo;

3191 return true;

3193 getStreamer().emitInt64(lo);

3194 getStreamer().emitInt64(hi);

3195 } else {

3196 getStreamer().emitInt64(hi);

3197 getStreamer().emitInt64(lo);

3198 }

3199 return false;

3200 };

3201

3202 return parseMany(parseOp);

3203}

3204

3205bool AsmParser::parseRealValue(const fltSemantics &Semantics, APInt &Res) {

3206

3207

3208 bool IsNeg = false;

3210 Lexer.Lex();

3211 IsNeg = true;

3213 Lexer.Lex();

3214

3216 return TokError(Lexer.getErr());

3219 return TokError("unexpected token in directive");

3220

3221

3223 StringRef IDVal = getTok().getString();

3230 else

3231 return TokError("invalid floating point literal");

3233 Value.convertFromString(IDVal, APFloat::rmNearestTiesToEven)

3234 .takeError()))

3235 return TokError("invalid floating point literal");

3236 if (IsNeg)

3237 Value.changeSign();

3238

3239

3240 Lex();

3241

3242 Res = Value.bitcastToAPInt();

3243

3244 return false;

3245}

3246

3247

3248

3249bool AsmParser::parseDirectiveRealValue(StringRef IDVal,

3250 const fltSemantics &Semantics) {

3251 auto parseOp = [&]() -> bool {

3252 APInt AsInt;

3253 if (checkForValidSection() || parseRealValue(Semantics, AsInt))

3254 return true;

3257 return false;

3258 };

3259

3260 return parseMany(parseOp);

3261}

3262

3263

3264

3265bool AsmParser::parseDirectiveZero() {

3266 SMLoc NumBytesLoc = Lexer.getLoc();

3267 const MCExpr *NumBytes;

3268 if (checkForValidSection() || parseExpression(NumBytes))

3269 return true;

3270

3271 int64_t Val = 0;

3273 Lex();

3274 if (parseAbsoluteExpression(Val))

3275 return true;

3276 }

3277

3278 if (parseEOL())

3279 return true;

3280 getStreamer().emitFill(*NumBytes, Val, NumBytesLoc);

3281

3282 return false;

3283}

3284

3285

3286

3287bool AsmParser::parseDirectiveFill() {

3288 SMLoc NumValuesLoc = Lexer.getLoc();

3289 const MCExpr *NumValues;

3290 if (checkForValidSection() || parseExpression(NumValues))

3291 return true;

3292

3293 int64_t FillSize = 1;

3294 int64_t FillExpr = 0;

3295

3296 SMLoc SizeLoc, ExprLoc;

3297

3299 SizeLoc = getTok().getLoc();

3300 if (parseAbsoluteExpression(FillSize))

3301 return true;

3303 ExprLoc = getTok().getLoc();

3304 if (parseAbsoluteExpression(FillExpr))

3305 return true;

3306 }

3307 }

3308 if (parseEOL())

3309 return true;

3310

3311 if (FillSize < 0) {

3312 Warning(SizeLoc, "'.fill' directive with negative size has no effect");

3313 return false;

3314 }

3315 if (FillSize > 8) {

3316 Warning(SizeLoc, "'.fill' directive with size greater than 8 has been truncated to 8");

3317 FillSize = 8;

3318 }

3319

3320 if (isUInt<32>(FillExpr) && FillSize > 4)

3321 Warning(ExprLoc, "'.fill' directive pattern has been truncated to 32-bits");

3322

3323 getStreamer().emitFill(*NumValues, FillSize, FillExpr, NumValuesLoc);

3324

3325 return false;

3326}

3327

3328

3329

3330bool AsmParser::parseDirectiveOrg() {

3331 const MCExpr *Offset;

3332 SMLoc OffsetLoc = Lexer.getLoc();

3333 if (checkForValidSection() || parseExpression(Offset))

3334 return true;

3335

3336

3337 int64_t FillExpr = 0;

3339 if (parseAbsoluteExpression(FillExpr))

3340 return true;

3341 if (parseEOL())

3342 return true;

3343

3344 getStreamer().emitValueToOffset(Offset, FillExpr, OffsetLoc);

3345 return false;

3346}

3347

3348

3349

3350bool AsmParser::parseDirectiveAlign(bool IsPow2, uint8_t ValueSize) {

3351 SMLoc AlignmentLoc = getLexer().getLoc();

3352 int64_t Alignment;

3353 SMLoc MaxBytesLoc;

3354 bool HasFillExpr = false;

3355 int64_t FillExpr = 0;

3356 int64_t MaxBytesToFill = 0;

3357 SMLoc FillExprLoc;

3358

3359 auto parseAlign = [&]() -> bool {

3360 if (parseAbsoluteExpression(Alignment))

3361 return true;

3363

3364

3365

3367 HasFillExpr = true;

3368 if (parseTokenLoc(FillExprLoc) || parseAbsoluteExpression(FillExpr))

3369 return true;

3370 }

3372 if (parseTokenLoc(MaxBytesLoc) ||

3373 parseAbsoluteExpression(MaxBytesToFill))

3374 return true;

3375 }

3376 return parseEOL();

3377 };

3378

3379 if (checkForValidSection())

3380 return true;

3381

3383 Warning(AlignmentLoc, "p2align directive with no operand(s) is ignored");

3384 return parseEOL();

3385 }

3386 if (parseAlign())

3387 return true;

3388

3389

3390 bool ReturnVal = false;

3391

3392

3393 if (IsPow2) {

3394

3395 if (Alignment >= 32) {

3396 ReturnVal |= Error(AlignmentLoc, "invalid alignment value");

3397 Alignment = 31;

3398 }

3399

3400 Alignment = 1ULL << Alignment;

3401 } else {

3402

3403

3404

3405 if (Alignment == 0)

3406 Alignment = 1;

3408 ReturnVal |= Error(AlignmentLoc, "alignment must be a power of 2");

3410 }

3412 ReturnVal |= Error(AlignmentLoc, "alignment must be smaller than 2**32");

3413 Alignment = 1u << 31;

3414 }

3415 }

3416

3417

3418 if (MaxBytesLoc.isValid()) {

3419 if (MaxBytesToFill < 1) {

3420 ReturnVal |= Error(MaxBytesLoc,

3421 "alignment directive can never be satisfied in this "

3422 "many bytes, ignoring maximum bytes expression");

3423 MaxBytesToFill = 0;

3424 }

3425

3426 if (MaxBytesToFill >= Alignment) {

3427 Warning(MaxBytesLoc, "maximum bytes expression exceeds alignment and "

3428 "has no effect");

3429 MaxBytesToFill = 0;

3430 }

3431 }

3432

3433 const MCSection *Section = getStreamer().getCurrentSectionOnly();

3434 assert(Section && "must have section to emit alignment");

3435

3436 if (HasFillExpr && FillExpr != 0 && Section->isBssSection()) {

3437 ReturnVal |=

3438 Warning(FillExprLoc, "ignoring non-zero fill value in BSS section '" +

3439 Section->getName() + "'");

3440 FillExpr = 0;

3441 }

3442

3443

3444

3445 if (MAI.useCodeAlign(*Section) && !HasFillExpr) {

3446 getStreamer().emitCodeAlignment(

3447 Align(Alignment), &getTargetParser().getSTI(), MaxBytesToFill);

3448 } else {

3449

3450 getStreamer().emitValueToAlignment(Align(Alignment), FillExpr, ValueSize,

3451 MaxBytesToFill);

3452 }

3453

3454 return ReturnVal;

3455}

3456

3457

3458

3459

3460bool AsmParser::parseDirectiveFile(SMLoc DirectiveLoc) {

3461

3462 int64_t FileNumber = -1;

3464 FileNumber = getTok().getIntVal();

3465 Lex();

3466

3467 if (FileNumber < 0)

3468 return TokError("negative file number");

3469 }

3470

3471 std::string Path;

3472

3473

3474

3475 if (parseEscapedString(Path))

3476 return true;

3477

3478 StringRef Directory;

3480 std::string FilenameData;

3482 if (check(FileNumber == -1,

3483 "explicit path specified, but no file number") ||

3484 parseEscapedString(FilenameData))

3485 return true;

3487 Directory = Path;

3488 } else {

3490 }

3491

3492 uint64_t MD5Hi, MD5Lo;

3493 bool HasMD5 = false;

3494

3495 std::optional Source;

3496 bool HasSource = false;

3497 std::string SourceString;

3498

3502 "unexpected token in '.file' directive") ||

3503 parseIdentifier(Keyword))

3504 return true;

3505 if (Keyword == "md5") {

3506 HasMD5 = true;

3507 if (check(FileNumber == -1,

3508 "MD5 checksum specified, but no file number") ||

3510 return true;

3511 } else if (Keyword == "source") {

3512 HasSource = true;

3513 if (check(FileNumber == -1,

3514 "source specified, but no file number") ||

3516 "unexpected token in '.file' directive") ||

3517 parseEscapedString(SourceString))

3518 return true;

3519 } else {

3520 return TokError("unexpected token in '.file' directive");

3521 }

3522 }

3523

3524 if (FileNumber == -1) {

3525

3526

3527

3528 if (getContext().getAsmInfo()->hasSingleParameterDotFile())

3529 getStreamer().emitFileDirective(Filename);

3530 } else {

3531

3532

3533

3537 }

3538

3539 std::optionalMD5::MD5Result CKMem;

3540 if (HasMD5) {

3541 MD5::MD5Result Sum;

3542 for (unsigned i = 0; i != 8; ++i) {

3543 Sum[i] = uint8_t(MD5Hi >> ((7 - i) * 8));

3544 Sum[i + 8] = uint8_t(MD5Lo >> ((7 - i) * 8));

3545 }

3546 CKMem = Sum;

3547 }

3548 if (HasSource) {

3549 char *SourceBuf = static_cast<char *>(Ctx.allocate(SourceString.size()));

3550 memcpy(SourceBuf, SourceString.data(), SourceString.size());

3551 Source = StringRef(SourceBuf, SourceString.size());

3552 }

3553 if (FileNumber == 0) {

3554

3557 getStreamer().emitDwarfFile0Directive(Directory, Filename, CKMem, Source);

3558 } else {

3559 Expected FileNumOrErr = getStreamer().tryEmitDwarfFileDirective(

3560 FileNumber, Directory, Filename, CKMem, Source);

3561 if (!FileNumOrErr)

3563 }

3564

3565

3567 ReportedInconsistentMD5 = true;

3568 return Warning(DirectiveLoc, "inconsistent use of MD5 checksums");

3569 }

3570 }

3571

3572 return false;

3573}

3574

3575

3576

3577bool AsmParser::parseDirectiveLine() {

3579 return parseEOL();

3580}

3581

3582

3583

3584

3585

3586

3587

3588

3589bool AsmParser::parseDirectiveLoc() {

3590 int64_t FileNumber = 0, LineNumber = 0;

3591 SMLoc Loc = getTok().getLoc();

3592 if (parseIntToken(FileNumber) ||

3594 "file number less than one in '.loc' directive") ||

3595 check(getContext().isValidDwarfFileNumber(FileNumber), Loc,

3596 "unassigned file number in '.loc' directive"))

3597 return true;

3598

3599

3601 LineNumber = getTok().getIntVal();

3602 if (LineNumber < 0)

3603 return TokError("line number less than zero in '.loc' directive");

3604 Lex();

3605 }

3606

3607 int64_t ColumnPos = 0;

3609 ColumnPos = getTok().getIntVal();

3610 if (ColumnPos < 0)

3611 return TokError("column position less than zero in '.loc' directive");

3612 Lex();

3613 }

3614

3615 auto PrevFlags = getContext().getCurrentDwarfLoc().getFlags();

3617 unsigned Isa = 0;

3619

3620 auto parseLocOp = [&]() -> bool {

3621 StringRef Name;

3622 SMLoc Loc = getTok().getLoc();

3623 if (parseIdentifier(Name))

3624 return TokError("unexpected token in '.loc' directive");

3625

3626 if (Name == "basic_block")

3628 else if (Name == "prologue_end")

3630 else if (Name == "epilogue_begin")

3632 else if (Name == "is_stmt") {

3633 Loc = getTok().getLoc();

3634 const MCExpr *Value;

3635 if (parseExpression(Value))

3636 return true;

3637

3639 int Value = MCE->getValue();

3641 Flags &= ~DWARF2_FLAG_IS_STMT;

3642 else if (Value == 1)

3644 else

3645 return Error(Loc, "is_stmt value not 0 or 1");

3646 } else {

3647 return Error(Loc, "is_stmt value not the constant value of 0 or 1");

3648 }

3649 } else if (Name == "isa") {

3650 Loc = getTok().getLoc();

3651 const MCExpr *Value;

3652 if (parseExpression(Value))

3653 return true;

3654

3656 int Value = MCE->getValue();

3658 return Error(Loc, "isa number less than zero");

3660 } else {

3661 return Error(Loc, "isa number not a constant value");

3662 }

3663 } else if (Name == "discriminator") {

3664 if (parseAbsoluteExpression(Discriminator))

3665 return true;

3666 } else {

3667 return Error(Loc, "unknown sub-directive in '.loc' directive");

3668 }

3669 return false;

3670 };

3671

3672 if (parseMany(parseLocOp, false ))

3673 return true;

3674

3675 getStreamer().emitDwarfLocDirective(FileNumber, LineNumber, ColumnPos, Flags,

3676 Isa, Discriminator, StringRef());

3677

3678 return false;

3679}

3680

3681

3682

3683bool AsmParser::parseDirectiveLocLabel(SMLoc DirectiveLoc) {

3684 StringRef Name;

3685 DirectiveLoc = Lexer.getLoc();

3686 if (parseIdentifier(Name))

3687 return TokError("expected identifier");

3688 if (parseEOL())

3689 return true;

3690 getStreamer().emitDwarfLocLabelDirective(DirectiveLoc, Name);

3691 return false;

3692}

3693

3694

3695

3696bool AsmParser::parseDirectiveStabs() {

3697 return TokError("unsupported directive '.stabs'");

3698}

3699

3700

3701

3702bool AsmParser::parseDirectiveCVFile() {

3703 SMLoc FileNumberLoc = getTok().getLoc();

3704 int64_t FileNumber;

3706 std::string Checksum;

3708

3709 if (parseIntToken(FileNumber, "expected file number") ||

3710 check(FileNumber < 1, FileNumberLoc, "file number less than one") ||

3712 "unexpected token in '.cv_file' directive") ||

3713 parseEscapedString(Filename))

3714 return true;

3717 "unexpected token in '.cv_file' directive") ||

3718 parseEscapedString(Checksum) ||

3719 parseIntToken(ChecksumKind,

3720 "expected checksum kind in '.cv_file' directive") ||

3721 parseEOL())

3722 return true;

3723 }

3724

3725 Checksum = fromHex(Checksum);

3726 void *CKMem = Ctx.allocate(Checksum.size(), 1);

3727 memcpy(CKMem, Checksum.data(), Checksum.size());

3728 ArrayRef<uint8_t> ChecksumAsBytes(reinterpret_cast<const uint8_t *>(CKMem),

3729 Checksum.size());

3730

3731 if (!getStreamer().emitCVFileDirective(FileNumber, Filename, ChecksumAsBytes,

3732 static_cast<uint8_t>(ChecksumKind)))

3733 return Error(FileNumberLoc, "file number already allocated");

3734

3735 return false;

3736}

3737

3738bool AsmParser::parseCVFunctionId(int64_t &FunctionId,

3739 StringRef DirectiveName) {

3740 SMLoc Loc;

3741 return parseTokenLoc(Loc) ||

3742 parseIntToken(FunctionId, "expected function id") ||

3743 check(FunctionId < 0 || FunctionId >= UINT_MAX, Loc,

3744 "expected function id within range [0, UINT_MAX)");

3745}

3746

3747bool AsmParser::parseCVFileId(int64_t &FileNumber, StringRef DirectiveName) {

3748 SMLoc Loc;

3749 return parseTokenLoc(Loc) ||

3750 parseIntToken(FileNumber, "expected file number") ||

3751 check(FileNumber < 1, Loc,

3752 "file number less than one in '" + DirectiveName +

3753 "' directive") ||

3754 check(!getCVContext().isValidFileNumber(FileNumber), Loc,

3755 "unassigned file number in '" + DirectiveName + "' directive");

3756}

3757

3758

3759

3760

3761

3762bool AsmParser::parseDirectiveCVFuncId() {

3763 SMLoc FunctionIdLoc = getTok().getLoc();

3764 int64_t FunctionId;

3765

3766 if (parseCVFunctionId(FunctionId, ".cv_func_id") || parseEOL())

3767 return true;

3768

3769 if (!getStreamer().emitCVFuncIdDirective(FunctionId))

3770 return Error(FunctionIdLoc, "function id already allocated");

3771

3772 return false;

3773}

3774

3775

3776

3777

3778

3779

3780

3781

3782

3783bool AsmParser::parseDirectiveCVInlineSiteId() {

3784 SMLoc FunctionIdLoc = getTok().getLoc();

3785 int64_t FunctionId;

3786 int64_t IAFunc;

3787 int64_t IAFile;

3788 int64_t IALine;

3789 int64_t IACol = 0;

3790

3791

3792 if (parseCVFunctionId(FunctionId, ".cv_inline_site_id"))

3793 return true;

3794

3795

3797 getTok().getIdentifier() != "within"),

3798 "expected 'within' identifier in '.cv_inline_site_id' directive"))

3799 return true;

3800 Lex();

3801

3802

3803 if (parseCVFunctionId(IAFunc, ".cv_inline_site_id"))

3804 return true;

3805

3806

3808 getTok().getIdentifier() != "inlined_at"),

3809 "expected 'inlined_at' identifier in '.cv_inline_site_id' "

3810 "directive") )

3811 return true;

3812 Lex();

3813

3814

3815 if (parseCVFileId(IAFile, ".cv_inline_site_id") ||

3816 parseIntToken(IALine, "expected line number after 'inlined_at'"))

3817 return true;

3818

3819

3821 IACol = getTok().getIntVal();

3822 Lex();

3823 }

3824

3825 if (parseEOL())

3826 return true;

3827

3828 if (!getStreamer().emitCVInlineSiteIdDirective(FunctionId, IAFunc, IAFile,

3829 IALine, IACol, FunctionIdLoc))

3830 return Error(FunctionIdLoc, "function id already allocated");

3831

3832 return false;

3833}

3834

3835

3836

3837

3838

3839

3840

3841

3842bool AsmParser::parseDirectiveCVLoc() {

3843 SMLoc DirectiveLoc = getTok().getLoc();

3844 int64_t FunctionId, FileNumber;

3845 if (parseCVFunctionId(FunctionId, ".cv_loc") ||

3846 parseCVFileId(FileNumber, ".cv_loc"))

3847 return true;

3848

3849 int64_t LineNumber = 0;

3851 LineNumber = getTok().getIntVal();

3852 if (LineNumber < 0)

3853 return TokError("line number less than zero in '.cv_loc' directive");

3854 Lex();

3855 }

3856

3857 int64_t ColumnPos = 0;

3859 ColumnPos = getTok().getIntVal();

3860 if (ColumnPos < 0)

3861 return TokError("column position less than zero in '.cv_loc' directive");

3862 Lex();

3863 }

3864

3865 bool PrologueEnd = false;

3866 uint64_t IsStmt = 0;

3867

3868 auto parseOp = [&]() -> bool {

3869 StringRef Name;

3870 SMLoc Loc = getTok().getLoc();

3871 if (parseIdentifier(Name))

3872 return TokError("unexpected token in '.cv_loc' directive");

3873 if (Name == "prologue_end")

3874 PrologueEnd = true;

3875 else if (Name == "is_stmt") {

3876 Loc = getTok().getLoc();

3877 const MCExpr *Value;

3878 if (parseExpression(Value))

3879 return true;

3880

3881 IsStmt = ~0ULL;

3883 IsStmt = MCE->getValue();

3884

3885 if (IsStmt > 1)

3886 return Error(Loc, "is_stmt value not 0 or 1");

3887 } else {

3888 return Error(Loc, "unknown sub-directive in '.cv_loc' directive");

3889 }

3890 return false;

3891 };

3892

3893 if (parseMany(parseOp, false ))

3894 return true;

3895

3896 getStreamer().emitCVLocDirective(FunctionId, FileNumber, LineNumber,

3897 ColumnPos, PrologueEnd, IsStmt, StringRef(),

3898 DirectiveLoc);

3899 return false;

3900}

3901

3902

3903

3904bool AsmParser::parseDirectiveCVLinetable() {

3905 int64_t FunctionId;

3906 MCSymbol *FnStartSym, *FnEndSym;

3907 SMLoc Loc = getTok().getLoc();

3908 if (parseCVFunctionId(FunctionId, ".cv_linetable") || parseComma() ||

3909 parseTokenLoc(Loc) ||

3910 check(parseSymbol(FnStartSym), Loc, "expected identifier in directive") ||

3911 parseComma() || parseTokenLoc(Loc) ||

3912 check(parseSymbol(FnEndSym), Loc, "expected identifier in directive"))

3913 return true;

3914

3915 getStreamer().emitCVLinetableDirective(FunctionId, FnStartSym, FnEndSym);

3916 return false;

3917}

3918

3919

3920

3921bool AsmParser::parseDirectiveCVInlineLinetable() {

3922 int64_t PrimaryFunctionId, SourceFileId, SourceLineNum;

3923 MCSymbol *FnStartSym, *FnEndSym;

3924 SMLoc Loc = getTok().getLoc();

3925 if (parseCVFunctionId(PrimaryFunctionId, ".cv_inline_linetable") ||

3926 parseTokenLoc(Loc) ||

3927 parseIntToken(SourceFileId, "expected SourceField") ||

3928 check(SourceFileId <= 0, Loc, "File id less than zero") ||

3929 parseTokenLoc(Loc) ||

3930 parseIntToken(SourceLineNum, "expected SourceLineNum") ||

3931 check(SourceLineNum < 0, Loc, "Line number less than zero") ||

3932 parseTokenLoc(Loc) ||

3933 check(parseSymbol(FnStartSym), Loc, "expected identifier") ||

3934 parseTokenLoc(Loc) ||

3935 check(parseSymbol(FnEndSym), Loc, "expected identifier"))

3936 return true;

3937

3938 if (parseEOL())

3939 return true;

3940

3941 getStreamer().emitCVInlineLinetableDirective(PrimaryFunctionId, SourceFileId,

3942 SourceLineNum, FnStartSym,

3943 FnEndSym);

3944 return false;

3945}

3946

3947void AsmParser::initializeCVDefRangeTypeMap() {

3948 CVDefRangeTypeMap["reg"] = CVDR_DEFRANGE_REGISTER;

3949 CVDefRangeTypeMap["frame_ptr_rel"] = CVDR_DEFRANGE_FRAMEPOINTER_REL;

3950 CVDefRangeTypeMap["subfield_reg"] = CVDR_DEFRANGE_SUBFIELD_REGISTER;

3951 CVDefRangeTypeMap["reg_rel"] = CVDR_DEFRANGE_REGISTER_REL;

3952}

3953

3954

3955

3956bool AsmParser::parseDirectiveCVDefRange() {

3957 SMLoc Loc;

3958 std::vector<std::pair<const MCSymbol *, const MCSymbol *>> Ranges;

3960 Loc = getLexer().getLoc();

3963 return Error(Loc, "expected identifier in directive");

3964

3965 Loc = getLexer().getLoc();

3968 return Error(Loc, "expected identifier in directive");

3969

3970 Ranges.push_back({GapStartSym, GapEndSym});

3971 }

3972

3973 StringRef CVDefRangeTypeStr;

3974 if (parseToken(

3976 "expected comma before def_range type in .cv_def_range directive") ||

3977 parseIdentifier(CVDefRangeTypeStr))

3978 return Error(Loc, "expected def_range type in directive");

3979

3981 CVDefRangeTypeMap.find(CVDefRangeTypeStr);

3982 CVDefRangeType CVDRType = (CVTypeIt == CVDefRangeTypeMap.end())

3983 ? CVDR_DEFRANGE

3984 : CVTypeIt->getValue();

3985 switch (CVDRType) {

3986 case CVDR_DEFRANGE_REGISTER: {

3987 int64_t DRRegister;

3988 if (parseToken(AsmToken::Comma, "expected comma before register number in "

3989 ".cv_def_range directive") ||

3990 parseAbsoluteExpression(DRRegister))

3991 return Error(Loc, "expected register number");

3992

3993 codeview::DefRangeRegisterHeader DRHdr;

3994 DRHdr.Register = DRRegister;

3996 getStreamer().emitCVDefRangeDirective(Ranges, DRHdr);

3997 break;

3998 }

3999 case CVDR_DEFRANGE_FRAMEPOINTER_REL: {

4000 int64_t DROffset;

4002 "expected comma before offset in .cv_def_range directive") ||

4003 parseAbsoluteExpression(DROffset))

4004 return Error(Loc, "expected offset value");

4005

4006 codeview::DefRangeFramePointerRelHeader DRHdr;

4007 DRHdr.Offset = DROffset;

4008 getStreamer().emitCVDefRangeDirective(Ranges, DRHdr);

4009 break;

4010 }

4011 case CVDR_DEFRANGE_SUBFIELD_REGISTER: {

4012 int64_t DRRegister;

4013 int64_t DROffsetInParent;

4014 if (parseToken(AsmToken::Comma, "expected comma before register number in "

4015 ".cv_def_range directive") ||

4016 parseAbsoluteExpression(DRRegister))

4017 return Error(Loc, "expected register number");

4019 "expected comma before offset in .cv_def_range directive") ||

4020 parseAbsoluteExpression(DROffsetInParent))

4021 return Error(Loc, "expected offset value");

4022

4023 codeview::DefRangeSubfieldRegisterHeader DRHdr;

4024 DRHdr.Register = DRRegister;

4027 getStreamer().emitCVDefRangeDirective(Ranges, DRHdr);

4028 break;

4029 }

4030 case CVDR_DEFRANGE_REGISTER_REL: {

4031 int64_t DRRegister;

4032 int64_t DRFlags;

4033 int64_t DRBasePointerOffset;

4034 if (parseToken(AsmToken::Comma, "expected comma before register number in "

4035 ".cv_def_range directive") ||

4036 parseAbsoluteExpression(DRRegister))

4037 return Error(Loc, "expected register value");

4038 if (parseToken(

4040 "expected comma before flag value in .cv_def_range directive") ||

4041 parseAbsoluteExpression(DRFlags))

4042 return Error(Loc, "expected flag value");

4043 if (parseToken(AsmToken::Comma, "expected comma before base pointer offset "

4044 "in .cv_def_range directive") ||

4045 parseAbsoluteExpression(DRBasePointerOffset))

4046 return Error(Loc, "expected base pointer offset value");

4047

4048 codeview::DefRangeRegisterRelHeader DRHdr;

4049 DRHdr.Register = DRRegister;

4050 DRHdr.Flags = DRFlags;

4052 getStreamer().emitCVDefRangeDirective(Ranges, DRHdr);

4053 break;

4054 }

4055 default:

4056 return Error(Loc, "unexpected def_range type in .cv_def_range directive");

4057 }

4058 return true;

4059}

4060

4061

4062

4063bool AsmParser::parseDirectiveCVString() {

4064 std::string Data;

4065 if (checkForValidSection() || parseEscapedString(Data))

4066 return true;

4067

4068

4069 std::pair<StringRef, unsigned> Insertion =

4070 getCVContext().addToStringTable(Data);

4071 getStreamer().emitInt32(Insertion.second);

4072 return false;

4073}

4074

4075

4076

4077bool AsmParser::parseDirectiveCVStringTable() {

4078 getStreamer().emitCVStringTableDirective();

4079 return false;

4080}

4081

4082

4083

4084bool AsmParser::parseDirectiveCVFileChecksums() {

4085 getStreamer().emitCVFileChecksumsDirective();

4086 return false;

4087}

4088

4089

4090

4091bool AsmParser::parseDirectiveCVFileChecksumOffset() {

4092 int64_t FileNo;

4093 if (parseIntToken(FileNo))

4094 return true;

4095 if (parseEOL())

4096 return true;

4097 getStreamer().emitCVFileChecksumOffsetDirective(FileNo);

4098 return false;

4099}

4100

4101

4102

4103bool AsmParser::parseDirectiveCVFPOData() {

4104 SMLoc DirLoc = getLexer().getLoc();

4107 return TokError("expected symbol name");

4108 if (parseEOL())

4109 return true;

4110 getStreamer().emitCVFPOData(ProcSym, DirLoc);

4111 return false;

4112}

4113

4114

4115

4116bool AsmParser::parseDirectiveCFISections() {

4117 StringRef Name;

4118 bool EH = false;

4119 bool Debug = false;

4120 bool SFrame = false;

4121

4123 for (;;) {

4124 if (parseIdentifier(Name))

4125 return TokError("expected .eh_frame, .debug_frame, or .sframe");

4126 if (Name == ".eh_frame")

4127 EH = true;

4128 else if (Name == ".debug_frame")

4130 else if (Name == ".sframe")

4131 SFrame = true;

4133 break;

4134 if (parseComma())

4135 return true;

4136 }

4137 }

4138 getStreamer().emitCFISections(EH, Debug, SFrame);

4139 return false;

4140}

4141

4142

4143

4144bool AsmParser::parseDirectiveCFIStartProc() {

4145 CFIStartProcLoc = StartTokLoc;

4146

4149 if (check(parseIdentifier(Simple) || Simple != "simple",

4150 "unexpected token") ||

4151 parseEOL())

4152 return true;

4153 }

4154

4155

4156

4157

4158

4159

4160 getStreamer().emitCFIStartProc(Simple.empty(), Lexer.getLoc());

4161 return false;

4162}

4163

4164

4165

4166bool AsmParser::parseDirectiveCFIEndProc() {

4167 CFIStartProcLoc = std::nullopt;

4168

4169 if (parseEOL())

4170 return true;

4171

4172 getStreamer().emitCFIEndProc();

4173 return false;

4174}

4175

4176

4177bool AsmParser::parseRegisterOrRegisterNumber(int64_t &Register,

4178 SMLoc DirectiveLoc) {

4179 MCRegister RegNo;

4180

4182 if (getTargetParser().parseRegister(RegNo, DirectiveLoc, DirectiveLoc))

4183 return true;

4184 Register = getContext().getRegisterInfo()->getDwarfRegNum(RegNo, true);

4185 } else

4186 return parseAbsoluteExpression(Register);

4187

4188 return false;

4189}

4190

4191

4192

4193bool AsmParser::parseDirectiveCFIDefCfa(SMLoc DirectiveLoc) {

4195 if (parseRegisterOrRegisterNumber(Register, DirectiveLoc) || parseComma() ||

4196 parseAbsoluteExpression(Offset) || parseEOL())

4197 return true;

4198

4199 getStreamer().emitCFIDefCfa(Register, Offset, DirectiveLoc);

4200 return false;

4201}

4202

4203

4204

4205bool AsmParser::parseDirectiveCFIDefCfaOffset(SMLoc DirectiveLoc) {

4207 if (parseAbsoluteExpression(Offset) || parseEOL())

4208 return true;

4209

4210 getStreamer().emitCFIDefCfaOffset(Offset, DirectiveLoc);

4211 return false;

4212}

4213

4214

4215

4216bool AsmParser::parseDirectiveCFIRegister(SMLoc DirectiveLoc) {

4217 int64_t Register1 = 0, Register2 = 0;

4218 if (parseRegisterOrRegisterNumber(Register1, DirectiveLoc) || parseComma() ||

4219 parseRegisterOrRegisterNumber(Register2, DirectiveLoc) || parseEOL())

4220 return true;

4221

4222 getStreamer().emitCFIRegister(Register1, Register2, DirectiveLoc);

4223 return false;

4224}

4225

4226

4227

4228bool AsmParser::parseDirectiveCFIWindowSave(SMLoc DirectiveLoc) {

4229 if (parseEOL())

4230 return true;

4231 getStreamer().emitCFIWindowSave(DirectiveLoc);

4232 return false;

4233}

4234

4235

4236

4237bool AsmParser::parseDirectiveCFIAdjustCfaOffset(SMLoc DirectiveLoc) {

4238 int64_t Adjustment = 0;

4239 if (parseAbsoluteExpression(Adjustment) || parseEOL())

4240 return true;

4241

4242 getStreamer().emitCFIAdjustCfaOffset(Adjustment, DirectiveLoc);

4243 return false;

4244}

4245

4246

4247

4248bool AsmParser::parseDirectiveCFIDefCfaRegister(SMLoc DirectiveLoc) {

4250 if (parseRegisterOrRegisterNumber(Register, DirectiveLoc) || parseEOL())

4251 return true;

4252

4253 getStreamer().emitCFIDefCfaRegister(Register, DirectiveLoc);

4254 return false;

4255}

4256

4257

4258

4259bool AsmParser::parseDirectiveCFILLVMDefAspaceCfa(SMLoc DirectiveLoc) {

4261 if (parseRegisterOrRegisterNumber(Register, DirectiveLoc) || parseComma() ||

4262 parseAbsoluteExpression(Offset) || parseComma() ||

4263 parseAbsoluteExpression(AddressSpace) || parseEOL())

4264 return true;

4265

4267 DirectiveLoc);

4268 return false;

4269}

4270

4271

4272

4273bool AsmParser::parseDirectiveCFIOffset(SMLoc DirectiveLoc) {

4276

4277 if (parseRegisterOrRegisterNumber(Register, DirectiveLoc) || parseComma() ||

4278 parseAbsoluteExpression(Offset) || parseEOL())

4279 return true;

4280

4281 getStreamer().emitCFIOffset(Register, Offset, DirectiveLoc);

4282 return false;

4283}

4284

4285

4286

4287bool AsmParser::parseDirectiveCFIRelOffset(SMLoc DirectiveLoc) {

4289

4290 if (parseRegisterOrRegisterNumber(Register, DirectiveLoc) || parseComma() ||

4291 parseAbsoluteExpression(Offset) || parseEOL())

4292 return true;

4293

4294 getStreamer().emitCFIRelOffset(Register, Offset, DirectiveLoc);

4295 return false;

4296}

4297

4299 if (Encoding & ~0xff)

4300 return false;

4301

4303 return true;

4304

4305 const unsigned Format = Encoding & 0xf;

4310 return false;

4311

4312 const unsigned Application = Encoding & 0x70;

4315 return false;

4316

4317 return true;

4318}

4319

4320

4321

4322

4323

4324bool AsmParser::parseDirectiveCFIPersonalityOrLsda(bool IsPersonality) {

4325 int64_t Encoding = 0;

4326 if (parseAbsoluteExpression(Encoding))

4327 return true;

4329 return false;

4330

4332 if (check(isValidEncoding(Encoding), "unsupported encoding.") ||

4333 parseComma() ||

4334 check(parseSymbol(Sym), "expected identifier in directive") || parseEOL())

4335 return true;

4336

4337 if (IsPersonality)

4338 getStreamer().emitCFIPersonality(Sym, Encoding);

4339 else

4340 getStreamer().emitCFILsda(Sym, Encoding);

4341 return false;

4342}

4343

4344

4345

4346bool AsmParser::parseDirectiveCFIRememberState(SMLoc DirectiveLoc) {

4347 if (parseEOL())

4348 return true;

4349 getStreamer().emitCFIRememberState(DirectiveLoc);

4350 return false;

4351}

4352

4353

4354

4355bool AsmParser::parseDirectiveCFIRestoreState(SMLoc DirectiveLoc) {

4356 if (parseEOL())

4357 return true;

4358 getStreamer().emitCFIRestoreState(DirectiveLoc);

4359 return false;

4360}

4361

4362

4363

4364bool AsmParser::parseDirectiveCFISameValue(SMLoc DirectiveLoc) {

4366

4367 if (parseRegisterOrRegisterNumber(Register, DirectiveLoc) || parseEOL())

4368 return true;

4369

4370 getStreamer().emitCFISameValue(Register, DirectiveLoc);

4371 return false;

4372}

4373

4374

4375

4376bool AsmParser::parseDirectiveCFIRestore(SMLoc DirectiveLoc) {

4378 if (parseRegisterOrRegisterNumber(Register, DirectiveLoc) || parseEOL())

4379 return true;

4380

4381 getStreamer().emitCFIRestore(Register, DirectiveLoc);

4382 return false;

4383}

4384

4385

4386

4387bool AsmParser::parseDirectiveCFIEscape(SMLoc DirectiveLoc) {

4388 std::string Values;

4389 int64_t CurrValue;

4390 if (parseAbsoluteExpression(CurrValue))

4391 return true;

4392

4393 Values.push_back((uint8_t)CurrValue);

4394

4396 Lex();

4397

4398 if (parseAbsoluteExpression(CurrValue))

4399 return true;

4400

4401 Values.push_back((uint8_t)CurrValue);

4402 }

4403

4404 getStreamer().emitCFIEscape(Values, DirectiveLoc);

4405 return false;

4406}

4407

4408

4409

4410bool AsmParser::parseDirectiveCFIReturnColumn(SMLoc DirectiveLoc) {

4412 if (parseRegisterOrRegisterNumber(Register, DirectiveLoc) || parseEOL())

4413 return true;

4414 getStreamer().emitCFIReturnColumn(Register);

4415 return false;

4416}

4417

4418

4419

4420bool AsmParser::parseDirectiveCFISignalFrame(SMLoc DirectiveLoc) {

4421 if (parseEOL())

4422 return true;

4423

4424 getStreamer().emitCFISignalFrame();

4425 return false;

4426}

4427

4428

4429

4430bool AsmParser::parseDirectiveCFIUndefined(SMLoc DirectiveLoc) {

4432

4433 if (parseRegisterOrRegisterNumber(Register, DirectiveLoc) || parseEOL())

4434 return true;

4435

4436 getStreamer().emitCFIUndefined(Register, DirectiveLoc);

4437 return false;

4438}

4439

4440

4441

4442bool AsmParser::parseDirectiveCFILabel(SMLoc Loc) {

4443 StringRef Name;

4444 Loc = Lexer.getLoc();

4445 if (parseIdentifier(Name))

4446 return TokError("expected identifier");

4447 if (parseEOL())

4448 return true;

4449 getStreamer().emitCFILabelDirective(Loc, Name);

4450 return false;

4451}

4452

4453

4454

4455bool AsmParser::parseDirectiveCFIValOffset(SMLoc DirectiveLoc) {

4458

4459 if (parseRegisterOrRegisterNumber(Register, DirectiveLoc) || parseComma() ||

4460 parseAbsoluteExpression(Offset) || parseEOL())

4461 return true;

4462

4463 getStreamer().emitCFIValOffset(Register, Offset, DirectiveLoc);

4464 return false;

4465}

4466

4467

4468

4469

4470bool AsmParser::parseDirectiveAltmacro(StringRef Directive) {

4471 if (parseEOL())

4472 return true;

4473 AltMacroMode = (Directive == ".altmacro");

4474 return false;

4475}

4476

4477

4478

4479

4480bool AsmParser::parseDirectiveMacrosOnOff(StringRef Directive) {

4481 if (parseEOL())

4482 return true;

4483 setMacrosEnabled(Directive == ".macros_on");

4484 return false;

4485}

4486

4487

4488

4489bool AsmParser::parseDirectiveMacro(SMLoc DirectiveLoc) {

4490 StringRef Name;

4491 if (parseIdentifier(Name))

4492 return TokError("expected identifier in '.macro' directive");

4493

4495 Lex();

4496

4499

4501 return Error(Lexer.getLoc(), "vararg parameter '" +

4503 "' should be the last parameter");

4504

4506 if (parseIdentifier(Parameter.Name))

4507 return TokError("expected identifier in '.macro' directive");

4508

4509

4510 for (const MCAsmMacroParameter& CurrParam : Parameters)

4511 if (CurrParam.Name == Parameter.Name)

4512 return TokError("macro '" + Name + "' has multiple parameters"

4513 " named '" + Parameter.Name + "'");

4514

4516 Lex();

4517

4518 SMLoc QualLoc;

4520

4521 QualLoc = Lexer.getLoc();

4522 if (parseIdentifier(Qualifier))

4523 return Error(QualLoc, "missing parameter qualifier for "

4524 "'" + Parameter.Name + "' in macro '" + Name + "'");

4525

4526 if (Qualifier == "req")

4528 else if (Qualifier == "vararg")

4530 else

4531 return Error(QualLoc, Qualifier + " is not a valid parameter qualifier "

4532 "for '" + Parameter.Name + "' in macro '" + Name + "'");

4533 }

4534

4536 Lex();

4537

4538 SMLoc ParamLoc;

4539

4540 ParamLoc = Lexer.getLoc();

4541 if (parseMacroArgument(Parameter.Value, false ))

4542 return true;

4543

4545 Warning(ParamLoc, "pointless default value for required parameter "

4546 "'" + Parameter.Name + "' in macro '" + Name + "'");

4547 }

4548

4549 Parameters.push_back(std::move(Parameter));

4550

4552 Lex();

4553 }

4554

4555

4556 Lexer.Lex();

4557

4558

4559 AsmToken EndToken, StartToken = getTok();

4560 unsigned MacroDepth = 0;

4561

4562 while (true) {

4563

4565 Lexer.Lex();

4566 }

4567

4568

4570 return Error(DirectiveLoc, "no matching '.endmacro' in definition");

4571

4572

4573

4575 if (getTok().getIdentifier() == ".endm" ||

4576 getTok().getIdentifier() == ".endmacro") {

4577 if (MacroDepth == 0) {

4578 EndToken = getTok();

4579 Lexer.Lex();

4581 return TokError("unexpected token in '" + EndToken.getIdentifier() +

4582 "' directive");

4583 break;

4584 } else {

4585

4586 --MacroDepth;

4587 }

4588 } else if (getTok().getIdentifier() == ".macro") {

4589

4590

4591 ++MacroDepth;

4592 }

4594 (void)parseCppHashLineFilenameComment(getLexer().getLoc());

4595 }

4596

4597

4598 eatToEndOfStatement();

4599 }

4600

4601 if (getContext().lookupMacro(Name)) {

4602 return Error(DirectiveLoc, "macro '" + Name + "' is already defined");

4603 }

4604

4607 StringRef Body = StringRef(BodyStart, BodyEnd - BodyStart);

4608 checkForBadMacro(DirectiveLoc, Name, Body, Parameters);

4609 MCAsmMacro Macro(Name, Body, std::move(Parameters));

4613 return false;

4614}

4615

4616

4617

4618

4619

4620

4621

4622

4623

4624

4625

4626

4627

4628

4629

4630void AsmParser::checkForBadMacro(SMLoc DirectiveLoc, StringRef Name,

4631 StringRef Body,

4633

4634

4635 unsigned NParameters = Parameters.size();

4636 if (NParameters == 0)

4637 return;

4638

4639 bool NamedParametersFound = false;

4640 bool PositionalParametersFound = false;

4641

4642

4643

4644

4645 while (!Body.empty()) {

4646

4647 std::size_t End = Body.size(), Pos = 0;

4648 for (; Pos != End; ++Pos) {

4649

4650

4651 if (Body[Pos] == '\\' && Pos + 1 != End)

4652 break;

4653

4654

4655 if (Body[Pos] != '$' || Pos + 1 == End)

4656 continue;

4657 char Next = Body[Pos + 1];

4658 if (Next == '$' || Next == 'n' ||

4659 isdigit(static_cast<unsigned char>(Next)))

4660 break;

4661 }

4662

4663

4664 if (Pos == End)

4665 break;

4666

4667 if (Body[Pos] == '$') {

4668 switch (Body[Pos + 1]) {

4669

4670 case '$':

4671 break;

4672

4673

4674 case 'n':

4675 PositionalParametersFound = true;

4676 break;

4677

4678

4679 default: {

4680 PositionalParametersFound = true;

4681 break;

4682 }

4683 }

4684 Pos += 2;

4685 } else {

4686 unsigned I = Pos + 1;

4688 ++I;

4689

4690 const char *Begin = Body.data() + Pos + 1;

4691 StringRef Argument(Begin, I - (Pos + 1));

4692 unsigned Index = 0;

4693 for (; Index < NParameters; ++Index)

4694 if (Parameters[Index].Name == Argument)

4695 break;

4696

4697 if (Index == NParameters) {

4698 if (Body[Pos + 1] == '(' && Body[Pos + 2] == ')')

4699 Pos += 3;

4700 else {

4701 Pos = I;

4702 }

4703 } else {

4704 NamedParametersFound = true;

4706 }

4707 }

4708

4709 Body = Body.substr(Pos);

4710 }

4711

4712 if (!NamedParametersFound && PositionalParametersFound)

4713 Warning(DirectiveLoc, "macro defined with named parameters which are not "

4714 "used in macro body, possible positional parameter "

4715 "found in body which will have no effect");

4716}

4717

4718

4719

4720bool AsmParser::parseDirectiveExitMacro(StringRef Directive) {

4721 if (parseEOL())

4722 return true;

4723

4724 if (!isInsideMacroInstantiation())

4725 return TokError("unexpected '" + Directive + "' in file, "

4726 "no current macro definition");

4727

4728

4729 while (TheCondStack.size() != ActiveMacros.back()->CondStackDepth) {

4730 TheCondState = TheCondStack.back();

4731 TheCondStack.pop_back();

4732 }

4733

4734 handleMacroExit();

4735 return false;

4736}

4737

4738

4739

4740

4741bool AsmParser::parseDirectiveEndMacro(StringRef Directive) {

4743 return TokError("unexpected token in '" + Directive + "' directive");

4744

4745

4746

4747 if (isInsideMacroInstantiation()) {

4748 handleMacroExit();

4749 return false;

4750 }

4751

4752

4753

4754 return TokError("unexpected '" + Directive + "' in file, "

4755 "no current macro definition");

4756}

4757

4758

4759

4760bool AsmParser::parseDirectivePurgeMacro(SMLoc DirectiveLoc) {

4761 StringRef Name;

4762 SMLoc Loc;

4763 if (parseTokenLoc(Loc) ||

4764 check(parseIdentifier(Name), Loc,

4765 "expected identifier in '.purgem' directive") ||

4766 parseEOL())

4767 return true;

4768

4769 if (getContext().lookupMacro(Name))

4770 return Error(DirectiveLoc, "macro '" + Name + "' is not defined");

4771

4774 << "Un-defining macro: " << Name << "\n");

4775 return false;

4776}

4777

4778

4779

4780bool AsmParser::parseDirectiveSpace(StringRef IDVal) {

4781 SMLoc NumBytesLoc = Lexer.getLoc();

4782 const MCExpr *NumBytes;

4783 if (checkForValidSection() || parseExpression(NumBytes))

4784 return true;

4785

4786 int64_t FillExpr = 0;

4788 if (parseAbsoluteExpression(FillExpr))

4789 return true;

4790 if (parseEOL())

4791 return true;

4792

4793

4794 getStreamer().emitFill(*NumBytes, FillExpr, NumBytesLoc);

4795

4796 return false;

4797}

4798

4799

4800

4801bool AsmParser::parseDirectiveDCB(StringRef IDVal, unsigned Size) {

4802 SMLoc NumValuesLoc = Lexer.getLoc();

4803 int64_t NumValues;

4804 if (checkForValidSection() || parseAbsoluteExpression(NumValues))

4805 return true;

4806

4807 if (NumValues < 0) {

4808 Warning(NumValuesLoc, "'" + Twine(IDVal) + "' directive with negative repeat count has no effect");

4809 return false;

4810 }

4811

4812 if (parseComma())

4813 return true;

4814

4815 const MCExpr *Value;

4816 SMLoc ExprLoc = getLexer().getLoc();

4817 if (parseExpression(Value))

4818 return true;

4819

4820

4822 assert(Size <= 8 && "Invalid size");

4823 uint64_t IntValue = MCE->getValue();

4825 return Error(ExprLoc, "literal value out of range for directive");

4826 for (uint64_t i = 0, e = NumValues; i != e; ++i)

4827 getStreamer().emitIntValue(IntValue, Size);

4828 } else {

4829 for (uint64_t i = 0, e = NumValues; i != e; ++i)

4830 getStreamer().emitValue(Value, Size, ExprLoc);

4831 }

4832

4833 return parseEOL();

4834}

4835

4836

4837

4838bool AsmParser::parseDirectiveRealDCB(StringRef IDVal, const fltSemantics &Semantics) {

4839 SMLoc NumValuesLoc = Lexer.getLoc();

4840 int64_t NumValues;

4841 if (checkForValidSection() || parseAbsoluteExpression(NumValues))

4842 return true;

4843

4844 if (NumValues < 0) {

4845 Warning(NumValuesLoc, "'" + Twine(IDVal) + "' directive with negative repeat count has no effect");

4846 return false;

4847 }

4848

4849 if (parseComma())

4850 return true;

4851

4852 APInt AsInt;

4853 if (parseRealValue(Semantics, AsInt) || parseEOL())

4854 return true;

4855

4856 for (uint64_t i = 0, e = NumValues; i != e; ++i)

4859

4860 return false;

4861}

4862

4863

4864

4865bool AsmParser::parseDirectiveDS(StringRef IDVal, unsigned Size) {

4866 SMLoc NumValuesLoc = Lexer.getLoc();

4867 int64_t NumValues;

4868 if (checkForValidSection() || parseAbsoluteExpression(NumValues) ||

4869 parseEOL())

4870 return true;

4871

4872 if (NumValues < 0) {

4873 Warning(NumValuesLoc, "'" + Twine(IDVal) + "' directive with negative repeat count has no effect");

4874 return false;

4875 }

4876

4877 for (uint64_t i = 0, e = NumValues; i != e; ++i)

4878 getStreamer().emitFill(Size, 0);

4879

4880 return false;

4881}

4882

4883

4884

4885bool AsmParser::parseDirectiveLEB128(bool Signed) {

4886 if (checkForValidSection())

4887 return true;

4888

4889 auto parseOp = [&]() -> bool {

4890 const MCExpr *Value;

4891 if (parseExpression(Value))

4892 return true;

4894 getStreamer().emitSLEB128Value(Value);

4895 else

4896 getStreamer().emitULEB128Value(Value);

4897 return false;

4898 };

4899

4900 return parseMany(parseOp);

4901}

4902

4903

4904

4905bool AsmParser::parseDirectiveSymbolAttribute(MCSymbolAttr Attr) {

4906 auto parseOp = [&]() -> bool {

4907 StringRef Name;

4908 SMLoc Loc = getTok().getLoc();

4909 if (parseIdentifier(Name))

4910 return Error(Loc, "expected identifier");

4911

4912 if (discardLTOSymbol(Name))

4913 return false;

4914

4916

4917

4918

4920 return Error(Loc, "non-local symbol required");

4921

4922 if (!getStreamer().emitSymbolAttribute(Sym, Attr))

4923 return Error(Loc, "unable to emit symbol attribute");

4924 return false;

4925 };

4926

4927 return parseMany(parseOp);

4928}

4929

4930

4931

4932bool AsmParser::parseDirectiveComm(bool IsLocal) {

4933 if (checkForValidSection())

4934 return true;

4935

4936 SMLoc IDLoc = getLexer().getLoc();

4939 return TokError("expected identifier in directive");

4940

4941 if (parseComma())

4942 return true;

4943

4944 int64_t Size;

4945 SMLoc SizeLoc = getLexer().getLoc();

4946 if (parseAbsoluteExpression(Size))

4947 return true;

4948

4949 int64_t Pow2Alignment = 0;

4950 SMLoc Pow2AlignmentLoc;

4952 Lex();

4953 Pow2AlignmentLoc = getLexer().getLoc();

4954 if (parseAbsoluteExpression(Pow2Alignment))

4955 return true;

4956

4959 return Error(Pow2AlignmentLoc, "alignment not supported on this target");

4960

4961

4965 return Error(Pow2AlignmentLoc, "alignment must be a power of 2");

4966 Pow2Alignment = Log2_64(Pow2Alignment);

4967 }

4968 }

4969

4970 if (parseEOL())

4971 return true;

4972

4973

4974

4975 if (Size < 0)

4976 return Error(SizeLoc, "size must be non-negative");

4977

4980 return Error(IDLoc, "invalid symbol redefinition");

4981

4982

4983 if (IsLocal) {

4984 getStreamer().emitLocalCommonSymbol(Sym, Size,

4985 Align(1ULL << Pow2Alignment));

4986 return false;

4987 }

4988

4989 getStreamer().emitCommonSymbol(Sym, Size, Align(1ULL << Pow2Alignment));

4990 return false;

4991}

4992

4993

4994

4995bool AsmParser::parseDirectiveAbort(SMLoc DirectiveLoc) {

4996 StringRef Str = parseStringToEndOfStatement();

4997 if (parseEOL())

4998 return true;

4999

5000 if (Str.empty())

5001 return Error(DirectiveLoc, ".abort detected. Assembly stopping");

5002

5003

5004 return Error(DirectiveLoc,

5005 ".abort '" + Str + "' detected. Assembly stopping");

5006}

5007

5008

5009

5010bool AsmParser::parseDirectiveInclude() {

5011

5013 SMLoc IncludeLoc = getTok().getLoc();

5014

5016 "expected string in '.include' directive") ||

5017 parseEscapedString(Filename) ||

5019 "unexpected token in '.include' directive") ||

5020

5021

5022 check(enterIncludeFile(Filename), IncludeLoc,

5023 "Could not find include file '" + Filename + "'"))

5024 return true;

5025

5026 return false;

5027}

5028

5029

5030

5031bool AsmParser::parseDirectiveIncbin() {

5032

5034 SMLoc IncbinLoc = getTok().getLoc();

5036 "expected string in '.incbin' directive") ||

5037 parseEscapedString(Filename))

5038 return true;

5039

5040 int64_t Skip = 0;

5041 const MCExpr *Count = nullptr;

5042 SMLoc SkipLoc, CountLoc;

5044

5045

5047 if (parseTokenLoc(SkipLoc) || parseAbsoluteExpression(Skip))

5048 return true;

5049 }

5051 CountLoc = getTok().getLoc();

5052 if (parseExpression(Count))

5053 return true;

5054 }

5055 }

5056

5057 if (parseEOL())

5058 return true;

5059

5060 if (check(Skip < 0, SkipLoc, "skip is negative"))

5061 return true;

5062

5063

5064 if (processIncbinFile(Filename, Skip, Count, CountLoc))

5065 return Error(IncbinLoc, "Could not find incbin file '" + Filename + "'");

5066 return false;

5067}

5068

5069

5070

5071bool AsmParser::parseDirectiveIf(SMLoc DirectiveLoc, DirectiveKind DirKind) {

5072 TheCondStack.push_back(TheCondState);

5074 if (TheCondState.Ignore) {

5075 eatToEndOfStatement();

5076 } else {

5077 int64_t ExprValue;

5078 if (parseAbsoluteExpression(ExprValue) || parseEOL())

5079 return true;

5080

5081 switch (DirKind) {

5082 default:

5084 case DK_IF:

5085 case DK_IFNE:

5086 break;

5087 case DK_IFEQ:

5088 ExprValue = ExprValue == 0;

5089 break;

5090 case DK_IFGE:

5091 ExprValue = ExprValue >= 0;

5092 break;

5093 case DK_IFGT:

5094 ExprValue = ExprValue > 0;

5095 break;

5096 case DK_IFLE:

5097 ExprValue = ExprValue <= 0;

5098 break;

5099 case DK_IFLT:

5100 ExprValue = ExprValue < 0;

5101 break;

5102 }

5103

5104 TheCondState.CondMet = ExprValue;

5106 }

5107

5108 return false;

5109}

5110

5111

5112

5113bool AsmParser::parseDirectiveIfb(SMLoc DirectiveLoc, bool ExpectBlank) {

5114 TheCondStack.push_back(TheCondState);

5116

5117 if (TheCondState.Ignore) {

5118 eatToEndOfStatement();

5119 } else {

5120 StringRef Str = parseStringToEndOfStatement();

5121

5122 if (parseEOL())

5123 return true;

5124

5125 TheCondState.CondMet = ExpectBlank == Str.empty();

5127 }

5128

5129 return false;

5130}

5131

5132

5133

5134

5135bool AsmParser::parseDirectiveIfc(SMLoc DirectiveLoc, bool ExpectEqual) {

5136 TheCondStack.push_back(TheCondState);

5138

5139 if (TheCondState.Ignore) {

5140 eatToEndOfStatement();

5141 } else {

5142 StringRef Str1 = parseStringToComma();

5143

5144 if (parseComma())

5145 return true;

5146

5147 StringRef Str2 = parseStringToEndOfStatement();

5148

5149 if (parseEOL())

5150 return true;

5151

5152 TheCondState.CondMet = ExpectEqual == (Str1.trim() == Str2.trim());

5154 }

5155

5156 return false;

5157}

5158

5159

5160

5161bool AsmParser::parseDirectiveIfeqs(SMLoc DirectiveLoc, bool ExpectEqual) {

5162 TheCondStack.push_back(TheCondState);

5164

5165 if (TheCondState.Ignore) {

5166 eatToEndOfStatement();

5167 } else {

5169 if (ExpectEqual)

5170 return TokError("expected string parameter for '.ifeqs' directive");

5171 return TokError("expected string parameter for '.ifnes' directive");

5172 }

5173

5174 StringRef String1 = getTok().getStringContents();

5175 Lex();

5176

5178 if (ExpectEqual)

5179 return TokError(

5180 "expected comma after first string for '.ifeqs' directive");

5181 return TokError(

5182 "expected comma after first string for '.ifnes' directive");

5183 }

5184

5185 Lex();

5186

5188 if (ExpectEqual)

5189 return TokError("expected string parameter for '.ifeqs' directive");

5190 return TokError("expected string parameter for '.ifnes' directive");

5191 }

5192

5193 StringRef String2 = getTok().getStringContents();

5194 Lex();

5195

5196 TheCondState.CondMet = ExpectEqual == (String1 == String2);

5198 }

5199

5200 return false;

5201}

5202

5203

5204

5205bool AsmParser::parseDirectiveIfdef(SMLoc DirectiveLoc, bool expect_defined) {

5206 StringRef Name;

5207 TheCondStack.push_back(TheCondState);

5209

5210 if (TheCondState.Ignore) {

5211 eatToEndOfStatement();

5212 } else {

5213 if (check(parseIdentifier(Name), "expected identifier after '.ifdef'") ||

5214 parseEOL())

5215 return true;

5216

5218

5219 if (expect_defined)

5221 else

5224 }

5225

5226 return false;

5227}

5228

5229

5230

5231bool AsmParser::parseDirectiveElseIf(SMLoc DirectiveLoc) {

5234 return Error(DirectiveLoc, "Encountered a .elseif that doesn't follow an"

5235 " .if or an .elseif");

5237

5238 bool LastIgnoreState = false;

5239 if (!TheCondStack.empty())

5240 LastIgnoreState = TheCondStack.back().Ignore;

5241 if (LastIgnoreState || TheCondState.CondMet) {

5242 TheCondState.Ignore = true;

5243 eatToEndOfStatement();

5244 } else {

5245 int64_t ExprValue;

5246 if (parseAbsoluteExpression(ExprValue))

5247 return true;

5248

5249 if (parseEOL())

5250 return true;

5251

5252 TheCondState.CondMet = ExprValue;

5254 }

5255

5256 return false;

5257}

5258

5259

5260

5261bool AsmParser::parseDirectiveElse(SMLoc DirectiveLoc) {

5262 if (parseEOL())

5263 return true;

5264

5267 return Error(DirectiveLoc, "Encountered a .else that doesn't follow "

5268 " an .if or an .elseif");

5270 bool LastIgnoreState = false;

5271 if (!TheCondStack.empty())

5272 LastIgnoreState = TheCondStack.back().Ignore;

5273 if (LastIgnoreState || TheCondState.CondMet)

5274 TheCondState.Ignore = true;

5275 else

5276 TheCondState.Ignore = false;

5277

5278 return false;

5279}

5280

5281

5282

5283bool AsmParser::parseDirectiveEnd(SMLoc DirectiveLoc) {

5284 if (parseEOL())

5285 return true;

5286

5288 Lexer.Lex();

5289

5290 return false;

5291}

5292

5293

5294

5295

5296bool AsmParser::parseDirectiveError(SMLoc L, bool WithMessage) {

5297 if (!TheCondStack.empty()) {

5298 if (TheCondStack.back().Ignore) {

5299 eatToEndOfStatement();

5300 return false;

5301 }

5302 }

5303

5304 if (!WithMessage)

5305 return Error(L, ".err encountered");

5306

5307 StringRef Message = ".error directive invoked in source file";

5310 return TokError(".error argument must be a string");

5311

5312 Message = getTok().getStringContents();

5313 Lex();

5314 }

5315

5316 return Error(L, Message);

5317}

5318

5319

5320

5321bool AsmParser::parseDirectiveWarning(SMLoc L) {

5322 if (!TheCondStack.empty()) {

5323 if (TheCondStack.back().Ignore) {

5324 eatToEndOfStatement();

5325 return false;

5326 }

5327 }

5328

5329 StringRef Message = ".warning directive invoked in source file";

5330

5333 return TokError(".warning argument must be a string");

5334

5335 Message = getTok().getStringContents();

5336 Lex();

5337 if (parseEOL())

5338 return true;

5339 }

5340

5341 return Warning(L, Message);

5342}

5343

5344

5345

5346bool AsmParser::parseDirectiveEndIf(SMLoc DirectiveLoc) {

5347 if (parseEOL())

5348 return true;

5349

5351 return Error(DirectiveLoc, "Encountered a .endif that doesn't follow "

5352 "an .if or .else");

5353 if (!TheCondStack.empty()) {

5354 TheCondState = TheCondStack.back();

5355 TheCondStack.pop_back();

5356 }

5357

5358 return false;

5359}

5360

5361void AsmParser::initializeDirectiveKindMap() {

5362

5363

5364

5365

5366

5367

5368 DirectiveKindMap[".set"] = DK_SET;

5369 DirectiveKindMap[".equ"] = DK_EQU;

5370 DirectiveKindMap[".equiv"] = DK_EQUIV;

5371 DirectiveKindMap[".ascii"] = DK_ASCII;

5372 DirectiveKindMap[".asciz"] = DK_ASCIZ;

5373 DirectiveKindMap[".string"] = DK_STRING;

5374 DirectiveKindMap[".byte"] = DK_BYTE;

5375 DirectiveKindMap[".base64"] = DK_BASE64;

5376 DirectiveKindMap[".short"] = DK_SHORT;

5377 DirectiveKindMap[".value"] = DK_VALUE;

5378 DirectiveKindMap[".2byte"] = DK_2BYTE;

5379 DirectiveKindMap[".long"] = DK_LONG;

5380 DirectiveKindMap[".int"] = DK_INT;

5381 DirectiveKindMap[".4byte"] = DK_4BYTE;

5382 DirectiveKindMap[".quad"] = DK_QUAD;

5383 DirectiveKindMap[".8byte"] = DK_8BYTE;

5384 DirectiveKindMap[".octa"] = DK_OCTA;

5385 DirectiveKindMap[".single"] = DK_SINGLE;

5386 DirectiveKindMap[".float"] = DK_FLOAT;

5387 DirectiveKindMap[".double"] = DK_DOUBLE;

5388 DirectiveKindMap[".align"] = DK_ALIGN;

5389 DirectiveKindMap[".align32"] = DK_ALIGN32;

5390 DirectiveKindMap[".balign"] = DK_BALIGN;

5391 DirectiveKindMap[".balignw"] = DK_BALIGNW;

5392 DirectiveKindMap[".balignl"] = DK_BALIGNL;

5393 DirectiveKindMap[".p2align"] = DK_P2ALIGN;

5394 DirectiveKindMap[".p2alignw"] = DK_P2ALIGNW;

5395 DirectiveKindMap[".p2alignl"] = DK_P2ALIGNL;

5396 DirectiveKindMap[".org"] = DK_ORG;

5397 DirectiveKindMap[".fill"] = DK_FILL;

5398 DirectiveKindMap[".zero"] = DK_ZERO;

5399 DirectiveKindMap[".extern"] = DK_EXTERN;

5400 DirectiveKindMap[".globl"] = DK_GLOBL;

5401 DirectiveKindMap[".global"] = DK_GLOBAL;

5402 DirectiveKindMap[".lazy_reference"] = DK_LAZY_REFERENCE;

5403 DirectiveKindMap[".no_dead_strip"] = DK_NO_DEAD_STRIP;

5404 DirectiveKindMap[".symbol_resolver"] = DK_SYMBOL_RESOLVER;

5405 DirectiveKindMap[".private_extern"] = DK_PRIVATE_EXTERN;

5406 DirectiveKindMap[".reference"] = DK_REFERENCE;

5407 DirectiveKindMap[".weak_definition"] = DK_WEAK_DEFINITION;

5408 DirectiveKindMap[".weak_reference"] = DK_WEAK_REFERENCE;

5409 DirectiveKindMap[".weak_def_can_be_hidden"] = DK_WEAK_DEF_CAN_BE_HIDDEN;

5410 DirectiveKindMap[".cold"] = DK_COLD;

5411 DirectiveKindMap[".comm"] = DK_COMM;

5412 DirectiveKindMap[".common"] = DK_COMMON;

5413 DirectiveKindMap[".lcomm"] = DK_LCOMM;

5414 DirectiveKindMap[".abort"] = DK_ABORT;

5415 DirectiveKindMap[".include"] = DK_INCLUDE;

5416 DirectiveKindMap[".incbin"] = DK_INCBIN;

5417 DirectiveKindMap[".code16"] = DK_CODE16;

5418 DirectiveKindMap[".code16gcc"] = DK_CODE16GCC;

5419 DirectiveKindMap[".rept"] = DK_REPT;

5420 DirectiveKindMap[".rep"] = DK_REPT;

5421 DirectiveKindMap[".irp"] = DK_IRP;

5422 DirectiveKindMap[".irpc"] = DK_IRPC;

5423 DirectiveKindMap[".endr"] = DK_ENDR;

5424 DirectiveKindMap[".if"] = DK_IF;

5425 DirectiveKindMap[".ifeq"] = DK_IFEQ;

5426 DirectiveKindMap[".ifge"] = DK_IFGE;

5427 DirectiveKindMap[".ifgt"] = DK_IFGT;

5428 DirectiveKindMap[".ifle"] = DK_IFLE;

5429 DirectiveKindMap[".iflt"] = DK_IFLT;

5430 DirectiveKindMap[".ifne"] = DK_IFNE;

5431 DirectiveKindMap[".ifb"] = DK_IFB;

5432 DirectiveKindMap[".ifnb"] = DK_IFNB;

5433 DirectiveKindMap[".ifc"] = DK_IFC;

5434 DirectiveKindMap[".ifeqs"] = DK_IFEQS;

5435 DirectiveKindMap[".ifnc"] = DK_IFNC;

5436 DirectiveKindMap[".ifnes"] = DK_IFNES;

5437 DirectiveKindMap[".ifdef"] = DK_IFDEF;

5438 DirectiveKindMap[".ifndef"] = DK_IFNDEF;

5439 DirectiveKindMap[".ifnotdef"] = DK_IFNOTDEF;

5440 DirectiveKindMap[".elseif"] = DK_ELSEIF;

5441 DirectiveKindMap[".else"] = DK_ELSE;

5442 DirectiveKindMap[".end"] = DK_END;

5443 DirectiveKindMap[".endif"] = DK_ENDIF;

5444 DirectiveKindMap[".skip"] = DK_SKIP;

5445 DirectiveKindMap[".space"] = DK_SPACE;

5446 DirectiveKindMap[".file"] = DK_FILE;

5447 DirectiveKindMap[".line"] = DK_LINE;

5448 DirectiveKindMap[".loc"] = DK_LOC;

5449 DirectiveKindMap[".loc_label"] = DK_LOC_LABEL;

5450 DirectiveKindMap[".stabs"] = DK_STABS;

5451 DirectiveKindMap[".cv_file"] = DK_CV_FILE;

5452 DirectiveKindMap[".cv_func_id"] = DK_CV_FUNC_ID;

5453 DirectiveKindMap[".cv_loc"] = DK_CV_LOC;

5454 DirectiveKindMap[".cv_linetable"] = DK_CV_LINETABLE;

5455 DirectiveKindMap[".cv_inline_linetable"] = DK_CV_INLINE_LINETABLE;

5456 DirectiveKindMap[".cv_inline_site_id"] = DK_CV_INLINE_SITE_ID;

5457 DirectiveKindMap[".cv_def_range"] = DK_CV_DEF_RANGE;

5458 DirectiveKindMap[".cv_string"] = DK_CV_STRING;

5459 DirectiveKindMap[".cv_stringtable"] = DK_CV_STRINGTABLE;

5460 DirectiveKindMap[".cv_filechecksums"] = DK_CV_FILECHECKSUMS;

5461 DirectiveKindMap[".cv_filechecksumoffset"] = DK_CV_FILECHECKSUM_OFFSET;

5462 DirectiveKindMap[".cv_fpo_data"] = DK_CV_FPO_DATA;

5463 DirectiveKindMap[".sleb128"] = DK_SLEB128;

5464 DirectiveKindMap[".uleb128"] = DK_ULEB128;

5465 DirectiveKindMap[".cfi_sections"] = DK_CFI_SECTIONS;

5466 DirectiveKindMap[".cfi_startproc"] = DK_CFI_STARTPROC;

5467 DirectiveKindMap[".cfi_endproc"] = DK_CFI_ENDPROC;

5468 DirectiveKindMap[".cfi_def_cfa"] = DK_CFI_DEF_CFA;

5469 DirectiveKindMap[".cfi_def_cfa_offset"] = DK_CFI_DEF_CFA_OFFSET;

5470 DirectiveKindMap[".cfi_adjust_cfa_offset"] = DK_CFI_ADJUST_CFA_OFFSET;

5471 DirectiveKindMap[".cfi_def_cfa_register"] = DK_CFI_DEF_CFA_REGISTER;

5472 DirectiveKindMap[".cfi_llvm_def_aspace_cfa"] = DK_CFI_LLVM_DEF_ASPACE_CFA;

5473 DirectiveKindMap[".cfi_offset"] = DK_CFI_OFFSET;

5474 DirectiveKindMap[".cfi_rel_offset"] = DK_CFI_REL_OFFSET;

5475 DirectiveKindMap[".cfi_personality"] = DK_CFI_PERSONALITY;

5476 DirectiveKindMap[".cfi_lsda"] = DK_CFI_LSDA;

5477 DirectiveKindMap[".cfi_remember_state"] = DK_CFI_REMEMBER_STATE;

5478 DirectiveKindMap[".cfi_restore_state"] = DK_CFI_RESTORE_STATE;

5479 DirectiveKindMap[".cfi_same_value"] = DK_CFI_SAME_VALUE;

5480 DirectiveKindMap[".cfi_restore"] = DK_CFI_RESTORE;

5481 DirectiveKindMap[".cfi_escape"] = DK_CFI_ESCAPE;

5482 DirectiveKindMap[".cfi_return_column"] = DK_CFI_RETURN_COLUMN;

5483 DirectiveKindMap[".cfi_signal_frame"] = DK_CFI_SIGNAL_FRAME;

5484 DirectiveKindMap[".cfi_undefined"] = DK_CFI_UNDEFINED;

5485 DirectiveKindMap[".cfi_register"] = DK_CFI_REGISTER;

5486 DirectiveKindMap[".cfi_window_save"] = DK_CFI_WINDOW_SAVE;

5487 DirectiveKindMap[".cfi_label"] = DK_CFI_LABEL;

5488 DirectiveKindMap[".cfi_b_key_frame"] = DK_CFI_B_KEY_FRAME;

5489 DirectiveKindMap[".cfi_mte_tagged_frame"] = DK_CFI_MTE_TAGGED_FRAME;

5490 DirectiveKindMap[".cfi_val_offset"] = DK_CFI_VAL_OFFSET;

5491 DirectiveKindMap[".macros_on"] = DK_MACROS_ON;

5492 DirectiveKindMap[".macros_off"] = DK_MACROS_OFF;

5493 DirectiveKindMap[".macro"] = DK_MACRO;

5494 DirectiveKindMap[".exitm"] = DK_EXITM;

5495 DirectiveKindMap[".endm"] = DK_ENDM;

5496 DirectiveKindMap[".endmacro"] = DK_ENDMACRO;

5497 DirectiveKindMap[".purgem"] = DK_PURGEM;

5498 DirectiveKindMap[".err"] = DK_ERR;

5499 DirectiveKindMap[".error"] = DK_ERROR;

5500 DirectiveKindMap[".warning"] = DK_WARNING;

5501 DirectiveKindMap[".altmacro"] = DK_ALTMACRO;

5502 DirectiveKindMap[".noaltmacro"] = DK_NOALTMACRO;

5503 DirectiveKindMap[".reloc"] = DK_RELOC;

5504 DirectiveKindMap[".dc"] = DK_DC;

5505 DirectiveKindMap[".dc.a"] = DK_DC_A;

5506 DirectiveKindMap[".dc.b"] = DK_DC_B;

5507 DirectiveKindMap[".dc.d"] = DK_DC_D;

5508 DirectiveKindMap[".dc.l"] = DK_DC_L;

5509 DirectiveKindMap[".dc.s"] = DK_DC_S;

5510 DirectiveKindMap[".dc.w"] = DK_DC_W;

5511 DirectiveKindMap[".dc.x"] = DK_DC_X;

5512 DirectiveKindMap[".dcb"] = DK_DCB;

5513 DirectiveKindMap[".dcb.b"] = DK_DCB_B;

5514 DirectiveKindMap[".dcb.d"] = DK_DCB_D;

5515 DirectiveKindMap[".dcb.l"] = DK_DCB_L;

5516 DirectiveKindMap[".dcb.s"] = DK_DCB_S;

5517 DirectiveKindMap[".dcb.w"] = DK_DCB_W;

5518 DirectiveKindMap[".dcb.x"] = DK_DCB_X;

5519 DirectiveKindMap[".ds"] = DK_DS;

5520 DirectiveKindMap[".ds.b"] = DK_DS_B;

5521 DirectiveKindMap[".ds.d"] = DK_DS_D;

5522 DirectiveKindMap[".ds.l"] = DK_DS_L;

5523 DirectiveKindMap[".ds.p"] = DK_DS_P;

5524 DirectiveKindMap[".ds.s"] = DK_DS_S;

5525 DirectiveKindMap[".ds.w"] = DK_DS_W;

5526 DirectiveKindMap[".ds.x"] = DK_DS_X;

5527 DirectiveKindMap[".print"] = DK_PRINT;

5528 DirectiveKindMap[".addrsig"] = DK_ADDRSIG;

5529 DirectiveKindMap[".addrsig_sym"] = DK_ADDRSIG_SYM;

5530 DirectiveKindMap[".pseudoprobe"] = DK_PSEUDO_PROBE;

5531 DirectiveKindMap[".lto_discard"] = DK_LTO_DISCARD;

5532 DirectiveKindMap[".lto_set_conditional"] = DK_LTO_SET_CONDITIONAL;

5533 DirectiveKindMap[".memtag"] = DK_MEMTAG;

5534}

5535

5536MCAsmMacro *AsmParser::parseMacroLikeBody(SMLoc DirectiveLoc) {

5537 AsmToken EndToken, StartToken = getTok();

5538

5539 unsigned NestLevel = 0;

5540 while (true) {

5541

5543 printError(DirectiveLoc, "no matching '.endr' in definition");

5544 return nullptr;

5545 }

5546

5548 StringRef Ident = getTok().getIdentifier();

5549 if (Ident == ".rep" || Ident == ".rept" || Ident == ".irp" ||

5550 Ident == ".irpc") {

5551 ++NestLevel;

5552 } else if (Ident == ".endr") {

5553 if (NestLevel == 0) {

5554 EndToken = getTok();

5555 Lex();

5557 break;

5558 printError(getTok().getLoc(), "expected newline");

5559 return nullptr;

5560 }

5561 --NestLevel;

5562 }

5563 }

5564

5565

5566 eatToEndOfStatement();

5567 }

5568

5571 StringRef Body = StringRef(BodyStart, BodyEnd - BodyStart);

5572

5573

5575 return &MacroLikeBodies.back();

5576}

5577

5578void AsmParser::instantiateMacroLikeBody(MCAsmMacro *M, SMLoc DirectiveLoc,

5579 raw_svector_ostream &OS) {

5580 OS << ".endr\n";

5581

5582 std::unique_ptr Instantiation =

5584

5585

5586

5587 MacroInstantiation *MI = new MacroInstantiation{

5588 DirectiveLoc, CurBuffer, getTok().getLoc(), TheCondStack.size()};

5589 ActiveMacros.push_back(MI);

5590

5591

5594 Lex();

5595}

5596

5597

5598

5599bool AsmParser::parseDirectiveRept(SMLoc DirectiveLoc, StringRef Dir) {

5600 const MCExpr *CountExpr;

5601 SMLoc CountLoc = getTok().getLoc();

5602 if (parseExpression(CountExpr))

5603 return true;

5604

5606 if (!CountExpr->evaluateAsAbsolute(Count, getStreamer().getAssemblerPtr())) {

5607 return Error(CountLoc, "unexpected token in '" + Dir + "' directive");

5608 }

5609

5610 if (check(Count < 0, CountLoc, "Count is negative") || parseEOL())

5611 return true;

5612

5613

5614 MCAsmMacro *M = parseMacroLikeBody(DirectiveLoc);

5615 if (!M)

5616 return true;

5617

5618

5619

5620 SmallString<256> Buf;

5621 raw_svector_ostream OS(Buf);

5622 while (Count--) {

5623

5624 if (expandMacro(OS, *M, {}, {}, false))

5625 return true;

5626 }

5627 instantiateMacroLikeBody(M, DirectiveLoc, OS);

5628

5629 return false;

5630}

5631

5632

5633

5634bool AsmParser::parseDirectiveIrp(SMLoc DirectiveLoc) {

5636 MCAsmMacroArguments A;

5637 if (check(parseIdentifier(Parameter.Name),

5638 "expected identifier in '.irp' directive") ||

5639 parseComma() || parseMacroArguments(nullptr, A) || parseEOL())

5640 return true;

5641

5642

5643 MCAsmMacro *M = parseMacroLikeBody(DirectiveLoc);

5644 if (!M)

5645 return true;

5646

5647

5648

5649 SmallString<256> Buf;

5650 raw_svector_ostream OS(Buf);

5651

5652 for (const MCAsmMacroArgument &Arg : A) {

5653

5654

5655 if (expandMacro(OS, *M, Parameter, Arg, true))

5656 return true;

5657 }

5658

5659 instantiateMacroLikeBody(M, DirectiveLoc, OS);

5660

5661 return false;

5662}

5663

5664

5665

5666bool AsmParser::parseDirectiveIrpc(SMLoc DirectiveLoc) {

5668 MCAsmMacroArguments A;

5669

5670 if (check(parseIdentifier(Parameter.Name),

5671 "expected identifier in '.irpc' directive") ||

5672 parseComma() || parseMacroArguments(nullptr, A))

5673 return true;

5674

5675 if (A.size() != 1 || A.front().size() != 1)

5676 return TokError("unexpected token in '.irpc' directive");

5677 if (parseEOL())

5678 return true;

5679

5680

5681 MCAsmMacro *M = parseMacroLikeBody(DirectiveLoc);

5682 if (!M)

5683 return true;

5684

5685

5686

5687 SmallString<256> Buf;

5688 raw_svector_ostream OS(Buf);

5689

5690 StringRef Values = A[0][0].is(AsmToken::String) ? A[0][0].getStringContents()

5691 : A[0][0].getString();

5692 for (std::size_t I = 0, End = Values.size(); I != End; ++I) {

5693 MCAsmMacroArgument Arg;

5695

5696

5697

5698 if (expandMacro(OS, *M, Parameter, Arg, true))

5699 return true;

5700 }

5701

5702 instantiateMacroLikeBody(M, DirectiveLoc, OS);

5703

5704 return false;

5705}

5706

5707bool AsmParser::parseDirectiveEndr(SMLoc DirectiveLoc) {

5708 if (ActiveMacros.empty())

5709 return TokError("unmatched '.endr' directive");

5710

5711

5712

5714

5715 handleMacroExit();

5716 return false;

5717}

5718

5719bool AsmParser::parseDirectiveMSEmit(SMLoc IDLoc, ParseStatementInfo &Info,

5720 size_t Len) {

5721 const MCExpr *Value;

5722 SMLoc ExprLoc = getLexer().getLoc();

5723 if (parseExpression(Value))

5724 return true;

5726 if (!MCE)

5727 return Error(ExprLoc, "unexpected expression in _emit");

5728 uint64_t IntValue = MCE->getValue();

5730 return Error(ExprLoc, "literal value out of range for directive");

5731

5732 Info.AsmRewrites->emplace_back(AOK_Emit, IDLoc, Len);

5733 return false;

5734}

5735

5736bool AsmParser::parseDirectiveMSAlign(SMLoc IDLoc, ParseStatementInfo &Info) {

5737 const MCExpr *Value;

5738 SMLoc ExprLoc = getLexer().getLoc();

5739 if (parseExpression(Value))

5740 return true;

5742 if (!MCE)

5743 return Error(ExprLoc, "unexpected expression in align");

5744 uint64_t IntValue = MCE->getValue();

5746 return Error(ExprLoc, "literal value not a power of two greater then zero");

5747

5749 return false;

5750}

5751

5752bool AsmParser::parseDirectivePrint(SMLoc DirectiveLoc) {

5753 const AsmToken StrTok = getTok();

5754 Lex();

5756 return Error(DirectiveLoc, "expected double quoted string after .print");

5757 if (parseEOL())

5758 return true;

5760 return false;

5761}

5762

5763bool AsmParser::parseDirectiveAddrsig() {

5764 if (parseEOL())

5765 return true;

5766 getStreamer().emitAddrsig();

5767 return false;

5768}

5769

5770bool AsmParser::parseDirectiveAddrsigSym() {

5772 if (check(parseSymbol(Sym), "expected identifier") || parseEOL())

5773 return true;

5774 getStreamer().emitAddrsigSym(Sym);

5775 return false;

5776}

5777

5778bool AsmParser::parseDirectivePseudoProbe() {

5779 int64_t Guid;

5781 int64_t Type;

5782 int64_t Attr;

5784 if (parseIntToken(Guid))

5785 return true;

5786 if (parseIntToken(Index))

5787 return true;

5788 if (parseIntToken(Type))

5789 return true;

5790 if (parseIntToken(Attr))

5791 return true;

5793 return true;

5794

5795

5797

5799

5800 Lex();

5801

5802 int64_t CallerGuid = 0;

5804 CallerGuid = getTok().getIntVal();

5805 Lex();

5806 }

5807

5808

5810 Lex();

5811

5812 int64_t CallerProbeId = 0;

5814 CallerProbeId = getTok().getIntVal();

5815 Lex();

5816 }

5817

5818 InlineSite Site(CallerGuid, CallerProbeId);

5820 }

5821

5822

5823 StringRef FnName;

5824 if (parseIdentifier(FnName))

5825 return Error(getLexer().getLoc(), "expected identifier");

5827

5828 if (parseEOL())

5829 return true;

5830

5831 getStreamer().emitPseudoProbe(Guid, Index, Type, Attr, Discriminator,

5832 InlineStack, FnSym);

5833 return false;

5834}

5835

5836

5837

5838

5839

5840

5841bool AsmParser::parseDirectiveLTODiscard() {

5842 auto ParseOp = [&]() -> bool {

5843 StringRef Name;

5844 SMLoc Loc = getTok().getLoc();

5845 if (parseIdentifier(Name))

5846 return Error(Loc, "expected identifier");

5847 LTODiscardSymbols.insert(Name);

5848 return false;

5849 };

5850

5851 LTODiscardSymbols.clear();

5852 return parseMany(ParseOp);

5853}

5854

5855

5856

5860 return -1;

5862 return 1;

5863

5864

5865

5866

5867

5870 return -1;

5871

5874 return 1;

5876}

5877

5878bool AsmParser::parseMSInlineAsm(

5879 std::string &AsmString, unsigned &NumOutputs, unsigned &NumInputs,

5880 SmallVectorImpl<std::pair<void *, bool>> &OpDecls,

5881 SmallVectorImplstd::string &Constraints,

5882 SmallVectorImplstd::string &Clobbers, const MCInstrInfo *MII,

5883 MCInstPrinter *IP, MCAsmParserSemaCallback &SI) {

5884 SmallVector<void *, 4> InputDecls;

5885 SmallVector<void *, 4> OutputDecls;

5888 SmallVector<std::string, 4> InputConstraints;

5889 SmallVector<std::string, 4> OutputConstraints;

5891

5893

5894

5895 Lex();

5896

5897

5898 unsigned InputIdx = 0;

5899 unsigned OutputIdx = 0;

5901

5902 if (parseCurlyBlockScope(AsmStrRewrites))

5903 continue;

5904

5905 ParseStatementInfo Info(&AsmStrRewrites);

5906 bool StatementErr = parseStatement(Info, &SI);

5907

5908 if (StatementErr || Info.ParseError) {

5909

5910 printPendingErrors();

5911 return true;

5912 }

5913

5914

5915 assert(!hasPendingError() && "unexpected error from parseStatement");

5916

5917 if (Info.Opcode == ~0U)

5918 continue;

5919

5920 const MCInstrDesc &Desc = MII->get(Info.Opcode);

5921

5922

5923 for (unsigned i = 1, e = Info.ParsedOperands.size(); i != e; ++i) {

5924 MCParsedAsmOperand &Operand = *Info.ParsedOperands[i];

5925

5926

5928 !getTargetParser().omitRegisterFromClobberLists(Operand.getReg())) {

5929 unsigned NumDefs = Desc.getNumDefs();

5930

5933 continue;

5934 }

5935

5936

5937 StringRef SymName = Operand.getSymName();

5938 if (SymName.empty())

5939 continue;

5940

5941 void *OpDecl = Operand.getOpDecl();

5942 if (!OpDecl)

5943 continue;

5944

5946 if (Operand.isImm()) {

5947

5949 Constraint = "r";

5950 else

5951 Constraint = "i";

5952 }

5953

5954 bool isOutput = (i == 1) && Desc.mayStore();

5957 if (isOutput) {

5958 ++InputIdx;

5961 OutputConstraints.push_back(("=" + Constraint).str());

5963 Restricted);

5964 } else {

5967 InputConstraints.push_back(Constraint.str());

5968 if (Desc.operands()[i - 1].isBranchTarget())

5970 Restricted);

5971 else

5973 Restricted);

5974 }

5975 }

5976

5977

5979 }

5980

5981

5982 NumOutputs = OutputDecls.size();

5983 NumInputs = InputDecls.size();

5984

5985

5988 Clobbers.assign(ClobberRegs.size(), std::string());

5989 for (unsigned I = 0, E = ClobberRegs.size(); I != E; ++I) {

5990 raw_string_ostream OS(Clobbers[I]);

5992 }

5993

5994

5995 if (NumOutputs || NumInputs) {

5996 unsigned NumExprs = NumOutputs + NumInputs;

5997 OpDecls.resize(NumExprs);

5998 Constraints.resize(NumExprs);

5999 for (unsigned i = 0; i < NumOutputs; ++i) {

6000 OpDecls[i] = std::make_pair(OutputDecls[i], OutputDeclsAddressOf[i]);

6001 Constraints[i] = OutputConstraints[i];

6002 }

6003 for (unsigned i = 0, j = NumOutputs; i < NumInputs; ++i, ++j) {

6004 OpDecls[j] = std::make_pair(InputDecls[i], InputDeclsAddressOf[i]);

6005 Constraints[j] = InputConstraints[i];

6006 }

6007 }

6008

6009

6010 std::string AsmStringIR;

6011 raw_string_ostream OS(AsmStringIR);

6012 StringRef ASMString =

6014 const char *AsmStart = ASMString.begin();

6015 const char *AsmEnd = ASMString.end();

6017 for (auto I = AsmStrRewrites.begin(), E = AsmStrRewrites.end(); I != E; ++I) {

6018 const AsmRewrite &AR = *I;

6019

6020 if (AR.Done)

6021 continue;

6023

6025 assert(Loc >= AsmStart && "Expected Loc to be at or after Start!");

6026

6027

6028 if (unsigned Len = Loc - AsmStart)

6029 OS << StringRef(AsmStart, Len);

6030

6031

6033 AsmStart = Loc + AR.Len;

6034 continue;

6035 }

6036

6037 unsigned AdditionalSkip = 0;

6038

6039 switch (Kind) {

6040 default:

6041 break;

6045 OS << "[";

6055 OS << " + ";

6056

6059 size_t OffsetLen = OffsetName.size();

6060 auto rewrite_it = std::find_if(

6061 I, AsmStrRewrites.end(), [&](const AsmRewrite &FusingAR) {

6062 return FusingAR.Loc == OffsetLoc && FusingAR.Len == OffsetLen &&

6063 (FusingAR.Kind == AOK_Input ||

6064 FusingAR.Kind == AOK_CallInput);

6065 });

6066 if (rewrite_it == AsmStrRewrites.end()) {

6067 OS << "offset " << OffsetName;

6069 OS << "${" << InputIdx++ << ":P}";

6070 rewrite_it->Done = true;

6071 } else {

6072 OS << '$' << InputIdx++;

6073 rewrite_it->Done = true;

6074 }

6075 }

6079 OS << "]";

6080 break;

6083 break;

6086 OS << "${" << InputIdx++ << ":P}";

6087 else

6088 OS << '$' << InputIdx++;

6089 break;

6091 OS << "${" << InputIdx++ << ":P}";

6092 break;

6095 OS << "${" << OutputIdx++ << ":P}";

6096 else

6097 OS << '$' << OutputIdx++;

6098 break;

6100 switch (AR.Val) {

6101 default: break;

6102 case 8: OS << "byte ptr "; break;

6103 case 16: OS << "word ptr "; break;

6104 case 32: OS << "dword ptr "; break;

6105 case 64: OS << "qword ptr "; break;

6106 case 80: OS << "xword ptr "; break;

6107 case 128: OS << "xmmword ptr "; break;

6108 case 256: OS << "ymmword ptr "; break;

6109 }

6110 break;

6112 OS << ".byte";

6113 break;

6115

6116

6117 OS << ".align";

6118 if (getContext().getAsmInfo()->getAlignmentIsInBytes())

6119 break;

6120

6121

6122

6123 unsigned Val = AR.Val;

6124 OS << ' ' << Val;

6125 assert(Val < 10 && "Expected alignment less then 2^10.");

6126 AdditionalSkip = (Val < 4) ? 2 : Val < 7 ? 3 : 4;

6127 break;

6128 }

6130 OS << ".even";

6131 break;

6133 OS << "\n\t";

6134 break;

6135 }

6136

6137

6138 AsmStart = Loc + AR.Len + AdditionalSkip;

6139 }

6140

6141

6142 if (AsmStart != AsmEnd)

6143 OS << StringRef(AsmStart, AsmEnd - AsmStart);

6144

6145 AsmString = std::move(AsmStringIR);

6146 return false;

6147}

6148

6149bool HLASMAsmParser::parseAsHLASMLabel(ParseStatementInfo &Info,

6150 MCAsmParserSemaCallback *SI) {

6151 AsmToken LabelTok = getTok();

6152 SMLoc LabelLoc = LabelTok.getLoc();

6153 StringRef LabelVal;

6154

6155 if (parseIdentifier(LabelVal))

6156 return Error(LabelLoc, "The HLASM Label has to be an Identifier");

6157

6158

6159

6160

6161 if (!getTargetParser().isLabel(LabelTok) || checkForValidSection())

6162 return true;

6163

6164

6165 lexLeadingSpaces();

6166

6167

6168

6170 return Error(LabelLoc,

6171 "Cannot have just a label for an HLASM inline asm statement");

6172

6174 getContext().getAsmInfo()->isHLASM() ? LabelVal.upper() : LabelVal);

6175

6176

6178

6179

6180

6181 if (enabledGenDwarfForAssembly())

6183 LabelLoc);

6184

6185 return false;

6186}

6187

6188bool HLASMAsmParser::parseAsMachineInstruction(ParseStatementInfo &Info,

6189 MCAsmParserSemaCallback *SI) {

6190 AsmToken OperationEntryTok = Lexer.getTok();

6191 SMLoc OperationEntryLoc = OperationEntryTok.getLoc();

6192 StringRef OperationEntryVal;

6193

6194

6195 if (parseIdentifier(OperationEntryVal))

6196 return Error(OperationEntryLoc, "unexpected token at start of statement");

6197

6198

6199

6200 lexLeadingSpaces();

6201

6202 return parseAndMatchAndEmitTargetInstruction(

6203 Info, OperationEntryVal, OperationEntryTok, OperationEntryLoc);

6204}

6205

6206bool HLASMAsmParser::parseStatement(ParseStatementInfo &Info,

6207 MCAsmParserSemaCallback *SI) {

6208 assert(!hasPendingError() && "parseStatement started with pending error");

6209

6210

6211 bool ShouldParseAsHLASMLabel = false;

6212

6213

6214

6215

6216

6217

6218

6220 ShouldParseAsHLASMLabel = true;

6221

6222

6223

6225

6226 if (getTok().getString().empty() || getTok().getString().front() == '\r' ||

6227 getTok().getString().front() == '\n')

6229 Lex();

6230 return false;

6231 }

6232

6233

6234

6235

6236 lexLeadingSpaces();

6237

6238

6239

6240

6242 if (getTok().getString().front() == '\n' ||

6243 getTok().getString().front() == '\r') {

6245 Lex();

6246 return false;

6247 }

6248 }

6249

6250

6251

6252 if (ShouldParseAsHLASMLabel) {

6253

6254

6255 if (parseAsHLASMLabel(Info, SI)) {

6256

6257

6258 eatToEndOfStatement();

6259 return true;

6260 }

6261 }

6262

6263 return parseAsMachineInstruction(Info, SI);

6264}

6265

6267 bool allow_redef,

6271

6272

6275 return Parser.TokError("missing expression");

6277 return true;

6278

6279

6281 return Parser.Error(

6282 EqualLoc, "relocation specifier not permitted in symbol equating");

6283

6284

6285

6287 if (Sym) {

6290 return Parser.Error(EqualLoc, "redefinition of '" + Name + "'");

6291

6292

6293

6296 } else if (Name == ".") {

6298 return false;

6299 } else

6301

6303

6304 return false;

6305}

6306

6307

6310 unsigned CB) {

6311 if (C.getTargetTriple().isSystemZ() && C.getTargetTriple().isOSzOS())

6312 return new HLASMAsmParser(SM, C, Out, MAI, CB);

6313

6314 return new AsmParser(SM, C, Out, MAI, CB);

6315}

assert(UImm &&(UImm !=~static_cast< T >(0)) &&"Invalid immediate!")

This file defines the StringMap class.

static bool isNot(const MachineRegisterInfo &MRI, const MachineInstr &MI)

This file declares a class to represent arbitrary precision floating point values and provide a varie...

This file implements a class to represent arbitrary precision integral constant values and operations...

static Expected< std::vector< unsigned > > getSymbols(SymbolicFile *Obj, uint16_t Index, raw_ostream &SymNames, SymMap *SymMap)

static bool isValidEncoding(int64_t Encoding)

Definition AsmParser.cpp:4298

static bool isAngleBracketString(SMLoc &StrLoc, SMLoc &EndLoc)

This function checks if the next token is type or arithmetic.

Definition AsmParser.cpp:1389

static unsigned getDarwinBinOpPrecedence(AsmToken::TokenKind K, MCBinaryExpr::Opcode &Kind, bool ShouldUseLogicalShr)

Definition AsmParser.cpp:1499

static unsigned getGNUBinOpPrecedence(const MCAsmInfo &MAI, AsmToken::TokenKind K, MCBinaryExpr::Opcode &Kind, bool ShouldUseLogicalShr)

Definition AsmParser.cpp:1575

static std::string angleBracketString(StringRef AltMacroStr)

creating a string without the escape characters '!'.

Definition AsmParser.cpp:1407

static int rewritesSort(const AsmRewrite *AsmRewriteA, const AsmRewrite *AsmRewriteB)

Definition AsmParser.cpp:5857

static bool parseHexOcta(AsmParser &Asm, uint64_t &hi, uint64_t &lo)

Definition AsmParser.cpp:3163

static bool isOperator(AsmToken::TokenKind kind)

Definition AsmParser.cpp:2557

static GCRegistry::Add< ErlangGC > A("erlang", "erlang-compatible garbage collector")

static GCRegistry::Add< CoreCLRGC > E("coreclr", "CoreCLR-compatible GC")

Analysis containing CSE Info

static ManagedStatic< cl::opt< bool, true >, CreateDebug > Debug

This file contains constants used for implementing Dwarf debug support.

#define DWARF2_FLAG_IS_STMT

#define DWARF2_FLAG_BASIC_BLOCK

#define DWARF2_LINE_DEFAULT_IS_STMT

#define DWARF2_FLAG_PROLOGUE_END

#define DWARF2_FLAG_EPILOGUE_BEGIN

static bool isIdentifierChar(char C)

Return true if the given character satisfies the following regular expression: [-a-zA-Z$....

Promote Memory to Register

ConstantRange Range(APInt(BitWidth, Low), APInt(BitWidth, High))

static bool isValid(const char C)

Returns true if C is a valid mangled character: <0-9a-zA-Z_>.

This file defines the SmallSet class.

This file defines the SmallString class.

This file defines the SmallVector class.

#define DEBUG_WITH_TYPE(TYPE,...)

DEBUG_WITH_TYPE macro - This macro should be used by passes to emit debug information.

static void DiagHandler(const SMDiagnostic &Diag, void *Context)

static APFloat getInf(const fltSemantics &Sem, bool Negative=false)

Factory for Positive and Negative Infinity.

static APFloat getNaN(const fltSemantics &Sem, bool Negative=false, uint64_t payload=0)

Factory for NaN values.

Class for arbitrary precision integers.

LLVM_ABI APInt getLoBits(unsigned numBits) const

Compute an APInt containing numBits lowbits from this APInt.

uint64_t getZExtValue() const

Get zero extended value.

LLVM_ABI APInt getHiBits(unsigned numBits) const

Compute an APInt containing numBits highbits from this APInt.

unsigned getBitWidth() const

Return the number of bits in the APInt.

uint64_t getLimitedValue(uint64_t Limit=UINT64_MAX) const

If this value is smaller than the specified limit, return it, otherwise return the limit value.

bool isIntN(unsigned N) const

Check if this APInt has an N-bits unsigned integer value.

ConditionalAssemblyType TheCond

SMLoc getLoc() const

Get the current source location.

const AsmToken peekTok(bool ShouldSkipSpace=true)

Look ahead at the next token to be lexed.

bool getAllowAtInIdentifier()

void UnLex(AsmToken const &Token)

AsmToken::TokenKind getKind() const

Get the kind of current token.

const MCAsmInfo & getMAI() const

const AsmToken & getTok() const

Get the current (last) lexed token.

bool is(AsmToken::TokenKind K) const

Check if the current token has kind K.

SMLoc getErrLoc()

Get the current error location.

const std::string & getErr()

Get the current error string.

const AsmToken & Lex()

Consume the next token from the input stream and return it.

void setSkipSpace(bool val)

Set whether spaces should be ignored by the lexer.

LLVM_ABI void setBuffer(StringRef Buf, const char *ptr=nullptr, bool EndStatementAtEOF=true)

Set buffer to be lexed.

bool isNot(AsmToken::TokenKind K) const

Check if the current token has kind K.

LLVM_ABI size_t peekTokens(MutableArrayRef< AsmToken > Buf, bool ShouldSkipSpace=true)

Look ahead an arbitrary number of tokens.

LLVM_ABI SMLoc getLoc() const

bool isNot(TokenKind K) const

StringRef getString() const

Get the string for the current token, this includes all characters (for example, the quotes on string...

StringRef getStringContents() const

Get the contents of a string token (without quotes).

bool is(TokenKind K) const

LLVM_ABI SMLoc getEndLoc() const

StringRef getIdentifier() const

Get the identifier string for the current token, which should be an identifier or a string.

Error takeError()

Take ownership of the stored error.

This class is intended to be used as a base class for asm properties and features specific to the tar...

bool preserveAsmComments() const

Return true if assembly (inline or otherwise) should be parsed.

bool isLittleEndian() const

True if the target is little endian.

bool useAtForSpecifier() const

bool doesAllowAtInName() const

StringRef getPrivateLabelPrefix() const

std::optional< uint32_t > getSpecifierForName(StringRef Name) const

LCOMM::LCOMMType getLCOMMDirectiveAlignmentType() const

bool shouldUseLogicalShr() const

StringRef getCommentString() const

bool hasSubsectionsViaSymbols() const

bool getCOMMDirectiveAlignmentIsInBytes() const

virtual bool useCodeAlign(const MCSection &Sec) const

bool useParensForSpecifier() const

bool getDollarIsPC() const

virtual ~MCAsmParserSemaCallback()

Generic assembler parser interface, for use by target specific assembly parsers.

bool Error(SMLoc L, const Twine &Msg, SMRange Range={})

Return an error at the location L, with the message Msg.

virtual bool parseExpression(const MCExpr *&Res, SMLoc &EndLoc)=0

Parse an arbitrary expression.

bool parseAtSpecifier(const MCExpr *&Res, SMLoc &EndLoc)

Definition AsmParser.cpp:1417

const AsmToken & getTok() const

Get the current AsmToken from the stream.

const MCExpr * applySpecifier(const MCExpr *E, uint32_t Variant)

Definition AsmParser.cpp:1321

bool parseOptionalToken(AsmToken::TokenKind T)

Attempt to parse and consume token, returning true on success.

virtual const AsmToken & Lex()=0

Get the next AsmToken in the stream, possibly handling file inclusion first.

bool TokError(const Twine &Msg, SMRange Range={})

Report an error at the current lexer location.

MCStreamer & getStreamer()

MCTargetAsmParser & getTargetParser() const

Binary assembler expressions.

const MCExpr * getLHS() const

Get the left-hand side expression of the binary operator.

const MCExpr * getRHS() const

Get the right-hand side expression of the binary operator.

Opcode getOpcode() const

Get the kind of this binary expression.

static LLVM_ABI const MCBinaryExpr * create(Opcode Op, const MCExpr *LHS, const MCExpr *RHS, MCContext &Ctx, SMLoc Loc=SMLoc())

@ AShr

Arithmetic shift right.

@ LShr

Logical shift right.

@ GTE

Signed greater than or equal comparison (result is either 0 or some target-specific non-zero value).

@ GT

Signed greater than comparison (result is either 0 or some target-specific non-zero value)

@ Xor

Bitwise exclusive or.

@ LT

Signed less than comparison (result is either 0 or some target-specific non-zero value).

@ LTE

Signed less than or equal comparison (result is either 0 or some target-specific non-zero value).

@ NE

Inequality comparison.

static LLVM_ABI const MCConstantExpr * create(int64_t Value, MCContext &Ctx, bool PrintInHex=false, unsigned SizeInBytes=0)

Context object for machine code objects.

void * allocate(unsigned Size, unsigned Align=8)

bool isDwarfMD5UsageConsistent(unsigned CUID) const

Reports whether MD5 checksum usage is consistent (all-or-none).

LLVM_ABI MCSymbol * createTempSymbol()

Create a temporary symbol with a unique name.

bool getGenDwarfForAssembly()

void setGenDwarfForAssembly(bool Value)

void setDwarfVersion(uint16_t v)

MCDwarfLineTable & getMCDwarfLineTable(unsigned CUID)

LLVM_ABI MCSymbol * lookupSymbol(const Twine &Name) const

Get the symbol for Name, or null.

LLVM_ABI MCSymbol * createDirectionalLocalSymbol(unsigned LocalLabelVal)

Create the definition of a directional local symbol for numbered label (used for "1:" definitions).

uint16_t getDwarfVersion() const

const MCAsmInfo * getAsmInfo() const

LLVM_ABI MCSymbol * cloneSymbol(MCSymbol &Sym)

Clone a symbol for the .set directive, replacing it in the symbol table.

LLVM_ABI MCSymbol * parseSymbol(const Twine &Name)

Variant of getOrCreateSymbol that handles backslash-escaped symbols.

LLVM_ABI MCSymbol * getDirectionalLocalSymbol(unsigned LocalLabelVal, bool Before)

Create and return a directional local symbol for numbered label (used for "1b" or 1f" references).

Base class for the full range of assembler expressions which are needed for parsing.

LLVM_ABI bool evaluateAsRelocatable(MCValue &Res, const MCAssembler *Asm) const

Try to evaluate the expression to a relocatable value, i.e.

@ Unary

Unary expressions.

@ Constant

Constant expressions.

@ SymbolRef

References to labels and assigned expressions.

@ Target

Target specific expression.

@ Specifier

Expression with a relocation specifier.

@ Binary

Binary expressions.

static LLVM_ABI void Make(MCSymbol *Symbol, MCStreamer *MCOS, SourceMgr &SrcMgr, SMLoc &Loc)

virtual void printRegName(raw_ostream &OS, MCRegister Reg)

Print the assembler register name.

const MCInstrDesc & get(unsigned Opcode) const

Return the machine instruction descriptor that corresponds to the specified instruction opcode.

virtual bool isMemUseUpRegs() const

isMemUseUpRegs - Is memory operand use up regs, for example, intel MS inline asm may use ARR[baseReg ...

virtual bool isReg() const =0

isReg - Is this a register operand?

virtual bool needAddressOf() const

needAddressOf - Do we need to emit code to get the address of the variable/label?

virtual MCRegister getReg() const =0

virtual bool isOffsetOfLocal() const

isOffsetOfLocal - Do we need to emit code to get the offset of the local variable,...

virtual StringRef getSymName()

virtual bool isImm() const =0

isImm - Is this an immediate operand?

unsigned getMCOperandNum()

StringRef getConstraint()

virtual void * getOpDecl()

void setBeginSymbol(MCSymbol *Sym)

MCSymbol * getBeginSymbol()

Streaming machine code generation interface.

virtual void emitAssignment(MCSymbol *Symbol, const MCExpr *Value)

Emit an assignment of Value to Symbol.

virtual void addBlankLine()

Emit a blank line to a .s file to pretty it up.

virtual void initSections(bool NoExecStack, const MCSubtargetInfo &STI)

Create the default sections and set the initial one.

void setStartTokLocPtr(const SMLoc *Loc)

virtual bool emitSymbolAttribute(MCSymbol *Symbol, MCSymbolAttr Attribute)=0

Add the given Attribute to Symbol.

virtual void addExplicitComment(const Twine &T)

Add explicit comment T.

virtual void emitLabel(MCSymbol *Symbol, SMLoc Loc=SMLoc())

Emit a label for Symbol into the current section.

MCTargetStreamer * getTargetStreamer()

virtual void emitValueToOffset(const MCExpr *Offset, unsigned char Value, SMLoc Loc)

Emit some number of copies of Value until the byte offset Offset is reached.

virtual void emitConditionalAssignment(MCSymbol *Symbol, const MCExpr *Value)

Emit an assignment of Value to Symbol, but only if Value is also emitted.

void finish(SMLoc EndLoc=SMLoc())

Finish emission of machine code.

Represent a reference to a symbol from inside an expression.

const MCSymbol & getSymbol() const

uint16_t getSpecifier() const

static const MCSymbolRefExpr * create(const MCSymbol *Symbol, MCContext &Ctx, SMLoc Loc=SMLoc())

MCSymbol - Instances of this class represent a symbol name in the MC file, and MCSymbols are created ...

bool isDefined() const

isDefined - Check if this symbol is defined (i.e., it has an address).

bool isUndefined() const

isUndefined - Check if this symbol undefined (i.e., implicitly defined).

StringRef getName() const

getName - Get the symbol name.

bool isVariable() const

isVariable - Check if this is a variable symbol.

bool isRedefinable() const

Check if this symbol is redefinable.

void setRedefinable(bool Value)

Mark this symbol as redefinable.

void redefineIfPossible()

Prepare this symbol to be redefined.

const MCExpr * getVariableValue() const

Get the expression of the variable symbol.

bool isTemporary() const

isTemporary - Check if this is an assembler temporary symbol.

Unary assembler expressions.

Opcode getOpcode() const

Get the kind of this unary expression.

static LLVM_ABI const MCUnaryExpr * create(Opcode Op, const MCExpr *Expr, MCContext &Ctx, SMLoc Loc=SMLoc())

static const MCUnaryExpr * createLNot(const MCExpr *Expr, MCContext &Ctx, SMLoc Loc=SMLoc())

const MCExpr * getSubExpr() const

Get the child of this unary expression.

static const MCUnaryExpr * createPlus(const MCExpr *Expr, MCContext &Ctx, SMLoc Loc=SMLoc())

static const MCUnaryExpr * createNot(const MCExpr *Expr, MCContext &Ctx, SMLoc Loc=SMLoc())

static const MCUnaryExpr * createMinus(const MCExpr *Expr, MCContext &Ctx, SMLoc Loc=SMLoc())

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.

StringRef getBuffer() const

constexpr bool isFailure() const

constexpr bool isSuccess() const

SourceMgr::DiagKind getKind() const

StringRef getLineContents() const

StringRef getMessage() const

ArrayRef< std::pair< unsigned, unsigned > > getRanges() const

const SourceMgr * getSourceMgr() const

Represents a location in source code.

static SMLoc getFromPointer(const char *Ptr)

constexpr const char * getPointer() const

constexpr bool isValid() const

std::pair< const_iterator, bool > insert(const T &V)

insert - Insert an element into the set if it isn't already there.

void assign(size_type NumElts, ValueParamT Elt)

reference emplace_back(ArgTypes &&... Args)

iterator erase(const_iterator CI)

void push_back(const T &Elt)

This owns the files read by a parser, handles include stacks, and handles diagnostic wrangling.

unsigned getMainFileID() const

const MemoryBuffer * getMemoryBuffer(unsigned i) const

LLVM_ABI void PrintMessage(raw_ostream &OS, SMLoc Loc, DiagKind Kind, const Twine &Msg, ArrayRef< SMRange > Ranges={}, ArrayRef< SMFixIt > FixIts={}, bool ShowColors=true) const

Emit a message about the specified location with the specified string.

SMLoc getParentIncludeLoc(unsigned i) const

LLVM_ABI void PrintIncludeStack(SMLoc IncludeLoc, raw_ostream &OS) const

Prints the names of included files and the line of the file they were included from.

LLVM_ABI unsigned FindBufferContainingLoc(SMLoc Loc) const

Return the ID of the buffer containing the specified location.

void(*)(const SMDiagnostic &, void *Context) DiagHandlerTy

Clients that want to handle their own diagnostics in a custom way can register a function pointer+con...

void setDiagHandler(DiagHandlerTy DH, void *Ctx=nullptr)

Specify a diagnostic handler to be invoked every time PrintMessage is called.

LLVM_ABI unsigned AddIncludeFile(const std::string &Filename, SMLoc IncludeLoc, std::string &IncludedFile)

Search for a file with the specified name in the current directory or in one of the IncludeDirs.

unsigned FindLineNumber(SMLoc Loc, unsigned BufferID=0) const

Find the line number for the specified location in the specified file.

unsigned AddNewSourceBuffer(std::unique_ptr< MemoryBuffer > F, SMLoc IncludeLoc)

Add a new source buffer to this source manager.

ValueTy lookup(StringRef Key) const

lookup - Return the entry for the specified key, or a default constructed value if no such entry exis...

StringMapIterBase< ValueTy, true > const_iterator

StringRef - Represent a constant reference to a string, i.e.

std::pair< StringRef, StringRef > split(char Separator) const

Split into two substrings around the first occurrence of a separator character.

std::string str() const

str - Get the contents as an std::string.

constexpr StringRef substr(size_t Start, size_t N=npos) const

Return a reference to the substring from [Start, Start + N).

bool starts_with(StringRef Prefix) const

Check if this string starts with the given Prefix.

constexpr bool empty() const

empty - Check if the string is empty.

StringRef drop_front(size_t N=1) const

Return a StringRef equal to 'this' but with the first N elements dropped.

LLVM_ABI std::string upper() const

Convert the given ASCII string to uppercase.

constexpr size_t size() const

size - Get the string size.

char front() const

front - Get the first character in the string.

constexpr const char * data() const

data - Get a pointer to the start of the string (which may not be null terminated).

StringRef take_front(size_t N=1) const

Return a StringRef equal to 'this' but with only the first N elements remaining.

StringRef trim(char Char) const

Return string with consecutive Char characters starting from the left and right removed.

LLVM_ABI std::string lower() const

LLVM_ABI int compare_insensitive(StringRef RHS) const

Compare two strings, ignoring case.

LLVM Value Representation.

StringRef str() const

Return a StringRef for the vector contents.

#define llvm_unreachable(msg)

Marks that the current location is not supposed to be reachable.

constexpr char Align[]

Key for Kernel::Arg::Metadata::mAlign.

constexpr char SymbolName[]

Key for Kernel::Metadata::mSymbolName.

unsigned ID

LLVM IR allows to use arbitrary numbers as calling convention identifiers.

@ C

The default llvm calling convention, compatible with C.

Flag

These should be considered private to the implementation of the MCInstrDesc class.

bool parseAssignmentExpression(StringRef Name, bool allow_redef, MCAsmParser &Parser, MCSymbol *&Symbol, const MCExpr *&Value)

Parse a value expression and return whether it can be assigned to a symbol with the given name.

Definition AsmParser.cpp:6266

LLVM_ABI SimpleSymbol parseSymbol(StringRef SymName)

Get symbol classification by parsing the name of a symbol.

std::variant< std::monostate, DecisionParameters, BranchParameters > Parameters

The type of MC/DC-specific parameters.

@ Parameter

An inlay hint that is for a parameter.

Context & getContext() const

LLVM_ABI Instruction & front() const

This is an optimization pass for GlobalISel generic memory operations.

bool errorToBool(Error Err)

Helper for converting an Error to a bool.

FunctionAddr VTableAddr Value

auto size(R &&Range, std::enable_if_t< std::is_base_of< std::random_access_iterator_tag, typename std::iterator_traits< decltype(Range.begin())>::iterator_category >::value, void > *=nullptr)

Get the size of a range.

std::string fromHex(StringRef Input)

Convert hexadecimal string Input to its binary representation. The return string is half the size of ...

constexpr bool isInt(int64_t x)

Checks if an integer fits into the given bit width.

unsigned hexDigitValue(char C)

Interpret the given character C as a hexadecimal digit and return its value.

decltype(auto) dyn_cast(const From &Val)

dyn_cast - Return the argument parameter cast to the specified type.

LLVM_ABI raw_fd_ostream & outs()

This returns a reference to a raw_fd_ostream for standard output.

std::tuple< uint64_t, uint32_t > InlineSite

void append_range(Container &C, Range &&R)

Wrapper function to append range R to container C.

constexpr bool isUIntN(unsigned N, uint64_t x)

Checks if an unsigned integer fits into the given (dynamic) bit width.

constexpr bool isPowerOf2_64(uint64_t Value)

Return true if the argument is a power of two > 0 (64 bit edition.)

std::vector< MCAsmMacroParameter > MCAsmMacroParameters

auto unique(Range &&R, Predicate P)

unsigned Log2_64(uint64_t Value)

Return the floor log base 2 of the specified value, -1 if the value is zero.

auto reverse(ContainerTy &&C)

cl::opt< unsigned > AsmMacroMaxNestingDepth

SmallVector< InlineSite, 8 > MCPseudoProbeInlineStack

const char AsmRewritePrecedence[]

LLVM_ABI raw_ostream & dbgs()

dbgs() - This returns a reference to a raw_ostream for debugging messages.

static bool hasDiscriminator(uint32_t Flags)

bool isDigit(char C)

Checks if character C is one of the 10 decimal digits.

FunctionAddr VTableAddr Count

constexpr bool isUInt(uint64_t x)

Checks if an unsigned integer fits into the given bit width.

LLVM_ABI llvm::Error decodeBase64(llvm::StringRef Input, std::vector< char > &Output)

class LLVM_GSL_OWNER SmallVector

Forward declaration of SmallVector so that calculateSmallVectorDefaultInlinedElements can reference s...

bool isa(const From &Val)

isa - Return true if the parameter to the template is an instance of one of the template type argu...

LLVM_ABI raw_fd_ostream & errs()

This returns a reference to a raw_ostream for standard error.

LLVM_ABI MCAsmParser * createMCAsmParser(SourceMgr &, MCContext &, MCStreamer &, const MCAsmInfo &, unsigned CB=0)

Create an MCAsmParser instance for parsing assembly similar to gas syntax.

Definition AsmParser.cpp:6308

FunctionAddr VTableAddr uintptr_t uintptr_t Data

@ Sub

Subtraction of integers.

FunctionAddr VTableAddr Next

auto count(R &&Range, const E &Element)

Wrapper function around std::count to count the number of times an element Element occurs in the give...

ArrayRef(const T &OneElt) -> ArrayRef< T >

std::string toString(const APInt &I, unsigned Radix, bool Signed, bool formatAsCLiteral=false, bool UpperCase=true, bool InsertSeparators=false)

decltype(auto) cast(const From &Val)

cast - Return the argument parameter cast to the specified type.

constexpr bool isIntN(unsigned N, int64_t x)

Checks if an signed integer fits into the given (dynamic) bit width.

bool isHexDigit(char C)

Checks if character C is a hexadecimal numeric character.

void array_pod_sort(IteratorTy Start, IteratorTy End)

array_pod_sort - This sorts an array with the specified start and end extent.

T bit_floor(T Value)

Returns the largest integral power of two no greater than Value if Value is nonzero.

void consumeError(Error Err)

Consume a Error without doing anything.

@ MCSA_WeakDefAutoPrivate

.weak_def_can_be_hidden (MachO)

@ MCSA_Memtag

.memtag (ELF)

@ MCSA_PrivateExtern

.private_extern (MachO)

@ MCSA_WeakReference

.weak_reference (MachO)

@ MCSA_LazyReference

.lazy_reference (MachO)

@ MCSA_Reference

.reference (MachO)

@ MCSA_SymbolResolver

.symbol_resolver (MachO)

@ MCSA_WeakDefinition

.weak_definition (MachO)

@ MCSA_Global

.type _foo, @gnu_unique_object

@ MCSA_NoDeadStrip

.no_dead_strip (MachO)

ArrayRef< int > hi(ArrayRef< int > Vuu)

ArrayRef< int > lo(ArrayRef< int > Vuu)

std::vector< AsmToken > Value

std::optional< MD5::MD5Result > Checksum

The MD5 checksum, if there is one.

std::optional< StringRef > Source

The source code of the file.