2013-01-09 1 views
15

저는 64 비트에 큰 델파이 코드베이스를 적용하려고합니다. 나는 그들을 교체 한 다음 캐스트 찾을 수 있습니다Delphi 64-bit : 잘못된 캐스트 찾기?

var 
    p1,p2 : pointer; 
begin 
    inc(Integer(p1),10); 
    p2 := Pointer(Integer(p1) + 42); 

64에서 해당 올바른 만드는 대신 nativeint로는-캐스트 : 대부분의 경우 포인터가 비슷한이 32 비트 값에서 /로 주조하는 선이있다 비트 모드.

그러나 나는 그들 모두를 발견했는지 확신 할 수 없습니다. 때로는 캐스트가 더 미묘하기 때문에 "integer ("는 충분하지 않습니다.) 문자열을 텍스트로 검색하는 것만으로도 충분하지 않습니다.

포인터 값이 정수 범위를 초과하면 "정수 ("캐스트가 64 비트에서 실패합니다. type 나는 메모리 관리자가 4GB 이상의 메모리를 할당하도록 강제 할 수 있다면 (포인터 값이 32 비트를 초과하여 사용하기 때문에) 런타임 오류가 발생하고 잘못된 캐스트를 더 쉽게 찾을 수 있습니다. 어떤 사람이 다른 기술을 추천 할 수 있습니까?

답변

21

사용중인 텍스트 검색 범위를 넘어서 이러한 캐스트를 찾는 데 필요한 마법의 마술은 없습니다. 컴파일러가 그러한 캐스트에 대해 경고한다면 정말 좋을 것입니다. 그것을 찾지 않으면 매우 실망 스럽습니다.

이러한 문제가 발견되면 NativeInt으로 변경하지 마십시오. 포인터를 입력 포인터로 변경하고 포인터 산술을 사용하십시오.

var 
    p1, p2: PByte; 
.... 
inc(p1, 10); 
p2 := p2; 
inc(p2, 42); 

그러면 코드가 영원 할 것입니다.

정수로 변환해야하는 경우가 있습니다. 예를 들어 주소를 SendMessage으로 전달할 때 그러나 적절한 경우 WPARAM 또는 LPARAM 중 하나로 전송하십시오.

런타임 오류를 강요하는 아이디어는 건전하고 고맙게도 원래는 아닙니다. FastMM 정식 버전을 사용하고 AlwaysAllocateTopDown을 정의해야합니다. 그러면 FastMM이 VirtualAlloc의 호출을 MEM_TOP_DOWN 플래그로 전달합니다. 이렇게하면 잘못된 캐스팅 대부분을 런타임 포인터 잘림 오류로 없앨 수 있습니다.

그러나 이는 메모리 관리자가 할당 한 메모리에 대해 하향식 할당 만 강제로 수행합니다. 프로세스의 다른 모듈은 bottom up의 기본 policy를 사용합니다. 기본 정책을 변경하기 위해 시스템 전체 설정을 설정할 수 있습니다. 값이 0x100000HKLM\System\CurrentControlSet\Control\Session Manager\Memory Management\AllocationPreference에서 REG_DWORD으로 설정하고 재부팅하십시오.

이 경우 컴퓨터에 안정성 문제가 발생할 수 있습니다. 많은 응용 프로그램이 이에 대처할 수 없습니다. 특히이 설정에 대처할 수있는 안티 바이러스 제품이 거의 없습니다. MSE는 컴퓨터 전반에 걸친 톱 다운 할당과 함께 작동하는 것으로 나타났습니다. 64 비트 디버거가 top down 할당 하에서 실행되지 않는 이유는 무엇입니까! 따라서 디버거없이 이러한 유형의 테스트를 수행해야합니다. 내 QC report이 아직 열려 있으며이 문제는 XE3에서도 해결되지 않았습니다.

+2

감사합니다. MEM_TOP_DOWN 플래그는 매우 흥미 롭습니다. 내가 일하고있는 프로젝트는 사용자 정의 디버그 할당자를 가지고 있으므로 지금은 플래그를 사용하도록 수정했다. 매우 느리지 만 이미 전환 버그를 찾고 있습니다. –