【问题标题】:Undefined reference to libssl function with Android NDK使用 Android NDK 对 libssl 函数的未定义引用
【发布时间】:2012-07-26 17:03:24
【问题描述】:

我对 Android 非常陌生,通常会编译和链接。我不知道哪些细节对我的问题很重要,所以我只会告诉你一切。如果您发现任何奇怪或不正确的地方,请告诉我。

我在 Android-NDK 中构建了 libcrypto.so 和 libssl.so 库。我编写了使用 openssl.so 中的函数的本机代码(而 openssl.so 使用了 libssl.so 中的函数)。代码可以编译,但是在链接时我收到“未定义的引用”错误:

./obj/local/armeabi/objs/pki_send/pki_send.o: In function `main':
/home/android/nativeserver/jni/pki_send.c:27: undefined reference to `RSA_generate_key'
collect2: ld returned 1 exit status
make: *** [obj/local/armeabi/pki_send] Error 1

我在谷歌上搜索了一个和我有同样问题的人,她甚至调用了相同的函数(除了这个人不是为 Android 构建的):http://ubuntuforums.org/showthread.php?t=1081028。我将在此处引用她的帖子中与我的问题相关的部分:

当我删除一个参数[导致“未定义引用”的函数]时,编译器说参数太少,当我添加一个参数时,编译器说参数太多,所以看起来有“一些" 对正确函数的一种引用。也许有一些链接发生错误?

我注意到了同样的行为。她通过使用 -lssl 设置进行编译解决了她的问题,该设置告诉编译器使用 openssl 库。为此,我更改了 Android.mk 文件中的模块:

LOCAL_LDLIBS += -ldl

到这里:

LOCAL_LDLIBS += -lssl -lcrypto -ldl 

为了安全起见,我包含了 -lcrypto,因为 libssl 依赖于 libcrypto。现在当我运行 ndk-build 时,我收到以下错误:

/home/android/android-ndk-r8/toolchains/arm-linux-androideabi-4.4.3/prebuilt/linux-x86/bin/../lib/gcc/arm-linux-androideabi/4.4.3/../../../../arm-linux-androideabi/bin/ld: cannot find -lssl
collect2: ld returned 1 exit status
make: *** [obj/local/armeabi/pki_send] Error 1

此错误表明“ld”找不到 libssl.so。我的 jni 目录中有 libcrypto.so 和 libssl.so。理想情况下,我想找到一种方法将 jni 目录添加到“ld”的搜索路径中,但我无法弄清楚。我试图通过将 libssl.so 和 libcrypto.so 添加到以下目录来解决这个问题:/android-ndk-r8/platforms/android-8/arch-arm/usr/lib(我相信“ld”在这里搜索图书馆)。完成此操作后,我再次运行 ndk-build 并收到“未定义引用”错误:

./obj/local/armeabi/objs/pki_send/pki_send.o: In function `main':
/home/android/nativeserver/jni/pki_send.c:27: undefined reference to `RSA_generate_key'
collect2: ld returned 1 exit status
make: *** [obj/local/armeabi/pki_send] Error 1

从这里开始,我不知道如何进行。

以防万一,这是我的 Android.mk 文件中的代码:

LOCAL_PATH := $(call my-dir)
APP_PLATFORM := android-8

include $(CLEAR_VARS)

LOCAL_MODULE    := crypto 
LOCAL_SRC_FILES := libcrypto.so 
LOCAL_EXPORT_C_INCLUDES := $(LOCAL_PATH)/../include/

include $(PREBUILT_SHARED_LIBRARY)

include $(CLEAR_VARS)

LOCAL_MODULE    := ssl 
LOCAL_SRC_FILES := libssl.so 
LOCAL_EXPORT_C_INCLUDES := $(LOCAL_PATH)/../include/

include $(PREBUILT_SHARED_LIBRARY)

include $(CLEAR_VARS)

LOCAL_SRC_FILES := pki_send.c 
LOCAL_MODULE    := pki_send 
LOCAL_SHARED_LIBRARIES := ssl crypto 
LOCAL_LDLIBS += -lssl -lcrypto -ldl

LOCAL_MODULE_TAGS := optional

include $(BUILD_EXECUTABLE)

编辑:我忘了补充一点:当我在 libcrypto.so 的本机代码中使用函数时,代码编译和链接都很好。看来我可以使用 libcrypto.so 中的任何函数。但是,给我带来问题的函数在 libssl.so 中。这可能很重要,也可能不重要。

【问题讨论】:

    标签: android-ndk linker openssl linker-errors


    【解决方案1】:

    我解决了这个问题。我调用的函数“RSA_generate_key”仅存在于已弃用的 libcrypto.so 版本中。我使用的是使用“RSA_generate_key_ex”的较新版本。我通过在 libcrypto.so 上做一个 readelf 发现了这一点:

    $ ./arm-linux-androideabi-readelf -all ~/nativeserver/jni/libcrypto.so |grep RSA_generate
       679: 00089239   992 FUNC    GLOBAL DEFAULT    7 RSA_generate_key_ex
     10334: 00089239   992 FUNC    GLOBAL DEFAULT    7 RSA_generate_key_ex
    

    程序仍然编译的原因是因为 RSA_generate_key 在 openssl/rsa.h 的头文件中,即使库没有它。

    【讨论】:

      猜你喜欢
      • 1970-01-01
      • 2018-02-24
      • 1970-01-01
      • 1970-01-01
      • 2012-07-18
      • 1970-01-01
      • 1970-01-01
      • 2019-03-08
      • 2017-01-12
      相关资源
      最近更新 更多