본문 바로가기

PL/C & C++

[C/C++] ifdef

extern "C", __cplusplus의 의미를 알게 되었다.

기본적으로, 오버로딩은 name mangling을 이용한 기법이다.

그러나, 이것이 c, c++ 코드가 함께 있다면, 이 때문에 빌드 시 에러가 발생할 것이다.

c코드의 경우, 명시적으로 컴파일러에게 c방식으로 컴파일하라고 알려주어야 한다.

c, c++ 소스가 산재해 있다면, c소스에는 __cplusplus 매크로와, extern "C"를 사용해서 name mangling을 피해가야 할 것이다.


extern "C"는 cpp 소스가 c 소스를 include 했을 때 맹글링 방지를 위한 도구였다. 그런데 코드는 그래도 있고, 만약에 c소스에서 c소스를 불러온다면 어떻게 될까? 컴파일 에러가 난다. 왜냐하면 extern "C"는 cpp에서만 정의되는 식별자이다. 따라서 c, cpp에 대해서 모두 불러와지기 위해서는 컴파일러를 검사한 후 cpp이라면 extern 처리를 해주는 것이다

 

extern "C" 의미는 안에 정의된 함수 혹은 헤더파일에 관해서는 맹글링하지 말라는 의미다. 

 

맹글링은 C++에서 사용되는 용어로, C++ 컴파일러 단계에서 함수 혹은 변수이름을 기존과 크게 다르게 바꾸는 행위를 말한다. C++은 C와 다르게 클래스 속성을 이용해서 매개변수를 달리해서 함수 이름을 동일하게 사용할 수 있게 된다. 즉 다형성을 지원하기에 가능한 일이다. 따라서 C++ 컴파일러에서의 맹글링 작업은 불가분의 관계에 있다.

 

extern "C"는 cpp 소스파일에서 c 소스를 가져다 쓸 때 필요하다.

cpp 소스는 다형성을 지원하지만 c 소스는 함수의 유일성이 보장된다. 따라서 맹글링 작업을 거칠 필요가 없다. 하지만 extern "C"를 사용한다면 c는 함수 이름자체가 심볼이 되지만 맹글링을 거치기 때문에 컴파일러가 위치를 찾지 못하고 에러를 발생시킨다


#ifdef __cplusplus
이건 말 그대로 __cplusplus라는것이 define되어있으면 extern "C"{를 삽입하라는 뜻입니다.

이런 코드를 쓰는 이유는 C와 C++간의 링커 재사용을 위해서 입니다.

처음 C++을 설계할때 컴파일러만 새로 설계하고 링커는 기존 라이브러리를 재사용 하려고

기존의 C링커를 그대로 사용하였습니다. 하지만 C++에서는 함수 다중선언 등과 같은 기능을

지원 하기위해 각 함수명을 인자에 따라 컴파일러가 다르게 부여합니다(Name Mangling).

당연히 C에 있던 함수들도 다른 이름이 주어지게 되고 그럴경우 라이브러리와 링크가 안되겠지요.

extern "C"라는 건 Name Mangling을 하지 않도록 하는것입니다. 그래야 C라이브러리를

링크 가능할테니까요.

컴파일러가 C++로 동작할 경우 __cplusplus 를 define한다고 보시면 될듯합니다.


: #ifdef __cplusplus
: extern "C" {
: #endif

: #ifdef __cplusplus
: }
: #endif

 


_WIN32 범용 윈도우 시스템을 나타내므로 플랫폼에 상관없이 항상 정의된다.
WIN32 _WIN32 같은 매크로인데 이것은 전처리기 기본 설정으로 정의된다.
, _WIN32, WIN32 언제나 정의된다고   있다. 만일 이것이 정의되지 않았다면
그것은 윈도우 시스템이 아닌 다른 OS(리눅스 ) 위한 것이라고   있다.

'PL > C & C++' 카테고리의 다른 글

[C] 변수형 출력  (0) 2020.07.21
[C] 배열 초기화  (0) 2020.07.20
[C] union, struct  (0) 2020.07.20
[C] C언어 전처리기  (0) 2020.07.09
[C++] 입력 받기  (0) 2020.07.08