2017-04-18 3 views
4

main() 전에 실행해야하는 정적 초기화 코드가 포함 된이 라이브러리가 있습니다. 모든 번역 단위를 함께 컴파일하면 모두 잘 작동하지만 정적 라이브러리 (.a 파일)를 제공하고 사용자가 자신의 응용 프로그램에 연결하면 링커가 내 정적을 수행하는 심볼을 무시합니다. 초기화. 내가 GNU 링크에 --whole-archive 옵션을 지정, 즉 GCC에 -Wl,--whole-archive 옵션을 지정하면 내가 링커가 정적 라이브러리에 모든를 선택할 수 있습니다 Y연결될 때 "필요한 것을 잡아라"와 "모든 것을 잡아라"사이에 무엇이 있습니까 (-Wl, - 전체 보관)?

대체.

하지만 중간 정도입니까? 일부 심볼을 ​​표시하고 링커가 항상 실행 파일을 선택하도록 할 수 있으며 나머지 심볼은 필요한 경우에만 추가 할 수 있습니까?

동기 부여 : 일부는 static blocks을 사용하여 클래스를 공장에서 등록합니다. 필자는 팩터가 채워지는 "마법 주문"을 수행해야하는 사용자 코드없이 내 코드를 (비 동적) 라이브러리로 사용할 수있게하려고합니다.

일부 관련 질문 :

답변

1

당신은 자연적으로 주어진 기능을 유지 (그리고이 호출 된 모든 코드를 링커를 강제 할 수 기능). link 명령에 -u my_function을 추가하십시오. 많은 빌드 시스템은 정적 라이브러리가 빌드 설정을 사용하는 사람들에게 '내보내기'하도록합니다. 프레임 워크를 NDK 빌드 안드로이드 에 대한 예를 들어, 당신은 당신의 모듈 Android.mk

include $(CLEAR_VARS) LOCAL_MODULE := the_best_static_library LOCAL_SRC_FILES := $(TARGET_ARCH_ABI)/libfoo.a LOCAL_EXPORT_C_INCLUDES := $(LOCAL_PATH)/include LOCAL_EXPORT_LDFLAGS := -u my_function include $(PREBUILT_STATIC_LIBRARY) 

같은 것을 지정할 수 있습니다. 사람들은 Android.mk에 간단한 문장

$(call import-module,third_party/the_best_static_library) 

N.B.를 추가하여 재사용이 접근 방식을 사용하려면 my_function()static으로 선언 할 수 없습니다. 일부 심볼이 파일 범위에서 정적으로 선언 된 경우 링커는 이름으로 전혀 알 수없는 것으로 추측합니다. 다행히 링커가 유지하기로 결정한 코드에서 참조되는 경우에는 제거되지도 않습니다. 또한 special effort을 만들지 않으면 링커에서 전체 컴파일 단위 (a.k.a.C 파일)를 제거하거나 유지합니다. 따라서 많은 기능과 데이터를 유지하기 위해 더미 함수를 "고정"하는 것은 일반적으로 enough입니다.

+1

(1)이 예제의 어떤 부분이 Android에만 해당합니까? GNU는 이러한 모든 플래그를 존중합니까? (2)'static'에 대해서 - 파일 범위에서 정적이라고 선언하지 않는다는 뜻인가요? 그것은 실제로 나에게 문제가 될 것입니다. 그러나 여전히, +1은 지금 당장 시도해 볼 기회가 생기면 받아 들일 것입니다. – einpoklum

+0

** statuc **에 대한 답변이 확장되었습니다. 링커 플래그에 관해서는, 내가 아는 한 모든 gcc 기반 툴체인에서 사용할 수 있습니다. Android 관련 자료는 정적 라이브러리의 사용자에게 지식을 배포하는 방법입니다. 헤더 파일에 액세스하는 방법은 무엇입니까? 귀하의 코드가 일부 제 3 자의 사전 구축 된 라이브러리에 달려 있음을 어떻게 그들에게 가르쳐 줍니까? –

관련 문제