2010-05-07 1 views
0

나는 7충돌 사용 WscRegisterForChanges

문서가 여기에 Windows에서 C++ 기능을 가진 WscRegisterForChanges를 사용하려고 해요 :

http://msdn.microsoft.com/en-us/library/bb432507(v=VS.85).aspx 내 문제가

콜백이 제대로 실행하는 경우에도 콜백의 실행이 끝나면 코드가 충돌합니다.

다음은 문제의 코드입니다. 그것은 매우 간단합니다, 그래서 나는 그것이 충돌 왜 확실하지 않다 :

 
#include 
#include 
#include 

void SecurityCenterChangeOccurred(void *param) { 
printf("Change occurred!\n"); 
} 

int main() { 
HRESULT result = S_OK; 
HANDLE callbackRegistration = NULL; 

result = WscRegisterForChanges(
    NULL, 
    &callbackRegistration, 
    (LPTHREAD_START_ROUTINE)SecurityCenterChangeOccurred, 
    NULL); 

while(1) { 
    Sleep(100); 
} 

return 0; 
} 

충돌이 발생할 때 내 호출 스택은 다음과 같습니다

 
> 00faf6e8() 
    [email protected]() + 0x1293 bytes 
    [email protected]@12() + 0x12 bytes 
    [email protected]() + 0x27 bytes 
    [email protected]() + 0x1b bytes 

내가으로 ExitThread를 추가하는 경우 (0); SecurityCenterChangeOccurred의 끝에, 나는 (그래서 내가으로 ExitThread를 사용한다고 생각하지 않습니다) 오류 다음과 같은 추적을 얻을 :

 
Unhandled exception at 0x7799852b (ntdll.dll) in WscRegisterForChangesCrash.exe: 0xC000071C: An invalid thread, handle %p, is specified for this operation. Possibly, a threadpool worker thread was specified. 

    [email protected]() + 0x3ca2f bytes 
    [email protected]() + 0x30 bytes 
> WscRegisterForChangesCrash.exe!SecurityCenterChangeOccurred(void * param=0x00000000) Line 8 + 0xa bytes C++ 
    wscapi.dll!WorkItemWrapper() + 0x19 bytes 
    [email protected]() + 0xdf bytes 
    [email protected]() + 0x1293 bytes 
    [email protected]@12() + 0x12 bytes 
    [email protected]() + 0x27 bytes 
    [email protected]() + 0x1b bytes 

사람이 이런 일이 될 수있는 이유는 어떤 아이디어가 있습니까?

크래시를 실행하려면 프로그램을 실행하고 방화벽을 켜거나 끄십시오.

답변

0

콜백에 WINAPI를 추가하는 것처럼 보입니다.

새로운 호출은 다음과 같습니다이 필요한 이유

 
void WINAPI SecurityCenterChangeOccurred(void *param) { 
    printf("Change occurred!\n"); 
} 

은 누군가가 말해 줄래?

1

이것은 호출 규칙 때문입니다. WinApi32 함수의 정의 | 콜백은 매크로 WINAPI 또는 CALLBACK 앞에 있어야합니다. 기본적으로 호출 규칙에 대한 컴파일러에게 매개 변수 순서를 스택에 푸시해야하며, 반환 값을 작성해야하며 호출자에게 복귀 한 후에 스택 복원을 호출해야합니다.

호출자와 수신자 간의 CC 정의 관계