Changeset 2836 for trunk/src/win32k/dev32/d32init.c
- Timestamp:
- Feb 21, 2000, 5:45:47 AM (26 years ago)
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/src/win32k/dev32/d32init.c
r2832 r2836 1 /* $Id: d32init.c,v 1.1 2 2000-02-20 04:27:23bird Exp $1 /* $Id: d32init.c,v 1.13 2000-02-21 04:45:46 bird Exp $ 2 2 * 3 3 * d32init.c - 32-bits init routines. … … 12 12 * Defined Constants * 13 13 *******************************************************************************/ 14 #define MAXSIZE_PROLOG 0x1 0/* Note that this must be synced with */14 #define MAXSIZE_PROLOG 0x18 /* Note that this must be synced with */ 15 15 /* the one used in calltab.asm. */ 16 16 #define static /* just to make all symbols visible in the kernel debugger. */ … … 32 32 #include "dev1632.h" 33 33 #include "dev32.h" 34 #include "dev32hlp.h" 34 35 #include "probkrnl.h" 35 36 #include "log.h" … … 38 39 #include "ldr.h" 39 40 #include "ldrCalls.h" 40 41 #include "macros.h" 42 43 /******************************************************************************* 44 * Global Variables * 45 *******************************************************************************/ 46 #ifdef DEBUG 47 static char * apszPE[] = {"FLAGS_PE_NOT", "FLAGS_PE_PE2LX", "FLAGS_PE_PE", "FLAGS_PE_MIXED", "!invalid!"}; 48 static char * apszInfoLevel[] = {"INFOLEVEL_QUIET", "INFOLEVEL_ERROR", "INFOLEVEL_WARNING", "INFOLEVEL_INFO", "INFOLEVEL_INFOALL", "!invalid!"}; 49 #endif 41 50 42 51 /******************************************************************************* 43 52 * Internal Functions * 44 53 *******************************************************************************/ 45 static ULONG readnum(const char *pszNum); 46 static signed char interpretFunctionProlog32(char *pach, BOOL fOverload); 47 static signed char interpretFunctionProlog16(char *pach, BOOL fOverload); 48 static int ImportTabInit(void); 54 static ULONG readnum(const char *pszNum); 55 _Inline int ModR_M_32bit(char bModRM); 56 static int interpretFunctionProlog32(char *pach, BOOL fOverload); 57 static int interpretFunctionProlog16(char *pach, BOOL fOverload); 58 static int ImportTabInit(void); 49 59 50 60 … … 59 69 /* extern(s) located in mytkExecPgm.asm */ 60 70 extern char mytkExecPgm; 61 71 extern char CODE32START; 72 extern char CODE32END; 73 extern char CONST32_ROEND; 74 extern char DATA16START; 75 extern char DATA16_CONSTEND; 62 76 63 77 … … 81 95 char *pszTmp; 82 96 ULONG ul; 97 APIRET rc; 98 LOCKHANDLE lhData16={0,0,0,0, 0,0,0,0, 0,0,0,0}; 99 LOCKHANDLE lhData = {0,0,0,0, 0,0,0,0, 0,0,0,0}; 100 LOCKHANDLE lhCode = {0,0,0,0, 0,0,0,0, 0,0,0,0}; 83 101 84 102 pulTKSSBase32 = (PULONG)_TKSSBase16; … … 258 276 259 277 /* log option summary - FIXME */ 260 kprintf(("Options - Summary\n")); 278 kprintf(("Options - Summary - Start\n")); 279 if (options.fQuiet) 280 kprintf(("\tQuiet init\n")); 281 else 282 kprintf(("\tVerbose init\n")); 283 284 if (options.fLogging) 285 kprintf(("\tlogging enabled\n")); 286 else 287 kprintf(("\tlogging disabled\n")); 288 kprintf(("\tCom port no.%d\n", options.usCom)); 289 261 290 kprintf(("\tKernel: ver%d.%d build %d type %s\n", 262 291 options.usVerMajor, … … 265 294 (options.fKernel & KF_SMP) ? "SMP" : "UNI" 266 295 )); 267 kprintf(("\tCom port no.%d\n", options.usCom)); 268 if (options.fQuiet) 269 kprintf(("\tQuiet init\n")); 270 else 271 kprintf(("\tVerbose init\n")); 272 if (options.fLogging) 273 kprintf(("\tlogging enabled\n")); 274 else 275 kprintf(("\tlogging disabled\n")); 296 kprintf(("\tfPE=%d (%s)\n", options.fPE, apszPE[MIN(options.fPE, 5)])); 297 kprintf(("\tulInfoLevel=%d (%s)\n", options.ulInfoLevel, apszInfoLevel[MIN(options.ulInfoLevel, 5)])); 298 kprintf(("\tfElf=%d\n", options.fElf)); 299 kprintf(("\tfScript=%d\n", options.fScript)); 300 kprintf(("\tfNoLoader=%d\n", options.fNoLoader)); 301 kprintf(("\tcbSwpHeapInit=0x%08x cbSwpHeapMax=0x%08x\n", 302 options.cbSwpHeapInit, options.cbSwpHeapMax)); 303 kprintf(("\tcbResHeapInit=0x%08x cbResHeapMax=0x%08x\n", 304 options.cbSwpHeapInit, options.cbSwpHeapMax)); 305 kprintf(("Options - Summary - End\n")); 276 306 /* end option summary */ 277 307 … … 294 324 if (ImportTabInit() != NO_ERROR) 295 325 return STATUS_DONE | STERR | ERROR_I24_QUIET_INIT_FAIL; 326 327 /* 328 * Lock the 32-bit objects/segments and 16-bit datasegment in memory 329 */ 330 /* 32-bit code segment */ 331 rc = D32Hlp_VMLock2(&CODE32START, 332 ((unsigned)&CODE32END & ~0xFFF) - (unsigned)&CODE32START, /* Round down so we don't overlap with the next request. */ 333 VMDHL_LONG, 334 SSToDS(&lhCode)); 335 if (rc != NO_ERROR) 336 kprintf(("code segment lock failed with with rc=%d\n", rc)); 337 338 /* 32-bit data segment */ 339 rc = D32Hlp_VMLock2(callTab, 340 &CONST32_ROEND - (char*)callTab, 341 VMDHL_LONG | VMDHL_WRITE, 342 SSToDS(&lhData)); 343 if (rc != NO_ERROR) 344 kprintf(("data segment lock failed with with rc=%d\n", rc)); 345 346 /* 16-bit data segment */ 347 rc = D32Hlp_VMLock2(&DATA16START, 348 &DATA16_CONSTEND - &DATA16START, 349 VMDHL_LONG | VMDHL_WRITE, 350 SSToDS(&lhData16)); 351 if (rc != NO_ERROR) 352 kprintf(("data segment lock failed with with rc=%d\n", rc)); 296 353 297 354 return STATUS_DONE; … … 395 452 396 453 454 455 /** 456 * Functions which cacluates the instructionsize given a ModR/M byte. 457 * @returns Number of bytes to add to cb and pach. 458 * @param bModRM ModR/M byte. 459 * @status completely implemented. 460 * @author knut st. osmundsen (knut.stange.osmundsen@pmsc.no) 461 */ 462 _Inline int ModR_M_32bit(char bModRM) 463 { 464 if ((bModRM & 0xc0) == 0x80 /* ex. mov ax,[ebp+11145543h] */ 465 || ((bModRM & 0xc0) == 0 && (bModRM & 0x07) == 5)) /* ex. mov ebp,[0ff231234h] */ 466 { /* 32-bit displacement */ 467 return 5; 468 } 469 else if ((bModRM & 0xc0) == 0x40) /* ex. mov ecx,[esi]+4fh */ 470 { /* 8-bit displacement */ 471 return 2; 472 } 473 /* no displacement (only /r byte) */ 474 return 1; 475 } 476 477 478 479 480 397 481 /** 398 482 * 32-bit! Interpret function prolog to find where to jmp back. … … 404 488 * FALSE: Function is to be imported. 405 489 */ 406 static signed charinterpretFunctionProlog32(char *pach, BOOL fOverload)490 static int interpretFunctionProlog32(char *pach, BOOL fOverload) 407 491 { 408 int cb; 492 int cb = -3; 493 494 kprintf(("interpretFunctionProlog32(0x%08x, %d):\n" 495 "\t%02x %02x %02x %02x - %02x %02x %02x %02x\n" 496 "\t%02x %02x %02x %02x - %02x %02x %02x %02x\n", 497 pach, fOverload, 498 pach[0], pach[1], pach[2], pach[3], pach[4], pach[5], pach[6], pach[7], 499 pach[8], pach[9], pach[10],pach[11],pach[12],pach[13],pach[14],pach[15])); 409 500 410 501 /* … … 416 507 * push ebp 417 508 * mov ecx, dword ptr [xxxxxxxx] 509 * 510 * These are allowed when not overloading: 511 * mov eax, imm32 512 * jmp short 513 * or 514 * mov eax, imm32 515 * push ebp 418 516 */ 419 420 if (pach[0] == 0x55 && pach[1] == 0x8b) 517 if ((pach[0] == 0x55 && (pach[1] == 0x8b || pach[1] == 0xa1)) /* two first prologs */ 518 || 519 (pach[0] == 0xB8 && (pach[5] == 0xEB || pach[5] == 0x55) && !fOverload) /* two last prologs */ 520 ) 421 521 { 422 if (pach[2] == 0xec) 423 cb = 3; 424 else 425 cb = 1; 426 while (cb < 5) 427 { 428 /* 429 * This is not at all very stable or correct - but it works 430 * for the current functions. 431 * There will never be any doubt when something goes wrong! 432 */ 433 switch(pach[cb]) 522 BOOL fForce; 523 cb = 0; 524 while (cb < 5 || fForce) /* 5 is the size of a jump instruction. */ 525 { 526 int cb2; 527 fForce = FALSE; 528 switch (*pach) 434 529 { 435 case 0x33: /* xor (ldrClose, ldrOpen) */ 436 cb +=2; 437 break; 438 case 0x8b: 439 if (pach[cb+1] == 0x0d) 440 cb += 6; 530 /* simple one byte prefixes */ 531 case 0x2e: /* cs segment override */ 532 case 0x36: /* ss segment override */ 533 case 0x3e: /* ds segment override */ 534 case 0x26: /* es segment override */ 535 case 0x64: /* fs segment override */ 536 case 0x65: /* gs segment override */ 537 fForce = TRUE; 538 break; 539 540 /* simple one byte instructions */ 541 case 0x50: /* push ax */ 542 case 0x51: /* push cx */ 543 case 0x52: /* push dx */ 544 case 0x53: /* push bx */ 545 case 0x54: /* push sp */ 546 case 0x55: /* push bp */ 547 case 0x56: /* push si */ 548 case 0x57: /* push di */ 549 break; 550 551 /* simple two byte instructions */ 552 case 0xb0: /* mov al, imm8 */ 553 case 0xb1: /* mov cl, imm8 */ 554 case 0xb2: /* mov dl, imm8 */ 555 case 0xb3: /* mov bl, imm8 */ 556 case 0xb4: /* mov ah, imm8 */ 557 case 0xb5: /* mov ch, imm8 */ 558 case 0xb6: /* mov dh, imm8 */ 559 case 0xb7: /* mov bh, imm8 */ 560 case 0x2c: /* sub al, imm8 */ 561 case 0x34: /* xor al, imm8 */ 562 case 0x3c: /* cmp al, imm8 */ 563 case 0x6a: /* push <byte> */ 564 pach++; 565 cb++; 566 break; 567 568 /* simple five byte instructions */ 569 case 0xb8: /* mov eax, imm32 */ 570 case 0xb9: /* mov ecx, imm32 */ 571 case 0xba: /* mov edx, imm32 */ 572 case 0xbb: /* mov ebx, imm32 */ 573 case 0xbc: /* mov esx, imm32 */ 574 case 0xbd: /* mov ebx, imm32 */ 575 case 0xbe: /* mov esi, imm32 */ 576 case 0xbf: /* mov edi, imm32 */ 577 case 0x2d: /* sub eax, imm32 */ 578 case 0x35: /* xor eax, imm32 */ 579 case 0x3d: /* cmp eax, imm32 */ 580 case 0x68: /* push <dword> */ 581 pach += 4; 582 cb += 4; 583 break; 584 585 /* complex sized instructions - "/r" */ 586 case 0x30: /* xor r/m8, r8 */ 587 case 0x31: /* xor r/m32, r32 */ 588 case 0x32: /* xor r8, r/m8 */ 589 case 0x33: /* xor r32, r/m32 */ 590 case 0x38: /* cmp r/m8, r8 */ 591 case 0x39: /* cmp r/m32, r32 */ 592 case 0x3a: /* cmp r8, r/m8 */ 593 case 0x3b: /* cmp r32, r/m32 */ 594 case 0x28: /* sub r/m8, r8 */ 595 case 0x29: /* sub r/m32, r32 */ 596 case 0x2a: /* sub r8, r/m8 */ 597 case 0x2b: /* sub r32, r/m32 */ 598 case 0x8b: /* mov /r */ 599 case 0x8d: /* lea /r */ 600 if ((pach[1] & 0x7) == 4 && (pach[1] & 0xc0) != 0xc0) /* invalid instruction!?! */ 601 return -1; 602 cb += cb2 = ModR_M_32bit(pach[1]); 603 pach += cb2; 604 break; 605 606 /* complex sized instruction - "/5 ib" */ 607 case 0x80: /* 5: sub r/m8, imm8 7: cmp r/m8, imm8 */ 608 case 0x83: /* 5: sub r/m32, imm8 7: cmp r/m32, imm8 */ 609 if ((pach[1] & 0x38) == (5<<3) 610 || (pach[1] & 0x38) == (7<<3) 611 ) 612 { 613 cb += cb2 = 1 + ModR_M_32bit(pach[1]); /* 1 is the size of the imm8 */ 614 pach += cb2; 615 } 441 616 else 442 cb += 2; /*????!*/ 443 break; 444 case 0x8d: /* lea (ldrRead) */ 445 cb += 3; 446 break; 447 case 0x83: /* sub (LDRQAppType) */ 448 cb += 3; 449 break; 617 { 618 kprintf(("interpretFunctionProlog32: unknown instruction (-3) 0x%x 0x%x 0x%x\n", pach[0], pach[1], pach[2])); 619 return -3; 620 } 621 break; 622 623 /* complex sized instruction - "/digit id" */ 624 case 0x81: /* sub r/m32, imm32 + more instructions! */ 625 if ((pach[1] & 0x38) == (5<<3) /* sub r/m32, imm32 */ 626 || (pach[1] & 0x38) == (7<<3) /* cmp r/m32, imm32 */ 627 ) 628 { 629 cb += cb2 = 4 + ModR_M_32bit(pach[1]); /* 4 is the size of the imm32 */ 630 pach += cb2; 631 } 632 else 633 { 634 kprintf(("interpretFunctionProlog32: unknown instruction (-2) 0x%x 0x%x 0x%x\n", pach[0], pach[1], pach[2])); 635 return -2; 636 } 637 break; 638 450 639 default: 451 kprintf(("interpretFunctionProlog : unknown instruction 0x%x\n", pach[cb]));640 kprintf(("interpretFunctionProlog32: unknown instruction 0x%x 0x%x 0x%x\n", pach[0], pach[1], pach[2])); 452 641 return 0; 453 642 } 454 } 455 } 456 else if (pach[0] == 0x55 && pach[1] == 0xa1) /* ldrEnum32bitRelRecs on WS4eB */ 457 { 458 cb = 1 + 5; 643 pach++; 644 cb++; 645 } 459 646 } 460 647 else 461 648 { 462 /* special case for IOSftReadAt and IOSftWriteAt */ 463 if (fOverload == FALSE && pach[0] == 0xB8 && (pach[5] == 0xEB || pach[5] == 0x55)) 464 cb = 5; 465 else 466 cb = 0; 649 kprintf(("interpretFunctionProlog32: unknown prolog start. 0x%x 0x%x 0x%x\n", pach[0], pach[1], pach[2])); 650 cb = 0; 467 651 } 468 469 return (signed char)cb; 652 return cb; 470 653 } 471 654 … … 480 663 * FALSE: Function is to be imported. 481 664 */ 482 static signed charinterpretFunctionProlog16(char *pach, BOOL fOverload)665 static int interpretFunctionProlog16(char *pach, BOOL fOverload) 483 666 { 484 int cb; 485 667 int cb = -7; 668 669 kprintf(("interpretFunctionProlog16(0x%08x, %d):\n" 670 "\t%02x %02x %02x %02x - %02x %02x %02x %02x\n" 671 "\t%02x %02x %02x %02x - %02x %02x %02x %02x\n", 672 pach, fOverload, 673 pach[0], pach[1], pach[2], pach[3], pach[4], pach[5], pach[6], pach[7], 674 pach[8], pach[9], pach[10],pach[11],pach[12],pach[13],pach[14],pach[15])); 486 675 /* 487 676 * Check for the well known prolog (the only that is supported now) … … 493 682 BOOL fForce; 494 683 cb = 0; 495 while (cb < 8 || fForce) 684 while (cb < 8 || fForce) /* 8 is the size of a 66h prefixed far jump instruction. */ 496 685 { 497 686 fForce = FALSE; … … 528 717 529 718 case 0x8b: /* mov /r */ 530 if ((pach[1] & 0xc0) == 10 /* ex. mov ax,bp+1114h */531 || ((pach[1] & 0xc0) == 0 && (pach[1] & 0x c0) == 6)) /* ex. mov bp,0ff23h */719 if ((pach[1] & 0xc0) == 0x80 /* ex. mov ax,bp+1114h */ 720 || ((pach[1] & 0xc0) == 0 && (pach[1] & 0x7) == 6)) /* ex. mov bp,0ff23h */ 532 721 { /* 16-bit displacement */ 533 722 pach += 3; … … 548 737 549 738 default: 550 kprintf(("interpretFunctionProlog : unknown instruction 0x%x 0x%x 0x%x\n", pach[0], pach[1], pach[2]));739 kprintf(("interpretFunctionProlog16: unknown instruction 0x%x 0x%x 0x%x\n", pach[0], pach[1], pach[2])); 551 740 return 0; 552 741 } … … 557 746 558 747 fOverload = fOverload; 559 return (signed char)cb;748 return cb; 560 749 } 750 561 751 562 752 … … 601 791 * Verify known function prolog. 602 792 */ 603 if ( _aImportTab[i].fType & EPT_32BIT)793 if (EPT32BitEntry(_aImportTab[i])) 604 794 { 605 795 cb = interpretFunctionProlog32((char*)_aImportTab[i].ulAddress, _aImportTab[i].fType == EPT_PROC32); 606 cbmin = 5; 796 cbmin = 5; /* Size of the jump instruction */ 607 797 } 608 798 else 609 799 { 610 800 cb = interpretFunctionProlog16((char*)_aImportTab[i].ulAddress, _aImportTab[i].fType == EPT_PROC16); 611 cbmin = 8;801 cbmin = 7; /* Size of the far jump instruction */ 612 802 } 613 803 … … 628 818 default: 629 819 kprintf(("VerifyImportTab32: only EPT_PROC is implemented\n",i)); 820 Int3(); /* temporary fix! */ 630 821 return STATUS_DONE | STERR | 4; 631 822 } … … 665 856 int i; 666 857 int cb; 667 858 int cbmin; 668 859 669 860 /* … … 676 867 continue; 677 868 678 if (_aImportTab[i].fType & EPT_32BIT) 869 if (EPT32BitEntry(_aImportTab[i])) 870 { 679 871 cb = interpretFunctionProlog32((char*)_aImportTab[i].ulAddress, _aImportTab[i].fType == EPT_PROC32); 872 cbmin = 5; /* Size of the jump instruction */ 873 } 680 874 else 875 { 681 876 cb = interpretFunctionProlog16((char*)_aImportTab[i].ulAddress, _aImportTab[i].fType == EPT_PROC16); 682 if (cb <= 0 || cb + 5 >= MAXSIZE_PROLOG) 683 { 684 kprintf(("ImportTabInit: verify failed for procedure no.%d, cb=%d\n", i, cb)); 877 cbmin = 7; /* Size of the far jump instruction */ 878 } 879 if (cb <= 0 || cb + cbmin >= MAXSIZE_PROLOG) 880 { 881 kprintf(("ImportTabInit: Verify failed for procedure no.%d, cb=%d\n", i, cb)); 685 882 return 1; 686 883 } … … 702 899 case EPT_PROC32: 703 900 { 704 cb = _aImportTab[i].cbProlog = interpretFunctionProlog32((char*)_aImportTab[i].ulAddress, TRUE); 705 if (cb > 0 && cb + 5 < MAXSIZE_PROLOG) 706 { 901 cb = interpretFunctionProlog32((char*)_aImportTab[i].ulAddress, TRUE); 902 _aImportTab[i].cbProlog = (char)cb; 903 if (cb >= 5 && cb + 5 < MAXSIZE_PROLOG) /* 5(1st): size of jump instruction in the function prolog which jumps to my overloading function */ 904 { /* 5(2nd): size of jump instruction which jumps back to the original function after executing the prolog copied to the callTab entry for this function. */ 707 905 /* 708 906 * Copy function prolog which will be overwritten by the jmp to calltabl. … … 743 941 Int3(); 744 942 745 cb = _aImportTab[i].cbProlog = interpretFunctionProlog16((char*)_aImportTab[i].ulAddress, TRUE); 746 if (cb > 0 && cb + 8 < MAXSIZE_PROLOG) /* a 16:32 jump must be prefixed with 66h in a 16-bit segment */ 747 { 943 cb = interpretFunctionProlog16((char*)_aImportTab[i].ulAddress, TRUE); 944 _aImportTab[i].cbProlog = (char)cb; 945 if (cb >= 8 && cb + 7 < MAXSIZE_PROLOG) /* 8: size of a 16:32 jump which jumps to my overloading function (prefixed with 66h in a 16-bit segment) */ 946 { /* 7: size of a 16:32 jump which is added to the call tab */ 748 947 /* 749 948 * Copy function prolog which is to be overwritten. … … 784 983 case EPT_PROCIMPORT32: 785 984 { 786 cb = _aImportTab[i].cbProlog = interpretFunctionProlog32((char*)_aImportTab[i].ulAddress, FALSE); 787 if (cb > 0 && cb + 5 < MAXSIZE_PROLOG) 985 cb = interpretFunctionProlog32((char*)_aImportTab[i].ulAddress, FALSE); 986 _aImportTab[i].cbProlog = (char)cb; 987 if (cb > 0) /* Since no prolog part is copied to the function table, it's ok as long as the prolog has been recognzied. */ 788 988 { 789 989 /* … … 811 1011 case EPT_PROCIMPORT16: 812 1012 { 813 cb = _aImportTab[i].cbProlog = interpretFunctionProlog16((char*)_aImportTab[i].ulAddress, FALSE); 814 if (cb > 0 && cb + 8 < MAXSIZE_PROLOG) 1013 cb = interpretFunctionProlog16((char*)_aImportTab[i].ulAddress, FALSE); 1014 _aImportTab[i].cbProlog = (char)cb; 1015 if (cb > 0) /* Since no prolog part is copied to the function table, it's ok as long as the prolog has been recognzied. */ 815 1016 { 816 1017 /* … … 842 1043 case EPT_VARIMPORT32: 843 1044 case EPT_VARIMPORT16: 1045 _aImportTab[i].cbProlog = (char)0; 844 1046 *(unsigned long*)(void*)&callTab[i][0] = _aImportTab[i].ulAddress; 845 1047 *(unsigned long*)(void*)&callTab[i][4] = _aImportTab[i].offObject;
Note:
See TracChangeset
for help on using the changeset viewer.