Changeset 550 for trunk/src/kernel32/winimage.cpp
- Timestamp:
- Aug 18, 1999, 7:18:01 PM (26 years ago)
- File:
-
- 1 edited
Legend:
- Unmodified
- Added
- Removed
-
trunk/src/kernel32/winimage.cpp
r544 r550 1 /* $Id: winimage.cpp,v 1.1 0 1999-08-18 12:24:16sandervl Exp $ */1 /* $Id: winimage.cpp,v 1.11 1999-08-18 17:18:01 sandervl Exp $ */ 2 2 3 3 /* … … 6 6 * Copyright 1998-1999 Sander van Leeuwen (sandervl@xs4all.nl) 7 7 * Copyright 1998 Knut St. Osmundsen 8 *9 8 * 10 9 * Project Odin Software License can be found in LICENSE.TXT … … 35 34 #include "unicode.h" 36 35 #include "winres.h" 36 #include "os2util.h" 37 37 38 38 char szErrorTitle[] = "Win32 for OS/2"; … … 58 58 Win32Image::Win32Image(char *szFileName) : 59 59 errorState(NO_ERROR), entryPoint(0), nrsections(0), imageSize(0), 60 imageVirtBase(-1), baseAddress(0),realBaseAddress(0), imageVirtEnd(0),60 imageVirtBase(-1), realBaseAddress(0), imageVirtEnd(0), 61 61 nrNameExports(0), nrOrdExports(0), nameexports(NULL), ordexports(NULL), 62 62 szFileName(NULL), NameTable(NULL), Win32Table(NULL), fullpath(NULL), … … 73 73 foutInit = TRUE; 74 74 } 75 hinstance = (HINSTANCE)this;76 75 this->szFileName = szFileName; 76 77 strcpy(szModule, StripPath(szFileName)); 78 strupr(szModule); 79 char *dot = strstr(szModule, "."); 80 while(dot) { 81 char *newdot = strstr(dot+1, "."); 82 if(newdot == NULL) break; 83 dot = newdot; 84 } 85 if(dot) 86 *dot = 0; 87 77 88 #ifdef DEBUG 78 89 magic = MAGIC_WINIMAGE; … … 83 94 Win32Image::Win32Image(HINSTANCE hinstance, int NameTableId, int Win32TableId) : 84 95 errorState(NO_ERROR), entryPoint(0), nrsections(0), imageSize(0), 85 imageVirtBase(-1), baseAddress(0),realBaseAddress(0), imageVirtEnd(0),96 imageVirtBase(-1), realBaseAddress(0), imageVirtEnd(0), 86 97 nrNameExports(0), nrOrdExports(0), nameexports(NULL), ordexports(NULL), 87 98 szFileName(NULL), NameTable(NULL), Win32Table(NULL), fullpath(NULL), … … 93 104 #endif 94 105 OS2ImageInit(hinstance, NameTableId, Win32TableId); 106 107 char *name = OS2GetDllName(hinstance); 108 strcpy(szModule, name); 109 strupr(szModule); 110 char *dot = strstr(szModule, "."); 111 while(dot) { 112 char *newdot = strstr(dot+1, "."); 113 if(newdot == NULL) break; 114 dot = newdot; 115 } 116 if(dot) 117 *dot = 0; 95 118 } 96 119 //****************************************************************************** … … 378 401 } 379 402 fout << "*************************PE SECTIONS END **************************" << endl; 380 imageSize += (imageVirtBase - oh.ImageBase);403 imageSize += imageVirtBase - oh.ImageBase; 381 404 fout << "Total size of Image " << imageSize << endl; 382 405 fout << "imageVirtBase " << imageVirtBase << endl; 383 406 fout << "imageVirtEnd " << imageVirtEnd << endl; 384 407 408 //In case there are any gaps between sections, adjust size 385 409 if(imageSize != imageVirtEnd - oh.ImageBase) { 386 410 fout << "imageSize != imageVirtEnd - oh.ImageBase!" << endl; … … 391 415 return(FALSE); 392 416 } 393 fout << "OS/2 base address " << baseAddress << endl;394 if(storeSections( ) == FALSE) {417 fout << "OS/2 base address " << realBaseAddress << endl; 418 if(storeSections((char *)win32file) == FALSE) { 395 419 fout << "Failed to store sections, rc " << errorState << endl; 396 420 return(FALSE); 397 421 } 398 entryPoint = baseAddress + oh.AddressOfEntryPoint;422 entryPoint = realBaseAddress + oh.AddressOfEntryPoint; 399 423 400 424 if(tlsDir != NULL) { … … 447 471 pResDir = (PIMAGE_RESOURCE_DIRECTORY)ImageDirectoryOffset(win32file, IMAGE_DIRECTORY_ENTRY_RESOURCE); 448 472 } 473 474 //SvL: Use pointer to image header as module handle now. Some apps needs this 475 hinstance = (HINSTANCE)realBaseAddress; 476 449 477 //set final memory protection flags (storeSections sets them to read/write) 450 478 if(setMemFlags() == FALSE) { … … 474 502 virtsize = ((virtsize - 1) & ~0xFFF) + PAGE_SIZE; 475 503 imageSize += virtsize; 476 section[nrsections].virtualsize 504 section[nrsections].virtualsize = virtsize; 477 505 478 506 if(virtaddress < imageVirtBase) 479 507 imageVirtBase = virtaddress; 480 508 if(virtaddress + virtsize > imageVirtEnd) 481 imageVirtEnd = virtaddress + virtsize;509 imageVirtEnd = virtaddress + virtsize; 482 510 483 511 nrsections++; … … 488 516 { 489 517 APIRET rc; 518 ULONG baseAddress; 490 519 491 520 if(fh.Characteristics & IMAGE_FILE_RELOCS_STRIPPED) { … … 525 554 //****************************************************************************** 526 555 #define FALLOC_SIZE (1024*1024) 556 //NOTE: Needs testing (while loop) 557 //TODO: Free unused (parts of) reservedMem 527 558 //****************************************************************************** 528 559 BOOL Win32Image::allocFixedMem(ULONG reservedMem) 529 560 { 530 561 ULONG address = 0; 531 ULONG lastaddress = 0;532 ULONG firstaddress= 0;533 ULONG diff, i ;562 ULONG *memallocs; 563 ULONG alloccnt = 0; 564 ULONG diff, i, baseAddress; 534 565 APIRET rc; 535 566 536 baseAddress =realBaseAddress = 0;567 realBaseAddress = 0; 537 568 538 569 if(reservedMem && reservedMem <= oh.ImageBase && … … 541 572 //ok, it fits perfectly 542 573 realBaseAddress = oh.ImageBase; 543 baseAddress = oh.ImageBase;544 574 return TRUE; 575 } 576 577 //Reserve enough space to store 4096 pointers to 1MB memory chunks 578 memallocs = (ULONG *)malloc(4096*sizeof(ULONG *)); 579 if(memallocs == NULL) { 580 fout << "allocFixedMem: MALLOC FAILED for memallocs" << endl; 581 return FALSE; 545 582 } 546 583 … … 548 585 rc = DosAllocMem((PPVOID)&address, FALLOC_SIZE, PAG_READ); 549 586 if(rc) break; 550 551 if(firstaddress == 0)552 firstaddress = address;553 587 554 588 fout << "DosAllocMem returned " << address << endl; … … 556 590 if(address > oh.ImageBase) {//we've passed it! 557 591 DosFreeMem((PVOID)address); 558 return(FALSE);592 break; 559 593 } 560 594 //found the right address 561 595 DosFreeMem((PVOID)address); 562 //align at 64 kb boundary 563 realBaseAddress = oh.ImageBase & 0xFFFF0000; 564 diff = realBaseAddress - address; 596 597 diff = address - oh.ImageBase; 565 598 if(diff) { 566 599 rc = DosAllocMem((PPVOID)&address, diff, PAG_READ); … … 570 603 if(rc) break; 571 604 572 if(baseAddress != realBaseAddress) {573 fout << "baseAddress != realBaseAddress!!" << endl;574 break;575 }576 605 if(diff) DosFreeMem((PVOID)address); 577 606 578 address = realBaseAddress;579 607 realBaseAddress = baseAddress; 580 baseAddress = oh.ImageBase;581 608 break; 582 609 } 583 lastaddress = address; 584 } 585 while(firstaddress <= lastaddress) { 586 DosFreeMem((PVOID)firstaddress); 587 firstaddress += FALLOC_SIZE; 588 } 589 if(baseAddress == 0) //Let me guess.. MS Office app? 610 memallocs[alloccnt++] = address; 611 } 612 for(i=0;i<alloccnt;i++) { 613 DosFreeMem((PVOID)memallocs[i]); 614 } 615 free(memallocs); 616 617 if(realBaseAddress == 0) //Let me guess.. MS Office app? 590 618 return(FALSE); 591 619 … … 594 622 //****************************************************************************** 595 623 //****************************************************************************** 596 BOOL Win32Image::storeSections( )624 BOOL Win32Image::storeSections(char *win32file) 597 625 { 598 626 int i; 599 627 APIRET rc; 600 628 ULONG pagFlags = PAG_COMMIT; 601 629 ULONG headersize; 630 WINIMAGE_LOOKUP *imgLookup; 631 632 //Commit memory for image header 633 headersize = sizeof(IMAGE_DOS_HEADER) + sizeof(IMAGE_NT_HEADERS) + 634 sizeof(IMAGE_SECTION_HEADER) * fh.NumberOfSections; 635 636 if(headersize + sizeof(WINIMAGE_LOOKUP) < PAGE_SIZE) { 637 headersize = PAGE_SIZE; 638 } 639 else {//ooops, just in case this doesn't work 640 fout << "ERROR: storeSections: header too big!!!!!! Fatal error" << endl; 641 return FALSE; 642 } 643 644 rc = DosSetMem((PVOID)realBaseAddress, headersize, pagFlags | PAG_WRITE | PAG_READ); 645 if(rc) { 646 fout << "DosSetMem failed for Image header! " << rc << endl; 647 return FALSE; 648 } 649 // Store the NT header at the load addr 650 memcpy((char *)realBaseAddress, win32file, sizeof(IMAGE_DOS_HEADER)); 651 memcpy((char *)PE_HEADER(realBaseAddress), PE_HEADER(win32file), sizeof(IMAGE_NT_HEADERS)); 652 memcpy(PE_SECTIONS(realBaseAddress), PE_SECTIONS(win32file), 653 sizeof(IMAGE_SECTION_HEADER) * fh.NumberOfSections ); 654 655 imgLookup = WINIMAGE_LOOKUPADDR(realBaseAddress); 656 imgLookup->image = this; 657 imgLookup->magic = MAGIC_WINIMAGE; 658 659 // Process all the image sections 602 660 for(i=0;i<nrsections;i++) { 603 section[i].realvirtaddr = baseAddress + (section[i].virtaddr - oh.ImageBase);661 section[i].realvirtaddr = realBaseAddress + (section[i].virtaddr - oh.ImageBase); 604 662 } 605 663 for(i=0;i<nrsections;i++) { … … 735 793 ULONG *fixup; 736 794 737 fixup = (ULONG *)(fixupaddr - oh.ImageBase + baseAddress);795 fixup = (ULONG *)(fixupaddr - oh.ImageBase + realBaseAddress); 738 796 orgaddr = *fixup; 739 *fixup = baseAddress + (*fixup - oh.ImageBase);797 *fixup = realBaseAddress + (*fixup - oh.ImageBase); 740 798 } 741 799 //****************************************************************************** … … 746 804 USHORT *fixup; 747 805 748 fixup = (USHORT *)(fixupaddr - oh.ImageBase + baseAddress);806 fixup = (USHORT *)(fixupaddr - oh.ImageBase + realBaseAddress); 749 807 orgaddr = *fixup; 750 808 if(fHighFixup) { 751 *fixup += (USHORT)(( baseAddress - oh.ImageBase) >> 16);809 *fixup += (USHORT)((realBaseAddress - oh.ImageBase) >> 16); 752 810 } 753 811 else { 754 *fixup += (USHORT)(( baseAddress - oh.ImageBase) & 0xFFFF);812 *fixup += (USHORT)((realBaseAddress - oh.ImageBase) & 0xFFFF); 755 813 } 756 814 } … … 762 820 ULONG apiaddr; 763 821 764 import = (ULONG *)(impaddr - oh.ImageBase + baseAddress);822 import = (ULONG *)(impaddr - oh.ImageBase + realBaseAddress); 765 823 apiaddr = WinDll->getApi(ordinal); 766 824 if(apiaddr == 0) { … … 777 835 ULONG apiaddr; 778 836 779 import = (ULONG *)(impaddr - oh.ImageBase + baseAddress);837 import = (ULONG *)(impaddr - oh.ImageBase + realBaseAddress); 780 838 apiaddr = WinDll->getApi(impname); 781 839 if(apiaddr == 0) { … … 893 951 free(tmp); 894 952 } 895 curnameexport->virtaddr = baseAddress + (virtaddr - oh.ImageBase);953 curnameexport->virtaddr = realBaseAddress + (virtaddr - oh.ImageBase); 896 954 curnameexport->ordinal = ordinal; 897 955 *(ULONG *)curnameexport->name = 0; … … 912 970 curordexport = ordexports; 913 971 } 914 curordexport->virtaddr = baseAddress + (virtaddr - oh.ImageBase);972 curordexport->virtaddr = realBaseAddress + (virtaddr - oh.ImageBase); 915 973 curordexport->ordinal = ordinal; 916 974 curordexport++; … … 1241 1299 return(0); 1242 1300 } 1243 / /******************************************************************************1244 / /******************************************************************************1301 /******************************************************************************/ 1302 /******************************************************************************/ 1245 1303 /*heximal(decimal) KSO Sun 24.05.1998*/ 1246 1304 char szHexBuffer[30];
Note:
See TracChangeset
for help on using the changeset viewer.