2009-12-02 3 views
3

C 프로그램이 실행 시간 (컴파일 시간 아님)에서 이 Little-Endian 또는 Big-Endian CPU에서 실행되는지 여부를 어떻게 결정합니까?MAC에서 C 프로그램의 RUN 시간에 CPU 유형을 확인하십시오

Intel-CPU가있는 MAC을 사용하여 MAC OSX의 Universal Binary 형식으로 프로그램을 작성하기 때문에 "실행 시간"확인이 아닌 "complie-time"이 필요한 이유가 있습니다. 이 프로그램은 Intel 및 Power-PC CPU 모두에서 실행됩니다. 즉, MAC의 Universal Binary 형식을 통해 Intel-CPU를 사용하는 프로그램을 만들고 PPC CPU에서 실행하고 싶습니다.

CPU 체크가 필요한 내 프로그램의 논리는 64 비트 정수의 호스트 - 네트워크 바이트 순서 변경 기능입니다. 바로 지금 나는 그것이 맹목적으로 인텔 - CPU에서 작동하지만, PPC에서 휴식 바이트 순서를 바꿀 수 있습니다. 다음은 C 함수입니다.

unsigned long long 
hton64b (const unsigned long long h64bits) { 
    // Low-order 32 bits in front, followed by high-order 32 bits. 
    return (
     (
     (unsigned long long) 
     (htonl((unsigned long) (h64bits & 0xFFFFFFFF))) 
     ) << 32 
    ) 
     | 
     (
     htonl((unsigned long) (((h64bits) >> 32) & 0xFFFFFFFF)) 
    ); 
}; // hton64b() 

크로스 플랫폼 방식으로이를 수행하는 더 좋은 방법은 무엇입니까?

감사

답변

1
  • 는 빅/리틀 엔디안의 어떠했는지를 테스트하기위한 가능한 전처리 매크로있을 것입니다. 예 :
 
    #ifdef LITTLE_ENDIAN 
    do it little endian way 
    #else 
    do it big endian way 
    #endif. 

이은 컴파일 시간이지만, 지방 바이너리에 대한 소스는 각 아키텍처에 대해, 이것은 문제가되지 않습니다 각각 따로 컴파일됩니다. 에서라도은 SYS에 betoh64() 함수가있는 경우

  • 임 확실하지/endian.h - 가없는 경우 - 그것은 옳은 일을 할 거라고 사용합니다.
  • 마지막 방법은 단순히 에서 호스트 엔디안 합리적인 아니다 방법을 개별 바이트의 풀기를하는 것입니다 - 당신은 단지 바이트가 소스에있는 순서를 알 필요가있다.

    uint64_t unpack64(uint8_t *src) 
    { 
        uint64_t val; 
    
        val = (uint64_t)src[0] << 56; 
        val |= (uint64_t)src[1] << 48; 
        val |= (uint64_t)src[2] << 40; 
        val |= (uint64_t)src[3] << 32; 
        val |= (uint64_t)src[4] << 24; 
        val |= (uint64_t)src[5] << 16; 
        val |= (uint64_t)src[6] << 8; 
        val |= (uint64_t)src[7]  ; 
    
        return val; 
    } 
    
0

당신은 맥에 유니버설 바이너리 한 번 각 아키텍처에 대해 여러 번 컴파일 된 것을 깨닫게합니까? 컴파일 시간에 대해 이야기 할 때 configure/make 시스템을 사용하여 소스에 알리는 방법을 말하는 것입니다. 그냥 gcc 상수 (예 : LITTLE_ENDIAN)를 사용하십시오.

2

검사하지 마십시오. 네트워크 독립적 인 값이 필요할 때마다 hton *을 사용하십시오. 좋은 설계를 위해서는 프로그램과 네트워크 독립적 인 정수가 필요한 모듈간에 인터페이스하는 모듈에만 국한되어야합니다.

이미 네트워크 주문중인 빅 엔디안 시스템에서 hton *은 아마도 매크로 일 뿐이므로 무료입니다. 리틀 엔디안 시스템에서는 어쨌든 그것을해야 할 필요가 있는지 확인하기 만하면됩니다.

이것이 충분하지 않은 경우 수행하려는 작업과 런타임시 시스템의 엔디안 니스를 알아야하는 이유에 대해 더 자세히 설명해야합니다.

0

당신은 런타임에 엔디안을 확인 할 필요가 없습니다.응용 프로그램을 유니버설 바이너리로 컴파일 할 때 인텔 시스템에서 빌드하는 경우 적절한 정의와 매크로를 사용하여 여러 번 컴파일됩니다. 런타임에 mach-o 로더는 유니버설 바이너리 (예 : PowerPC의 경우 ppc 또는 Intel의 경우 i386)에서 실행할 최적의 아키텍처를 선택합니다.

유니버설 바이너리는 다중 아키텍처에 대해 하나의 바이너리를 의미하지 않습니다. 하나의 아키텍처에 대해 하나의 바이너리를 포함하는 하나의 팻 바이너리를 의미합니다.

자세한 내용은 http://developer.apple.com/legacy/mac/library/documentation/MacOSX/Conceptual/universal_binary/universal_binary_intro/universal_binary_intro.html을 참조하십시오.

관련 문제