android错误动态加载libc ++.所以本机库

Adr*_*nho 8 c++ java-native-interface android native

我正在尝试构建一个概念验证Android应用程序,它使用OpenSSH代码与服务器建立SSH会话.

为此,我使用android源代码构建所需的库,然后将它们提升到一个AndroidStudio本机项目,其中所有内容都应该打包并安装在设备上.

但是,其中一个库(libc ++.so)无法在设备上动态加载消息" java.lang.UnsatisfiedLinkError:dlopen failed:找不到符号"__register_atfork"由"libc ++.so"... " 引用

加载libc ++时会抛出此错误.来自MainActivity java代码的库(我现在一次加载一个库以确定它失败的地方):

public class MainActivity extends AppCompatListActivity implements OnHostStatusChangedListener {
    ...................
    static {
        System.loadLibrary("dl");
        System.loadLibrary("c");
        System.loadLibrary("m");
        System.loadLibrary("c++"); // <--- Error dlopen failed: cannot locate symbol "__register_atfork" referenced by "libc++.so
        System.loadLibrary("ssh");
        System.loadLibrary("vrx-native");
    }
    .............
}
Run Code Online (Sandbox Code Playgroud)

我对错误消息的解释是libc ++所需的符号__register_atfork.所以没有任何其他库定义.但检查库符号表我不明白为什么dlopen无法识别在libc.so上定义的符号:

$readelf -s libc++.so
Symbol table '.dynsym' contains 2367 entries:
   Num:    Value  Size Type    Bind   Vis      Ndx Name
     0: 00000000     0 NOTYPE  LOCAL  DEFAULT  UND 
     .....................
     3: 00000000     0 FUNC    GLOBAL DEFAULT  UND __register_atfork@LIBC (2) <-- Undefined symbol reference
     .....................

$readelf -s libc.so
Symbol table '.dynsym' contains 1505 entries:
   Num:    Value  Size Type    Bind   Vis      Ndx Name
     0: 00000000     0 NOTYPE  LOCAL  DEFAULT  UND 
     .............
    62: 00043509   120 FUNC    GLOBAL DEFAULT   13 __register_atfork@@LIBC
    ..............
    7518: 00043509   120 FUNC    GLOBAL DEFAULT   13 __register_atfork <-- symbol defined and exported by libc.so!!!
Run Code Online (Sandbox Code Playgroud)

检查库的标题和动态部分也没有提供任何关于为什么这可能失败的线索:

$ readelf -hd libc++.so
ELF Header:
  Magic:   7f 45 4c 46 01 01 01 00 00 00 00 00 00 00 00 00 
  Class:                             ELF32
  Data:                              2's complement, little endian
  Version:                           1 (current)
  OS/ABI:                            UNIX - System V
  ABI Version:                       0
  Type:                              DYN (Shared object file)
  Machine:                           ARM
  Version:                           0x1
  Entry point address:               0x0
  Start of program headers:          52 (bytes into file)
  Start of section headers:          573972 (bytes into file)
  Flags:                             0x5000200, Version5 EABI, soft-float ABI
  Size of this header:               52 (bytes)
  Size of program headers:           32 (bytes)
  Number of program headers:         9
  Size of section headers:           40 (bytes)
  Number of section headers:         29
  Section header string table index: 28

Dynamic section at offset 0x8abf8 contains 29 entries:
  Tag        Type                         Name/Value
 0x00000003 (PLTGOT)                     0x8dfe8
 0x00000002 (PLTRELSZ)                   8216 (bytes)
 0x00000017 (JMPREL)                     0x2d738
 0x00000014 (PLTREL)                     REL
 0x6000000f (Operating System specific: 6000000f)        0x2b280
 0x60000010 (Operating System specific: 60000010)        0x24b8
 0x00000013 (RELENT)                     8 (bytes)
 0x6ffffffa (RELCOUNT)                   397
 0x00000006 (SYMTAB)                     0x21a0
 0x0000000b (SYMENT)                     16 (bytes)
 0x00000005 (STRTAB)                     0xb590
 0x0000000a (STRSZ)                      107756 (bytes)
 0x00000004 (HASH)                       0x25a7c
 0x00000001 (NEEDED)                     Shared library: [libdl.so]
 0x00000001 (NEEDED)                     Shared library: [libc.so]
 0x00000001 (NEEDED)                     Shared library: [libm.so]
 0x0000000e (SONAME)                     Library soname: [libc++.so]
 0x0000001a (FINI_ARRAY)                 0x8b3c0
 0x0000001c (FINI_ARRAYSZ)               4 (bytes)
 0x00000019 (INIT_ARRAY)                 0x8dbf4
 0x0000001b (INIT_ARRAYSZ)               4 (bytes)
 0x0000001e (FLAGS)                      BIND_NOW
 0x6ffffffb (FLAGS_1)                    Flags: NOW
 0x6ffffff0 (VERSYM)                     0x29f94
 0x6ffffffc (VERDEF)                     0x2b214
 0x6ffffffd (VERDEFNUM)                  1
 0x6ffffffe (VERNEED)                    0x2b230
 0x6fffffff (VERNEEDNUM)                 2
 0x00000000 (NULL)                       0x0

$ readelf -hd libc.so
ELF Header:
  Magic:   7f 45 4c 46 01 01 01 00 00 00 00 00 00 00 00 00 
  Class:                             ELF32
  Data:                              2's complement, little endian
  Version:                           1 (current)
  OS/ABI:                            UNIX - System V
  ABI Version:                       0
  Type:                              DYN (Shared object file)
  Machine:                           ARM
  Version:                           0x1
  Entry point address:               0x0
  Start of program headers:          52 (bytes into file)
  Start of section headers:          757116 (bytes into file)
  Flags:                             0x5000200, Version5 EABI, soft-float ABI
  Size of this header:               52 (bytes)
  Size of program headers:           32 (bytes)
  Number of program headers:         10
  Size of section headers:           40 (bytes)
  Number of section headers:         33
  Section header string table index: 30

Dynamic section at offset 0x8232c contains 27 entries:
  Tag        Type                         Name/Value
 0x00000003 (PLTGOT)                     0x835bc
 0x00000002 (PLTRELSZ)                   5232 (bytes)
 0x00000017 (JMPREL)                     0x105c4
 0x00000014 (PLTREL)                     REL
 0x00000011 (REL)                        0xd85c
 0x00000012 (RELSZ)                      11624 (bytes)
 0x00000013 (RELENT)                     8 (bytes)
 0x6ffffffa (RELCOUNT)                   1304
 0x00000006 (SYMTAB)                     0x1c0
 0x0000000b (SYMENT)                     16 (bytes)
 0x00000005 (STRTAB)                     0x5fd0
 0x0000000a (STRSZ)                      17483 (bytes)
 0x00000004 (HASH)                       0xa41c
 0x00000001 (NEEDED)                     Shared library: [libdl.so]
 0x0000000e (SONAME)                     Library soname: [libc.so]
 0x00000019 (INIT_ARRAY)                 0x83304
 0x0000001b (INIT_ARRAYSZ)               36 (bytes)
 0x0000001a (FINI_ARRAY)                 0x83328
 0x0000001c (FINI_ARRAYSZ)               4 (bytes)
 0x0000001e (FLAGS)                      BIND_NOW
 0x6ffffffb (FLAGS_1)                    Flags: NOW
 0x6ffffff0 (VERSYM)                     0xcbc4
 0x6ffffffc (VERDEF)                     0xd788
 0x6ffffffd (VERDEFNUM)                  5
 0x6ffffffe (VERNEED)                    0xd82c
 0x6fffffff (VERNEEDNUM)                 1
 0x00000000 (NULL)                       0x0
Run Code Online (Sandbox Code Playgroud)

任何帮助赞赏

更新:调查(2)on 的含义__register_atfork@LIBC (2)

检查readelf源我们可以看到(2)令牌正在打印:

if (version_string)
{
    if (sym_info == symbol_undefined)
    printf ("@%s (%d)", version_string, vna_other);
else
    printf (sym_info == symbol_hidden ? "@%s" : "@@%s",
    version_string);
}
Run Code Online (Sandbox Code Playgroud)

vna_other正在从struct Elf32_External_Sym,member st_other... 加载...

typedef struct {
  unsigned char st_name[4];             /* Symbol name, index in string tbl */
  unsigned char st_value[4];            /* Value of the symbol */
  unsigned char st_size[4];             /* Associated symbol size */
  unsigned char st_info[1];             /* Type and binding attributes */
  unsigned char st_other[1];            /* No defined meaning, 0 */
  unsigned char st_shndx[2];            /* Associated section index */
} Elf32_External_Sym;
Run Code Online (Sandbox Code Playgroud)

ELF规范声明(第32页):

st_other该成员目前持有0且没有明确的含义.

也许这对ARM有一些特殊的意义?不,本文档没有定义任何特定于ARM的内容st_other......

更新:调查st_otherELF文件定义中的含义

发现这个帖子标题为Request to extend symbol visibilities(st_other)

符号可见性当前由符号的st_other字段的最低2位表示.

帖子提到了目前进入的可见性属性st_other......

#define STV_DEFAULT     0
#define STV_INTERNAL    1
#define STV_HIDDEN      2
#define STV_PROTECTED   3
Run Code Online (Sandbox Code Playgroud)

...并提出两个新的可见性属性......

#define STV_SINGLETON   4
#define STV_ELIMINATE   5
Run Code Online (Sandbox Code Playgroud)

似乎(2)在readelf符号表输出对应STV_HIDDEN符号st_other成员的属性...