As usual, AutoCAD seems to be a good test-bench for wine :-) I spotted the problem that seemed coming from VirtualQuety function, but that is (I guess... hmmmm) more a problem of memory handling in wine.
I made a little test app; here the results in wine and win2k, later on the app itself : WINE RESULTS : Memory info about '004012F0' : Base Address : 00401000 Allocation Base : 00400000 Allocation Protect : PAGE_READONLY | PAGE_WRITECOPY | PAGE_EXECUTE_READWRITE | PAGE_NOACCESS Region Size : 00017000 State : MEM_COMMIT Protect : PAGE_WRITECOPY <----- HERE Type : MEM_PRIVATE WIN2k RESULTS : Memory info about '004012F0' : Base Address : 00401000 Allocation Base : 00400000 Allocation Protect : PAGE_EXECUTE_WRITECOPY Region Size : 00001000 State : MEM_COMMIT Protect : PAGE_EXECUTE_READ <---- AND HERE Type : MEM_IMAGE Well, dunno too much about Type field, I didn't find an app that check it yet; I did find the app that uses Protect flag; I think it's poor coded, but as usual we should make bad apps work too :-) The app put some data in code page, not yet spotted if hard or soft-coded, then before reading it checks Protect field to see if it has not set the PAGE_GUARD, NO_ACCESS and WRITECOPY flags; if t has, it hangs some 10.000 lines later (sigh....) I think wine should set Protect flag quite as like as possible as windoze For AutoCAD2000 I put a dirty hack in process.c, but is really ugly; i'd prefer not to put my hands (bytes ?) too deeply inside some code that I don't understand completely... Attached is the test source (compiled in Borland CBuilder, but should work with any compiler, apart some unuseful pragma's). If needed I can post the compiled too :-) Regards Max
//--------------------------------------------------------------------------- #pragma hdrstop //--------------------------------------------------------------------------- #include <stdio.h> #include <windows.h> // CONVERTS Protect FLAG TO STRING char *Protect2String(DWORD ap) { static char AB[1000] ; AB[0] = 0 ; if(ap & PAGE_GUARD) strcat(AB, "PAGE_GUARD | ") ; if(ap & PAGE_NOCACHE) strcat(AB, "PAGE_NOCACHE | ") ; if(ap & PAGE_READONLY) strcat(AB, "PAGE_READONLY | ") ; if(ap & PAGE_READWRITE) strcat(AB, "PAGE_READWRITE | ") ; if(ap & PAGE_WRITECOPY) strcat(AB, "PAGE_WRITECOPY | ") ; if(ap & PAGE_EXECUTE) strcat(AB, "PAGE_EXECUTE | ") ; if(ap & PAGE_EXECUTE_READ) strcat(AB, "PAGE_EXECUTE_READ | ") ; if(ap & PAGE_EXECUTE_READWRITE) strcat(AB, "PAGE_EXECUTE_READWRITE | ") ; if(ap & PAGE_EXECUTE_WRITECOPY) strcat(AB, "PAGE_EXECUTE_WRITECOPY | ") ; if(ap & PAGE_NOACCESS) strcat(AB, "PAGE_NOACCESS | ") ; if(strlen(AB) >= 2) AB[strlen(AB) - 2] = 0 ; return AB ; } // END Protect2String() // CONVERTS State FLAG TO STRING char *State2String(DWORD s) { static char S[30] ; S[0] = 0 ; switch(s) { case MEM_COMMIT : sprintf(S, "MEM_COMMIT") ; break ; case MEM_FREE : sprintf(S, "MEM_FREE") ; break ; case MEM_RESERVE : sprintf(S, "MEM_RESERVE") ; break ; default : sprintf(S, "<oops... state flag error>") ; break ; } ; // case return S ; } // END State2String() // CONVERTS Type FLAG TO STRING char *Type2String(DWORD t) { static char T[30] ; T[0] = 0 ; switch(t) { case MEM_IMAGE : sprintf(T, "MEM_IMAGE") ; break ; case MEM_MAPPED : sprintf(T, "MEM_MAPPED") ; break ; case MEM_PRIVATE : sprintf(T, "MEM_PRIVATE") ; break ; default : sprintf(T, "<oops... Type error>") ; break ; } ; // case return T ; } // END Type2String() #pragma argsused int main(int argc, char* argv[]) { // THIS PROGRAM SHOWS DIFFERENT // BEHAVIOUR OF VirtualQuery() // ON WINDOWS 2000 AND WINE // NOT (YET) TESTED ON win95 MEMORY_BASIC_INFORMATION buf ; size_t bufsiz = sizeof(buf) ; DWORD result ; // QUERIES INFO ABOUT MEMORY PAGE // OF Type2String FUNCTION result = VirtualQuery(&Type2String, &buf, bufsiz) ; if(result == bufsiz) { // PRINTS OUT RESULTS fprintf(stdout, "\nMemory info about '%p' :\n", &Type2String) ; fprintf(stdout, " Base Address : %p\n", buf.BaseAddress) ; fprintf(stdout, " Allocation Base : %p\n", buf.AllocationBase) ; fprintf(stdout, " Allocation Protect : %s\n", Protect2String(buf.AllocationProtect)) ; fprintf(stdout, " Region Size : %p\n", buf.RegionSize) ; fprintf(stdout, " State : %s\n", State2String(buf.State)) ; fprintf(stdout, " Protect : %s\n", Protect2String(buf.Protect)) ; fprintf(stdout, " Type : %s\n", Type2String(buf.Type)) ; } else { fprintf(stderr, "\nVirtualQuery Error\n") ; } return 0; } //---------------------------------------------------------------------------