32 비트 응용 프로그램을 c에서 64 비트 응용 프로그램으로 변환합니다

StackOverflow https://stackoverflow.com/questions/411798

  •  03-07-2019
  •  | 
  •  

문제

현재 32bits 응용 프로그램을 C의 64bits 응용 프로그램으로 변환하려고 노력하고 있습니다.이 응용 프로그램은 현재 X86 아키텍처 (Windows, OSX, UNIX, Linux)에서 작업하고 있습니다. 따라서 코딩을 시작하기 전에 응용 프로그램을 변환하는 동안 무엇을 고려해야하는지 알고 싶었습니다.

도움이 되었습니까?

해결책

  1. 누가 그것을 썼는지 알아보십시오. 그들은 바보입니까? 그것들입니다 몇 년 전부터? 그들에게 질문을 할 수 있습니까? 그들은 여러 플랫폼과 시스템의 존재에 익숙합니까? 앎 프로그램의 저자의 사고 방식 문제가 발생할 때 문제를 이해하는 데 도움이됩니다.
  2. 64 비트 기계/빌드 환경을 구입하고 실행하십시오.
  3. int로 Long을 교체하십시오. 그것을 완벽하게 알고 있습니다 LONG 아니다 long.
  4. 바꾸다 (int)&x 캐스트와 타이핑 intptr_t 그리고 (unsigned int)&x ~와 함께 uintptr_t
  5. 주조 구조에 의존하는 모든 것을 감사합니다 char* 포인터 산술을 수행합니다.
  6. <4 >에 대한 Regex 검색이 가정 한 경우 4 = sizeof(void*)
  7. 인내하십시오. 문제가 발생하면 같은 문제가있는 경우 다른 곳을보고 솔루션을 매크로로 감싸십시오.
  8. 사용하지 마십시오 #ifdef RUN64 또는 비슷한 것. 128 비트 플랫폼이 유행에 빠지면 후회할 것입니다.
  9. 프로그램의 다른 곳에서 이식성 차이를 숨길 수있는 일부 중앙 매크로 측면에서 모든 변경 사항을 캡슐화하십시오.
  10. 커버리지 테스터를 사용하여 모든 것을 다루는지 확인하십시오 (적절한 경우)

편집하다 추가 uintptr_t 주석에 의해 제안 된대로 참고.

다른 팁

아직 언급되지 않은 잠재적 인 문제 중 하나는 앱이 디스크에서 이진 데이터를 읽거나 쓰면 fread), 당신은 매우 신중하게 확인하고 아마도 두 명의 독자가있는 것입니다. 하나는 레거시 파일과 64 비트 파일 용입니다. 또는 다음과 같은 유형을 사용하도록주의를 기울이면 uint32_t 그래서 <stdint.h> 헤더 파일, structs를 비트 포트 호환으로 재정의 할 수 있습니다. 어쨌든 이진 I/O 조심해야 할 일입니다.

이것은 실제로 응용 프로그램과 그것이 코딩 된 방법에 따라 다릅니다. 일부 코드는 64 비트 컴파일러로 다시 컴파일 될 수 있으며 만 작동하지만 일반적으로 코드가 휴대 성을 염두에두고 설계된 경우에만 발생합니다.

코드에 기본 유형 및 포인터의 크기에 대해 많은 가정이있는 경우, 비트 포장 해킹이 많거나 바이트 지정 프로토콜을 사용하여 외부 프로세스와 대화하지만 기본 유형의 크기에 대한 일부 가정을 사용하는 경우. 깨끗한 컴파일을 얻으려면 일부 또는 많은 작업이 필요할 수 있습니다.

거의 모든 캐스트 및 컴파일러 경고는 체크 아웃이 필요한 적기입니다. 코드가 "경고 청소"로 시작하지 않으면 많은 작업이 필요할 수 있다는 신호이기도합니다.

값에 대한 올바른 유형을 사용한 경우 (예 : size_t, ptrdiff_t, uintptr_t, 고정 된 크기의 int 유형 stdint.h 적절한 경우 - 하드 코드 값 크기가 아닌 경우 코드는 상자에서 작동해야합니다.

64 비트로 전환 할 때 직면하는 주요 문제는 포인터의 크기가 32 -duh 대신 64 비트가 다르다는 것입니다. 정수의 크기와 길이 크기는 플랫폼에 따라 다를 수 있다는 것입니다.

이것이 왜 문제입니까? 코드가 그 크기 (int) == sizeof (void*)를 가정하지 않는 한 것은 아닙니다. 이것은 불쾌한 포인터 버그로 이어질 수 있습니다.

글쎄, 기본적으로, 변경 수는 상당히 작지만 응용 프로그램이 조심스럽게 작성되지 않도록 신중하게 작성되지 않으면 여전히 주요 작업이 될 것입니다.

주요 차이점은 포인터가 비트 너비가 64이고 하지만 대부분의 다른 데이터 유형은 변하지 않습니다. int는 여전히 32 비트이며 길고 길은 아마도 여전히 32 비트 일 것입니다. 따라서 코드가 INT와 포인터 사이에 캐스트되면 깨질 것입니다. 마찬가지로, 다른 구성원에 대한 특정 오프셋에 의존하는 모든 구조 또는 유사한 구조물은 다른 멤버가 더 커질 수 있으므로 오프셋을 변경할 수 있으므로 파손될 수 있습니다.

물론, 코드는 처음에는 이러한 트릭에 의존해서는 안됩니다. 따라서 이상적인 세상에서는 전혀 문제가되지 않을 것이며 단순히 다시 컴파일하고 모든 것이 작동 할 수 있습니다. 그러나 당신은 아마 이상적인 세상에 살지 않을 것입니다 ...;)

C에서 32 비트와 64 비트 프로그래밍의 두 가지 주요 차이점은 크기 (void*)와 크기 (Long)입니다. 당신이 가질 주요 문제는 가장 유니 닉스 시스템이 64 비트로 긴 I32LP64 표준을 사용하는 것입니다. 크로스 플랫폼 컴파일을 지원 해야하는 경우 32 비트 및 64 비트 정수의 아키텍처 기반 TypEdef 세트를 사용하여 모든 코드가 일관되게 작동하도록 할 수 있습니다. 이것은 C99 표준의 일부로 stdint.h의 일부로 제공됩니다. C99 컴파일러를 사용하지 않는 경우 자신의 동등한 것을 굴려야 할 수도 있습니다.

다른 곳에서 언급 한 바와 같이 변환에 대한 주요 관심사는 크기 (int) == sizeof (long) == sizeof (void*)를 가정하는 코드, 디스크에 작성된 데이터 및 크로스 플랫폼 IPC에 대한 코드를 지원하는 코드입니다.

이 뒤에있는 역사를 잘 검토하려면 이것을 살펴보십시오. 기사 ACM 대기열에서.

이미 좋은 답변이 많이 있습니다.

사용을 고려하십시오 김벨 보풀. 문제가되는 구성 유형을 정확히 지적 할 수 있습니다. 당신의 경험이 내 것과 같다면, 그것은 또한 당신에게 32/64 비트 포트와 관련이없는 시스템에서 많은 버그를 보여줄 것입니다.

개발자를위한 약 64 비트 :

기사에 관한 기사 64 비트 개발

링크 수집 64 비트 리소스

도구 viva64

라이센스 : CC-BY-SA ~와 함께 속성
제휴하지 않습니다 StackOverflow
scroll top