| 1 | diff --git a/sysdeps/linux-gnu/proc.c b/sysdeps/linux-gnu/proc.c |
| 2 | index 953fd86..bdb96cb 100644 |
| 3 | --- a/sysdeps/linux-gnu/proc.c |
| 4 | +++ b/sysdeps/linux-gnu/proc.c |
| 5 | @@ -524,9 +524,53 @@ crawl_linkmap(struct process *proc, struct lt_r_debug_64 *dbg) |
| 6 | || strcmp(lib_name, "linux-vdso.so.1") == 0 |
| 7 | || strcmp(lib_name, "linux-gate.so.1") == 0 |
| 8 | || strcmp(lib_name, "linux-vdso32.so.1") == 0 |
| 9 | - || strcmp(lib_name, "linux-vdso64.so.1") == 0) |
| 10 | + || strcmp(lib_name, "linux-vdso64.so.1") == 0 |
| 11 | + || strcmp(lib_name, "[vdso]") == 0 |
| 12 | + /* Android linker includes itself in list of libraries |
| 13 | + * on GNU linker it appears as empty string */ |
| 14 | + || strcmp(lib_name, "/system/bin/linker") == 0 |
| 15 | + || strcmp(lib_name, "/system/bin/linker64") == 0) |
| 16 | continue; |
| 17 | |
| 18 | + /* On Android main executable is included in library list |
| 19 | + * On GNU it appears as empty string */ |
| 20 | + if (rlm.l_prev == 0 && strstr(lib_name, ".so") == NULL) { |
| 21 | + continue; |
| 22 | + } |
| 23 | + |
| 24 | + /* Android < 6 provides just library name without full path, |
| 25 | + * will find full path ourselves */ |
| 26 | + if (lib_name[0] != '/') { |
| 27 | + char local_path[1024]; |
| 28 | + /* Include path from LD_LIBRARY_PATH */ |
| 29 | + const char *path = getenv("LD_LIBRARY_PATH"); |
| 30 | + if (path) { |
| 31 | + strlcpy(local_path, path, sizeof(local_path)); |
| 32 | + } else { |
| 33 | + local_path[0] = '\0'; |
| 34 | + } |
| 35 | + /* Include default path (hardcoded in /system/bin/linker) */ |
| 36 | + strlcat( |
| 37 | + local_path, |
| 38 | + select_32_64(proc, ":/vendor/lib:/system/lib", ":/vendor/lib64:/system/lib64"), |
| 39 | + sizeof(local_path) |
| 40 | + ); |
| 41 | + |
| 42 | + char *local_path_ptr = local_path; |
| 43 | + const char *tested_path; |
| 44 | + char full_lib_name[BUFSIZ]; |
| 45 | + while ((tested_path = strsep(&local_path_ptr, ":"))) { |
| 46 | + if (tested_path[0] == '\0') { |
| 47 | + continue; |
| 48 | + } |
| 49 | + snprintf(full_lib_name, sizeof(full_lib_name), "%s/%s", tested_path, lib_name); |
| 50 | + if (access(full_lib_name, F_OK) == 0) { |
| 51 | + strlcpy(lib_name, full_lib_name, sizeof(lib_name)); |
| 52 | + break; |
| 53 | + } |
| 54 | + } |
| 55 | + } |
| 56 | + |
| 57 | /* Do we have that library already? */ |
| 58 | if (proc_each_library(proc, NULL, library_with_key_cb, &key)) |
| 59 | continue; |