1 //===-- MipsMCCodeEmitter.cpp - Convert Mips Code to Machine Code ---------===// 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 implements the MipsMCCodeEmitter class. 10 // 11 //===----------------------------------------------------------------------===// 12 13 #include "MipsMCCodeEmitter.h" 14 #include "MCTargetDesc/MipsFixupKinds.h" 15 #include "MCTargetDesc/MipsMCExpr.h" 16 #include "MCTargetDesc/MipsMCTargetDesc.h" 17 #include "llvm/ADT/APFloat.h" 18 #include "llvm/ADT/APInt.h" 19 #include "llvm/ADT/SmallVector.h" 20 #include "llvm/MC/MCContext.h" 21 #include "llvm/MC/MCExpr.h" 22 #include "llvm/MC/MCFixup.h" 23 #include "llvm/MC/MCInst.h" 24 #include "llvm/MC/MCInstrDesc.h" 25 #include "llvm/MC/MCInstrInfo.h" 26 #include "llvm/MC/MCRegisterInfo.h" 27 #include "llvm/MC/MCSubtargetInfo.h" 28 #include "llvm/Support/Casting.h" 29 #include "llvm/Support/ErrorHandling.h" 30 #include "llvm/Support/raw_ostream.h" 31 #include <cassert> 32 #include <cstdint> 33 34 using namespace llvm; 35 36 #define DEBUG_TYPE "mccodeemitter" 37 38 #define GET_INSTRMAP_INFO 39 #include "MipsGenInstrInfo.inc" 40 #undef GET_INSTRMAP_INFO 41 42 namespace llvm { 43 44 MCCodeEmitter *createMipsMCCodeEmitterEB(const MCInstrInfo &MCII, 45 const MCRegisterInfo &MRI, 46 MCContext &Ctx) { 47 return new MipsMCCodeEmitter(MCII, Ctx, false); 48 } 49 50 MCCodeEmitter *createMipsMCCodeEmitterEL(const MCInstrInfo &MCII, 51 const MCRegisterInfo &MRI, 52 MCContext &Ctx) { 53 return new MipsMCCodeEmitter(MCII, Ctx, true); 54 } 55 56 } // end namespace llvm 57 58 // If the D<shift> instruction has a shift amount that is greater 59 // than 31 (checked in calling routine), lower it to a D<shift>32 instruction 60 static void LowerLargeShift(MCInst& Inst) { 61 assert(Inst.getNumOperands() == 3 && "Invalid no. of operands for shift!"); 62 assert(Inst.getOperand(2).isImm()); 63 64 int64_t Shift = Inst.getOperand(2).getImm(); 65 if (Shift <= 31) 66 return; // Do nothing 67 Shift -= 32; 68 69 // saminus32 70 Inst.getOperand(2).setImm(Shift); 71 72 switch (Inst.getOpcode()) { 73 default: 74 // Calling function is not synchronized 75 llvm_unreachable("Unexpected shift instruction"); 76 case Mips::DSLL: 77 Inst.setOpcode(Mips::DSLL32); 78 return; 79 case Mips::DSRL: 80 Inst.setOpcode(Mips::DSRL32); 81 return; 82 case Mips::DSRA: 83 Inst.setOpcode(Mips::DSRA32); 84 return; 85 case Mips::DROTR: 86 Inst.setOpcode(Mips::DROTR32); 87 return; 88 } 89 } 90 91 // Fix a bad compact branch encoding for beqc/bnec. 92 void MipsMCCodeEmitter::LowerCompactBranch(MCInst& Inst) const { 93 // Encoding may be illegal !(rs < rt), but this situation is 94 // easily fixed. 95 unsigned RegOp0 = Inst.getOperand(0).getReg(); 96 unsigned RegOp1 = Inst.getOperand(1).getReg(); 97 98 unsigned Reg0 = Ctx.getRegisterInfo()->getEncodingValue(RegOp0); 99 unsigned Reg1 = Ctx.getRegisterInfo()->getEncodingValue(RegOp1); 100 101 if (Inst.getOpcode() == Mips::BNEC || Inst.getOpcode() == Mips::BEQC || 102 Inst.getOpcode() == Mips::BNEC64 || Inst.getOpcode() == Mips::BEQC64) { 103 assert(Reg0 != Reg1 && "Instruction has bad operands ($rs == $rt)!"); 104 if (Reg0 < Reg1) 105 return; 106 } else if (Inst.getOpcode() == Mips::BNVC || Inst.getOpcode() == Mips::BOVC) { 107 if (Reg0 >= Reg1) 108 return; 109 } else if (Inst.getOpcode() == Mips::BNVC_MMR6 || 110 Inst.getOpcode() == Mips::BOVC_MMR6) { 111 if (Reg1 >= Reg0) 112 return; 113 } else 114 llvm_unreachable("Cannot rewrite unknown branch!"); 115 116 Inst.getOperand(0).setReg(RegOp1); 117 Inst.getOperand(1).setReg(RegOp0); 118 } 119 120 bool MipsMCCodeEmitter::isMicroMips(const MCSubtargetInfo &STI) const { 121 return STI.getFeatureBits()[Mips::FeatureMicroMips]; 122 } 123 124 bool MipsMCCodeEmitter::isMips32r6(const MCSubtargetInfo &STI) const { 125 return STI.getFeatureBits()[Mips::FeatureMips32r6]; 126 } 127 128 void MipsMCCodeEmitter::EmitByte(unsigned char C, raw_ostream &OS) const { 129 OS << (char)C; 130 } 131 132 void MipsMCCodeEmitter::emitInstruction(uint64_t Val, unsigned Size, 133 const MCSubtargetInfo &STI, 134 raw_ostream &OS) const { 135 // Output the instruction encoding in little endian byte order. 136 // Little-endian byte ordering: 137 // mips32r2: 4 | 3 | 2 | 1 138 // microMIPS: 2 | 1 | 4 | 3 139 if (IsLittleEndian && Size == 4 && isMicroMips(STI)) { 140 emitInstruction(Val >> 16, 2, STI, OS); 141 emitInstruction(Val, 2, STI, OS); 142 } else { 143 for (unsigned i = 0; i < Size; ++i) { 144 unsigned Shift = IsLittleEndian ? i * 8 : (Size - 1 - i) * 8; 145 EmitByte((Val >> Shift) & 0xff, OS); 146 } 147 } 148 } 149 150 /// encodeInstruction - Emit the instruction. 151 /// Size the instruction with Desc.getSize(). 152 void MipsMCCodeEmitter:: 153 encodeInstruction(const MCInst &MI, raw_ostream &OS, 154 SmallVectorImpl<MCFixup> &Fixups, 155 const MCSubtargetInfo &STI) const 156 { 157 // Non-pseudo instructions that get changed for direct object 158 // only based on operand values. 159 // If this list of instructions get much longer we will move 160 // the check to a function call. Until then, this is more efficient. 161 MCInst TmpInst = MI; 162 switch (MI.getOpcode()) { 163 // If shift amount is >= 32 it the inst needs to be lowered further 164 case Mips::DSLL: 165 case Mips::DSRL: 166 case Mips::DSRA: 167 case Mips::DROTR: 168 LowerLargeShift(TmpInst); 169 break; 170 // Compact branches, enforce encoding restrictions. 171 case Mips::BEQC: 172 case Mips::BNEC: 173 case Mips::BEQC64: 174 case Mips::BNEC64: 175 case Mips::BOVC: 176 case Mips::BOVC_MMR6: 177 case Mips::BNVC: 178 case Mips::BNVC_MMR6: 179 LowerCompactBranch(TmpInst); 180 } 181 182 unsigned long N = Fixups.size(); 183 uint32_t Binary = getBinaryCodeForInstr(TmpInst, Fixups, STI); 184 185 // Check for unimplemented opcodes. 186 // Unfortunately in MIPS both NOP and SLL will come in with Binary == 0 187 // so we have to special check for them. 188 const unsigned Opcode = TmpInst.getOpcode(); 189 if ((Opcode != Mips::NOP) && (Opcode != Mips::SLL) && 190 (Opcode != Mips::SLL_MM) && (Opcode != Mips::SLL_MMR6) && !Binary) 191 llvm_unreachable("unimplemented opcode in encodeInstruction()"); 192 193 int NewOpcode = -1; 194 if (isMicroMips(STI)) { 195 if (isMips32r6(STI)) { 196 NewOpcode = Mips::MipsR62MicroMipsR6(Opcode, Mips::Arch_micromipsr6); 197 if (NewOpcode == -1) 198 NewOpcode = Mips::Std2MicroMipsR6(Opcode, Mips::Arch_micromipsr6); 199 } 200 else 201 NewOpcode = Mips::Std2MicroMips(Opcode, Mips::Arch_micromips); 202 203 // Check whether it is Dsp instruction. 204 if (NewOpcode == -1) 205 NewOpcode = Mips::Dsp2MicroMips(Opcode, Mips::Arch_mmdsp); 206 207 if (NewOpcode != -1) { 208 if (Fixups.size() > N) 209 Fixups.pop_back(); 210 211 TmpInst.setOpcode (NewOpcode); 212 Binary = getBinaryCodeForInstr(TmpInst, Fixups, STI); 213 } 214 215 if (((MI.getOpcode() == Mips::MOVEP_MM) || 216 (MI.getOpcode() == Mips::MOVEP_MMR6))) { 217 unsigned RegPair = getMovePRegPairOpValue(MI, 0, Fixups, STI); 218 Binary = (Binary & 0xFFFFFC7F) | (RegPair << 7); 219 } 220 } 221 222 const MCInstrDesc &Desc = MCII.get(TmpInst.getOpcode()); 223 224 // Get byte count of instruction 225 unsigned Size = Desc.getSize(); 226 if (!Size) 227 llvm_unreachable("Desc.getSize() returns 0"); 228 229 emitInstruction(Binary, Size, STI, OS); 230 } 231 232 /// getBranchTargetOpValue - Return binary encoding of the branch 233 /// target operand. If the machine operand requires relocation, 234 /// record the relocation and return zero. 235 unsigned MipsMCCodeEmitter:: 236 getBranchTargetOpValue(const MCInst &MI, unsigned OpNo, 237 SmallVectorImpl<MCFixup> &Fixups, 238 const MCSubtargetInfo &STI) const { 239 const MCOperand &MO = MI.getOperand(OpNo); 240 241 // If the destination is an immediate, divide by 4. 242 if (MO.isImm()) return MO.getImm() >> 2; 243 244 assert(MO.isExpr() && 245 "getBranchTargetOpValue expects only expressions or immediates"); 246 247 const MCExpr *FixupExpression = MCBinaryExpr::createAdd( 248 MO.getExpr(), MCConstantExpr::create(-4, Ctx), Ctx); 249 Fixups.push_back(MCFixup::create(0, FixupExpression, 250 MCFixupKind(Mips::fixup_Mips_PC16))); 251 return 0; 252 } 253 254 /// getBranchTargetOpValue1SImm16 - Return binary encoding of the branch 255 /// target operand. If the machine operand requires relocation, 256 /// record the relocation and return zero. 257 unsigned MipsMCCodeEmitter:: 258 getBranchTargetOpValue1SImm16(const MCInst &MI, unsigned OpNo, 259 SmallVectorImpl<MCFixup> &Fixups, 260 const MCSubtargetInfo &STI) const { 261 const MCOperand &MO = MI.getOperand(OpNo); 262 263 // If the destination is an immediate, divide by 2. 264 if (MO.isImm()) return MO.getImm() >> 1; 265 266 assert(MO.isExpr() && 267 "getBranchTargetOpValue expects only expressions or immediates"); 268 269 const MCExpr *FixupExpression = MCBinaryExpr::createAdd( 270 MO.getExpr(), MCConstantExpr::create(-4, Ctx), Ctx); 271 Fixups.push_back(MCFixup::create(0, FixupExpression, 272 MCFixupKind(Mips::fixup_Mips_PC16))); 273 return 0; 274 } 275 276 /// getBranchTargetOpValueMMR6 - Return binary encoding of the branch 277 /// target operand. If the machine operand requires relocation, 278 /// record the relocation and return zero. 279 unsigned MipsMCCodeEmitter:: 280 getBranchTargetOpValueMMR6(const MCInst &MI, unsigned OpNo, 281 SmallVectorImpl<MCFixup> &Fixups, 282 const MCSubtargetInfo &STI) const { 283 const MCOperand &MO = MI.getOperand(OpNo); 284 285 // If the destination is an immediate, divide by 2. 286 if (MO.isImm()) 287 return MO.getImm() >> 1; 288 289 assert(MO.isExpr() && 290 "getBranchTargetOpValueMMR6 expects only expressions or immediates"); 291 292 const MCExpr *FixupExpression = MCBinaryExpr::createAdd( 293 MO.getExpr(), MCConstantExpr::create(-2, Ctx), Ctx); 294 Fixups.push_back(MCFixup::create(0, FixupExpression, 295 MCFixupKind(Mips::fixup_Mips_PC16))); 296 return 0; 297 } 298 299 /// getBranchTargetOpValueLsl2MMR6 - Return binary encoding of the branch 300 /// target operand. If the machine operand requires relocation, 301 /// record the relocation and return zero. 302 unsigned MipsMCCodeEmitter:: 303 getBranchTargetOpValueLsl2MMR6(const MCInst &MI, unsigned OpNo, 304 SmallVectorImpl<MCFixup> &Fixups, 305 const MCSubtargetInfo &STI) const { 306 const MCOperand &MO = MI.getOperand(OpNo); 307 308 // If the destination is an immediate, divide by 4. 309 if (MO.isImm()) 310 return MO.getImm() >> 2; 311 312 assert(MO.isExpr() && 313 "getBranchTargetOpValueLsl2MMR6 expects only expressions or immediates"); 314 315 const MCExpr *FixupExpression = MCBinaryExpr::createAdd( 316 MO.getExpr(), MCConstantExpr::create(-4, Ctx), Ctx); 317 Fixups.push_back(MCFixup::create(0, FixupExpression, 318 MCFixupKind(Mips::fixup_Mips_PC16))); 319 return 0; 320 } 321 322 /// getBranchTarget7OpValueMM - Return binary encoding of the microMIPS branch 323 /// target operand. If the machine operand requires relocation, 324 /// record the relocation and return zero. 325 unsigned MipsMCCodeEmitter:: 326 getBranchTarget7OpValueMM(const MCInst &MI, unsigned OpNo, 327 SmallVectorImpl<MCFixup> &Fixups, 328 const MCSubtargetInfo &STI) const { 329 const MCOperand &MO = MI.getOperand(OpNo); 330 331 // If the destination is an immediate, divide by 2. 332 if (MO.isImm()) return MO.getImm() >> 1; 333 334 assert(MO.isExpr() && 335 "getBranchTargetOpValueMM expects only expressions or immediates"); 336 337 const MCExpr *Expr = MO.getExpr(); 338 Fixups.push_back(MCFixup::create(0, Expr, 339 MCFixupKind(Mips::fixup_MICROMIPS_PC7_S1))); 340 return 0; 341 } 342 343 /// getBranchTargetOpValueMMPC10 - Return binary encoding of the microMIPS 344 /// 10-bit branch target operand. If the machine operand requires relocation, 345 /// record the relocation and return zero. 346 unsigned MipsMCCodeEmitter:: 347 getBranchTargetOpValueMMPC10(const MCInst &MI, unsigned OpNo, 348 SmallVectorImpl<MCFixup> &Fixups, 349 const MCSubtargetInfo &STI) const { 350 const MCOperand &MO = MI.getOperand(OpNo); 351 352 // If the destination is an immediate, divide by 2. 353 if (MO.isImm()) return MO.getImm() >> 1; 354 355 assert(MO.isExpr() && 356 "getBranchTargetOpValuePC10 expects only expressions or immediates"); 357 358 const MCExpr *Expr = MO.getExpr(); 359 Fixups.push_back(MCFixup::create(0, Expr, 360 MCFixupKind(Mips::fixup_MICROMIPS_PC10_S1))); 361 return 0; 362 } 363 364 /// getBranchTargetOpValue - Return binary encoding of the microMIPS branch 365 /// target operand. If the machine operand requires relocation, 366 /// record the relocation and return zero. 367 unsigned MipsMCCodeEmitter:: 368 getBranchTargetOpValueMM(const MCInst &MI, unsigned OpNo, 369 SmallVectorImpl<MCFixup> &Fixups, 370 const MCSubtargetInfo &STI) const { 371 const MCOperand &MO = MI.getOperand(OpNo); 372 373 // If the destination is an immediate, divide by 2. 374 if (MO.isImm()) return MO.getImm() >> 1; 375 376 assert(MO.isExpr() && 377 "getBranchTargetOpValueMM expects only expressions or immediates"); 378 379 const MCExpr *Expr = MO.getExpr(); 380 Fixups.push_back(MCFixup::create(0, Expr, 381 MCFixupKind(Mips:: 382 fixup_MICROMIPS_PC16_S1))); 383 return 0; 384 } 385 386 /// getBranchTarget21OpValue - Return binary encoding of the branch 387 /// target operand. If the machine operand requires relocation, 388 /// record the relocation and return zero. 389 unsigned MipsMCCodeEmitter:: 390 getBranchTarget21OpValue(const MCInst &MI, unsigned OpNo, 391 SmallVectorImpl<MCFixup> &Fixups, 392 const MCSubtargetInfo &STI) const { 393 const MCOperand &MO = MI.getOperand(OpNo); 394 395 // If the destination is an immediate, divide by 4. 396 if (MO.isImm()) return MO.getImm() >> 2; 397 398 assert(MO.isExpr() && 399 "getBranchTarget21OpValue expects only expressions or immediates"); 400 401 const MCExpr *FixupExpression = MCBinaryExpr::createAdd( 402 MO.getExpr(), MCConstantExpr::create(-4, Ctx), Ctx); 403 Fixups.push_back(MCFixup::create(0, FixupExpression, 404 MCFixupKind(Mips::fixup_MIPS_PC21_S2))); 405 return 0; 406 } 407 408 /// getBranchTarget21OpValueMM - Return binary encoding of the branch 409 /// target operand for microMIPS. If the machine operand requires 410 /// relocation, record the relocation and return zero. 411 unsigned MipsMCCodeEmitter:: 412 getBranchTarget21OpValueMM(const MCInst &MI, unsigned OpNo, 413 SmallVectorImpl<MCFixup> &Fixups, 414 const MCSubtargetInfo &STI) const { 415 const MCOperand &MO = MI.getOperand(OpNo); 416 417 // If the destination is an immediate, divide by 4. 418 if (MO.isImm()) return MO.getImm() >> 2; 419 420 assert(MO.isExpr() && 421 "getBranchTarget21OpValueMM expects only expressions or immediates"); 422 423 const MCExpr *FixupExpression = MCBinaryExpr::createAdd( 424 MO.getExpr(), MCConstantExpr::create(-4, Ctx), Ctx); 425 Fixups.push_back(MCFixup::create(0, FixupExpression, 426 MCFixupKind(Mips::fixup_MICROMIPS_PC21_S1))); 427 return 0; 428 } 429 430 /// getBranchTarget26OpValue - Return binary encoding of the branch 431 /// target operand. If the machine operand requires relocation, 432 /// record the relocation and return zero. 433 unsigned MipsMCCodeEmitter:: 434 getBranchTarget26OpValue(const MCInst &MI, unsigned OpNo, 435 SmallVectorImpl<MCFixup> &Fixups, 436 const MCSubtargetInfo &STI) const { 437 const MCOperand &MO = MI.getOperand(OpNo); 438 439 // If the destination is an immediate, divide by 4. 440 if (MO.isImm()) return MO.getImm() >> 2; 441 442 assert(MO.isExpr() && 443 "getBranchTarget26OpValue expects only expressions or immediates"); 444 445 const MCExpr *FixupExpression = MCBinaryExpr::createAdd( 446 MO.getExpr(), MCConstantExpr::create(-4, Ctx), Ctx); 447 Fixups.push_back(MCFixup::create(0, FixupExpression, 448 MCFixupKind(Mips::fixup_MIPS_PC26_S2))); 449 return 0; 450 } 451 452 /// getBranchTarget26OpValueMM - Return binary encoding of the branch 453 /// target operand. If the machine operand requires relocation, 454 /// record the relocation and return zero. 455 unsigned MipsMCCodeEmitter::getBranchTarget26OpValueMM( 456 const MCInst &MI, unsigned OpNo, SmallVectorImpl<MCFixup> &Fixups, 457 const MCSubtargetInfo &STI) const { 458 const MCOperand &MO = MI.getOperand(OpNo); 459 460 // If the destination is an immediate, divide by 2. 461 if (MO.isImm()) 462 return MO.getImm() >> 1; 463 464 assert(MO.isExpr() && 465 "getBranchTarget26OpValueMM expects only expressions or immediates"); 466 467 const MCExpr *FixupExpression = MCBinaryExpr::createAdd( 468 MO.getExpr(), MCConstantExpr::create(-4, Ctx), Ctx); 469 Fixups.push_back(MCFixup::create(0, FixupExpression, 470 MCFixupKind(Mips::fixup_MICROMIPS_PC26_S1))); 471 return 0; 472 } 473 474 /// getJumpOffset16OpValue - Return binary encoding of the jump 475 /// target operand. If the machine operand requires relocation, 476 /// record the relocation and return zero. 477 unsigned MipsMCCodeEmitter:: 478 getJumpOffset16OpValue(const MCInst &MI, unsigned OpNo, 479 SmallVectorImpl<MCFixup> &Fixups, 480 const MCSubtargetInfo &STI) const { 481 const MCOperand &MO = MI.getOperand(OpNo); 482 483 if (MO.isImm()) return MO.getImm(); 484 485 assert(MO.isExpr() && 486 "getJumpOffset16OpValue expects only expressions or an immediate"); 487 488 const MCExpr *Expr = MO.getExpr(); 489 Mips::Fixups FixupKind = 490 isMicroMips(STI) ? Mips::fixup_MICROMIPS_LO16 : Mips::fixup_Mips_LO16; 491 Fixups.push_back(MCFixup::create(0, Expr, MCFixupKind(FixupKind))); 492 return 0; 493 } 494 495 /// getJumpTargetOpValue - Return binary encoding of the jump 496 /// target operand. If the machine operand requires relocation, 497 /// record the relocation and return zero. 498 unsigned MipsMCCodeEmitter:: 499 getJumpTargetOpValue(const MCInst &MI, unsigned OpNo, 500 SmallVectorImpl<MCFixup> &Fixups, 501 const MCSubtargetInfo &STI) const { 502 const MCOperand &MO = MI.getOperand(OpNo); 503 // If the destination is an immediate, divide by 4. 504 if (MO.isImm()) return MO.getImm()>>2; 505 506 assert(MO.isExpr() && 507 "getJumpTargetOpValue expects only expressions or an immediate"); 508 509 const MCExpr *Expr = MO.getExpr(); 510 Fixups.push_back(MCFixup::create(0, Expr, 511 MCFixupKind(Mips::fixup_Mips_26))); 512 return 0; 513 } 514 515 unsigned MipsMCCodeEmitter:: 516 getJumpTargetOpValueMM(const MCInst &MI, unsigned OpNo, 517 SmallVectorImpl<MCFixup> &Fixups, 518 const MCSubtargetInfo &STI) const { 519 const MCOperand &MO = MI.getOperand(OpNo); 520 // If the destination is an immediate, divide by 2. 521 if (MO.isImm()) return MO.getImm() >> 1; 522 523 assert(MO.isExpr() && 524 "getJumpTargetOpValueMM expects only expressions or an immediate"); 525 526 const MCExpr *Expr = MO.getExpr(); 527 Fixups.push_back(MCFixup::create(0, Expr, 528 MCFixupKind(Mips::fixup_MICROMIPS_26_S1))); 529 return 0; 530 } 531 532 unsigned MipsMCCodeEmitter:: 533 getUImm5Lsl2Encoding(const MCInst &MI, unsigned OpNo, 534 SmallVectorImpl<MCFixup> &Fixups, 535 const MCSubtargetInfo &STI) const { 536 const MCOperand &MO = MI.getOperand(OpNo); 537 if (MO.isImm()) { 538 // The immediate is encoded as 'immediate << 2'. 539 unsigned Res = getMachineOpValue(MI, MO, Fixups, STI); 540 assert((Res & 3) == 0); 541 return Res >> 2; 542 } 543 544 assert(MO.isExpr() && 545 "getUImm5Lsl2Encoding expects only expressions or an immediate"); 546 547 return 0; 548 } 549 550 unsigned MipsMCCodeEmitter:: 551 getSImm3Lsa2Value(const MCInst &MI, unsigned OpNo, 552 SmallVectorImpl<MCFixup> &Fixups, 553 const MCSubtargetInfo &STI) const { 554 const MCOperand &MO = MI.getOperand(OpNo); 555 if (MO.isImm()) { 556 int Value = MO.getImm(); 557 return Value >> 2; 558 } 559 560 return 0; 561 } 562 563 unsigned MipsMCCodeEmitter:: 564 getUImm6Lsl2Encoding(const MCInst &MI, unsigned OpNo, 565 SmallVectorImpl<MCFixup> &Fixups, 566 const MCSubtargetInfo &STI) const { 567 const MCOperand &MO = MI.getOperand(OpNo); 568 if (MO.isImm()) { 569 unsigned Value = MO.getImm(); 570 return Value >> 2; 571 } 572 573 return 0; 574 } 575 576 unsigned MipsMCCodeEmitter:: 577 getSImm9AddiuspValue(const MCInst &MI, unsigned OpNo, 578 SmallVectorImpl<MCFixup> &Fixups, 579 const MCSubtargetInfo &STI) const { 580 const MCOperand &MO = MI.getOperand(OpNo); 581 if (MO.isImm()) { 582 unsigned Binary = (MO.getImm() >> 2) & 0x0000ffff; 583 return (((Binary & 0x8000) >> 7) | (Binary & 0x00ff)); 584 } 585 586 return 0; 587 } 588 589 unsigned MipsMCCodeEmitter:: 590 getExprOpValue(const MCExpr *Expr, SmallVectorImpl<MCFixup> &Fixups, 591 const MCSubtargetInfo &STI) const { 592 int64_t Res; 593 594 if (Expr->evaluateAsAbsolute(Res)) 595 return Res; 596 597 MCExpr::ExprKind Kind = Expr->getKind(); 598 if (Kind == MCExpr::Constant) { 599 return cast<MCConstantExpr>(Expr)->getValue(); 600 } 601 602 if (Kind == MCExpr::Binary) { 603 unsigned Res = 604 getExprOpValue(cast<MCBinaryExpr>(Expr)->getLHS(), Fixups, STI); 605 Res += getExprOpValue(cast<MCBinaryExpr>(Expr)->getRHS(), Fixups, STI); 606 return Res; 607 } 608 609 if (Kind == MCExpr::Target) { 610 const MipsMCExpr *MipsExpr = cast<MipsMCExpr>(Expr); 611 612 Mips::Fixups FixupKind = Mips::Fixups(0); 613 switch (MipsExpr->getKind()) { 614 case MipsMCExpr::MEK_None: 615 case MipsMCExpr::MEK_Special: 616 llvm_unreachable("Unhandled fixup kind!"); 617 break; 618 case MipsMCExpr::MEK_DTPREL: 619 // MEK_DTPREL is used for marking TLS DIEExpr only 620 // and contains a regular sub-expression. 621 return getExprOpValue(MipsExpr->getSubExpr(), Fixups, STI); 622 case MipsMCExpr::MEK_CALL_HI16: 623 FixupKind = Mips::fixup_Mips_CALL_HI16; 624 break; 625 case MipsMCExpr::MEK_CALL_LO16: 626 FixupKind = Mips::fixup_Mips_CALL_LO16; 627 break; 628 case MipsMCExpr::MEK_DTPREL_HI: 629 FixupKind = isMicroMips(STI) ? Mips::fixup_MICROMIPS_TLS_DTPREL_HI16 630 : Mips::fixup_Mips_DTPREL_HI; 631 break; 632 case MipsMCExpr::MEK_DTPREL_LO: 633 FixupKind = isMicroMips(STI) ? Mips::fixup_MICROMIPS_TLS_DTPREL_LO16 634 : Mips::fixup_Mips_DTPREL_LO; 635 break; 636 case MipsMCExpr::MEK_GOTTPREL: 637 FixupKind = isMicroMips(STI) ? Mips::fixup_MICROMIPS_GOTTPREL 638 : Mips::fixup_Mips_GOTTPREL; 639 break; 640 case MipsMCExpr::MEK_GOT: 641 FixupKind = isMicroMips(STI) ? Mips::fixup_MICROMIPS_GOT16 642 : Mips::fixup_Mips_GOT; 643 break; 644 case MipsMCExpr::MEK_GOT_CALL: 645 FixupKind = isMicroMips(STI) ? Mips::fixup_MICROMIPS_CALL16 646 : Mips::fixup_Mips_CALL16; 647 break; 648 case MipsMCExpr::MEK_GOT_DISP: 649 FixupKind = isMicroMips(STI) ? Mips::fixup_MICROMIPS_GOT_DISP 650 : Mips::fixup_Mips_GOT_DISP; 651 break; 652 case MipsMCExpr::MEK_GOT_HI16: 653 FixupKind = Mips::fixup_Mips_GOT_HI16; 654 break; 655 case MipsMCExpr::MEK_GOT_LO16: 656 FixupKind = Mips::fixup_Mips_GOT_LO16; 657 break; 658 case MipsMCExpr::MEK_GOT_PAGE: 659 FixupKind = isMicroMips(STI) ? Mips::fixup_MICROMIPS_GOT_PAGE 660 : Mips::fixup_Mips_GOT_PAGE; 661 break; 662 case MipsMCExpr::MEK_GOT_OFST: 663 FixupKind = isMicroMips(STI) ? Mips::fixup_MICROMIPS_GOT_OFST 664 : Mips::fixup_Mips_GOT_OFST; 665 break; 666 case MipsMCExpr::MEK_GPREL: 667 FixupKind = Mips::fixup_Mips_GPREL16; 668 break; 669 case MipsMCExpr::MEK_LO: 670 // Check for %lo(%neg(%gp_rel(X))) 671 if (MipsExpr->isGpOff()) 672 FixupKind = isMicroMips(STI) ? Mips::fixup_MICROMIPS_GPOFF_LO 673 : Mips::fixup_Mips_GPOFF_LO; 674 else 675 FixupKind = isMicroMips(STI) ? Mips::fixup_MICROMIPS_LO16 676 : Mips::fixup_Mips_LO16; 677 break; 678 case MipsMCExpr::MEK_HIGHEST: 679 FixupKind = isMicroMips(STI) ? Mips::fixup_MICROMIPS_HIGHEST 680 : Mips::fixup_Mips_HIGHEST; 681 break; 682 case MipsMCExpr::MEK_HIGHER: 683 FixupKind = isMicroMips(STI) ? Mips::fixup_MICROMIPS_HIGHER 684 : Mips::fixup_Mips_HIGHER; 685 break; 686 case MipsMCExpr::MEK_HI: 687 // Check for %hi(%neg(%gp_rel(X))) 688 if (MipsExpr->isGpOff()) 689 FixupKind = isMicroMips(STI) ? Mips::fixup_MICROMIPS_GPOFF_HI 690 : Mips::fixup_Mips_GPOFF_HI; 691 else 692 FixupKind = isMicroMips(STI) ? Mips::fixup_MICROMIPS_HI16 693 : Mips::fixup_Mips_HI16; 694 break; 695 case MipsMCExpr::MEK_PCREL_HI16: 696 FixupKind = Mips::fixup_MIPS_PCHI16; 697 break; 698 case MipsMCExpr::MEK_PCREL_LO16: 699 FixupKind = Mips::fixup_MIPS_PCLO16; 700 break; 701 case MipsMCExpr::MEK_TLSGD: 702 FixupKind = isMicroMips(STI) ? Mips::fixup_MICROMIPS_TLS_GD 703 : Mips::fixup_Mips_TLSGD; 704 break; 705 case MipsMCExpr::MEK_TLSLDM: 706 FixupKind = isMicroMips(STI) ? Mips::fixup_MICROMIPS_TLS_LDM 707 : Mips::fixup_Mips_TLSLDM; 708 break; 709 case MipsMCExpr::MEK_TPREL_HI: 710 FixupKind = isMicroMips(STI) ? Mips::fixup_MICROMIPS_TLS_TPREL_HI16 711 : Mips::fixup_Mips_TPREL_HI; 712 break; 713 case MipsMCExpr::MEK_TPREL_LO: 714 FixupKind = isMicroMips(STI) ? Mips::fixup_MICROMIPS_TLS_TPREL_LO16 715 : Mips::fixup_Mips_TPREL_LO; 716 break; 717 case MipsMCExpr::MEK_NEG: 718 FixupKind = 719 isMicroMips(STI) ? Mips::fixup_MICROMIPS_SUB : Mips::fixup_Mips_SUB; 720 break; 721 } 722 Fixups.push_back(MCFixup::create(0, MipsExpr, MCFixupKind(FixupKind))); 723 return 0; 724 } 725 726 if (Kind == MCExpr::SymbolRef) 727 Ctx.reportError(Expr->getLoc(), "expected an immediate"); 728 return 0; 729 } 730 731 /// getMachineOpValue - Return binary encoding of operand. If the machine 732 /// operand requires relocation, record the relocation and return zero. 733 unsigned MipsMCCodeEmitter:: 734 getMachineOpValue(const MCInst &MI, const MCOperand &MO, 735 SmallVectorImpl<MCFixup> &Fixups, 736 const MCSubtargetInfo &STI) const { 737 if (MO.isReg()) { 738 unsigned Reg = MO.getReg(); 739 unsigned RegNo = Ctx.getRegisterInfo()->getEncodingValue(Reg); 740 return RegNo; 741 } else if (MO.isImm()) { 742 return static_cast<unsigned>(MO.getImm()); 743 } else if (MO.isFPImm()) { 744 return static_cast<unsigned>(APFloat(MO.getFPImm()) 745 .bitcastToAPInt().getHiBits(32).getLimitedValue()); 746 } 747 // MO must be an Expr. 748 assert(MO.isExpr()); 749 return getExprOpValue(MO.getExpr(),Fixups, STI); 750 } 751 752 /// Return binary encoding of memory related operand. 753 /// If the offset operand requires relocation, record the relocation. 754 template <unsigned ShiftAmount> 755 unsigned MipsMCCodeEmitter::getMemEncoding(const MCInst &MI, unsigned OpNo, 756 SmallVectorImpl<MCFixup> &Fixups, 757 const MCSubtargetInfo &STI) const { 758 // Base register is encoded in bits 20-16, offset is encoded in bits 15-0. 759 assert(MI.getOperand(OpNo).isReg()); 760 unsigned RegBits = getMachineOpValue(MI, MI.getOperand(OpNo), Fixups, STI) 761 << 16; 762 unsigned OffBits = getMachineOpValue(MI, MI.getOperand(OpNo+1), Fixups, STI); 763 764 // Apply the scale factor if there is one. 765 OffBits >>= ShiftAmount; 766 767 return (OffBits & 0xFFFF) | RegBits; 768 } 769 770 unsigned MipsMCCodeEmitter:: 771 getMemEncodingMMImm4(const MCInst &MI, unsigned OpNo, 772 SmallVectorImpl<MCFixup> &Fixups, 773 const MCSubtargetInfo &STI) const { 774 // Base register is encoded in bits 6-4, offset is encoded in bits 3-0. 775 assert(MI.getOperand(OpNo).isReg()); 776 unsigned RegBits = getMachineOpValue(MI, MI.getOperand(OpNo), 777 Fixups, STI) << 4; 778 unsigned OffBits = getMachineOpValue(MI, MI.getOperand(OpNo+1), 779 Fixups, STI); 780 781 return (OffBits & 0xF) | RegBits; 782 } 783 784 unsigned MipsMCCodeEmitter:: 785 getMemEncodingMMImm4Lsl1(const MCInst &MI, unsigned OpNo, 786 SmallVectorImpl<MCFixup> &Fixups, 787 const MCSubtargetInfo &STI) const { 788 // Base register is encoded in bits 6-4, offset is encoded in bits 3-0. 789 assert(MI.getOperand(OpNo).isReg()); 790 unsigned RegBits = getMachineOpValue(MI, MI.getOperand(OpNo), 791 Fixups, STI) << 4; 792 unsigned OffBits = getMachineOpValue(MI, MI.getOperand(OpNo+1), 793 Fixups, STI) >> 1; 794 795 return (OffBits & 0xF) | RegBits; 796 } 797 798 unsigned MipsMCCodeEmitter:: 799 getMemEncodingMMImm4Lsl2(const MCInst &MI, unsigned OpNo, 800 SmallVectorImpl<MCFixup> &Fixups, 801 const MCSubtargetInfo &STI) const { 802 // Base register is encoded in bits 6-4, offset is encoded in bits 3-0. 803 assert(MI.getOperand(OpNo).isReg()); 804 unsigned RegBits = getMachineOpValue(MI, MI.getOperand(OpNo), 805 Fixups, STI) << 4; 806 unsigned OffBits = getMachineOpValue(MI, MI.getOperand(OpNo+1), 807 Fixups, STI) >> 2; 808 809 return (OffBits & 0xF) | RegBits; 810 } 811 812 unsigned MipsMCCodeEmitter:: 813 getMemEncodingMMSPImm5Lsl2(const MCInst &MI, unsigned OpNo, 814 SmallVectorImpl<MCFixup> &Fixups, 815 const MCSubtargetInfo &STI) const { 816 // Register is encoded in bits 9-5, offset is encoded in bits 4-0. 817 assert(MI.getOperand(OpNo).isReg() && 818 (MI.getOperand(OpNo).getReg() == Mips::SP || 819 MI.getOperand(OpNo).getReg() == Mips::SP_64) && 820 "Unexpected base register!"); 821 unsigned OffBits = getMachineOpValue(MI, MI.getOperand(OpNo+1), 822 Fixups, STI) >> 2; 823 824 return OffBits & 0x1F; 825 } 826 827 unsigned MipsMCCodeEmitter:: 828 getMemEncodingMMGPImm7Lsl2(const MCInst &MI, unsigned OpNo, 829 SmallVectorImpl<MCFixup> &Fixups, 830 const MCSubtargetInfo &STI) const { 831 // Register is encoded in bits 9-7, offset is encoded in bits 6-0. 832 assert(MI.getOperand(OpNo).isReg() && 833 MI.getOperand(OpNo).getReg() == Mips::GP && 834 "Unexpected base register!"); 835 836 unsigned OffBits = getMachineOpValue(MI, MI.getOperand(OpNo+1), 837 Fixups, STI) >> 2; 838 839 return OffBits & 0x7F; 840 } 841 842 unsigned MipsMCCodeEmitter:: 843 getMemEncodingMMImm9(const MCInst &MI, unsigned OpNo, 844 SmallVectorImpl<MCFixup> &Fixups, 845 const MCSubtargetInfo &STI) const { 846 // Base register is encoded in bits 20-16, offset is encoded in bits 8-0. 847 assert(MI.getOperand(OpNo).isReg()); 848 unsigned RegBits = getMachineOpValue(MI, MI.getOperand(OpNo), Fixups, 849 STI) << 16; 850 unsigned OffBits = 851 getMachineOpValue(MI, MI.getOperand(OpNo + 1), Fixups, STI); 852 853 return (OffBits & 0x1FF) | RegBits; 854 } 855 856 unsigned MipsMCCodeEmitter:: 857 getMemEncodingMMImm11(const MCInst &MI, unsigned OpNo, 858 SmallVectorImpl<MCFixup> &Fixups, 859 const MCSubtargetInfo &STI) const { 860 // Base register is encoded in bits 20-16, offset is encoded in bits 10-0. 861 assert(MI.getOperand(OpNo).isReg()); 862 unsigned RegBits = getMachineOpValue(MI, MI.getOperand(OpNo), Fixups, 863 STI) << 16; 864 unsigned OffBits = getMachineOpValue(MI, MI.getOperand(OpNo+1), Fixups, STI); 865 866 return (OffBits & 0x07FF) | RegBits; 867 } 868 869 unsigned MipsMCCodeEmitter:: 870 getMemEncodingMMImm12(const MCInst &MI, unsigned OpNo, 871 SmallVectorImpl<MCFixup> &Fixups, 872 const MCSubtargetInfo &STI) const { 873 // opNum can be invalid if instruction had reglist as operand. 874 // MemOperand is always last operand of instruction (base + offset). 875 switch (MI.getOpcode()) { 876 default: 877 break; 878 case Mips::SWM32_MM: 879 case Mips::LWM32_MM: 880 OpNo = MI.getNumOperands() - 2; 881 break; 882 } 883 884 // Base register is encoded in bits 20-16, offset is encoded in bits 11-0. 885 assert(MI.getOperand(OpNo).isReg()); 886 unsigned RegBits = getMachineOpValue(MI, MI.getOperand(OpNo), Fixups, STI) 887 << 16; 888 unsigned OffBits = getMachineOpValue(MI, MI.getOperand(OpNo+1), Fixups, STI); 889 890 return (OffBits & 0x0FFF) | RegBits; 891 } 892 893 unsigned MipsMCCodeEmitter:: 894 getMemEncodingMMImm16(const MCInst &MI, unsigned OpNo, 895 SmallVectorImpl<MCFixup> &Fixups, 896 const MCSubtargetInfo &STI) const { 897 // Base register is encoded in bits 20-16, offset is encoded in bits 15-0. 898 assert(MI.getOperand(OpNo).isReg()); 899 unsigned RegBits = getMachineOpValue(MI, MI.getOperand(OpNo), Fixups, 900 STI) << 16; 901 unsigned OffBits = getMachineOpValue(MI, MI.getOperand(OpNo+1), Fixups, STI); 902 903 return (OffBits & 0xFFFF) | RegBits; 904 } 905 906 unsigned MipsMCCodeEmitter:: 907 getMemEncodingMMImm4sp(const MCInst &MI, unsigned OpNo, 908 SmallVectorImpl<MCFixup> &Fixups, 909 const MCSubtargetInfo &STI) const { 910 // opNum can be invalid if instruction had reglist as operand 911 // MemOperand is always last operand of instruction (base + offset) 912 switch (MI.getOpcode()) { 913 default: 914 break; 915 case Mips::SWM16_MM: 916 case Mips::SWM16_MMR6: 917 case Mips::LWM16_MM: 918 case Mips::LWM16_MMR6: 919 OpNo = MI.getNumOperands() - 2; 920 break; 921 } 922 923 // Offset is encoded in bits 4-0. 924 assert(MI.getOperand(OpNo).isReg()); 925 // Base register is always SP - thus it is not encoded. 926 assert(MI.getOperand(OpNo+1).isImm()); 927 unsigned OffBits = getMachineOpValue(MI, MI.getOperand(OpNo+1), Fixups, STI); 928 929 return ((OffBits >> 2) & 0x0F); 930 } 931 932 // FIXME: should be called getMSBEncoding 933 // 934 unsigned 935 MipsMCCodeEmitter::getSizeInsEncoding(const MCInst &MI, unsigned OpNo, 936 SmallVectorImpl<MCFixup> &Fixups, 937 const MCSubtargetInfo &STI) const { 938 assert(MI.getOperand(OpNo-1).isImm()); 939 assert(MI.getOperand(OpNo).isImm()); 940 unsigned Position = getMachineOpValue(MI, MI.getOperand(OpNo-1), Fixups, STI); 941 unsigned Size = getMachineOpValue(MI, MI.getOperand(OpNo), Fixups, STI); 942 943 return Position + Size - 1; 944 } 945 946 template <unsigned Bits, int Offset> 947 unsigned 948 MipsMCCodeEmitter::getUImmWithOffsetEncoding(const MCInst &MI, unsigned OpNo, 949 SmallVectorImpl<MCFixup> &Fixups, 950 const MCSubtargetInfo &STI) const { 951 assert(MI.getOperand(OpNo).isImm()); 952 unsigned Value = getMachineOpValue(MI, MI.getOperand(OpNo), Fixups, STI); 953 Value -= Offset; 954 return Value; 955 } 956 957 unsigned 958 MipsMCCodeEmitter::getSimm19Lsl2Encoding(const MCInst &MI, unsigned OpNo, 959 SmallVectorImpl<MCFixup> &Fixups, 960 const MCSubtargetInfo &STI) const { 961 const MCOperand &MO = MI.getOperand(OpNo); 962 if (MO.isImm()) { 963 // The immediate is encoded as 'immediate << 2'. 964 unsigned Res = getMachineOpValue(MI, MO, Fixups, STI); 965 assert((Res & 3) == 0); 966 return Res >> 2; 967 } 968 969 assert(MO.isExpr() && 970 "getSimm19Lsl2Encoding expects only expressions or an immediate"); 971 972 const MCExpr *Expr = MO.getExpr(); 973 Mips::Fixups FixupKind = isMicroMips(STI) ? Mips::fixup_MICROMIPS_PC19_S2 974 : Mips::fixup_MIPS_PC19_S2; 975 Fixups.push_back(MCFixup::create(0, Expr, MCFixupKind(FixupKind))); 976 return 0; 977 } 978 979 unsigned 980 MipsMCCodeEmitter::getSimm18Lsl3Encoding(const MCInst &MI, unsigned OpNo, 981 SmallVectorImpl<MCFixup> &Fixups, 982 const MCSubtargetInfo &STI) const { 983 const MCOperand &MO = MI.getOperand(OpNo); 984 if (MO.isImm()) { 985 // The immediate is encoded as 'immediate << 3'. 986 unsigned Res = getMachineOpValue(MI, MI.getOperand(OpNo), Fixups, STI); 987 assert((Res & 7) == 0); 988 return Res >> 3; 989 } 990 991 assert(MO.isExpr() && 992 "getSimm18Lsl2Encoding expects only expressions or an immediate"); 993 994 const MCExpr *Expr = MO.getExpr(); 995 Mips::Fixups FixupKind = isMicroMips(STI) ? Mips::fixup_MICROMIPS_PC18_S3 996 : Mips::fixup_MIPS_PC18_S3; 997 Fixups.push_back(MCFixup::create(0, Expr, MCFixupKind(FixupKind))); 998 return 0; 999 } 1000 1001 unsigned 1002 MipsMCCodeEmitter::getUImm3Mod8Encoding(const MCInst &MI, unsigned OpNo, 1003 SmallVectorImpl<MCFixup> &Fixups, 1004 const MCSubtargetInfo &STI) const { 1005 assert(MI.getOperand(OpNo).isImm()); 1006 const MCOperand &MO = MI.getOperand(OpNo); 1007 return MO.getImm() % 8; 1008 } 1009 1010 unsigned 1011 MipsMCCodeEmitter::getUImm4AndValue(const MCInst &MI, unsigned OpNo, 1012 SmallVectorImpl<MCFixup> &Fixups, 1013 const MCSubtargetInfo &STI) const { 1014 assert(MI.getOperand(OpNo).isImm()); 1015 const MCOperand &MO = MI.getOperand(OpNo); 1016 unsigned Value = MO.getImm(); 1017 switch (Value) { 1018 case 128: return 0x0; 1019 case 1: return 0x1; 1020 case 2: return 0x2; 1021 case 3: return 0x3; 1022 case 4: return 0x4; 1023 case 7: return 0x5; 1024 case 8: return 0x6; 1025 case 15: return 0x7; 1026 case 16: return 0x8; 1027 case 31: return 0x9; 1028 case 32: return 0xa; 1029 case 63: return 0xb; 1030 case 64: return 0xc; 1031 case 255: return 0xd; 1032 case 32768: return 0xe; 1033 case 65535: return 0xf; 1034 } 1035 llvm_unreachable("Unexpected value"); 1036 } 1037 1038 unsigned 1039 MipsMCCodeEmitter::getRegisterListOpValue(const MCInst &MI, unsigned OpNo, 1040 SmallVectorImpl<MCFixup> &Fixups, 1041 const MCSubtargetInfo &STI) const { 1042 unsigned res = 0; 1043 1044 // Register list operand is always first operand of instruction and it is 1045 // placed before memory operand (register + imm). 1046 1047 for (unsigned I = OpNo, E = MI.getNumOperands() - 2; I < E; ++I) { 1048 unsigned Reg = MI.getOperand(I).getReg(); 1049 unsigned RegNo = Ctx.getRegisterInfo()->getEncodingValue(Reg); 1050 if (RegNo != 31) 1051 res++; 1052 else 1053 res |= 0x10; 1054 } 1055 return res; 1056 } 1057 1058 unsigned 1059 MipsMCCodeEmitter::getRegisterListOpValue16(const MCInst &MI, unsigned OpNo, 1060 SmallVectorImpl<MCFixup> &Fixups, 1061 const MCSubtargetInfo &STI) const { 1062 return (MI.getNumOperands() - 4); 1063 } 1064 1065 unsigned 1066 MipsMCCodeEmitter::getMovePRegPairOpValue(const MCInst &MI, unsigned OpNo, 1067 SmallVectorImpl<MCFixup> &Fixups, 1068 const MCSubtargetInfo &STI) const { 1069 unsigned res = 0; 1070 1071 if (MI.getOperand(0).getReg() == Mips::A1 && 1072 MI.getOperand(1).getReg() == Mips::A2) 1073 res = 0; 1074 else if (MI.getOperand(0).getReg() == Mips::A1 && 1075 MI.getOperand(1).getReg() == Mips::A3) 1076 res = 1; 1077 else if (MI.getOperand(0).getReg() == Mips::A2 && 1078 MI.getOperand(1).getReg() == Mips::A3) 1079 res = 2; 1080 else if (MI.getOperand(0).getReg() == Mips::A0 && 1081 MI.getOperand(1).getReg() == Mips::S5) 1082 res = 3; 1083 else if (MI.getOperand(0).getReg() == Mips::A0 && 1084 MI.getOperand(1).getReg() == Mips::S6) 1085 res = 4; 1086 else if (MI.getOperand(0).getReg() == Mips::A0 && 1087 MI.getOperand(1).getReg() == Mips::A1) 1088 res = 5; 1089 else if (MI.getOperand(0).getReg() == Mips::A0 && 1090 MI.getOperand(1).getReg() == Mips::A2) 1091 res = 6; 1092 else if (MI.getOperand(0).getReg() == Mips::A0 && 1093 MI.getOperand(1).getReg() == Mips::A3) 1094 res = 7; 1095 1096 return res; 1097 } 1098 1099 unsigned 1100 MipsMCCodeEmitter::getMovePRegSingleOpValue(const MCInst &MI, unsigned OpNo, 1101 SmallVectorImpl<MCFixup> &Fixups, 1102 const MCSubtargetInfo &STI) const { 1103 assert(((OpNo == 2) || (OpNo == 3)) && 1104 "Unexpected OpNo for movep operand encoding!"); 1105 1106 MCOperand Op = MI.getOperand(OpNo); 1107 assert(Op.isReg() && "Operand of movep is not a register!"); 1108 switch (Op.getReg()) { 1109 default: 1110 llvm_unreachable("Unknown register for movep!"); 1111 case Mips::ZERO: return 0; 1112 case Mips::S1: return 1; 1113 case Mips::V0: return 2; 1114 case Mips::V1: return 3; 1115 case Mips::S0: return 4; 1116 case Mips::S2: return 5; 1117 case Mips::S3: return 6; 1118 case Mips::S4: return 7; 1119 } 1120 } 1121 1122 unsigned 1123 MipsMCCodeEmitter::getSimm23Lsl2Encoding(const MCInst &MI, unsigned OpNo, 1124 SmallVectorImpl<MCFixup> &Fixups, 1125 const MCSubtargetInfo &STI) const { 1126 const MCOperand &MO = MI.getOperand(OpNo); 1127 assert(MO.isImm() && "getSimm23Lsl2Encoding expects only an immediate"); 1128 // The immediate is encoded as 'immediate >> 2'. 1129 unsigned Res = static_cast<unsigned>(MO.getImm()); 1130 assert((Res & 3) == 0); 1131 return Res >> 2; 1132 } 1133 1134 #include "MipsGenMCCodeEmitter.inc" 1135