decoder.cc revision 11793:ef606668d247
1/* 2 * Copyright (c) 2011 Google 3 * All rights reserved. 4 * 5 * Redistribution and use in source and binary forms, with or without 6 * modification, are permitted provided that the following conditions are 7 * met: redistributions of source code must retain the above copyright 8 * notice, this list of conditions and the following disclaimer; 9 * redistributions in binary form must reproduce the above copyright 10 * notice, this list of conditions and the following disclaimer in the 11 * documentation and/or other materials provided with the distribution; 12 * neither the name of the copyright holders nor the names of its 13 * contributors may be used to endorse or promote products derived from 14 * this software without specific prior written permission. 15 * 16 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS 17 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT 18 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR 19 * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT 20 * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, 21 * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT 22 * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, 23 * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY 24 * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 25 * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 26 * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 27 * 28 * Authors: Gabe Black 29 */ 30 31#include "arch/x86/decoder.hh" 32 33#include "arch/x86/regs/misc.hh" 34#include "base/misc.hh" 35#include "base/trace.hh" 36#include "base/types.hh" 37#include "debug/Decoder.hh" 38 39namespace X86ISA 40{ 41 42Decoder::State 43Decoder::doResetState() 44{ 45 origPC = basePC + offset; 46 DPRINTF(Decoder, "Setting origPC to %#x\n", origPC); 47 instBytes = &decodePages->lookup(origPC); 48 chunkIdx = 0; 49 50 emi.rex = 0; 51 emi.legacy = 0; 52 emi.vex = 0; 53 54 emi.opcode.type = BadOpcode; 55 emi.opcode.op = 0; 56 57 immediateCollected = 0; 58 emi.immediate = 0; 59 emi.displacement = 0; 60 emi.dispSize = 0; 61 62 emi.modRM = 0; 63 emi.sib = 0; 64 65 if (instBytes->si) { 66 return FromCacheState; 67 } else { 68 instBytes->chunks.clear(); 69 return PrefixState; 70 } 71} 72 73void 74Decoder::process() 75{ 76 //This function drives the decoder state machine. 77 78 //Some sanity checks. You shouldn't try to process more bytes if 79 //there aren't any, and you shouldn't overwrite an already 80 //decoder ExtMachInst. 81 assert(!outOfBytes); 82 assert(!instDone); 83 84 if (state == ResetState) 85 state = doResetState(); 86 if (state == FromCacheState) { 87 state = doFromCacheState(); 88 } else { 89 instBytes->chunks.push_back(fetchChunk); 90 } 91 92 //While there's still something to do... 93 while (!instDone && !outOfBytes) { 94 uint8_t nextByte = getNextByte(); 95 switch (state) { 96 case PrefixState: 97 state = doPrefixState(nextByte); 98 break; 99 100 case TwoByteVexState: 101 state = doTwoByteVexState(nextByte); 102 break; 103 104 case ThreeByteVexFirstState: 105 state = doThreeByteVexFirstState(nextByte); 106 break; 107 108 case ThreeByteVexSecondState: 109 state = doThreeByteVexSecondState(nextByte); 110 break; 111 112 case OneByteOpcodeState: 113 state = doOneByteOpcodeState(nextByte); 114 break; 115 case TwoByteOpcodeState: 116 state = doTwoByteOpcodeState(nextByte); 117 break; 118 case ThreeByte0F38OpcodeState: 119 state = doThreeByte0F38OpcodeState(nextByte); 120 break; 121 case ThreeByte0F3AOpcodeState: 122 state = doThreeByte0F3AOpcodeState(nextByte); 123 break; 124 case ModRMState: 125 state = doModRMState(nextByte); 126 break; 127 case SIBState: 128 state = doSIBState(nextByte); 129 break; 130 case DisplacementState: 131 state = doDisplacementState(); 132 break; 133 case ImmediateState: 134 state = doImmediateState(); 135 break; 136 case ErrorState: 137 panic("Went to the error state in the decoder.\n"); 138 default: 139 panic("Unrecognized state! %d\n", state); 140 } 141 } 142} 143 144Decoder::State 145Decoder::doFromCacheState() 146{ 147 DPRINTF(Decoder, "Looking at cache state.\n"); 148 if ((fetchChunk & instBytes->masks[chunkIdx]) != 149 instBytes->chunks[chunkIdx]) { 150 DPRINTF(Decoder, "Decode cache miss.\n"); 151 // The chached chunks didn't match what was fetched. Fall back to the 152 // predecoder. 153 instBytes->chunks[chunkIdx] = fetchChunk; 154 instBytes->chunks.resize(chunkIdx + 1); 155 instBytes->si = NULL; 156 chunkIdx = 0; 157 fetchChunk = instBytes->chunks[0]; 158 offset = origPC % sizeof(MachInst); 159 basePC = origPC - offset; 160 return PrefixState; 161 } else if (chunkIdx == instBytes->chunks.size() - 1) { 162 // We matched the cache, so use its value. 163 instDone = true; 164 offset = instBytes->lastOffset; 165 if (offset == sizeof(MachInst)) 166 outOfBytes = true; 167 return ResetState; 168 } else { 169 // We matched so far, but need to check more chunks. 170 chunkIdx++; 171 outOfBytes = true; 172 return FromCacheState; 173 } 174} 175 176//Either get a prefix and record it in the ExtMachInst, or send the 177//state machine on to get the opcode(s). 178Decoder::State 179Decoder::doPrefixState(uint8_t nextByte) 180{ 181 uint8_t prefix = Prefixes[nextByte]; 182 State nextState = PrefixState; 183 // REX prefixes are only recognized in 64 bit mode. 184 if (prefix == RexPrefix && emi.mode.submode != SixtyFourBitMode) 185 prefix = 0; 186 if (prefix) 187 consumeByte(); 188 switch(prefix) 189 { 190 //Operand size override prefixes 191 case OperandSizeOverride: 192 DPRINTF(Decoder, "Found operand size override prefix.\n"); 193 emi.legacy.op = true; 194 break; 195 case AddressSizeOverride: 196 DPRINTF(Decoder, "Found address size override prefix.\n"); 197 emi.legacy.addr = true; 198 break; 199 //Segment override prefixes 200 case CSOverride: 201 case DSOverride: 202 case ESOverride: 203 case FSOverride: 204 case GSOverride: 205 case SSOverride: 206 DPRINTF(Decoder, "Found segment override.\n"); 207 emi.legacy.seg = prefix; 208 break; 209 case Lock: 210 DPRINTF(Decoder, "Found lock prefix.\n"); 211 emi.legacy.lock = true; 212 break; 213 case Rep: 214 DPRINTF(Decoder, "Found rep prefix.\n"); 215 emi.legacy.rep = true; 216 break; 217 case Repne: 218 DPRINTF(Decoder, "Found repne prefix.\n"); 219 emi.legacy.repne = true; 220 break; 221 case RexPrefix: 222 DPRINTF(Decoder, "Found Rex prefix %#x.\n", nextByte); 223 emi.rex = nextByte; 224 break; 225 226 case Vex2Prefix: 227 DPRINTF(Decoder, "Found VEX two-byte prefix %#x.\n", nextByte); 228 emi.vex.zero = nextByte; 229 nextState = TwoByteVexState; 230 break; 231 232 case Vex3Prefix: 233 DPRINTF(Decoder, "Found VEX three-byte prefix %#x.\n", nextByte); 234 emi.vex.zero = nextByte; 235 nextState = ThreeByteVexFirstState; 236 break; 237 238 case 0: 239 nextState = OneByteOpcodeState; 240 break; 241 242 default: 243 panic("Unrecognized prefix %#x\n", nextByte); 244 } 245 return nextState; 246} 247 248Decoder::State 249Decoder::doTwoByteVexState(uint8_t nextByte) 250{ 251 assert(emi.vex.zero == 0xc5); 252 consumeByte(); 253 TwoByteVex tbe = 0; 254 tbe.first = nextByte; 255 256 emi.vex.first.r = tbe.first.r; 257 emi.vex.first.x = 1; 258 emi.vex.first.b = 1; 259 emi.vex.first.map_select = 1; 260 261 emi.vex.second.w = 0; 262 emi.vex.second.vvvv = tbe.first.vvvv; 263 emi.vex.second.l = tbe.first.l; 264 emi.vex.second.pp = tbe.first.pp; 265 266 emi.opcode.type = Vex; 267 return OneByteOpcodeState; 268} 269 270Decoder::State 271Decoder::doThreeByteVexFirstState(uint8_t nextByte) 272{ 273 consumeByte(); 274 emi.vex.first = nextByte; 275 return ThreeByteVexSecondState; 276} 277 278Decoder::State 279Decoder::doThreeByteVexSecondState(uint8_t nextByte) 280{ 281 consumeByte(); 282 emi.vex.second = nextByte; 283 emi.opcode.type = Vex; 284 return OneByteOpcodeState; 285} 286 287// Load the first opcode byte. Determine if there are more opcode bytes, and 288// if not, what immediate and/or ModRM is needed. 289Decoder::State 290Decoder::doOneByteOpcodeState(uint8_t nextByte) 291{ 292 State nextState = ErrorState; 293 consumeByte(); 294 295 if (emi.vex.zero != 0) { 296 DPRINTF(Decoder, "Found VEX opcode %#x.\n", nextByte); 297 emi.opcode.op = nextByte; 298 const uint8_t opcode_map = emi.vex.first.map_select; 299 nextState = processExtendedOpcode(ImmediateTypeVex[opcode_map]); 300 } else if (nextByte == 0x0f) { 301 nextState = TwoByteOpcodeState; 302 DPRINTF(Decoder, "Found opcode escape byte %#x.\n", nextByte); 303 } else { 304 DPRINTF(Decoder, "Found one byte opcode %#x.\n", nextByte); 305 emi.opcode.type = OneByteOpcode; 306 emi.opcode.op = nextByte; 307 308 nextState = processOpcode(ImmediateTypeOneByte, UsesModRMOneByte, 309 nextByte >= 0xA0 && nextByte <= 0xA3); 310 } 311 return nextState; 312} 313 314// Load the second opcode byte. Determine if there are more opcode bytes, and 315// if not, what immediate and/or ModRM is needed. 316Decoder::State 317Decoder::doTwoByteOpcodeState(uint8_t nextByte) 318{ 319 State nextState = ErrorState; 320 consumeByte(); 321 if (nextByte == 0x38) { 322 nextState = ThreeByte0F38OpcodeState; 323 DPRINTF(Decoder, "Found opcode escape byte %#x.\n", nextByte); 324 } else if (nextByte == 0x3a) { 325 nextState = ThreeByte0F3AOpcodeState; 326 DPRINTF(Decoder, "Found opcode escape byte %#x.\n", nextByte); 327 } else { 328 DPRINTF(Decoder, "Found two byte opcode %#x.\n", nextByte); 329 emi.opcode.type = TwoByteOpcode; 330 emi.opcode.op = nextByte; 331 332 nextState = processOpcode(ImmediateTypeTwoByte, UsesModRMTwoByte); 333 } 334 return nextState; 335} 336 337// Load the third opcode byte and determine what immediate and/or ModRM is 338// needed. 339Decoder::State 340Decoder::doThreeByte0F38OpcodeState(uint8_t nextByte) 341{ 342 consumeByte(); 343 344 DPRINTF(Decoder, "Found three byte 0F38 opcode %#x.\n", nextByte); 345 emi.opcode.type = ThreeByte0F38Opcode; 346 emi.opcode.op = nextByte; 347 348 return processOpcode(ImmediateTypeThreeByte0F38, UsesModRMThreeByte0F38); 349} 350 351// Load the third opcode byte and determine what immediate and/or ModRM is 352// needed. 353Decoder::State 354Decoder::doThreeByte0F3AOpcodeState(uint8_t nextByte) 355{ 356 consumeByte(); 357 358 DPRINTF(Decoder, "Found three byte 0F3A opcode %#x.\n", nextByte); 359 emi.opcode.type = ThreeByte0F3AOpcode; 360 emi.opcode.op = nextByte; 361 362 return processOpcode(ImmediateTypeThreeByte0F3A, UsesModRMThreeByte0F3A); 363} 364 365// Generic opcode processing which determines the immediate size, and whether 366// or not there's a modrm byte. 367Decoder::State 368Decoder::processOpcode(ByteTable &immTable, ByteTable &modrmTable, 369 bool addrSizedImm) 370{ 371 State nextState = ErrorState; 372 const uint8_t opcode = emi.opcode.op; 373 374 //Figure out the effective operand size. This can be overriden to 375 //a fixed value at the decoder level. 376 int logOpSize; 377 if (emi.rex.w) 378 logOpSize = 3; // 64 bit operand size 379 else if (emi.legacy.op) 380 logOpSize = altOp; 381 else 382 logOpSize = defOp; 383 384 //Set the actual op size 385 emi.opSize = 1 << logOpSize; 386 387 //Figure out the effective address size. This can be overriden to 388 //a fixed value at the decoder level. 389 int logAddrSize; 390 if (emi.legacy.addr) 391 logAddrSize = altAddr; 392 else 393 logAddrSize = defAddr; 394 395 //Set the actual address size 396 emi.addrSize = 1 << logAddrSize; 397 398 //Figure out the effective stack width. This can be overriden to 399 //a fixed value at the decoder level. 400 emi.stackSize = 1 << stack; 401 402 //Figure out how big of an immediate we'll retreive based 403 //on the opcode. 404 int immType = immTable[opcode]; 405 if (addrSizedImm) 406 immediateSize = SizeTypeToSize[logAddrSize - 1][immType]; 407 else 408 immediateSize = SizeTypeToSize[logOpSize - 1][immType]; 409 410 //Determine what to expect next 411 if (modrmTable[opcode]) { 412 nextState = ModRMState; 413 } else { 414 if (immediateSize) { 415 nextState = ImmediateState; 416 } else { 417 instDone = true; 418 nextState = ResetState; 419 } 420 } 421 return nextState; 422} 423 424Decoder::State 425Decoder::processExtendedOpcode(ByteTable &immTable) 426{ 427 //Figure out the effective operand size. This can be overriden to 428 //a fixed value at the decoder level. 429 int logOpSize; 430 if (emi.vex.second.w) 431 logOpSize = 3; // 64 bit operand size 432 else if (emi.vex.second.pp == 1) 433 logOpSize = altOp; 434 else 435 logOpSize = defOp; 436 437 //Set the actual op size 438 emi.opSize = 1 << logOpSize; 439 440 //Figure out the effective address size. This can be overriden to 441 //a fixed value at the decoder level. 442 int logAddrSize; 443 if (emi.legacy.addr) 444 logAddrSize = altAddr; 445 else 446 logAddrSize = defAddr; 447 448 //Set the actual address size 449 emi.addrSize = 1 << logAddrSize; 450 451 //Figure out the effective stack width. This can be overriden to 452 //a fixed value at the decoder level. 453 emi.stackSize = 1 << stack; 454 455 //Figure out how big of an immediate we'll retreive based 456 //on the opcode. 457 const uint8_t opcode = emi.opcode.op; 458 459 if (emi.vex.zero == 0xc5 || emi.vex.zero == 0xc4) { 460 int immType = immTable[opcode]; 461 // Assume 64-bit mode; 462 immediateSize = SizeTypeToSize[2][immType]; 463 } 464 465 if (opcode == 0x77) { 466 instDone = true; 467 return ResetState; 468 } 469 return ModRMState; 470} 471 472//Get the ModRM byte and determine what displacement, if any, there is. 473//Also determine whether or not to get the SIB byte, displacement, or 474//immediate next. 475Decoder::State 476Decoder::doModRMState(uint8_t nextByte) 477{ 478 State nextState = ErrorState; 479 ModRM modRM = nextByte; 480 DPRINTF(Decoder, "Found modrm byte %#x.\n", nextByte); 481 if (defOp == 1) { 482 //figure out 16 bit displacement size 483 if ((modRM.mod == 0 && modRM.rm == 6) || modRM.mod == 2) 484 displacementSize = 2; 485 else if (modRM.mod == 1) 486 displacementSize = 1; 487 else 488 displacementSize = 0; 489 } else { 490 //figure out 32/64 bit displacement size 491 if ((modRM.mod == 0 && modRM.rm == 5) || modRM.mod == 2) 492 displacementSize = 4; 493 else if (modRM.mod == 1) 494 displacementSize = 1; 495 else 496 displacementSize = 0; 497 } 498 499 // The "test" instruction in group 3 needs an immediate, even though 500 // the other instructions with the same actual opcode don't. 501 if (emi.opcode.type == OneByteOpcode && (modRM.reg & 0x6) == 0) { 502 if (emi.opcode.op == 0xF6) 503 immediateSize = 1; 504 else if (emi.opcode.op == 0xF7) 505 immediateSize = (emi.opSize == 8) ? 4 : emi.opSize; 506 } 507 508 //If there's an SIB, get that next. 509 //There is no SIB in 16 bit mode. 510 if (modRM.rm == 4 && modRM.mod != 3) { 511 // && in 32/64 bit mode) 512 nextState = SIBState; 513 } else if (displacementSize) { 514 nextState = DisplacementState; 515 } else if (immediateSize) { 516 nextState = ImmediateState; 517 } else { 518 instDone = true; 519 nextState = ResetState; 520 } 521 //The ModRM byte is consumed no matter what 522 consumeByte(); 523 emi.modRM = modRM; 524 return nextState; 525} 526 527//Get the SIB byte. We don't do anything with it at this point, other 528//than storing it in the ExtMachInst. Determine if we need to get a 529//displacement or immediate next. 530Decoder::State 531Decoder::doSIBState(uint8_t nextByte) 532{ 533 State nextState = ErrorState; 534 emi.sib = nextByte; 535 DPRINTF(Decoder, "Found SIB byte %#x.\n", nextByte); 536 consumeByte(); 537 if (emi.modRM.mod == 0 && emi.sib.base == 5) 538 displacementSize = 4; 539 if (displacementSize) { 540 nextState = DisplacementState; 541 } else if (immediateSize) { 542 nextState = ImmediateState; 543 } else { 544 instDone = true; 545 nextState = ResetState; 546 } 547 return nextState; 548} 549 550//Gather up the displacement, or at least as much of it 551//as we can get. 552Decoder::State 553Decoder::doDisplacementState() 554{ 555 State nextState = ErrorState; 556 557 getImmediate(immediateCollected, 558 emi.displacement, 559 displacementSize); 560 561 DPRINTF(Decoder, "Collecting %d byte displacement, got %d bytes.\n", 562 displacementSize, immediateCollected); 563 564 if (displacementSize == immediateCollected) { 565 //Reset this for other immediates. 566 immediateCollected = 0; 567 //Sign extend the displacement 568 switch(displacementSize) 569 { 570 case 1: 571 emi.displacement = sext<8>(emi.displacement); 572 break; 573 case 2: 574 emi.displacement = sext<16>(emi.displacement); 575 break; 576 case 4: 577 emi.displacement = sext<32>(emi.displacement); 578 break; 579 default: 580 panic("Undefined displacement size!\n"); 581 } 582 DPRINTF(Decoder, "Collected displacement %#x.\n", 583 emi.displacement); 584 if (immediateSize) { 585 nextState = ImmediateState; 586 } else { 587 instDone = true; 588 nextState = ResetState; 589 } 590 591 emi.dispSize = displacementSize; 592 } 593 else 594 nextState = DisplacementState; 595 return nextState; 596} 597 598//Gather up the immediate, or at least as much of it 599//as we can get 600Decoder::State 601Decoder::doImmediateState() 602{ 603 State nextState = ErrorState; 604 605 getImmediate(immediateCollected, 606 emi.immediate, 607 immediateSize); 608 609 DPRINTF(Decoder, "Collecting %d byte immediate, got %d bytes.\n", 610 immediateSize, immediateCollected); 611 612 if (immediateSize == immediateCollected) 613 { 614 //Reset this for other immediates. 615 immediateCollected = 0; 616 617 //XXX Warning! The following is an observed pattern and might 618 //not always be true! 619 620 //Instructions which use 64 bit operands but 32 bit immediates 621 //need to have the immediate sign extended to 64 bits. 622 //Instructions which use true 64 bit immediates won't be 623 //affected, and instructions that use true 32 bit immediates 624 //won't notice. 625 switch(immediateSize) 626 { 627 case 4: 628 emi.immediate = sext<32>(emi.immediate); 629 break; 630 case 1: 631 emi.immediate = sext<8>(emi.immediate); 632 } 633 634 DPRINTF(Decoder, "Collected immediate %#x.\n", 635 emi.immediate); 636 instDone = true; 637 nextState = ResetState; 638 } 639 else 640 nextState = ImmediateState; 641 return nextState; 642} 643 644Decoder::InstBytes Decoder::dummy; 645Decoder::InstCacheMap Decoder::instCacheMap; 646 647StaticInstPtr 648Decoder::decode(ExtMachInst mach_inst, Addr addr) 649{ 650 DecodeCache::InstMap::iterator iter = instMap->find(mach_inst); 651 if (iter != instMap->end()) 652 return iter->second; 653 654 StaticInstPtr si = decodeInst(mach_inst); 655 (*instMap)[mach_inst] = si; 656 return si; 657} 658 659StaticInstPtr 660Decoder::decode(PCState &nextPC) 661{ 662 if (!instDone) 663 return NULL; 664 instDone = false; 665 updateNPC(nextPC); 666 667 StaticInstPtr &si = instBytes->si; 668 if (si) 669 return si; 670 671 // We didn't match in the AddrMap, but we still populated an entry. Fix 672 // up its byte masks. 673 const int chunkSize = sizeof(MachInst); 674 675 instBytes->lastOffset = offset; 676 677 Addr firstBasePC = basePC - (instBytes->chunks.size() - 1) * chunkSize; 678 Addr firstOffset = origPC - firstBasePC; 679 Addr totalSize = instBytes->lastOffset - firstOffset + 680 (instBytes->chunks.size() - 1) * chunkSize; 681 int start = firstOffset; 682 instBytes->masks.clear(); 683 684 while (totalSize) { 685 int end = start + totalSize; 686 end = (chunkSize < end) ? chunkSize : end; 687 int size = end - start; 688 int idx = instBytes->masks.size(); 689 690 MachInst maskVal = mask(size * 8) << (start * 8); 691 assert(maskVal); 692 693 instBytes->masks.push_back(maskVal); 694 instBytes->chunks[idx] &= instBytes->masks[idx]; 695 totalSize -= size; 696 start = 0; 697 } 698 699 si = decode(emi, origPC); 700 return si; 701} 702 703} 704