2013-08-17 1 views
2

필자가 쓰는 일부 C 코드에 이상한 문제가 발생했습니다. 다음 코드를 고려하십시오 POSIX.1-2008, 헤더 파일 <에서 sys/stat.h에 따르면sys/stat.h가 -std = c1x 인 ino_t를 정의하지 않는 이유는 무엇입니까?

#include <sys/stat.h> 
ino_t inode; 

>는 ino_t1 정의

< SYS /stat.h > 헤더는 blkcnt_t, blksize_t, 0123을 정의해야합니다. 179,, ino_t, mode_t, nlink_t, uid_t, gid_t, off_ttime_t 유형 <SYS/types.h>에 기재된.

내 리눅스 시스템의 파일에 TEST.C을 장소 위의 소스 코드를 컴파일 할 때이 문제가 발생 :

내가 어떤을 지정할 때 ino_t의 정의 revelead하지 왜
 
$ cat test.c 
#include <sys/stat.h> 
ino_t inode; 
$ uname -srm 
Linux 3.8.0-26-generic x86_64 
$ lsb_release -d 
Description: Ubuntu 13.04 
$ gcc -c test.c 
$ gcc -std=c90 test.c 
test.c:2:1: error: unknown type name 'ino_t' 
$ gcc -std=c99 test.c  
test.c:2:1: error: unknown type name 'ino_t' 
$ gcc -std=c1x test.c 
test.c:2:1: error: unknown type name 'ino_t' 

-std 옵션은 무엇입니까?

답변

3

내 설명서 페이지 fstat에는 sys/types.h도 포함되어 있으며이 문제는 저를 위해 문제를 해결합니다. sys/stat.h에있는 ino_t의 정의는 기능 매크로 __USE_XOPEN__USE_XOPEN2K으로 보호됩니다. sys/types.h의 정의는 그렇게 보호되지 않습니다.

설명서 페이지에는 unistd.h이 포함되어 있다고되어 있지만 문제를 해결할 필요는 없습니다. feature_test_macros의 설명서에 따라 페이지

:

__STRICT_ANSI__ ISO 표준 C.이 매크로

내재적 gcc에서 정의 된 (1) 예를 들어, 호출되면, 또는 -std=c99 -ansi 플래그.

나는 모든 XOPEN 기능도 꺼져 있음을 의미합니다. 그러나 나는 그것에 대한 설명을 찾을 수 없습니다.

P. R .. (아래 참조)은 feature_test_macros의 매뉴얼 페이지에도 설명되어 있지만 필자의 제한된 두뇌는 정확한 문구를 찾을 수 없다고 느낀다. 따라서 독자의 연습 문제로 남겨두고 싶다. 어디서나 설명이 가능하다면 실제로 매뉴얼 페이지에서 기대할 수 있습니다.

는 다음과 같이 대답의 요지임을주의 :

너는 모든이 매뉴얼 페이지에 언급 된 파일을 포함하고 사람이 필요하지 않을 수도 리버스 엔지니어링을 시도하지 포함되어야한다.

+1

아하. 방금 200809L에 _POSIX_C_SOURCE를 정의하는 것 또한 트릭을 수행한다는 것을 알았습니다. – fuz

+0

'man feature_test_macros' –

+0

@R .. 아직 찾을 수 없기 때문에 힌트가 더 필요합니다. –

0

-std=cXX 대신 -std=gnuXX을 사용한 경우 프로그램이 불만없이 컴파일되었을 것입니다.

$ cc -std=c11 -fsyntax-only test.c ; echo $? 
test.c:2:1: error: unknown type name ‘ino_t’; did you mean ‘__ino_t’? 
1 

하지만

$ cc -std=gnu11 -fsyntax-only test.c ; echo $? 
0 

많은 사람들이 제대로 -std=cXX 옵션의 효과를 이해하지 않습니다. 그들은 이 아니며은 그 자체로 GCC에게 엄격하게 부합 (예 : GNU 확장의 모든 사용 진단)을 지시합니다. 엄격한 준수를 원할 경우 -Wall -Wpedantic 옵션을 제공해야합니다. 응용 프로그램의 네임 스페이스에

  1. System-specific predefined macros

    -std=cXX 모드에서 사용할 수 없습니다 :

    -std=cXX 모드와 해당 -std=gnuXX 모드 사이에 세 개의 차이가 있습니다

    , 그 중 두 사람은 당신이 원하는 것을 일반적으로하지 않습니다. 이것은 좋은 것입니다; application-namespace 미리 정의 된 매크로는 기껏해야 confusing이고, 최악의 경우 합법적 인 코드를 벗어납니다. 그러나 여전히 매크로를 찾는 시스템 헤더 파일을 손상시키는 것으로 알려져 있습니다.

  2. Trigraphs-std=cXX 모드에서 활성화되고 -std=gnuXX 모드에서는 비활성화됩니다. 당신은 삼부작을 원하지 않습니다. 그들은 발명되었을 때 이미 쓸데없는 것이었고, IMNSHO는 아주 오래전에 C 표준에서 삭제되어야했습니다.

  3. -std=cXX 모드에서 GNU libc는 헤더에 표시되는 지정된 C 표준을 초과하는 확장의 수를 최소화하려고 시도합니다. (주의 : GCC와 함께 사용할 수있는 많은 다른 C 라이브러리는 이 아니며이 아닙니다.) C 표준의 일부가 아닌 sys/stat.h과 같은 헤더의 경우에는 " 우리가 지원하는이 헤더의 가장 오래된 버전에 존재한다. "이것은 POSIX.1-1993과 같이 매우 오래되고 제한적인 것이 많다. 이것은 당신을 망쳤다. feature test macros을 정의하여 GNU libc가 최신 POSIX 등의 기능을 제공하도록함으로써이 문제를 해결할 수 있습니다.

처음부터 새로운 C 프로그램을 작성하는 경우, 당신이 -Wall-Wpedantic (및 기타 -W switches의 아마 무리)를 사용하는 것이 좋습니다하지만 난 하지유일한로, -std=cXX의 사용을 권장 할 긍정적 인 효과는 시스템 특정 사전 설정을 해제하는 것이며 시스템 헤더를 손상시킬 수 있습니다. _GNU_SOURCE 또는 이와 동등한 번호로 _POSIX_C_SOURCE 또는 _XOPEN_SOURCE 설정을 찾으려는 시도가 번거롭고 번거롭지도 않습니다. 특히, 번들로 제공하는 타사 코드 또는 사용되지 않는 대체 코드를 사용할 수 있습니다. 하지만 여전히 평범한 기능들, 예를 들어 gettimeofday).

관련 문제