2010-12-09 2 views
4

D2010에서 AsyncPro를 실행하려고합니다. Source Forge의 5.00 버전 사용.Delphi 2010의 ASyncPro 5.00 - 범위 검사 오류

아래의 MakeLong 라인에서 범위 검사 오류로 아래의 AsyncPro 코드 (OOMisc.pas)가 실패했습니다. 디버깅을 시작하는 방법에 대한 단서가 없습니다.

누구나 ASyncPro를 D2010에서 실행 중이거나 아래에서 어떤 일이 벌어 질지에 대한 통찰력이 있습니까? 소스 포지 (SourceForge)에 대한 저의 글은 응답이 없었습니다.

function SafeYield : LongInt; 
    {-Allow other processes a chance to run} 
var 
    Msg : TMsg; 
begin 
    SafeYield := 0; 
    if PeekMessage(Msg, 0, 0, 0, PM_REMOVE) then begin 
    if Msg.Message = wm_Quit then 
     {Re-post quit message so main message loop will terminate} 
     PostQuitMessage(Msg.WParam) 
    else begin 
     TranslateMessage(Msg); 
     DispatchMessage(Msg); 
    end; 
    {Return message so caller can act on message if necessary} 
    SafeYield := MAKELONG(Msg.Message, Msg.hwnd); // Range Check Error on this line! 
    end; 
end; 

TIA

답변

2

당신이 범위에 체크하여 코드를 컴파일 것으로 보인다 :

{$R+} 
function Test(A, B: LongWord): LongInt; 
begin 
    Result:= MakeLong(A,B); 
// Project .. raised exception class ERangeError with message 'Range check error'. 
end; 

당신은 런타임 오류를 제거하는 오프 확인 범위를 전환 할 수 있지만,

SafeYield := MAKELONG(Msg.Message, Msg.hwnd) 

의 결과가 잘못 인수 중 하나 (또는 ​​둘 다)가 2^16 - 1보다 큰 경우

코드가 32 비트 버전으로 변경되지 않고 16 비트 AsyncPro 버전에서 이식 된 것처럼 보이며 버그는 t 모든 32 비트 AsyncPro 버전을 포괄합니다.

1

MAKELONG 유형 말씀의 두 개의 매개 변수 (16 비트)를 취하고, Msg.Message 및 Msg.HWnd는 당신이 범위 검사 오류를 얻고있는 것은 놀라운 일이 아니다 모두 32 비트 얼마나로보고 . 일반적으로 윈도우 메시지는 < $ 8000이므로 그 값이 문제가 아닌지 의심 스럽습니다. 그러나 HWnd의 정수 값은 맵 전체에 걸쳐있을 수 있으며 확실하게> $ FFFF입니다. 이 때문에 위의 코드는 실제로 의미가 없지만 16 비트 버전에서 유물로 남은 것 같습니다.

범위 검사가 활성화되어 있으므로 위의 코드가 약간의 재검토가 필요하다는 사실을 분명히 강조하고 있습니다. Win32에서는 메시지 값과 창 핸들을 더 이상 32 비트에 맞출 수 없습니다.

진행 방법에 대한 몇 가지 힌트를 제공해 주셨으면합니다. 이 함수를 호출하는 코드를 고려하지 않고 대체 구현을 제안 할 수는 없습니다.

1

나는 Allen의 의견을 되풀이 하겠지만, 앞으로 나아갈 것이다. 코드가 어떻게 사용되고 있는지 (OoMisc에서도 DelayTicks를 참조하십시오) 호출자는 반환 값이 중요하지 않거나 메시지임을 가정합니다. 번호에 Msg.hwnd를 추가하는 것은 작동하지 않을뿐만 아니라 호출자가 기대하는 것이 아닙니다.

repeat 
    if Yield then 
    Res := SafeYield; 
until (**Res = wm_Quit**) or TimerExpired(ET); 

이 코드는 메시지 만 필요합니다.

I 라인을 변경할 것이다

SafeYield := MAKELONG(Msg.Message, Msg.hwnd); 

SafeYield := Msg.Message; 
0

(1) 그 코드는 메시지 펌프와

(2) (컨텍스트)가 보호되고 R- 컴파일러 지시자. AwDefine에서 범위 검사가 해제됩니다. {$ R- 범위 검사 없음}.INC

그래서 (1) 다른 메시지가 중지 코드가 발생하면,이 메시지를 통해 전환 될 때이 될 것이며,

(2) 범위 검사 오류가 여기에서 오지 않는 곳입니다.

이것은 비동기 프로세스가 범위 검사 예외 또는 모달 메시지를 유발하고 있음을 나타냅니다. 델파이 버전에서 범위 검사 오류 (및 목록 색인 메시지)는 소스/디버그 정보를 제공하지 않으므로 오류가 비동기 통신 이벤트에 연결될 수 있다고 제안 할 수 있습니다. focus/lost-focus/activate/paint 이벤트.