1 //===- MILexer.h - Lexer for machine instructions ---------------*- C++ -*-===// 2 // 3 // Part of the LLVM Project, under the Apache License v2.0 with LLVM Exceptions. 4 // See https://llvm.org/LICENSE.txt for license information. 5 // SPDX-License-Identifier: Apache-2.0 WITH LLVM-exception 6 // 7 //===----------------------------------------------------------------------===// 8 // 9 // This file declares the function that lexes the machine instruction source 10 // string. 11 // 12 //===----------------------------------------------------------------------===// 13 14 #ifndef LLVM_LIB_CODEGEN_MIRPARSER_MILEXER_H 15 #define LLVM_LIB_CODEGEN_MIRPARSER_MILEXER_H 16 17 #include "llvm/ADT/APSInt.h" 18 #include "llvm/ADT/StringRef.h" 19 #include <string> 20 21 namespace llvm { 22 23 class Twine; 24 25 /// A token produced by the machine instruction lexer. 26 struct MIToken { 27 enum TokenKind { 28 // Markers 29 Eof, 30 Error, 31 Newline, 32 33 // Tokens with no info. 34 comma, 35 equal, 36 underscore, 37 colon, 38 coloncolon, 39 dot, 40 exclaim, 41 lparen, 42 rparen, 43 lbrace, 44 rbrace, 45 plus, 46 minus, 47 less, 48 greater, 49 50 // Keywords 51 kw_implicit, 52 kw_implicit_define, 53 kw_def, 54 kw_dead, 55 kw_dereferenceable, 56 kw_killed, 57 kw_undef, 58 kw_internal, 59 kw_early_clobber, 60 kw_debug_use, 61 kw_renamable, 62 kw_tied_def, 63 kw_frame_setup, 64 kw_frame_destroy, 65 kw_nnan, 66 kw_ninf, 67 kw_nsz, 68 kw_arcp, 69 kw_contract, 70 kw_afn, 71 kw_reassoc, 72 kw_nuw, 73 kw_nsw, 74 kw_exact, 75 kw_nofpexcept, 76 kw_debug_location, 77 kw_debug_instr_number, 78 kw_cfi_same_value, 79 kw_cfi_offset, 80 kw_cfi_rel_offset, 81 kw_cfi_def_cfa_register, 82 kw_cfi_def_cfa_offset, 83 kw_cfi_adjust_cfa_offset, 84 kw_cfi_escape, 85 kw_cfi_def_cfa, 86 kw_cfi_register, 87 kw_cfi_remember_state, 88 kw_cfi_restore, 89 kw_cfi_restore_state, 90 kw_cfi_undefined, 91 kw_cfi_window_save, 92 kw_cfi_aarch64_negate_ra_sign_state, 93 kw_blockaddress, 94 kw_intrinsic, 95 kw_target_index, 96 kw_half, 97 kw_float, 98 kw_double, 99 kw_x86_fp80, 100 kw_fp128, 101 kw_ppc_fp128, 102 kw_target_flags, 103 kw_volatile, 104 kw_non_temporal, 105 kw_invariant, 106 kw_align, 107 kw_addrspace, 108 kw_stack, 109 kw_got, 110 kw_jump_table, 111 kw_constant_pool, 112 kw_call_entry, 113 kw_custom, 114 kw_liveout, 115 kw_address_taken, 116 kw_landing_pad, 117 kw_ehfunclet_entry, 118 kw_liveins, 119 kw_successors, 120 kw_floatpred, 121 kw_intpred, 122 kw_shufflemask, 123 kw_pre_instr_symbol, 124 kw_post_instr_symbol, 125 kw_heap_alloc_marker, 126 kw_bbsections, 127 kw_unknown_size, 128 129 // Named metadata keywords 130 md_tbaa, 131 md_alias_scope, 132 md_noalias, 133 md_range, 134 md_diexpr, 135 md_dilocation, 136 137 // Identifier tokens 138 Identifier, 139 NamedRegister, 140 NamedVirtualRegister, 141 MachineBasicBlockLabel, 142 MachineBasicBlock, 143 StackObject, 144 FixedStackObject, 145 NamedGlobalValue, 146 GlobalValue, 147 ExternalSymbol, 148 MCSymbol, 149 150 // Other tokens 151 IntegerLiteral, 152 FloatingPointLiteral, 153 HexLiteral, 154 VectorLiteral, 155 VirtualRegister, 156 ConstantPoolItem, 157 JumpTableIndex, 158 NamedIRBlock, 159 IRBlock, 160 NamedIRValue, 161 IRValue, 162 QuotedIRValue, // `<constant value>` 163 SubRegisterIndex, 164 StringConstant 165 }; 166 167 private: 168 TokenKind Kind = Error; 169 StringRef Range; 170 StringRef StringValue; 171 std::string StringValueStorage; 172 APSInt IntVal; 173 174 public: 175 MIToken() = default; 176 177 MIToken &reset(TokenKind Kind, StringRef Range); 178 179 MIToken &setStringValue(StringRef StrVal); 180 MIToken &setOwnedStringValue(std::string StrVal); 181 MIToken &setIntegerValue(APSInt IntVal); 182 kindMIToken183 TokenKind kind() const { return Kind; } 184 isErrorMIToken185 bool isError() const { return Kind == Error; } 186 isNewlineOrEOFMIToken187 bool isNewlineOrEOF() const { return Kind == Newline || Kind == Eof; } 188 isErrorOrEOFMIToken189 bool isErrorOrEOF() const { return Kind == Error || Kind == Eof; } 190 isRegisterMIToken191 bool isRegister() const { 192 return Kind == NamedRegister || Kind == underscore || 193 Kind == NamedVirtualRegister || Kind == VirtualRegister; 194 } 195 isRegisterFlagMIToken196 bool isRegisterFlag() const { 197 return Kind == kw_implicit || Kind == kw_implicit_define || 198 Kind == kw_def || Kind == kw_dead || Kind == kw_killed || 199 Kind == kw_undef || Kind == kw_internal || 200 Kind == kw_early_clobber || Kind == kw_debug_use || 201 Kind == kw_renamable; 202 } 203 isMemoryOperandFlagMIToken204 bool isMemoryOperandFlag() const { 205 return Kind == kw_volatile || Kind == kw_non_temporal || 206 Kind == kw_dereferenceable || Kind == kw_invariant || 207 Kind == StringConstant; 208 } 209 isMIToken210 bool is(TokenKind K) const { return Kind == K; } 211 isNotMIToken212 bool isNot(TokenKind K) const { return Kind != K; } 213 locationMIToken214 StringRef::iterator location() const { return Range.begin(); } 215 rangeMIToken216 StringRef range() const { return Range; } 217 218 /// Return the token's string value. stringValueMIToken219 StringRef stringValue() const { return StringValue; } 220 integerValueMIToken221 const APSInt &integerValue() const { return IntVal; } 222 hasIntegerValueMIToken223 bool hasIntegerValue() const { 224 return Kind == IntegerLiteral || Kind == MachineBasicBlock || 225 Kind == MachineBasicBlockLabel || Kind == StackObject || 226 Kind == FixedStackObject || Kind == GlobalValue || 227 Kind == VirtualRegister || Kind == ConstantPoolItem || 228 Kind == JumpTableIndex || Kind == IRBlock || Kind == IRValue; 229 } 230 }; 231 232 /// Consume a single machine instruction token in the given source and return 233 /// the remaining source string. 234 StringRef lexMIToken( 235 StringRef Source, MIToken &Token, 236 function_ref<void(StringRef::iterator, const Twine &)> ErrorCallback); 237 238 } // end namespace llvm 239 240 #endif // LLVM_LIB_CODEGEN_MIRPARSER_MILEXER_H 241