2011-04-28 4 views
6

표준 C 프로토 타입을 사용하여 malloc/calloc/realloc/free를 구현하는 커스텀 라이브러리를 작성했고,이를 컴파일하는 방법을 알아 냈습니다. 표준 응용 프로그램을 연결하여 라이브러리를 테스트하고 싶습니다. 이것을하기위한 좋은 방법은 무엇입니까? 일단 작업 라이브러리가 있으면 LD_PRELOAD를 사용하여로드 할 수 있다고 가정합니다. 그러나 함수를 공존 시키려면 어떻게해야합니까? 그러나 시스템 라이브러리보다 우선합니다. 내 함수는 메모리를 실행하기 위해 malloc을 호출해야하므로 stdlib을 완전히 뺄 수는 없다 ... Help?커스텀 malloc 컴파일하기

+1

필자의 대답은 동적 링커의 사용에 있다고 확신합니다. – conartist6

답변

4

바꾸려는 함수는 시스템 호출이 아닌 매크로가 아닌 표준 C 함수입니다. 따라서 함수에 동일한 이름을 지정하고 공유 라이브러리에 컴파일해야합니다.

그런 다음 LD_PRELOAD을 사용하여 바이너리가 시작되기 전에 라이브러리를 미리로드하십시오. 모든 주소가 한 번 해결되기 때문에 링커는 함수의 주소를 알아 내고 이름을 기억하며 나중에 표준 라이브러리에서 찾지 않습니다.

프로그램이 표준 런타임과 정적으로 연결된 경우이 방법이 작동하지 않을 수 있습니다. 또한 보간을위한 또 다른 API가 있으므로 Mac OS X에서는 작동하지 않습니다.

리눅스에서, 예를 들어, 함수는 (당신이 malloc 당신 자신의 구현에 시스템 malloc을 사용하려는 경우 예), 수동 dlopen를 사용하여 표준 라이브러리를 열 필요가 공존 기능을 조회하기 위해서는 거기에 dlsym을 사용해야하고 나중에 주소로 전화하십시오.

+0

더 많은 문제가 발생할 것이라고 생각했지만 표준 라이브러리를 포함하지 않고 malloc을로드하고 dlsym을 종료하면 모든 것이 잘 컴파일됩니다. 감사! – conartist6

+0

@ conartist6 : 환영합니다 :) –

1

이 라이브러리를 사용할 소스 코드를 제어 할 수 있다면 다음과 같은 가능성이 있습니다. 다른 함수 이름을 사용하십시오 : 예를 들어, malloc 대신 newCoolMalloc을 호출하십시오. 이 방법은 때때로 더 단순하며 특별한 링커 옵션에 의존하지 않습니다.

코드에서 #define을 사용하여 코드에서 원하는 기능 집합을 호출하게하십시오. #define malloc을 다른 것으로 정의 할 수 있습니다. 예를 들면 다음과 같습니다.

#define malloc newCoolMalloc 
#define free newCoolFree 

그렇다면 일관성있게 작성해야합니다. 그렇지 않으면 stdlib malloc을 한 곳에서 사용하고 다른 곳에서는 sttylib를 사용하는 위험을 감수해야합니다. 이러한 상황을 완화하는 데 도움이되는 한 가지 방법은 자신의 코드에서 (가능한 경우) 할당 및 자유 기능에 대한 사용자 지정 이름을 사용하는 것입니다. 그런 다음 올바른 것을 호출하는 것이 더 쉽습니다. 사용자 정의 malloc 함수 또는 원래 stdlib malloc 함수에 대한 다양한 사용자 정의 이름을 정의 할 수 있습니다.

예를 들어, 코드에서 실제 이름으로 mallocPlaceHolder을 사용할 수 있습니다 :

someThing = mallocPlaceHolder(nbytes); 

을 다음 당신의 정의는 더 같을 것이다 :

#define mallocPlaceHolder myCoolMalloc 

하면 양식 mallocPlaceHolder의 기능 없음 (및 관련 무료)가 실제로 존재하면 다른 라이브러리를 혼합하지 않아도됩니다.

+0

불행히도 이것은 나를 위해 작동하지 않습니다. 이 라이브러리를 사용하여 다른 사람의 응용 프로그램을 실행하여 할당자를 테스트하려고합니다.이론적으로 포함 된 것들로 다시 컴파일 할 수 있지만 시간과 노력은 LD_PRELOAD로 저장됩니다. – conartist6

2

malloc()malloc()으로 쓰지 마십시오. sbrk을 사용하여 작성하십시오. OS에서 직접 메모리를 가져옵니다.

+0

재미있는 제안. 나는 그것을 들여다 볼 것이다. – conartist6

+0

일부 시스템에서는'sbrk()'를 더 이상 사용할 수 없습니다. 예를 들어 현재 맥 OS X에서'brk 및 sbrk 기능은 가상 메모리 관리가 출현하기 이전의 역사적 호기심이다. '라고 말했고, 기능의 전체 소스를 보면, 더 재미있게 :'errno = ENOMEM; return ((void *) - 1);' – achedeuzot