On Sun, 2007-08-05 at 21:12 +0200, Peter Dons Tychsen wrote: > On Sat, 2007-08-04 at 12:04 +0900, Dmitry Timoshkov wrote: > > "Peter Dons Tychsen" <[EMAIL PROTECTED]> wrote: > > > > > 1) Yes i did testing on Windows-XP. I did it by putting together various > > > examples and by checking with InSendMessage() for all cases. This > > > clearly showed that WM_ACTIVATEAPP was always posted and never sent. > > > > Looks like you misunderstood the InSendMessage behaviour and that led to > > some confusion. > > > > Wine test harness for message sequences works just fine, there is no need > > to blame it. > > > > I have found a new way of proving that ACTIVATEAPP must be sent using > the PostMessage call and not the SendMessage call. I have also found a > way to extend the unit test system to cover this. > > After realizing my bummer with InSendMessage() i set out to create a new > function that would do what i want: Check if a message was sent with > PostMessage() or SendMessage() on windows. I could not find any function > that would do this so i made my own hack (below): > > This piece of code, if inserted into the test system, could (on original > Windows) show us which messages we are incorrectly posting or sending. I > can probably also be used for other test purposes. I works by checking > the call stack for the calls SendMessageA() and SendMessageW(). Works > like charm on Windows-XP. Will need some work to also work inside Wine, > but that is not important for now. > > Usage: > > 1) Call call_stack_check_init(). > 2) Call called_from_send_message() inside the Proc handler. > > Cheers, > > /Pedro > > ------ CODE BEGIN -------- > > void call_stack_check_init(void) > { > HANDLE process = GetCurrentProcess(); > SymSetOptions(SYMOPT_UNDNAME | SYMOPT_DEFERRED_LOADS); > SymInitialize(process, NULL, TRUE); > } > > #define SYM_MAX_NAME_SIZE 1000 > BOOL call_stack_check_search(char *func) > { > STACKFRAME64 call_stack; > CONTEXT context; > HANDLE thread = GetCurrentThread(); > SYMBOL_INFO *sym = (SYMBOL_INFO *) malloc(sizeof(SYMBOL_INFO) + > SYM_MAX_NAME_SIZE); > CHAR name[SYM_MAX_NAME_SIZE]; > HANDLE process = GetCurrentProcess(); > > /* Setup symbol buffer */ > ZeroMemory(sym, sizeof(SYMBOL_INFO) + SYM_MAX_NAME_SIZE); > sym->SizeOfStruct = sizeof(SYMBOL_INFO); > sym->MaxNameLen = SYM_MAX_NAME_SIZE; > > /* Get thread context */ > ZeroMemory(&context, sizeof(context)); > context.ContextFlags = CONTEXT_FULL; > __asm call x; > __asm x: pop eax; > __asm mov context.Eip, eax; > __asm mov context.Ebp, ebp; > __asm mov context.Esp, esp; > > /* Setup stack walk offset */ > ZeroMemory(&call_stack, sizeof(call_stack)); > call_stack.AddrPC.Offset = context.Eip; > call_stack.AddrStack.Offset = context.Esp; > call_stack.AddrFrame.Offset = context.Ebp; > call_stack.AddrPC.Mode = AddrModeFlat; > call_stack.AddrStack.Mode = AddrModeFlat; > call_stack.AddrFrame.Mode = AddrModeFlat; > > while(1) > { > DWORD64 disp = 0; > > /* Walk that rusty old stack... */ > if(!StackWalk64( > IMAGE_FILE_MACHINE_I386, > process, > thread, > &call_stack, > NULL, > NULL, > SymFunctionTableAccess64, > SymGetModuleBase64, > NULL)) return FALSE; > > /* Get the next symbol on stack */ > if(SymFromAddr(GetCurrentProcess(), call_stack.AddrPC.Offset, &disp, > sym)) > { > /* Make it readable */ > UnDecorateSymbolName(sym->Name, name, SYM_MAX_NAME_SIZE, > UNDNAME_COMPLETE | > UNDNAME_NO_THISTYPE | > UNDNAME_NO_SPECIAL_SYMS | > UNDNAME_NO_MEMBER_TYPE | > UNDNAME_NO_MS_KEYWORDS | > UNDNAME_NO_ACCESS_SPECIFIERS); > > /* Check for match */ > if(!strcmp(func, name)) return TRUE; > } > } > > return FALSE; > } > BOOL called_from_send_message(void) > { > if (call_stack_check_search("SendMessageW")) return TRUE; > if (call_stack_check_search("SendMessageA")) return TRUE; > > return FALSE; > } > > ----- CODE END -----
By the way, this code does prove (if run on Windows-XP), that ACTIVATEAPP should be posted and not sent. /pedro