2014-06-24 4 views
3

동적 라이브러리에 이미 존재하는 함수의 Wy 재정의가 컴파일 및 링크 오류를 발생시키지 않습니까? 아래의 기능을 아래와 같이 이미 존재하는 평균 함수의 공유 라이브러리 정의 내부동적 또는 정적 라이브러리에 이미있는 함수를 재정의해도 오류가 발생하지 않는 이유는 무엇입니까?

#include "calc_mean.h" 
#include <stdio.h> 

int mean(int t, int v) { 
    return 0; 
} 

int main() { 
    int theMean = mean(3,6); 
    printf("\n %d\n",theMean); 
} 

에서

.

#include <stdio.h> 
#include "calc_mean.h" 

int mean(int a, int b) { 
    return (a+b)/2; 
} 

평균 함수의 정의는 이미 공유 라이브러리 libmean.so 존재한다. 그러나 컴파일하는 동안 나는 재정의 오류를 보지 못하고 컴파일은 성공적이다.

o/p는 4 대신 0이되므로 공유 라이브러리 내부의 mean의 함수 정의는 실행되지 않지만 주 모듈 내부의 함수 정의가 실행됩니다.

왜 이런 일이 발생합니까?

+0

왜 오류가 발생 했습니까? –

+0

항상 공유 lib 함수를 다시 사용할 수 있습니다. 소스 코드는 컴파일시 prio입니다. – Yann

+0

하지만 함수의 정의가 이미 공유 라이브러리에 있고 공유 라이브러리와 함께 주 프로그램을 연결하고 있습니다. 따라서 라이브러리에 이미 정의 된 함수를 다시 정의하면 오류가 발생합니다. –

답변

5

링커는 컴파일/링크 프로세스 중에 함수가 아직 발견되지 않은 경우에만 함수를 라이브러리에서 링크합니다.

기능상의 차이점은 다른 유형의 기호가 있다는 것입니다. 라이브러리 함수는 약한 기호입니다. 아직 정의되지 않은 경우에만 포함됩니다. nm은 개체 또는 실행 파일의 기호를 나열하는 도구입니다. 이 카드는 manpage이며 기호 유형 목록을 찾을 수 있습니다.

weak symbols에 대한 위키 백과 페이지가 있습니다.

+0

왜 'nm - D /lib/x86_64-linux-gnu/libc.so.6'는'puts'가'W'이고,'printf'는'T'라고 알려주지 만, 나는 GCC 프로그램에서 둘 다 다시 정의 할 수 있습니까? 이것은 약 해지는 것처럼 보입니다 (ELF 의미에서)는 질문이 아닙니다. –

-1

컴파일러 오류를 제공해야하기 때문에 제대로 공유 라이브러리를 연결 했 :

정의가 동일한 경우에도

+0

예 올바르게 연결했습니다. –

1

이 (한 외부 표시 기능이 정의를 갖는 '의미'의 여러 정의, 비 인라인 함수의 경우) 정의되지 않은 동작이 발생하며 진단은 필요하지 않습니다. (참조 : C99 6.9 # 5 및 부록 J.2)

C에서 일부 불법 코드에는 컴파일러 진단이 필요하고 일부는 불필요합니다. 일반적으로 진단을 필요로하지 않는 사람은 이유는

  • 가 오류를 감지하고보고하는 모든 컴파일러를 필요로하기에 너무 금지 간주됩니다
  • 을 진단하지 않은 사용중인 기존 시스템이 있었고, 표준위원회는 기존의 이행을 부적합하게 만들기를 원하지 않았다.

이 경우 첫 번째 경우에 해당하는 것으로 추정됩니다. 그들은 컴파일러/링커가 약한 기호 인 을 확장으로 구현하기를 원했기 때문에 컴파일러가 여기에 경고를 주어야한다고 명시하지 않았습니다. 또는 아마도 일반적으로이를 감지하는 것이 실제로 어렵습니다. 링커를 작성하려 한 적이 없습니다.

진단을 제공하지 않으면 구현의 품질 문제로 간주되어야합니다. 아마도 링커에 다른 플래그를 전달하여이 코드를 거부 할 수도 있습니다. 그렇지 않다면 버그 리포트 나 기능 요청을 할 수 있습니다.