1 /** @file 2 3 Copyright (c) 2007, Intel Corporation. All rights reserved.<BR> 4 This program and the accompanying materials 5 are licensed and made available under the terms and conditions of the BSD License 6 which accompanies this distribution. The full text of the license may be found at 7 http://opensource.org/licenses/bsd-license.php 8 9 THE PROGRAM IS DISTRIBUTED UNDER THE BSD LICENSE ON AN "AS IS" BASIS, 10 WITHOUT WARRANTIES OR REPRESENTATIONS OF ANY KIND, EITHER EXPRESS OR IMPLIED. 11 12 13 **/ 14 15 #include "Edb.h" 16 17 // 18 // Debugger Disasm definition 19 // 20 #define EDB_DISASM_DEFINE(func) \ 21 UINTN \ 22 func ( \ 23 IN EFI_PHYSICAL_ADDRESS InstructionAddress, \ 24 IN EFI_SYSTEM_CONTEXT SystemContext, \ 25 OUT CHAR16 **DisasmString \ 26 ) 27 28 EDB_DISASM_DEFINE (EdbDisasmBREAK); 29 EDB_DISASM_DEFINE (EdbDisasmJMP); 30 EDB_DISASM_DEFINE (EdbDisasmJMP8); 31 EDB_DISASM_DEFINE (EdbDisasmCALL); 32 EDB_DISASM_DEFINE (EdbDisasmRET); 33 EDB_DISASM_DEFINE (EdbDisasmCMP); 34 EDB_DISASM_DEFINE (EdbDisasmUnsignedDataManip); 35 EDB_DISASM_DEFINE (EdbDisasmSignedDataManip); 36 EDB_DISASM_DEFINE (EdbDisasmMOVxx); 37 EDB_DISASM_DEFINE (EdbDisasmMOVsnw); 38 EDB_DISASM_DEFINE (EdbDisasmMOVsnd); 39 EDB_DISASM_DEFINE (EdbDisasmLOADSP); 40 EDB_DISASM_DEFINE (EdbDisasmSTORESP); 41 EDB_DISASM_DEFINE (EdbDisasmPUSH); 42 EDB_DISASM_DEFINE (EdbDisasmPOP); 43 EDB_DISASM_DEFINE (EdbDisasmCMPI); 44 EDB_DISASM_DEFINE (EdbDisasmPUSHn); 45 EDB_DISASM_DEFINE (EdbDisasmPOPn); 46 EDB_DISASM_DEFINE (EdbDisasmMOVI); 47 EDB_DISASM_DEFINE (EdbDisasmMOVIn); 48 EDB_DISASM_DEFINE (EdbDisasmMOVREL); 49 50 // 51 // Debugger Disasm Table 52 // 53 EDB_DISASM_INSTRUCTION mEdbDisasmInstructionTable[] = { 54 EdbDisasmBREAK, // opcode 0x00 BREAK 55 EdbDisasmJMP, // opcode 0x01 JMP 56 EdbDisasmJMP8, // opcode 0x02 JMP8 57 EdbDisasmCALL, // opcode 0x03 CALL 58 EdbDisasmRET, // opcode 0x04 RET 59 EdbDisasmCMP, // opcode 0x05 CMPEQ 60 EdbDisasmCMP, // opcode 0x06 CMPLTE 61 EdbDisasmCMP, // opcode 0x07 CMPGTE 62 EdbDisasmCMP, // opcode 0x08 CMPULTE 63 EdbDisasmCMP, // opcode 0x09 CMPUGTE 64 EdbDisasmUnsignedDataManip, // opcode 0x0A NOT 65 EdbDisasmSignedDataManip, // opcode 0x0B NEG 66 EdbDisasmSignedDataManip, // opcode 0x0C ADD 67 EdbDisasmSignedDataManip, // opcode 0x0D SUB 68 EdbDisasmSignedDataManip, // opcode 0x0E MUL 69 EdbDisasmUnsignedDataManip, // opcode 0x0F MULU 70 EdbDisasmSignedDataManip, // opcode 0x10 DIV 71 EdbDisasmUnsignedDataManip, // opcode 0x11 DIVU 72 EdbDisasmSignedDataManip, // opcode 0x12 MOD 73 EdbDisasmUnsignedDataManip, // opcode 0x13 MODU 74 EdbDisasmUnsignedDataManip, // opcode 0x14 AND 75 EdbDisasmUnsignedDataManip, // opcode 0x15 OR 76 EdbDisasmUnsignedDataManip, // opcode 0x16 XOR 77 EdbDisasmUnsignedDataManip, // opcode 0x17 SHL 78 EdbDisasmUnsignedDataManip, // opcode 0x18 SHR 79 EdbDisasmSignedDataManip, // opcode 0x19 ASHR 80 EdbDisasmUnsignedDataManip, // opcode 0x1A EXTNDB 81 EdbDisasmUnsignedDataManip, // opcode 0x1B EXTNDW 82 EdbDisasmUnsignedDataManip, // opcode 0x1C EXTNDD 83 EdbDisasmMOVxx, // opcode 0x1D MOVBW 84 EdbDisasmMOVxx, // opcode 0x1E MOVWW 85 EdbDisasmMOVxx, // opcode 0x1F MOVDW 86 EdbDisasmMOVxx, // opcode 0x20 MOVQW 87 EdbDisasmMOVxx, // opcode 0x21 MOVBD 88 EdbDisasmMOVxx, // opcode 0x22 MOVWD 89 EdbDisasmMOVxx, // opcode 0x23 MOVDD 90 EdbDisasmMOVxx, // opcode 0x24 MOVQD 91 EdbDisasmMOVsnw, // opcode 0x25 MOVSNW 92 EdbDisasmMOVsnd, // opcode 0x26 MOVSND 93 NULL, // opcode 0x27 94 EdbDisasmMOVxx, // opcode 0x28 MOVQQ 95 EdbDisasmLOADSP, // opcode 0x29 LOADSP 96 EdbDisasmSTORESP, // opcode 0x2A STORESP 97 EdbDisasmPUSH, // opcode 0x2B PUSH 98 EdbDisasmPOP, // opcode 0x2C POP 99 EdbDisasmCMPI, // opcode 0x2D CMPIEQ 100 EdbDisasmCMPI, // opcode 0x2E CMPILTE 101 EdbDisasmCMPI, // opcode 0x2F CMPIGTE 102 EdbDisasmCMPI, // opcode 0x30 CMPIULTE 103 EdbDisasmCMPI, // opcode 0x31 CMPIUGTE 104 EdbDisasmMOVxx, // opcode 0x32 MOVNW 105 EdbDisasmMOVxx, // opcode 0x33 MOVND 106 NULL, // opcode 0x34 107 EdbDisasmPUSHn, // opcode 0x35 PUSHN 108 EdbDisasmPOPn, // opcode 0x36 POPN 109 EdbDisasmMOVI, // opcode 0x37 MOVI 110 EdbDisasmMOVIn, // opcode 0x38 MOVIN 111 EdbDisasmMOVREL, // opcode 0x39 MOVREL 112 }; 113 114 /** 115 116 Disasm instruction - BREAK. 117 118 @param InstructionAddress - The instruction address 119 @param SystemContext - EBC system context. 120 @param DisasmString - The instruction string 121 122 @return Instruction length 123 124 **/ 125 UINTN 126 EdbDisasmBREAK ( 127 IN EFI_PHYSICAL_ADDRESS InstructionAddress, 128 IN EFI_SYSTEM_CONTEXT SystemContext, 129 OUT CHAR16 **DisasmString 130 ) 131 { 132 ASSERT (GET_OPCODE(InstructionAddress) == OPCODE_BREAK); 133 134 if (*(UINT8 *)(UINTN)(InstructionAddress + 1) > 6) { 135 return 0; 136 } 137 138 // 139 // Construct Disasm String 140 // 141 if (DisasmString != NULL) { 142 *DisasmString = EdbPreInstructionString (); 143 144 EdbPrintInstructionName (L"BREAK"); 145 EdbPrintDatan (*(UINT8 *)(UINTN)(InstructionAddress + 1)); 146 147 EdbPostInstructionString (); 148 } 149 150 return 2; 151 } 152 153 extern CONST UINT8 mJMPLen[]; 154 155 /** 156 157 Disasm instruction - JMP. 158 159 @param InstructionAddress - The instruction address 160 @param SystemContext - EBC system context. 161 @param DisasmString - The instruction string 162 163 @return Instruction length 164 165 **/ 166 UINTN 167 EdbDisasmJMP ( 168 IN EFI_PHYSICAL_ADDRESS InstructionAddress, 169 IN EFI_SYSTEM_CONTEXT SystemContext, 170 OUT CHAR16 **DisasmString 171 ) 172 { 173 UINT8 Modifiers; 174 UINT8 Operands; 175 UINTN Size; 176 UINT32 Data32; 177 UINT64 Data64; 178 179 ASSERT (GET_OPCODE(InstructionAddress) == OPCODE_JMP); 180 181 Modifiers = GET_MODIFIERS (InstructionAddress); 182 Operands = GET_OPERANDS (InstructionAddress); 183 Size = (UINTN)mJMPLen[(Modifiers >> 6) & 0x03]; 184 185 // 186 // Construct Disasm String 187 // 188 if (DisasmString != NULL) { 189 *DisasmString = EdbPreInstructionString (); 190 191 EdbPrintInstructionName (L"JMP"); 192 // if (Modifiers & OPCODE_M_IMMDATA64) { 193 // EdbPrintInstructionName (L"64"); 194 // } else { 195 // EdbPrintInstructionName (L"32"); 196 // } 197 if ((Modifiers & CONDITION_M_CONDITIONAL) != 0) { 198 if ((Modifiers & JMP_M_CS) != 0) { 199 EdbPrintInstructionName (L"cs"); 200 } else { 201 EdbPrintInstructionName (L"cc"); 202 } 203 } 204 205 InstructionAddress += 2; 206 if ((Modifiers & OPCODE_M_IMMDATA64) != 0) { 207 CopyMem (&Data64, (VOID *)(UINTN)(InstructionAddress), sizeof(UINT64)); 208 if ((Modifiers & OPCODE_M_IMMDATA) != 0) { 209 EdbPrintData64 (Data64); 210 } else { 211 return 0; 212 } 213 } else { 214 CopyMem (&Data32, (VOID *)(UINTN)(InstructionAddress), sizeof(UINT32)); 215 EdbPrintRegister1 (Operands); 216 217 if ((Operands & OPERAND_M_INDIRECT1) == 0) { 218 if ((Modifiers & OPCODE_M_IMMDATA) == 0) { 219 Data32 = 0; 220 } 221 EdbPrintImmDatan (Data32); 222 } else { 223 EdbPrintRawIndexData32 (Data32); 224 } 225 } 226 227 EdbPostInstructionString (); 228 } 229 230 return Size; 231 } 232 233 /** 234 235 Disasm instruction - JMP8. 236 237 @param InstructionAddress - The instruction address 238 @param SystemContext - EBC system context. 239 @param DisasmString - The instruction string 240 241 @return Instruction length 242 243 **/ 244 UINTN 245 EdbDisasmJMP8 ( 246 IN EFI_PHYSICAL_ADDRESS InstructionAddress, 247 IN EFI_SYSTEM_CONTEXT SystemContext, 248 OUT CHAR16 **DisasmString 249 ) 250 { 251 UINT8 Modifiers; 252 253 ASSERT (GET_OPCODE(InstructionAddress) == OPCODE_JMP8); 254 Modifiers = GET_MODIFIERS (InstructionAddress); 255 256 // 257 // Construct Disasm String 258 // 259 if (DisasmString != NULL) { 260 *DisasmString = EdbPreInstructionString (); 261 262 EdbPrintInstructionName (L"JMP8"); 263 if ((Modifiers & CONDITION_M_CONDITIONAL) != 0) { 264 if ((Modifiers & JMP_M_CS) != 0) { 265 EdbPrintInstructionName (L"cs"); 266 } else { 267 EdbPrintInstructionName (L"cc"); 268 } 269 } 270 271 EdbPrintData8 (*(UINT8 *)(UINTN)(InstructionAddress + 1)); 272 273 EdbPostInstructionString (); 274 } 275 276 return 2; 277 } 278 279 /** 280 281 Disasm instruction - CALL. 282 283 @param InstructionAddress - The instruction address 284 @param SystemContext - EBC system context. 285 @param DisasmString - The instruction string 286 287 @return Instruction length 288 289 **/ 290 UINTN 291 EdbDisasmCALL ( 292 IN EFI_PHYSICAL_ADDRESS InstructionAddress, 293 IN EFI_SYSTEM_CONTEXT SystemContext, 294 OUT CHAR16 **DisasmString 295 ) 296 { 297 UINT8 Modifiers; 298 UINT8 Operands; 299 UINTN Size; 300 UINT32 Data32; 301 UINT64 Data64; 302 UINT64 Ip; 303 UINTN Result; 304 EFI_PHYSICAL_ADDRESS SavedInstructionAddress; 305 306 ASSERT (GET_OPCODE(InstructionAddress) == OPCODE_CALL); 307 SavedInstructionAddress = InstructionAddress; 308 309 Modifiers = GET_MODIFIERS (InstructionAddress); 310 Operands = GET_OPERANDS (InstructionAddress); 311 Size = (UINTN)mJMPLen[(Modifiers >> 6) & 0x03]; 312 313 // 314 // Construct Disasm String 315 // 316 if (DisasmString != NULL) { 317 *DisasmString = EdbPreInstructionString (); 318 319 EdbPrintInstructionName (L"CALL"); 320 // if (Modifiers & OPCODE_M_IMMDATA64) { 321 // EdbPrintInstructionName (L"64"); 322 // } else { 323 // EdbPrintInstructionName (L"32"); 324 // } 325 if ((Operands & OPERAND_M_NATIVE_CALL) != 0) { 326 EdbPrintInstructionName (L"EX"); 327 } 328 // if ((Operands & OPERAND_M_RELATIVE_ADDR) == 0) { 329 // EdbPrintInstructionName (L"a"); 330 // } 331 332 InstructionAddress += 2; 333 if ((Modifiers & OPCODE_M_IMMDATA64) != 0) { 334 CopyMem (&Data64, (VOID *)(UINTN)(InstructionAddress), sizeof(UINT64)); 335 Ip = Data64; 336 if ((Modifiers & OPCODE_M_IMMDATA) != 0) { 337 Result = EdbFindAndPrintSymbol ((UINTN)Ip); 338 if (Result == 0) { 339 EdbPrintData64 (Data64); 340 } 341 } else { 342 return 0; 343 } 344 } else { 345 if ((Modifiers & OPCODE_M_IMMDATA) != 0) { 346 CopyMem (&Data32, (VOID *)(UINTN)(InstructionAddress), sizeof(UINT32)); 347 } else { 348 Data32 = 0; 349 } 350 351 if ((Operands & OPERAND_M_OP1) == 0) { 352 Ip = (UINT64)Data32; 353 } else { 354 Ip = GetRegisterValue (SystemContext, (Operands & OPERAND_M_OP1)); 355 } 356 357 if ((Operands & OPERAND_M_INDIRECT1) == 0) { 358 if ((Operands & OPERAND_M_RELATIVE_ADDR) != 0) { 359 Result = EdbFindAndPrintSymbol ((UINTN)(SavedInstructionAddress + Ip + Size)); 360 } else { 361 Result = EdbFindAndPrintSymbol ((UINTN)Ip); 362 } 363 if (Result == 0) { 364 EdbPrintRegister1 (Operands); 365 if ((Modifiers & OPCODE_M_IMMDATA) != 0) { 366 EdbPrintImmData32 (Data32); 367 } 368 } 369 } else { 370 EdbPrintRegister1 (Operands); 371 if ((Modifiers & OPCODE_M_IMMDATA) != 0) { 372 EdbPrintRawIndexData32 (Data32); 373 } 374 } 375 } 376 377 EdbPostInstructionString (); 378 } 379 380 return Size; 381 } 382 383 /** 384 385 Disasm instruction - RET. 386 387 @param InstructionAddress - The instruction address 388 @param SystemContext - EBC system context. 389 @param DisasmString - The instruction string 390 391 @return Instruction length 392 393 **/ 394 UINTN 395 EdbDisasmRET ( 396 IN EFI_PHYSICAL_ADDRESS InstructionAddress, 397 IN EFI_SYSTEM_CONTEXT SystemContext, 398 OUT CHAR16 **DisasmString 399 ) 400 { 401 ASSERT (GET_OPCODE(InstructionAddress) == OPCODE_RET); 402 403 if (*(UINT8 *)(UINTN)(InstructionAddress + 1) != 0) { 404 return 0; 405 } 406 407 // 408 // Construct Disasm String 409 // 410 if (DisasmString != NULL) { 411 *DisasmString = EdbPreInstructionString (); 412 413 EdbPrintInstructionName (L"RET"); 414 415 EdbPostInstructionString (); 416 } 417 418 return 2; 419 } 420 421 /** 422 423 Disasm instruction - CMP. 424 425 @param InstructionAddress - The instruction address 426 @param SystemContext - EBC system context. 427 @param DisasmString - The instruction string 428 429 @return Instruction length 430 431 **/ 432 UINTN 433 EdbDisasmCMP ( 434 IN EFI_PHYSICAL_ADDRESS InstructionAddress, 435 IN EFI_SYSTEM_CONTEXT SystemContext, 436 OUT CHAR16 **DisasmString 437 ) 438 { 439 UINT8 Opcode; 440 UINT8 Modifiers; 441 UINT8 Operands; 442 UINT16 Data16; 443 UINTN Size; 444 445 ASSERT ( 446 (GET_OPCODE(InstructionAddress) == OPCODE_CMPEQ) || 447 (GET_OPCODE(InstructionAddress) == OPCODE_CMPLTE) || 448 (GET_OPCODE(InstructionAddress) == OPCODE_CMPGTE) || 449 (GET_OPCODE(InstructionAddress) == OPCODE_CMPULTE) || 450 (GET_OPCODE(InstructionAddress) == OPCODE_CMPUGTE) 451 ); 452 453 Opcode = GET_OPCODE (InstructionAddress); 454 Modifiers = GET_MODIFIERS (InstructionAddress); 455 Operands = GET_OPERANDS (InstructionAddress); 456 if ((Modifiers & OPCODE_M_IMMDATA) != 0) { 457 Size = 4; 458 } else { 459 Size = 2; 460 } 461 462 // 463 // Construct Disasm String 464 // 465 if (DisasmString != NULL) { 466 *DisasmString = EdbPreInstructionString (); 467 468 EdbPrintInstructionName (L"CMP"); 469 // if (Modifiers & OPCODE_M_64BIT) { 470 // EdbPrintInstructionName (L"64"); 471 // } else { 472 // EdbPrintInstructionName (L"32"); 473 // } 474 switch (Opcode) { 475 case OPCODE_CMPEQ: 476 EdbPrintInstructionName (L"eq"); 477 break; 478 case OPCODE_CMPLTE: 479 EdbPrintInstructionName (L"lte"); 480 break; 481 case OPCODE_CMPGTE: 482 EdbPrintInstructionName (L"gte"); 483 break; 484 case OPCODE_CMPULTE: 485 EdbPrintInstructionName (L"ulte"); 486 break; 487 case OPCODE_CMPUGTE: 488 EdbPrintInstructionName (L"ugte"); 489 break; 490 } 491 492 EdbPrintRegister1 (Operands); 493 InstructionAddress += 2; 494 495 EdbPrintComma (); 496 EdbPrintRegister2 (Operands); 497 498 if ((Modifiers & OPCODE_M_IMMDATA) != 0) { 499 CopyMem (&Data16, (VOID *)(UINTN)(InstructionAddress), sizeof(UINT16)); 500 if ((Operands & OPERAND_M_INDIRECT2) != 0) { 501 EdbPrintRawIndexData16 (Data16); 502 } else { 503 EdbPrintImmDatan (Data16); 504 } 505 } 506 507 EdbPostInstructionString (); 508 } 509 510 return Size; 511 } 512 513 /** 514 515 Disasm instruction - Unsigned Data Manipulate. 516 517 @param InstructionAddress - The instruction address 518 @param SystemContext - EBC system context. 519 @param DisasmString - The instruction string 520 521 @return Instruction length 522 523 **/ 524 UINTN 525 EdbDisasmUnsignedDataManip ( 526 IN EFI_PHYSICAL_ADDRESS InstructionAddress, 527 IN EFI_SYSTEM_CONTEXT SystemContext, 528 OUT CHAR16 **DisasmString 529 ) 530 { 531 UINT8 Modifiers; 532 UINT8 Opcode; 533 UINT8 Operands; 534 UINTN Size; 535 UINT16 Data16; 536 537 ASSERT ( 538 (GET_OPCODE(InstructionAddress) == OPCODE_NOT) || 539 (GET_OPCODE(InstructionAddress) == OPCODE_MULU) || 540 (GET_OPCODE(InstructionAddress) == OPCODE_DIVU) || 541 (GET_OPCODE(InstructionAddress) == OPCODE_MODU) || 542 (GET_OPCODE(InstructionAddress) == OPCODE_AND) || 543 (GET_OPCODE(InstructionAddress) == OPCODE_OR) || 544 (GET_OPCODE(InstructionAddress) == OPCODE_XOR) || 545 (GET_OPCODE(InstructionAddress) == OPCODE_SHL) || 546 (GET_OPCODE(InstructionAddress) == OPCODE_SHR) || 547 (GET_OPCODE(InstructionAddress) == OPCODE_EXTNDB) || 548 (GET_OPCODE(InstructionAddress) == OPCODE_EXTNDW) || 549 (GET_OPCODE(InstructionAddress) == OPCODE_EXTNDD) 550 ); 551 552 Opcode = GET_OPCODE (InstructionAddress); 553 Operands = GET_OPERANDS (InstructionAddress); 554 Modifiers = GET_MODIFIERS (InstructionAddress); 555 if ((Modifiers & DATAMANIP_M_IMMDATA) != 0) { 556 Size = 4; 557 } else { 558 Size = 2; 559 } 560 561 // 562 // Construct Disasm String 563 // 564 if (DisasmString != NULL) { 565 *DisasmString = EdbPreInstructionString (); 566 567 switch (Opcode) { 568 case OPCODE_NOT: 569 EdbPrintInstructionName (L"NOT"); 570 break; 571 case OPCODE_MULU: 572 EdbPrintInstructionName (L"MULU"); 573 break; 574 case OPCODE_DIVU: 575 EdbPrintInstructionName (L"DIVU"); 576 break; 577 case OPCODE_MODU: 578 EdbPrintInstructionName (L"MODU"); 579 break; 580 case OPCODE_AND: 581 EdbPrintInstructionName (L"AND"); 582 break; 583 case OPCODE_OR: 584 EdbPrintInstructionName (L"OR"); 585 break; 586 case OPCODE_XOR: 587 EdbPrintInstructionName (L"XOR"); 588 break; 589 case OPCODE_SHL: 590 EdbPrintInstructionName (L"SHL"); 591 break; 592 case OPCODE_SHR: 593 EdbPrintInstructionName (L"SHR"); 594 break; 595 case OPCODE_EXTNDB: 596 EdbPrintInstructionName (L"EXTNDB"); 597 break; 598 case OPCODE_EXTNDW: 599 EdbPrintInstructionName (L"EXTNDW"); 600 break; 601 case OPCODE_EXTNDD: 602 EdbPrintInstructionName (L"EXTNDD"); 603 break; 604 } 605 // if (Modifiers & DATAMANIP_M_64) { 606 // EdbPrintInstructionName (L"64"); 607 // } else { 608 // EdbPrintInstructionName (L"32"); 609 // } 610 611 EdbPrintRegister1 (Operands); 612 EdbPrintComma (); 613 EdbPrintRegister2 (Operands); 614 615 InstructionAddress += 2; 616 if ((Modifiers & DATAMANIP_M_IMMDATA) != 0) { 617 CopyMem (&Data16, (VOID *)(UINTN)(InstructionAddress), sizeof(UINT16)); 618 if ((Operands & OPERAND_M_INDIRECT2) != 0) { 619 EdbPrintRawIndexData16 (Data16); 620 } else { 621 EdbPrintImmDatan (Data16); 622 } 623 } 624 625 EdbPostInstructionString (); 626 } 627 628 return Size; 629 } 630 631 /** 632 633 Disasm instruction - Signed Data Manipulate, 634 635 @param InstructionAddress - The instruction address 636 @param SystemContext - EBC system context. 637 @param DisasmString - The instruction string 638 639 @return Instruction length 640 641 **/ 642 UINTN 643 EdbDisasmSignedDataManip ( 644 IN EFI_PHYSICAL_ADDRESS InstructionAddress, 645 IN EFI_SYSTEM_CONTEXT SystemContext, 646 OUT CHAR16 **DisasmString 647 ) 648 { 649 UINT8 Modifiers; 650 UINT8 Opcode; 651 UINT8 Operands; 652 UINTN Size; 653 UINT16 Data16; 654 655 ASSERT ( 656 (GET_OPCODE(InstructionAddress) == OPCODE_NEG) || 657 (GET_OPCODE(InstructionAddress) == OPCODE_ADD) || 658 (GET_OPCODE(InstructionAddress) == OPCODE_SUB) || 659 (GET_OPCODE(InstructionAddress) == OPCODE_MUL) || 660 (GET_OPCODE(InstructionAddress) == OPCODE_DIV) || 661 (GET_OPCODE(InstructionAddress) == OPCODE_MOD) || 662 (GET_OPCODE(InstructionAddress) == OPCODE_ASHR) 663 ); 664 665 Opcode = GET_OPCODE (InstructionAddress); 666 Operands = GET_OPERANDS (InstructionAddress); 667 Modifiers = GET_MODIFIERS (InstructionAddress); 668 if ((Modifiers & DATAMANIP_M_IMMDATA) != 0) { 669 Size = 4; 670 } else { 671 Size = 2; 672 } 673 674 // 675 // Construct Disasm String 676 // 677 if (DisasmString != NULL) { 678 *DisasmString = EdbPreInstructionString (); 679 680 switch (Opcode) { 681 case OPCODE_NEG: 682 EdbPrintInstructionName (L"NEG"); 683 break; 684 case OPCODE_ADD: 685 EdbPrintInstructionName (L"ADD"); 686 break; 687 case OPCODE_SUB: 688 EdbPrintInstructionName (L"SUB"); 689 break; 690 case OPCODE_MUL: 691 EdbPrintInstructionName (L"MUL"); 692 break; 693 case OPCODE_DIV: 694 EdbPrintInstructionName (L"DIV"); 695 break; 696 case OPCODE_MOD: 697 EdbPrintInstructionName (L"MOD"); 698 break; 699 case OPCODE_ASHR: 700 EdbPrintInstructionName (L"ASHR"); 701 break; 702 } 703 // if (Modifiers & DATAMANIP_M_64) { 704 // EdbPrintInstructionName (L"64"); 705 // } else { 706 // EdbPrintInstructionName (L"32"); 707 // } 708 709 EdbPrintRegister1 (Operands); 710 EdbPrintComma (); 711 EdbPrintRegister2 (Operands); 712 713 InstructionAddress += 2; 714 if ((Modifiers & DATAMANIP_M_IMMDATA) != 0) { 715 CopyMem (&Data16, (VOID *)(UINTN)(InstructionAddress), sizeof(UINT16)); 716 if ((Operands & OPERAND_M_INDIRECT2) != 0) { 717 EdbPrintRawIndexData16 (Data16); 718 } else { 719 EdbPrintImmDatan (Data16); 720 } 721 } 722 723 EdbPostInstructionString (); 724 } 725 726 return Size; 727 } 728 729 /** 730 731 Disasm instruction - MOVxx. 732 733 @param InstructionAddress - The instruction address 734 @param SystemContext - EBC system context. 735 @param DisasmString - The instruction string 736 737 @return Instruction length 738 739 **/ 740 UINTN 741 EdbDisasmMOVxx ( 742 IN EFI_PHYSICAL_ADDRESS InstructionAddress, 743 IN EFI_SYSTEM_CONTEXT SystemContext, 744 OUT CHAR16 **DisasmString 745 ) 746 { 747 UINT8 Modifiers; 748 UINT8 Opcode; 749 UINT8 Operands; 750 UINTN Size; 751 UINT16 Data16; 752 UINT32 Data32; 753 UINT64 Data64; 754 755 ASSERT ( 756 (GET_OPCODE(InstructionAddress) == OPCODE_MOVBW) || 757 (GET_OPCODE(InstructionAddress) == OPCODE_MOVWW) || 758 (GET_OPCODE(InstructionAddress) == OPCODE_MOVDW) || 759 (GET_OPCODE(InstructionAddress) == OPCODE_MOVQW) || 760 (GET_OPCODE(InstructionAddress) == OPCODE_MOVBD) || 761 (GET_OPCODE(InstructionAddress) == OPCODE_MOVWD) || 762 (GET_OPCODE(InstructionAddress) == OPCODE_MOVDD) || 763 (GET_OPCODE(InstructionAddress) == OPCODE_MOVQD) || 764 (GET_OPCODE(InstructionAddress) == OPCODE_MOVQQ) || 765 (GET_OPCODE(InstructionAddress) == OPCODE_MOVNW) || 766 (GET_OPCODE(InstructionAddress) == OPCODE_MOVND) 767 ); 768 769 Opcode = GET_OPCODE (InstructionAddress); 770 Modifiers = GET_MODIFIERS (InstructionAddress); 771 Operands = GET_OPERANDS (InstructionAddress); 772 Size = 2; 773 if ((Modifiers & (OPCODE_M_IMMED_OP1 | OPCODE_M_IMMED_OP2)) != 0) { 774 if ((Opcode <= OPCODE_MOVQW) || (Opcode == OPCODE_MOVNW)) { 775 if ((Modifiers & OPCODE_M_IMMED_OP1) != 0) { 776 Size += 2; 777 } 778 if ((Modifiers & OPCODE_M_IMMED_OP2) != 0) { 779 Size += 2; 780 } 781 } else if (((Opcode <= OPCODE_MOVQD) || (Opcode == OPCODE_MOVND)) != 0) { 782 if ((Modifiers & OPCODE_M_IMMED_OP1) != 0) { 783 Size += 4; 784 } 785 if ((Modifiers & OPCODE_M_IMMED_OP2) != 0) { 786 Size += 4; 787 } 788 } else if (Opcode == OPCODE_MOVQQ) { 789 if ((Modifiers & OPCODE_M_IMMED_OP1) != 0) { 790 Size += 8; 791 } 792 if ((Modifiers & OPCODE_M_IMMED_OP2) != 0) { 793 Size += 8; 794 } 795 } 796 } 797 798 // 799 // Construct Disasm String 800 // 801 if (DisasmString != NULL) { 802 *DisasmString = EdbPreInstructionString (); 803 804 EdbPrintInstructionName (L"MOV"); 805 switch (Opcode) { 806 case OPCODE_MOVBW: 807 EdbPrintInstructionName (L"bw"); 808 break; 809 case OPCODE_MOVWW: 810 EdbPrintInstructionName (L"ww"); 811 break; 812 case OPCODE_MOVDW: 813 EdbPrintInstructionName (L"dw"); 814 break; 815 case OPCODE_MOVQW: 816 EdbPrintInstructionName (L"qw"); 817 break; 818 case OPCODE_MOVBD: 819 EdbPrintInstructionName (L"bd"); 820 break; 821 case OPCODE_MOVWD: 822 EdbPrintInstructionName (L"wd"); 823 break; 824 case OPCODE_MOVDD: 825 EdbPrintInstructionName (L"dd"); 826 break; 827 case OPCODE_MOVQD: 828 EdbPrintInstructionName (L"qd"); 829 break; 830 case OPCODE_MOVQQ: 831 EdbPrintInstructionName (L"qq"); 832 break; 833 case OPCODE_MOVNW: 834 EdbPrintInstructionName (L"nw"); 835 break; 836 case OPCODE_MOVND: 837 EdbPrintInstructionName (L"nd"); 838 break; 839 } 840 841 EdbPrintRegister1 (Operands); 842 843 InstructionAddress += 2; 844 if ((Modifiers & OPCODE_M_IMMED_OP1) != 0) { 845 if ((Opcode <= OPCODE_MOVQW) || (Opcode == OPCODE_MOVNW)) { 846 CopyMem (&Data16, (VOID *)(UINTN)(InstructionAddress), sizeof(UINT16)); 847 InstructionAddress += 2; 848 EdbPrintRawIndexData16 (Data16); 849 } else if ((Opcode <= OPCODE_MOVQD) || (Opcode == OPCODE_MOVND)) { 850 CopyMem (&Data32, (VOID *)(UINTN)(InstructionAddress), sizeof(UINT32)); 851 InstructionAddress += 4; 852 EdbPrintRawIndexData32 (Data32); 853 } else if (Opcode == OPCODE_MOVQQ) { 854 CopyMem (&Data64, (VOID *)(UINTN)(InstructionAddress), sizeof(UINT64)); 855 InstructionAddress += 8; 856 EdbPrintRawIndexData64 (Data64); 857 } 858 } 859 860 EdbPrintComma (); 861 EdbPrintRegister2 (Operands); 862 863 if ((Modifiers & OPCODE_M_IMMED_OP2) != 0) { 864 if ((Opcode <= OPCODE_MOVQW) || (Opcode == OPCODE_MOVNW)) { 865 CopyMem (&Data16, (VOID *)(UINTN)(InstructionAddress), sizeof(UINT16)); 866 EdbPrintRawIndexData16 (Data16); 867 } else if ((Opcode <= OPCODE_MOVQD) || (Opcode == OPCODE_MOVND)) { 868 CopyMem (&Data32, (VOID *)(UINTN)(InstructionAddress), sizeof(UINT32)); 869 EdbPrintRawIndexData32 (Data32); 870 } else if (Opcode == OPCODE_MOVQQ) { 871 CopyMem (&Data64, (VOID *)(UINTN)(InstructionAddress), sizeof(UINT64)); 872 EdbPrintRawIndexData64 (Data64); 873 } 874 } 875 876 EdbPostInstructionString (); 877 } 878 879 return Size; 880 } 881 882 /** 883 884 Disasm instruction - MOVsnw. 885 886 @param InstructionAddress - The instruction address 887 @param SystemContext - EBC system context. 888 @param DisasmString - The instruction string 889 890 @return Instruction length 891 892 **/ 893 UINTN 894 EdbDisasmMOVsnw ( 895 IN EFI_PHYSICAL_ADDRESS InstructionAddress, 896 IN EFI_SYSTEM_CONTEXT SystemContext, 897 OUT CHAR16 **DisasmString 898 ) 899 { 900 UINT8 Modifiers; 901 UINT8 Operands; 902 UINTN Size; 903 UINT16 Data16; 904 905 ASSERT (GET_OPCODE(InstructionAddress) == OPCODE_MOVSNW); 906 907 Modifiers = GET_MODIFIERS (InstructionAddress); 908 Operands = GET_OPERANDS (InstructionAddress); 909 Size = 2; 910 if ((Modifiers & OPCODE_M_IMMED_OP1) != 0) { 911 Size += 2; 912 } 913 if ((Modifiers & OPCODE_M_IMMED_OP2) != 0) { 914 Size += 2; 915 } 916 917 // 918 // Construct Disasm String 919 // 920 if (DisasmString != NULL) { 921 *DisasmString = EdbPreInstructionString (); 922 923 EdbPrintInstructionName (L"MOVsnw"); 924 925 EdbPrintRegister1 (Operands); 926 927 InstructionAddress += 2; 928 if ((Modifiers & OPCODE_M_IMMED_OP1) != 0) { 929 CopyMem (&Data16, (VOID *)(UINTN)(InstructionAddress), sizeof(UINT16)); 930 InstructionAddress += 2; 931 EdbPrintRawIndexData16 (Data16); 932 } 933 934 EdbPrintComma (); 935 EdbPrintRegister2 (Operands); 936 937 if ((Modifiers & OPCODE_M_IMMED_OP2) != 0) { 938 CopyMem (&Data16, (VOID *)(UINTN)(InstructionAddress), sizeof(UINT16)); 939 if ((Operands & OPERAND_M_INDIRECT2) != 0) { 940 EdbPrintRawIndexData16 (Data16); 941 } else { 942 EdbPrintImmDatan (Data16); 943 } 944 } 945 946 EdbPostInstructionString (); 947 } 948 949 return Size; 950 } 951 952 /** 953 954 Disasm instruction - MOVsnd. 955 956 @param InstructionAddress - The instruction address 957 @param SystemContext - EBC system context. 958 @param DisasmString - The instruction string 959 960 @return Instruction length 961 962 **/ 963 UINTN 964 EdbDisasmMOVsnd ( 965 IN EFI_PHYSICAL_ADDRESS InstructionAddress, 966 IN EFI_SYSTEM_CONTEXT SystemContext, 967 OUT CHAR16 **DisasmString 968 ) 969 { 970 UINT8 Modifiers; 971 UINT8 Operands; 972 UINTN Size; 973 UINT32 Data32; 974 975 ASSERT (GET_OPCODE(InstructionAddress) == OPCODE_MOVSND); 976 977 Modifiers = GET_MODIFIERS (InstructionAddress); 978 Operands = GET_OPERANDS (InstructionAddress); 979 Size = 2; 980 if ((Modifiers & OPCODE_M_IMMED_OP1) != 0) { 981 Size += 4; 982 } 983 if ((Modifiers & OPCODE_M_IMMED_OP2) != 0) { 984 Size += 4; 985 } 986 987 // 988 // Construct Disasm String 989 // 990 if (DisasmString != NULL) { 991 *DisasmString = EdbPreInstructionString (); 992 993 EdbPrintInstructionName (L"MOVsnd"); 994 995 EdbPrintRegister1 (Operands); 996 997 InstructionAddress += 2; 998 if ((Modifiers & OPCODE_M_IMMED_OP1) != 0) { 999 CopyMem (&Data32, (VOID *)(UINTN)(InstructionAddress), sizeof(UINT32)); 1000 InstructionAddress += 4; 1001 EdbPrintRawIndexData32 (Data32); 1002 } 1003 1004 EdbPrintComma (); 1005 EdbPrintRegister2 (Operands); 1006 1007 if ((Modifiers & OPCODE_M_IMMED_OP2) != 0) { 1008 CopyMem (&Data32, (VOID *)(UINTN)(InstructionAddress), sizeof(UINT32)); 1009 if ((Operands & OPERAND_M_INDIRECT2) != 0) { 1010 EdbPrintRawIndexData32 (Data32); 1011 } else { 1012 EdbPrintImmDatan (Data32); 1013 } 1014 } 1015 1016 EdbPostInstructionString (); 1017 } 1018 1019 return Size; 1020 } 1021 1022 /** 1023 1024 Disasm instruction - LOADSP. 1025 1026 @param InstructionAddress - The instruction address 1027 @param SystemContext - EBC system context. 1028 @param DisasmString - The instruction string 1029 1030 @return Instruction length 1031 1032 **/ 1033 UINTN 1034 EdbDisasmLOADSP ( 1035 IN EFI_PHYSICAL_ADDRESS InstructionAddress, 1036 IN EFI_SYSTEM_CONTEXT SystemContext, 1037 OUT CHAR16 **DisasmString 1038 ) 1039 { 1040 UINT8 Operands; 1041 1042 ASSERT (GET_OPCODE(InstructionAddress) == OPCODE_LOADSP); 1043 1044 Operands = GET_OPERANDS (InstructionAddress); 1045 1046 // 1047 // Construct Disasm String 1048 // 1049 if (DisasmString != NULL) { 1050 *DisasmString = EdbPreInstructionString (); 1051 1052 EdbPrintInstructionName (L"LOADSP"); 1053 1054 EdbPrintDedicatedRegister1 (Operands); 1055 1056 EdbPrintRegister2 (Operands); 1057 1058 EdbPostInstructionString (); 1059 } 1060 1061 return 2; 1062 } 1063 1064 /** 1065 1066 Disasm instruction - STORESP. 1067 1068 @param InstructionAddress - The instruction address 1069 @param SystemContext - EBC system context. 1070 @param DisasmString - The instruction string 1071 1072 @return Instruction length 1073 1074 **/ 1075 UINTN 1076 EdbDisasmSTORESP ( 1077 IN EFI_PHYSICAL_ADDRESS InstructionAddress, 1078 IN EFI_SYSTEM_CONTEXT SystemContext, 1079 OUT CHAR16 **DisasmString 1080 ) 1081 { 1082 UINT8 Operands; 1083 1084 ASSERT (GET_OPCODE(InstructionAddress) == OPCODE_STORESP); 1085 1086 Operands = GET_OPERANDS (InstructionAddress); 1087 1088 // 1089 // Construct Disasm String 1090 // 1091 if (DisasmString != NULL) { 1092 *DisasmString = EdbPreInstructionString (); 1093 1094 EdbPrintInstructionName (L"STORESP"); 1095 1096 EdbPrintRegister1 (Operands); 1097 1098 EdbPrintDedicatedRegister2 (Operands); 1099 1100 EdbPostInstructionString (); 1101 } 1102 1103 return 2; 1104 } 1105 1106 1107 /** 1108 1109 Disasm instruction - PUSH. 1110 1111 @param InstructionAddress - The instruction address 1112 @param SystemContext - EBC system context. 1113 @param DisasmString - The instruction string 1114 1115 @return Instruction length 1116 1117 **/ 1118 UINTN 1119 EdbDisasmPUSH ( 1120 IN EFI_PHYSICAL_ADDRESS InstructionAddress, 1121 IN EFI_SYSTEM_CONTEXT SystemContext, 1122 OUT CHAR16 **DisasmString 1123 ) 1124 { 1125 UINT8 Modifiers; 1126 UINT8 Operands; 1127 UINTN Size; 1128 UINT16 Data16; 1129 1130 ASSERT (GET_OPCODE(InstructionAddress) == OPCODE_PUSH); 1131 1132 Operands = GET_OPERANDS (InstructionAddress); 1133 Modifiers = GET_MODIFIERS (InstructionAddress); 1134 if ((Modifiers & PUSHPOP_M_IMMDATA) != 0) { 1135 Size = 4; 1136 } else { 1137 Size = 2; 1138 } 1139 1140 // 1141 // Construct Disasm String 1142 // 1143 if (DisasmString != NULL) { 1144 *DisasmString = EdbPreInstructionString (); 1145 1146 EdbPrintInstructionName (L"PUSH"); 1147 // if (Modifiers & PUSHPOP_M_64) { 1148 // EdbPrintInstructionName (L"64"); 1149 // } else { 1150 // EdbPrintInstructionName (L"32"); 1151 // } 1152 1153 EdbPrintRegister1 (Operands); 1154 1155 InstructionAddress += 2; 1156 if ((Modifiers & PUSHPOP_M_IMMDATA) != 0) { 1157 CopyMem (&Data16, (VOID *)(UINTN)(InstructionAddress), sizeof(UINT16)); 1158 if ((Operands & OPERAND_M_INDIRECT1) != 0) { 1159 EdbPrintRawIndexData16 (Data16); 1160 } else { 1161 EdbPrintImmDatan (Data16); 1162 } 1163 } 1164 1165 EdbPostInstructionString (); 1166 } 1167 1168 return Size; 1169 } 1170 1171 /** 1172 1173 Disasm instruction - POP. 1174 1175 @param InstructionAddress - The instruction address 1176 @param SystemContext - EBC system context. 1177 @param DisasmString - The instruction string 1178 1179 @return Instruction length 1180 1181 **/ 1182 UINTN 1183 EdbDisasmPOP ( 1184 IN EFI_PHYSICAL_ADDRESS InstructionAddress, 1185 IN EFI_SYSTEM_CONTEXT SystemContext, 1186 OUT CHAR16 **DisasmString 1187 ) 1188 { 1189 UINT8 Modifiers; 1190 UINT8 Operands; 1191 UINTN Size; 1192 UINT16 Data16; 1193 1194 ASSERT (GET_OPCODE(InstructionAddress) == OPCODE_POP); 1195 1196 Operands = GET_OPERANDS (InstructionAddress); 1197 Modifiers = GET_MODIFIERS (InstructionAddress); 1198 if ((Modifiers & PUSHPOP_M_IMMDATA) != 0) { 1199 Size = 4; 1200 } else { 1201 Size = 2; 1202 } 1203 1204 // 1205 // Construct Disasm String 1206 // 1207 if (DisasmString != NULL) { 1208 *DisasmString = EdbPreInstructionString (); 1209 1210 EdbPrintInstructionName (L"POP"); 1211 // if (Modifiers & PUSHPOP_M_64) { 1212 // EdbPrintInstructionName (L"64"); 1213 // } else { 1214 // EdbPrintInstructionName (L"32"); 1215 // } 1216 1217 EdbPrintRegister1 (Operands); 1218 1219 InstructionAddress += 2; 1220 if ((Modifiers & PUSHPOP_M_IMMDATA) != 0) { 1221 CopyMem (&Data16, (VOID *)(UINTN)(InstructionAddress), sizeof(UINT16)); 1222 if ((Operands & OPERAND_M_INDIRECT1) != 0) { 1223 EdbPrintRawIndexData16 (Data16); 1224 } else { 1225 EdbPrintImmDatan (Data16); 1226 } 1227 } 1228 1229 EdbPostInstructionString (); 1230 } 1231 1232 return Size; 1233 } 1234 1235 /** 1236 1237 Disasm instruction - CMPI. 1238 1239 @param InstructionAddress - The instruction address 1240 @param SystemContext - EBC system context. 1241 @param DisasmString - The instruction string 1242 1243 @return Instruction length 1244 1245 **/ 1246 UINTN 1247 EdbDisasmCMPI ( 1248 IN EFI_PHYSICAL_ADDRESS InstructionAddress, 1249 IN EFI_SYSTEM_CONTEXT SystemContext, 1250 OUT CHAR16 **DisasmString 1251 ) 1252 { 1253 UINT8 Modifiers; 1254 UINT8 Opcode; 1255 UINT8 Operands; 1256 UINT16 Data16; 1257 UINT32 Data32; 1258 UINTN Size; 1259 1260 ASSERT ( 1261 (GET_OPCODE(InstructionAddress) == OPCODE_CMPIEQ) || 1262 (GET_OPCODE(InstructionAddress) == OPCODE_CMPILTE) || 1263 (GET_OPCODE(InstructionAddress) == OPCODE_CMPIGTE) || 1264 (GET_OPCODE(InstructionAddress) == OPCODE_CMPIULTE) || 1265 (GET_OPCODE(InstructionAddress) == OPCODE_CMPIUGTE) 1266 ); 1267 1268 Modifiers = GET_MODIFIERS (InstructionAddress); 1269 Opcode = GET_OPCODE (InstructionAddress); 1270 Operands = GET_OPERANDS (InstructionAddress); 1271 1272 if ((Operands & 0xE0) != 0) { 1273 return 0; 1274 } 1275 1276 Size = 2; 1277 if ((Operands & OPERAND_M_CMPI_INDEX) != 0) { 1278 Size += 2; 1279 } 1280 if ((Modifiers & OPCODE_M_CMPI32_DATA) != 0) { 1281 Size += 4; 1282 } else { 1283 Size += 2; 1284 } 1285 1286 // 1287 // Construct Disasm String 1288 // 1289 if (DisasmString != NULL) { 1290 *DisasmString = EdbPreInstructionString (); 1291 1292 EdbPrintInstructionName (L"CMPI"); 1293 // if (Modifiers & OPCODE_M_CMPI64) { 1294 // EdbPrintInstructionName (L"64"); 1295 // } else { 1296 // EdbPrintInstructionName (L"32"); 1297 // } 1298 if ((Modifiers & OPCODE_M_CMPI32_DATA) != 0) { 1299 EdbPrintInstructionName (L"d"); 1300 } else { 1301 EdbPrintInstructionName (L"w"); 1302 } 1303 switch (Opcode) { 1304 case OPCODE_CMPIEQ: 1305 EdbPrintInstructionName (L"eq"); 1306 break; 1307 case OPCODE_CMPILTE: 1308 EdbPrintInstructionName (L"lte"); 1309 break; 1310 case OPCODE_CMPIGTE: 1311 EdbPrintInstructionName (L"gte"); 1312 break; 1313 case OPCODE_CMPIULTE: 1314 EdbPrintInstructionName (L"ulte"); 1315 break; 1316 case OPCODE_CMPIUGTE: 1317 EdbPrintInstructionName (L"ugte"); 1318 break; 1319 } 1320 1321 EdbPrintRegister1 (Operands); 1322 1323 InstructionAddress += 2; 1324 if ((Operands & OPERAND_M_CMPI_INDEX) != 0) { 1325 CopyMem (&Data16, (VOID *)(UINTN)(InstructionAddress), sizeof(UINT16)); 1326 InstructionAddress += 2; 1327 EdbPrintRawIndexData16 (Data16); 1328 } 1329 1330 EdbPrintComma (); 1331 1332 if ((Modifiers & OPCODE_M_CMPI32_DATA) != 0) { 1333 CopyMem (&Data32, (VOID *)(UINTN)(InstructionAddress), sizeof(UINT32)); 1334 EdbPrintDatan (Data32); 1335 } else { 1336 CopyMem (&Data16, (VOID *)(UINTN)(InstructionAddress), sizeof(UINT16)); 1337 EdbPrintDatan (Data16); 1338 } 1339 1340 EdbPostInstructionString (); 1341 } 1342 1343 return Size; 1344 } 1345 1346 /** 1347 1348 Disasm instruction - PUSHn. 1349 1350 @param InstructionAddress - The instruction address 1351 @param SystemContext - EBC system context. 1352 @param DisasmString - The instruction string 1353 1354 @return Instruction length 1355 1356 **/ 1357 UINTN 1358 EdbDisasmPUSHn ( 1359 IN EFI_PHYSICAL_ADDRESS InstructionAddress, 1360 IN EFI_SYSTEM_CONTEXT SystemContext, 1361 OUT CHAR16 **DisasmString 1362 ) 1363 { 1364 UINT8 Modifiers; 1365 UINT8 Operands; 1366 UINTN Size; 1367 UINT16 Data16; 1368 1369 ASSERT (GET_OPCODE(InstructionAddress) == OPCODE_PUSHN); 1370 1371 Operands = GET_OPERANDS (InstructionAddress); 1372 Modifiers = GET_MODIFIERS (InstructionAddress); 1373 if ((Modifiers & PUSHPOP_M_IMMDATA) != 0) { 1374 Size = 4; 1375 } else { 1376 Size = 2; 1377 } 1378 1379 // 1380 // Construct Disasm String 1381 // 1382 if (DisasmString != NULL) { 1383 *DisasmString = EdbPreInstructionString (); 1384 1385 EdbPrintInstructionName (L"PUSHn"); 1386 1387 EdbPrintRegister1 (Operands); 1388 1389 InstructionAddress += 2; 1390 if ((Modifiers & PUSHPOP_M_IMMDATA) != 0) { 1391 CopyMem (&Data16, (VOID *)(UINTN)(InstructionAddress), sizeof(UINT16)); 1392 if ((Operands & OPERAND_M_INDIRECT1) != 0) { 1393 EdbPrintRawIndexData16 (Data16); 1394 } else { 1395 EdbPrintImmDatan (Data16); 1396 } 1397 } 1398 1399 EdbPostInstructionString (); 1400 } 1401 1402 return Size; 1403 } 1404 1405 /** 1406 1407 Disasm instruction - POPn. 1408 1409 @param InstructionAddress - The instruction address 1410 @param SystemContext - EBC system context. 1411 @param DisasmString - The instruction string 1412 1413 @return Instruction length 1414 1415 **/ 1416 UINTN 1417 EdbDisasmPOPn ( 1418 IN EFI_PHYSICAL_ADDRESS InstructionAddress, 1419 IN EFI_SYSTEM_CONTEXT SystemContext, 1420 OUT CHAR16 **DisasmString 1421 ) 1422 { 1423 UINT8 Modifiers; 1424 UINT8 Operands; 1425 UINTN Size; 1426 UINT16 Data16; 1427 1428 ASSERT (GET_OPCODE(InstructionAddress) == OPCODE_POPN); 1429 1430 Operands = GET_OPERANDS (InstructionAddress); 1431 Modifiers = GET_MODIFIERS (InstructionAddress); 1432 if ((Modifiers & PUSHPOP_M_IMMDATA) != 0) { 1433 Size = 4; 1434 } else { 1435 Size = 2; 1436 } 1437 1438 // 1439 // Construct Disasm String 1440 // 1441 if (DisasmString != NULL) { 1442 *DisasmString = EdbPreInstructionString (); 1443 1444 EdbPrintInstructionName (L"POPn"); 1445 1446 EdbPrintRegister1 (Operands); 1447 1448 InstructionAddress += 2; 1449 if ((Modifiers & PUSHPOP_M_IMMDATA) != 0) { 1450 CopyMem (&Data16, (VOID *)(UINTN)(InstructionAddress), sizeof(UINT16)); 1451 if ((Operands & OPERAND_M_INDIRECT1) != 0) { 1452 EdbPrintRawIndexData16 (Data16); 1453 } else { 1454 EdbPrintImmDatan (Data16); 1455 } 1456 } 1457 1458 EdbPostInstructionString (); 1459 } 1460 1461 return Size; 1462 } 1463 1464 /** 1465 1466 Disasm instruction - MOVI. 1467 1468 @param InstructionAddress - The instruction address 1469 @param SystemContext - EBC system context. 1470 @param DisasmString - The instruction string 1471 1472 @return Instruction length 1473 1474 **/ 1475 UINTN 1476 EdbDisasmMOVI ( 1477 IN EFI_PHYSICAL_ADDRESS InstructionAddress, 1478 IN EFI_SYSTEM_CONTEXT SystemContext, 1479 OUT CHAR16 **DisasmString 1480 ) 1481 { 1482 UINT8 Modifiers; 1483 UINT8 Operands; 1484 UINTN Size; 1485 UINT16 Data16; 1486 UINT32 Data32; 1487 UINT64 Data64; 1488 1489 ASSERT (GET_OPCODE(InstructionAddress) == OPCODE_MOVI); 1490 1491 Modifiers = GET_MODIFIERS (InstructionAddress); 1492 Operands = GET_OPERANDS (InstructionAddress); 1493 1494 if ((Operands & MOVI_M_IMMDATA) != 0) { 1495 Size = 4; 1496 } else { 1497 Size = 2; 1498 } 1499 if ((Modifiers & MOVI_M_DATAWIDTH) == MOVI_DATAWIDTH16) { 1500 Size += 2; 1501 } else if ((Modifiers & MOVI_M_DATAWIDTH) == MOVI_DATAWIDTH32) { 1502 Size += 4; 1503 } else if ((Modifiers & MOVI_M_DATAWIDTH) == MOVI_DATAWIDTH64) { 1504 Size += 8; 1505 } 1506 1507 // 1508 // Construct Disasm String 1509 // 1510 if (DisasmString != NULL) { 1511 *DisasmString = EdbPreInstructionString (); 1512 1513 EdbPrintInstructionName (L"MOVI"); 1514 switch (Operands & MOVI_M_MOVEWIDTH) { 1515 case MOVI_MOVEWIDTH8: 1516 EdbPrintInstructionName (L"b"); 1517 break; 1518 case MOVI_MOVEWIDTH16: 1519 EdbPrintInstructionName (L"w"); 1520 break; 1521 case MOVI_MOVEWIDTH32: 1522 EdbPrintInstructionName (L"d"); 1523 break; 1524 case MOVI_MOVEWIDTH64: 1525 EdbPrintInstructionName (L"q"); 1526 break; 1527 } 1528 switch (Modifiers & MOVI_M_DATAWIDTH) { 1529 case MOVI_DATAWIDTH16: 1530 EdbPrintInstructionName (L"w"); 1531 break; 1532 case MOVI_DATAWIDTH32: 1533 EdbPrintInstructionName (L"d"); 1534 break; 1535 case MOVI_DATAWIDTH64: 1536 EdbPrintInstructionName (L"q"); 1537 break; 1538 } 1539 1540 EdbPrintRegister1 (Operands); 1541 1542 InstructionAddress += 2; 1543 if ((Operands & MOVI_M_IMMDATA) != 0) { 1544 CopyMem (&Data16, (VOID *)(UINTN)(InstructionAddress), sizeof(UINT16)); 1545 InstructionAddress += 2; 1546 EdbPrintRawIndexData16 (Data16); 1547 } 1548 1549 EdbPrintComma (); 1550 1551 switch (Modifiers & MOVI_M_DATAWIDTH) { 1552 case MOVI_DATAWIDTH16: 1553 CopyMem (&Data16, (VOID *)(UINTN)(InstructionAddress), sizeof(UINT16)); 1554 EdbPrintDatan (Data16); 1555 break; 1556 case MOVI_DATAWIDTH32: 1557 CopyMem (&Data32, (VOID *)(UINTN)(InstructionAddress), sizeof(UINT32)); 1558 EdbPrintDatan (Data32); 1559 break; 1560 case MOVI_DATAWIDTH64: 1561 CopyMem (&Data64, (VOID *)(UINTN)(InstructionAddress), sizeof(UINT64)); 1562 EdbPrintData64n (Data64); 1563 break; 1564 } 1565 1566 EdbPostInstructionString (); 1567 } 1568 1569 return Size; 1570 } 1571 1572 /** 1573 1574 Disasm instruction - MOVIn. 1575 1576 @param InstructionAddress - The instruction address 1577 @param SystemContext - EBC system context. 1578 @param DisasmString - The instruction string 1579 1580 @return Instruction length 1581 1582 **/ 1583 UINTN 1584 EdbDisasmMOVIn ( 1585 IN EFI_PHYSICAL_ADDRESS InstructionAddress, 1586 IN EFI_SYSTEM_CONTEXT SystemContext, 1587 OUT CHAR16 **DisasmString 1588 ) 1589 { 1590 UINT8 Modifiers; 1591 UINT8 Operands; 1592 UINTN Size; 1593 UINT16 Data16; 1594 UINT32 Data32; 1595 UINT64 Data64; 1596 1597 ASSERT (GET_OPCODE(InstructionAddress) == OPCODE_MOVIN); 1598 1599 Modifiers = GET_MODIFIERS (InstructionAddress); 1600 Operands = GET_OPERANDS (InstructionAddress); 1601 1602 if ((Operands & MOVI_M_IMMDATA) != 0) { 1603 Size = 4; 1604 } else { 1605 Size = 2; 1606 } 1607 if ((Modifiers & MOVI_M_DATAWIDTH) == MOVI_DATAWIDTH16) { 1608 Size += 2; 1609 } else if ((Modifiers & MOVI_M_DATAWIDTH) == MOVI_DATAWIDTH32) { 1610 Size += 4; 1611 } else if ((Modifiers & MOVI_M_DATAWIDTH) == MOVI_DATAWIDTH64) { 1612 Size += 8; 1613 } 1614 1615 // 1616 // Construct Disasm String 1617 // 1618 if (DisasmString != NULL) { 1619 *DisasmString = EdbPreInstructionString (); 1620 1621 EdbPrintInstructionName (L"MOVIn"); 1622 switch (Modifiers & MOVI_M_DATAWIDTH) { 1623 case MOVI_DATAWIDTH16: 1624 EdbPrintInstructionName (L"w"); 1625 break; 1626 case MOVI_DATAWIDTH32: 1627 EdbPrintInstructionName (L"d"); 1628 break; 1629 case MOVI_DATAWIDTH64: 1630 EdbPrintInstructionName (L"q"); 1631 break; 1632 } 1633 1634 EdbPrintRegister1 (Operands); 1635 1636 InstructionAddress += 2; 1637 if ((Operands & MOVI_M_IMMDATA) != 0) { 1638 CopyMem (&Data16, (VOID *)(UINTN)(InstructionAddress), sizeof(UINT16)); 1639 InstructionAddress += 2; 1640 EdbPrintRawIndexData16 (Data16); 1641 } 1642 1643 EdbPrintComma (); 1644 1645 switch (Modifiers & MOVI_M_DATAWIDTH) { 1646 case MOVI_DATAWIDTH16: 1647 CopyMem (&Data16, (VOID *)(UINTN)(InstructionAddress), sizeof(UINT16)); 1648 EdbPrintRawIndexData16 (Data16); 1649 break; 1650 case MOVI_DATAWIDTH32: 1651 CopyMem (&Data32, (VOID *)(UINTN)(InstructionAddress), sizeof(UINT32)); 1652 EdbPrintRawIndexData32 (Data32); 1653 break; 1654 case MOVI_DATAWIDTH64: 1655 CopyMem (&Data64, (VOID *)(UINTN)(InstructionAddress), sizeof(UINT64)); 1656 EdbPrintRawIndexData64 (Data64); 1657 break; 1658 } 1659 1660 EdbPostInstructionString (); 1661 } 1662 1663 return Size; 1664 } 1665 1666 /** 1667 1668 Disasm instruction - MOVREL. 1669 1670 @param InstructionAddress - The instruction address 1671 @param SystemContext - EBC system context. 1672 @param DisasmString - The instruction string 1673 1674 @return Instruction length 1675 1676 **/ 1677 UINTN 1678 EdbDisasmMOVREL ( 1679 IN EFI_PHYSICAL_ADDRESS InstructionAddress, 1680 IN EFI_SYSTEM_CONTEXT SystemContext, 1681 OUT CHAR16 **DisasmString 1682 ) 1683 { 1684 UINT8 Modifiers; 1685 UINT8 Operands; 1686 UINTN Size; 1687 UINT16 Data16; 1688 UINT32 Data32; 1689 UINT64 Data64; 1690 UINTN Result; 1691 EFI_PHYSICAL_ADDRESS SavedInstructionAddress; 1692 1693 ASSERT (GET_OPCODE(InstructionAddress) == OPCODE_MOVREL); 1694 SavedInstructionAddress = InstructionAddress; 1695 1696 Modifiers = GET_MODIFIERS (InstructionAddress); 1697 Operands = GET_OPERANDS (InstructionAddress); 1698 1699 if ((Operands & MOVI_M_IMMDATA) != 0) { 1700 Size = 4; 1701 } else { 1702 Size = 2; 1703 } 1704 if ((Modifiers & MOVI_M_DATAWIDTH) == MOVI_DATAWIDTH16) { 1705 Size += 2; 1706 } else if ((Modifiers & MOVI_M_DATAWIDTH) == MOVI_DATAWIDTH32) { 1707 Size += 4; 1708 } else if ((Modifiers & MOVI_M_DATAWIDTH) == MOVI_DATAWIDTH64) { 1709 Size += 8; 1710 } else { 1711 return 0; 1712 } 1713 1714 // 1715 // Construct Disasm String 1716 // 1717 if (DisasmString != NULL) { 1718 *DisasmString = EdbPreInstructionString (); 1719 1720 EdbPrintInstructionName (L"MOVrel"); 1721 switch (Modifiers & MOVI_M_DATAWIDTH) { 1722 case MOVI_DATAWIDTH16: 1723 EdbPrintInstructionName (L"w"); 1724 break; 1725 case MOVI_DATAWIDTH32: 1726 EdbPrintInstructionName (L"d"); 1727 break; 1728 case MOVI_DATAWIDTH64: 1729 EdbPrintInstructionName (L"q"); 1730 break; 1731 } 1732 1733 EdbPrintRegister1 (Operands); 1734 1735 InstructionAddress += 2; 1736 if ((Operands & MOVI_M_IMMDATA) != 0) { 1737 CopyMem (&Data16, (VOID *)(UINTN)(InstructionAddress), sizeof(UINT16)); 1738 InstructionAddress += 2; 1739 EdbPrintRawIndexData16 (Data16); 1740 } 1741 1742 EdbPrintComma (); 1743 1744 switch (Modifiers & MOVI_M_DATAWIDTH) { 1745 case MOVI_DATAWIDTH16: 1746 CopyMem (&Data16, (VOID *)(UINTN)(InstructionAddress), sizeof(UINT16)); 1747 Result = EdbFindAndPrintSymbol ((UINTN)(SavedInstructionAddress + Size + (INT16)Data16)); 1748 if (Result == 0) { 1749 EdbPrintData16 (Data16); 1750 } 1751 break; 1752 case MOVI_DATAWIDTH32: 1753 CopyMem (&Data32, (VOID *)(UINTN)(InstructionAddress), sizeof(UINT32)); 1754 Result = EdbFindAndPrintSymbol ((UINTN)(SavedInstructionAddress + Size + (INT32)Data32)); 1755 if (Result == 0) { 1756 EdbPrintData32 (Data32); 1757 } 1758 break; 1759 case MOVI_DATAWIDTH64: 1760 CopyMem (&Data64, (VOID *)(UINTN)(InstructionAddress), sizeof(UINT64)); 1761 if (sizeof(UINTN) == sizeof(UINT64)) { 1762 Result = EdbFindAndPrintSymbol ((UINTN)(SavedInstructionAddress + Size + (INT64)Data64)); 1763 } else { 1764 Result = 0; 1765 } 1766 if (Result == 0) { 1767 EdbPrintData64 (Data64); 1768 } 1769 break; 1770 } 1771 1772 EdbPostInstructionString (); 1773 } 1774 1775 return Size; 1776 } 1777