简体   繁体   English

使用动态库交叉编译 C 代码时出错

[英]Error during Cross-compiling C code with Dynamic libraries

I've two files:我有两个文件:

lib.c库文件

#include<stdio.h>

void hi() {
  printf("Hi i'm a library function in lib.so\n");
} 

and main.c和 main.c

#include<stdio.h>
#include<dlfcn.h>
/* based on Jeff Scudder's code */
int main() {
  void *SharedObjectFile;
  void (*hi)();

  // Load the shared libary;
  SharedObjectFile = dlopen("./lib.so", RTLD_LAZY);

  // Obtain the address of a function in the shared library.
  ciao = dlsym(SharedObjectFile, "hi");

  // Use the dynamically loaded function.
  (*hi)();

  dlclose(SharedObjectFile);
}

And I've tried to build an executables using the following commands:我尝试使用以下命令构建可执行文件:

export LD_LIBRARY_PATH= pwd导出 LD_LIBRARY_PATH= pwd

gcc -c -fpic lib.c gcc -c -fpic lib.c

gcc -shared -lc -o lib.so lib.o gcc -shared -lc -o lib.so lib.o

gcc main.c -ldl gcc main.c -ldl

And it works pretty well.而且效果很好。 Then I've tried to export my program on Android (Nexus One, with ARM-v7-0a arch) using the following commands:然后我尝试使用以下命令在 Android(Nexus One,带有 ARM-v7-0a arch)上导出我的程序:

export LD_LIBRARY_PATH= pwd导出 LD_LIBRARY_PATH= pwd

arm-none-linux-gnueabi-gcc -c -fpic lib.c arm-none-linux-gnueabi-gcc -c -fpic lib.c

arm-none-linux-gnueabi-gcc -shared -lc -o lib.so lib.o arm-none-linux-gnueabi-gcc -shared -lc -o lib.so lib.o

arm-none-linux-gnueabi-gcc main.c -ldl -o main arm-none-linux-gnueabi-gcc main.c -ldl -o main

adb push main /system/app adb push main /system/app

The result of executing ./main on the correct folder on my smartphone is just:在我的智能手机上的正确文件夹上执行 ./main 的结果只是:

./main: not found ./主要:未找到

even if my file is right there!即使我的文件就在那里!

Am I missing anything during the cross-compile process?我在交叉编译过程中遗漏了什么吗? Any help?有什么帮助吗? I'm using the cross-compiler from CodeSourcery and it works well for static programs without .so libraries.我正在使用 CodeSourcery 的交叉编译器,它适用于没有 .so 库的静态程序。 Thanks谢谢

EDIT : as Igor states below, that was a linker issue.编辑:正如 Igor 在下面所说,这是一个链接器问题。 This command fixes it:此命令修复它:

arm-none-linux-gnueabi-gcc -o test main.c -Wl,--dynamic-linker=/system/bin/linker -ldl arm-none-linux-gnueabi-gcc -o test main.c -Wl,--dynamic-linker=/system/bin/linker -ldl

in my very case I need other libraries because in /system/lib/ there are no many .so files.就我而言,我需要其他库,因为在 /system/lib/ 中没有很多 .so 文件。

The "not found" message refers not to the shared object but to the dynamic linker. “未找到”消息不是指共享对象,而是指动态链接器。 Linux uses /lib/ld-linux.so.2 (or /lib64/ld-linux-x86-64.so.2 for x64) while Android uses /bin/linker . Linux 使用/lib/ld-linux.so.2 (或/lib64/ld-linux-x86-64.so.2 for x64)而 Android 使用/bin/linker You can check which dynamic loader your program uses with readelf -l , eg:您可以使用readelf -l检查您的程序使用哪个动态加载器,例如:

Program Headers:
  Type           Offset   VirtAddr   PhysAddr   FileSiz MemSiz  Flg Align
  PHDR           0x000034 0x08048034 0x08048034 0x00100 0x00100 R E 0x4
  INTERP         0x000134 0x08048134 0x08048134 0x00013 0x00013 R   0x1
      [Requesting program interpreter: /lib/ld-linux.so.2]

You can specify a linker to use with ld's --dynamic-linker switch, but there are likely to be other differences.您可以指定要与 ld 的--dynamic-linker开关一起使用--dynamic-linker器,但可能存在其他差异。 For example, Android uses a stripped-down libc implementation called bionic, and it may be missing functionality that your program relies on, or have different behavior.例如,Android 使用称为仿生的精简 libc 实现,它可能缺少您的程序所依赖的功能,或者具有不同的行为。

You should use NDK or another Android-targeted toolchain when compiling programs for Android.在为 Android 编译程序时,您应该使用 NDK 或其他面向 Android 的工具链。 Even though it's based on Linux kernel, the differences are large enough that Linux-targeted toolchains are not sufficient.即使它基于 Linux 内核,差异也足够大,以至于针对 Linux 的工具链是不够的。

声明:本站的技术帖子网页,遵循CC BY-SA 4.0协议,如果您需要转载,请注明本站网址或者原文地址。任何问题请咨询:yoyou2525@163.com.

 
粤ICP备18138465号  © 2020-2024 STACKOOM.COM