1 /*
2 * Copyright (C) 2008 The Android Open Source Project
3 * All rights reserved.
4 *
5 * Redistribution and use in source and binary forms, with or without
6 * modification, are permitted provided that the following conditions
7 * are met:
8 * * Redistributions of source code must retain the above copyright
9 * notice, this list of conditions and the following disclaimer.
10 * * Redistributions in binary form must reproduce the above copyright
11 * notice, this list of conditions and the following disclaimer in
12 * the documentation and/or other materials provided with the
13 * distribution.
14 *
15 * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
16 * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
17 * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS
18 * FOR A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE
19 * COPYRIGHT OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT,
20 * INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING,
21 * BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS
22 * OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED
23 * AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY,
24 * OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT
25 * OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
26 * SUCH DAMAGE.
27 */
28
29 #include <android/api-level.h>
30 #include <errno.h>
31 #include <fcntl.h>
32 #include <inttypes.h>
33 #include <pthread.h>
34 #include <stdio.h>
35 #include <stdlib.h>
36 #include <string.h>
37 #include <sys/mman.h>
38 #include <sys/param.h>
39 #include <unistd.h>
40
41 #include <new>
42 #include <string>
43 #include <unordered_map>
44 #include <vector>
45
46 // Private C library headers.
47 #include "private/bionic_globals.h"
48 #include "private/bionic_tls.h"
49 #include "private/KernelArgumentBlock.h"
50 #include "private/ScopedPthreadMutexLocker.h"
51 #include "private/ScopeGuard.h"
52
53 #include "linker.h"
54 #include "linker_block_allocator.h"
55 #include "linker_gdb_support.h"
56 #include "linker_debug.h"
57 #include "linker_dlwarning.h"
58 #include "linker_sleb128.h"
59 #include "linker_phdr.h"
60 #include "linker_relocs.h"
61 #include "linker_reloc_iterators.h"
62 #include "linker_utils.h"
63
64 #include "android-base/strings.h"
65 #include "ziparchive/zip_archive.h"
66
67 extern void __libc_init_globals(KernelArgumentBlock&);
68 extern void __libc_init_AT_SECURE(KernelArgumentBlock&);
69
70 extern "C" void _start();
71
72 // Override macros to use C++ style casts.
73 #undef ELF_ST_TYPE
74 #define ELF_ST_TYPE(x) (static_cast<uint32_t>(x) & 0xf)
75
76 struct android_namespace_t {
77 public:
android_namespace_tandroid_namespace_t78 android_namespace_t() : name_(nullptr), is_isolated_(false) {}
79
get_nameandroid_namespace_t80 const char* get_name() const { return name_; }
set_nameandroid_namespace_t81 void set_name(const char* name) { name_ = name; }
82
is_isolatedandroid_namespace_t83 bool is_isolated() const { return is_isolated_; }
set_isolatedandroid_namespace_t84 void set_isolated(bool isolated) { is_isolated_ = isolated; }
85
get_ld_library_pathsandroid_namespace_t86 const std::vector<std::string>& get_ld_library_paths() const {
87 return ld_library_paths_;
88 }
set_ld_library_pathsandroid_namespace_t89 void set_ld_library_paths(std::vector<std::string>&& library_paths) {
90 ld_library_paths_ = library_paths;
91 }
92
get_default_library_pathsandroid_namespace_t93 const std::vector<std::string>& get_default_library_paths() const {
94 return default_library_paths_;
95 }
set_default_library_pathsandroid_namespace_t96 void set_default_library_paths(std::vector<std::string>&& library_paths) {
97 default_library_paths_ = library_paths;
98 }
99
get_permitted_pathsandroid_namespace_t100 const std::vector<std::string>& get_permitted_paths() const {
101 return permitted_paths_;
102 }
set_permitted_pathsandroid_namespace_t103 void set_permitted_paths(std::vector<std::string>&& permitted_paths) {
104 permitted_paths_ = permitted_paths;
105 }
106
add_soinfoandroid_namespace_t107 void add_soinfo(soinfo* si) {
108 soinfo_list_.push_back(si);
109 }
110
add_soinfosandroid_namespace_t111 void add_soinfos(const soinfo::soinfo_list_t& soinfos) {
112 for (auto si : soinfos) {
113 add_soinfo(si);
114 si->add_secondary_namespace(this);
115 }
116 }
117
remove_soinfoandroid_namespace_t118 void remove_soinfo(soinfo* si) {
119 soinfo_list_.remove_if([&](soinfo* candidate) {
120 return si == candidate;
121 });
122 }
123
soinfo_listandroid_namespace_t124 const soinfo::soinfo_list_t& soinfo_list() const { return soinfo_list_; }
125
126 // For isolated namespaces - checks if the file is on the search path;
127 // always returns true for not isolated namespace.
128 bool is_accessible(const std::string& path);
129
130 private:
131 const char* name_;
132 bool is_isolated_;
133 std::vector<std::string> ld_library_paths_;
134 std::vector<std::string> default_library_paths_;
135 std::vector<std::string> permitted_paths_;
136 soinfo::soinfo_list_t soinfo_list_;
137
138 DISALLOW_COPY_AND_ASSIGN(android_namespace_t);
139 };
140
141 android_namespace_t g_default_namespace;
142
143 static std::unordered_map<uintptr_t, soinfo*> g_soinfo_handles_map;
144 static android_namespace_t* g_anonymous_namespace = &g_default_namespace;
145
146 static ElfW(Addr) get_elf_exec_load_bias(const ElfW(Ehdr)* elf);
147
148 static LinkerTypeAllocator<soinfo> g_soinfo_allocator;
149 static LinkerTypeAllocator<LinkedListEntry<soinfo>> g_soinfo_links_allocator;
150
151 static LinkerTypeAllocator<android_namespace_t> g_namespace_allocator;
152 static LinkerTypeAllocator<LinkedListEntry<android_namespace_t>> g_namespace_list_allocator;
153
154 static soinfo* solist;
155 static soinfo* sonext;
156 static soinfo* somain; // main process, always the one after libdl_info
157
158 #if defined(__LP64__)
159 static const char* const kSystemLibDir = "/system/lib64";
160 static const char* const kVendorLibDir = "/vendor/lib64";
161 static const char* const kAsanSystemLibDir = "/data/lib64";
162 static const char* const kAsanVendorLibDir = "/data/vendor/lib64";
163 #else
164 static const char* const kSystemLibDir = "/system/lib";
165 static const char* const kVendorLibDir = "/vendor/lib";
166 static const char* const kAsanSystemLibDir = "/data/lib";
167 static const char* const kAsanVendorLibDir = "/data/vendor/lib";
168 #endif
169
170 static const char* const kDefaultLdPaths[] = {
171 kSystemLibDir,
172 kVendorLibDir,
173 nullptr
174 };
175
176 static const char* const kAsanDefaultLdPaths[] = {
177 kAsanSystemLibDir,
178 kSystemLibDir,
179 kAsanVendorLibDir,
180 kVendorLibDir,
181 nullptr
182 };
183
184 // Is ASAN enabled?
185 static bool g_is_asan = false;
186
is_system_library(const std::string & realpath)187 static bool is_system_library(const std::string& realpath) {
188 for (const auto& dir : g_default_namespace.get_default_library_paths()) {
189 if (file_is_in_dir(realpath, dir)) {
190 return true;
191 }
192 }
193 return false;
194 }
195
196 // Checks if the file exists and not a directory.
file_exists(const char * path)197 static bool file_exists(const char* path) {
198 int fd = TEMP_FAILURE_RETRY(open(path, O_RDONLY | O_CLOEXEC));
199 if (fd == -1) {
200 return false;
201 } else {
202 close(fd);
203 return true;
204 }
205 }
206 static std::string dirname(const char *path);
207
208 // TODO(dimitry): The grey-list is a workaround for http://b/26394120 ---
209 // gradually remove libraries from this list until it is gone.
is_greylisted(const char * name,const soinfo * needed_by)210 static bool is_greylisted(const char* name, const soinfo* needed_by) {
211 static const char* const kLibraryGreyList[] = {
212 "libandroid_runtime.so",
213 "libbinder.so",
214 "libcrypto.so",
215 "libcutils.so",
216 "libexpat.so",
217 "libgui.so",
218 "libmedia.so",
219 "libnativehelper.so",
220 "libskia.so",
221 "libssl.so",
222 "libstagefright.so",
223 "libsqlite.so",
224 "libui.so",
225 "libutils.so",
226 "libvorbisidec.so",
227 nullptr
228 };
229
230 // limit greylisting to apps targeting sdk version 23 and below
231 if (get_application_target_sdk_version() > 23) {
232 return false;
233 }
234
235 // if the library needed by a system library - implicitly assume it
236 // is greylisted
237
238 if (needed_by != nullptr && is_system_library(needed_by->get_realpath())) {
239 return true;
240 }
241
242 // if this is an absolute path - make sure it points to /system/lib(64)
243 if (name[0] == '/' && dirname(name) == kSystemLibDir) {
244 // and reduce the path to basename
245 name = basename(name);
246 }
247
248 for (size_t i = 0; kLibraryGreyList[i] != nullptr; ++i) {
249 if (strcmp(name, kLibraryGreyList[i]) == 0) {
250 return true;
251 }
252 }
253
254 return false;
255 }
256 // END OF WORKAROUND
257
258 static const ElfW(Versym) kVersymNotNeeded = 0;
259 static const ElfW(Versym) kVersymGlobal = 1;
260
261 static const char* const* g_default_ld_paths;
262 static std::vector<std::string> g_ld_preload_names;
263
264 static std::vector<soinfo*> g_ld_preloads;
265
266 static bool g_public_namespace_initialized;
267 static soinfo::soinfo_list_t g_public_namespace;
268
269 __LIBC_HIDDEN__ int g_ld_debug_verbosity;
270
271 __LIBC_HIDDEN__ abort_msg_t* g_abort_message = nullptr; // For debuggerd.
272
dirname(const char * path)273 static std::string dirname(const char *path) {
274 const char* last_slash = strrchr(path, '/');
275 if (last_slash == path) return "/";
276 else if (last_slash == nullptr) return ".";
277 else
278 return std::string(path, last_slash - path);
279 }
280
281 #if STATS
282 struct linker_stats_t {
283 int count[kRelocMax];
284 };
285
286 static linker_stats_t linker_stats;
287
count_relocation(RelocationKind kind)288 void count_relocation(RelocationKind kind) {
289 ++linker_stats.count[kind];
290 }
291 #else
count_relocation(RelocationKind)292 void count_relocation(RelocationKind) {
293 }
294 #endif
295
296 #if COUNT_PAGES
297 uint32_t bitmask[4096];
298 #endif
299
300 static char __linker_dl_err_buf[768];
301
linker_get_error_buffer()302 char* linker_get_error_buffer() {
303 return &__linker_dl_err_buf[0];
304 }
305
linker_get_error_buffer_size()306 size_t linker_get_error_buffer_size() {
307 return sizeof(__linker_dl_err_buf);
308 }
309
notify_gdb_of_load(soinfo * info)310 static void notify_gdb_of_load(soinfo* info) {
311 if (info->is_linker() || info->is_main_executable()) {
312 // gdb already knows about the linker and the main executable.
313 return;
314 }
315
316 link_map* map = &(info->link_map_head);
317
318 map->l_addr = info->load_bias;
319 // link_map l_name field is not const.
320 map->l_name = const_cast<char*>(info->get_realpath());
321 map->l_ld = info->dynamic;
322
323 CHECK(map->l_name != nullptr);
324 CHECK(map->l_name[0] != '\0');
325
326 notify_gdb_of_load(map);
327 }
328
notify_gdb_of_unload(soinfo * info)329 static void notify_gdb_of_unload(soinfo* info) {
330 notify_gdb_of_unload(&(info->link_map_head));
331 }
332
is_accessible(const std::string & file)333 bool android_namespace_t::is_accessible(const std::string& file) {
334 if (!is_isolated_) {
335 return true;
336 }
337
338 for (const auto& dir : ld_library_paths_) {
339 if (file_is_in_dir(file, dir)) {
340 return true;
341 }
342 }
343
344 for (const auto& dir : default_library_paths_) {
345 if (file_is_in_dir(file, dir)) {
346 return true;
347 }
348 }
349
350 for (const auto& dir : permitted_paths_) {
351 if (file_is_under_dir(file, dir)) {
352 return true;
353 }
354 }
355
356 return false;
357 }
358
alloc()359 LinkedListEntry<soinfo>* SoinfoListAllocator::alloc() {
360 return g_soinfo_links_allocator.alloc();
361 }
362
free(LinkedListEntry<soinfo> * entry)363 void SoinfoListAllocator::free(LinkedListEntry<soinfo>* entry) {
364 g_soinfo_links_allocator.free(entry);
365 }
366
alloc()367 LinkedListEntry<android_namespace_t>* NamespaceListAllocator::alloc() {
368 return g_namespace_list_allocator.alloc();
369 }
370
free(LinkedListEntry<android_namespace_t> * entry)371 void NamespaceListAllocator::free(LinkedListEntry<android_namespace_t>* entry) {
372 g_namespace_list_allocator.free(entry);
373 }
374
soinfo_alloc(android_namespace_t * ns,const char * name,struct stat * file_stat,off64_t file_offset,uint32_t rtld_flags)375 static soinfo* soinfo_alloc(android_namespace_t* ns, const char* name,
376 struct stat* file_stat, off64_t file_offset,
377 uint32_t rtld_flags) {
378 if (strlen(name) >= PATH_MAX) {
379 DL_ERR("library name \"%s\" too long", name);
380 return nullptr;
381 }
382
383 soinfo* si = new (g_soinfo_allocator.alloc()) soinfo(ns, name, file_stat,
384 file_offset, rtld_flags);
385
386 sonext->next = si;
387 sonext = si;
388
389 si->generate_handle();
390 ns->add_soinfo(si);
391
392 TRACE("name %s: allocated soinfo @ %p", name, si);
393 return si;
394 }
395
soinfo_free(soinfo * si)396 static void soinfo_free(soinfo* si) {
397 if (si == nullptr) {
398 return;
399 }
400
401 if (si->base != 0 && si->size != 0) {
402 if (!si->is_mapped_by_caller()) {
403 munmap(reinterpret_cast<void*>(si->base), si->size);
404 } else {
405 // remap the region as PROT_NONE, MAP_ANONYMOUS | MAP_NORESERVE
406 mmap(reinterpret_cast<void*>(si->base), si->size, PROT_NONE,
407 MAP_FIXED | MAP_PRIVATE | MAP_ANONYMOUS | MAP_NORESERVE, -1, 0);
408 }
409 }
410
411 soinfo *prev = nullptr, *trav;
412
413 TRACE("name %s: freeing soinfo @ %p", si->get_realpath(), si);
414
415 for (trav = solist; trav != nullptr; trav = trav->next) {
416 if (trav == si) {
417 break;
418 }
419 prev = trav;
420 }
421
422 if (trav == nullptr) {
423 // si was not in solist
424 DL_ERR("name \"%s\"@%p is not in solist!", si->get_realpath(), si);
425 return;
426 }
427
428 // clear links to/from si
429 si->remove_all_links();
430
431 // prev will never be null, because the first entry in solist is
432 // always the static libdl_info.
433 prev->next = si->next;
434 if (si == sonext) {
435 sonext = prev;
436 }
437
438 si->~soinfo();
439 g_soinfo_allocator.free(si);
440 }
441
442 // For every path element this function checks of it exists, and is a directory,
443 // and normalizes it:
444 // 1. For regular path it converts it to realpath()
445 // 2. For path in a zip file it uses realpath on the zipfile
446 // normalizes entry name by calling normalize_path function.
resolve_paths(std::vector<std::string> & paths,std::vector<std::string> * resolved_paths)447 static void resolve_paths(std::vector<std::string>& paths,
448 std::vector<std::string>* resolved_paths) {
449 resolved_paths->clear();
450 for (const auto& path : paths) {
451 char resolved_path[PATH_MAX];
452 const char* original_path = path.c_str();
453 if (realpath(original_path, resolved_path) != nullptr) {
454 struct stat s;
455 if (stat(resolved_path, &s) == 0) {
456 if (S_ISDIR(s.st_mode)) {
457 resolved_paths->push_back(resolved_path);
458 } else {
459 DL_WARN("Warning: \"%s\" is not a directory (excluding from path)", resolved_path);
460 continue;
461 }
462 } else {
463 DL_WARN("Warning: cannot stat file \"%s\": %s", resolved_path, strerror(errno));
464 continue;
465 }
466 } else {
467 std::string zip_path;
468 std::string entry_path;
469
470 std::string normalized_path;
471
472 if (!normalize_path(original_path, &normalized_path)) {
473 DL_WARN("Warning: unable to normalize \"%s\"", original_path);
474 continue;
475 }
476
477 if (parse_zip_path(normalized_path.c_str(), &zip_path, &entry_path)) {
478 if (realpath(zip_path.c_str(), resolved_path) == nullptr) {
479 DL_WARN("Warning: unable to resolve \"%s\": %s", zip_path.c_str(), strerror(errno));
480 continue;
481 }
482
483 resolved_paths->push_back(std::string(resolved_path) + kZipFileSeparator + entry_path);
484 }
485 }
486 }
487 }
488
split_path(const char * path,const char * delimiters,std::vector<std::string> * paths)489 static void split_path(const char* path, const char* delimiters,
490 std::vector<std::string>* paths) {
491 if (path != nullptr && path[0] != 0) {
492 *paths = android::base::Split(path, delimiters);
493 }
494 }
495
parse_path(const char * path,const char * delimiters,std::vector<std::string> * resolved_paths)496 static void parse_path(const char* path, const char* delimiters,
497 std::vector<std::string>* resolved_paths) {
498 std::vector<std::string> paths;
499 split_path(path, delimiters, &paths);
500 resolve_paths(paths, resolved_paths);
501 }
502
parse_LD_LIBRARY_PATH(const char * path)503 static void parse_LD_LIBRARY_PATH(const char* path) {
504 std::vector<std::string> ld_libary_paths;
505 parse_path(path, ":", &ld_libary_paths);
506 g_default_namespace.set_ld_library_paths(std::move(ld_libary_paths));
507 }
508
set_dt_runpath(const char * path)509 void soinfo::set_dt_runpath(const char* path) {
510 if (!has_min_version(3)) {
511 return;
512 }
513
514 std::vector<std::string> runpaths;
515
516 split_path(path, ":", &runpaths);
517
518 std::string origin = dirname(get_realpath());
519 // FIXME: add $LIB and $PLATFORM.
520 std::pair<std::string, std::string> substs[] = {{"ORIGIN", origin}};
521 for (auto&& s : runpaths) {
522 size_t pos = 0;
523 while (pos < s.size()) {
524 pos = s.find("$", pos);
525 if (pos == std::string::npos) break;
526 for (const auto& subst : substs) {
527 const std::string& token = subst.first;
528 const std::string& replacement = subst.second;
529 if (s.substr(pos + 1, token.size()) == token) {
530 s.replace(pos, token.size() + 1, replacement);
531 // -1 to compensate for the ++pos below.
532 pos += replacement.size() - 1;
533 break;
534 } else if (s.substr(pos + 1, token.size() + 2) == "{" + token + "}") {
535 s.replace(pos, token.size() + 3, replacement);
536 pos += replacement.size() - 1;
537 break;
538 }
539 }
540 // Skip $ in case it did not match any of the known substitutions.
541 ++pos;
542 }
543 }
544
545 resolve_paths(runpaths, &dt_runpath_);
546 }
547
parse_LD_PRELOAD(const char * path)548 static void parse_LD_PRELOAD(const char* path) {
549 g_ld_preload_names.clear();
550 if (path != nullptr) {
551 // We have historically supported ':' as well as ' ' in LD_PRELOAD.
552 g_ld_preload_names = android::base::Split(path, " :");
553 std::remove_if(g_ld_preload_names.begin(),
554 g_ld_preload_names.end(),
555 [] (const std::string& s) { return s.empty(); });
556 }
557 }
558
realpath_fd(int fd,std::string * realpath)559 static bool realpath_fd(int fd, std::string* realpath) {
560 std::vector<char> buf(PATH_MAX), proc_self_fd(PATH_MAX);
561 __libc_format_buffer(&proc_self_fd[0], proc_self_fd.size(), "/proc/self/fd/%d", fd);
562 if (readlink(&proc_self_fd[0], &buf[0], buf.size()) == -1) {
563 PRINT("readlink(\"%s\") failed: %s [fd=%d]", &proc_self_fd[0], strerror(errno), fd);
564 return false;
565 }
566
567 *realpath = &buf[0];
568 return true;
569 }
570
571 #if defined(__arm__)
572
573 // For a given PC, find the .so that it belongs to.
574 // Returns the base address of the .ARM.exidx section
575 // for that .so, and the number of 8-byte entries
576 // in that section (via *pcount).
577 //
578 // Intended to be called by libc's __gnu_Unwind_Find_exidx().
579 //
580 // This function is exposed via dlfcn.cpp and libdl.so.
dl_unwind_find_exidx(_Unwind_Ptr pc,int * pcount)581 _Unwind_Ptr dl_unwind_find_exidx(_Unwind_Ptr pc, int* pcount) {
582 uintptr_t addr = reinterpret_cast<uintptr_t>(pc);
583
584 for (soinfo* si = solist; si != 0; si = si->next) {
585 if ((addr >= si->base) && (addr < (si->base + si->size))) {
586 *pcount = si->ARM_exidx_count;
587 return reinterpret_cast<_Unwind_Ptr>(si->ARM_exidx);
588 }
589 }
590 *pcount = 0;
591 return nullptr;
592 }
593
594 #endif
595
596 // Here, we only have to provide a callback to iterate across all the
597 // loaded libraries. gcc_eh does the rest.
do_dl_iterate_phdr(int (* cb)(dl_phdr_info * info,size_t size,void * data),void * data)598 int do_dl_iterate_phdr(int (*cb)(dl_phdr_info* info, size_t size, void* data), void* data) {
599 int rv = 0;
600 for (soinfo* si = solist; si != nullptr; si = si->next) {
601 dl_phdr_info dl_info;
602 dl_info.dlpi_addr = si->link_map_head.l_addr;
603 dl_info.dlpi_name = si->link_map_head.l_name;
604 dl_info.dlpi_phdr = si->phdr;
605 dl_info.dlpi_phnum = si->phnum;
606 rv = cb(&dl_info, sizeof(dl_phdr_info), data);
607 if (rv != 0) {
608 break;
609 }
610 }
611 return rv;
612 }
613
ElfW(Versym)614 const ElfW(Versym)* soinfo::get_versym(size_t n) const {
615 if (has_min_version(2) && versym_ != nullptr) {
616 return versym_ + n;
617 }
618
619 return nullptr;
620 }
621
ElfW(Addr)622 ElfW(Addr) soinfo::get_verneed_ptr() const {
623 if (has_min_version(2)) {
624 return verneed_ptr_;
625 }
626
627 return 0;
628 }
629
get_verneed_cnt() const630 size_t soinfo::get_verneed_cnt() const {
631 if (has_min_version(2)) {
632 return verneed_cnt_;
633 }
634
635 return 0;
636 }
637
ElfW(Addr)638 ElfW(Addr) soinfo::get_verdef_ptr() const {
639 if (has_min_version(2)) {
640 return verdef_ptr_;
641 }
642
643 return 0;
644 }
645
get_verdef_cnt() const646 size_t soinfo::get_verdef_cnt() const {
647 if (has_min_version(2)) {
648 return verdef_cnt_;
649 }
650
651 return 0;
652 }
653
654 template<typename F>
for_each_verdef(const soinfo * si,F functor)655 static bool for_each_verdef(const soinfo* si, F functor) {
656 if (!si->has_min_version(2)) {
657 return true;
658 }
659
660 uintptr_t verdef_ptr = si->get_verdef_ptr();
661 if (verdef_ptr == 0) {
662 return true;
663 }
664
665 size_t offset = 0;
666
667 size_t verdef_cnt = si->get_verdef_cnt();
668 for (size_t i = 0; i<verdef_cnt; ++i) {
669 const ElfW(Verdef)* verdef = reinterpret_cast<ElfW(Verdef)*>(verdef_ptr + offset);
670 size_t verdaux_offset = offset + verdef->vd_aux;
671 offset += verdef->vd_next;
672
673 if (verdef->vd_version != 1) {
674 DL_ERR("unsupported verdef[%zd] vd_version: %d (expected 1) library: %s",
675 i, verdef->vd_version, si->get_realpath());
676 return false;
677 }
678
679 if ((verdef->vd_flags & VER_FLG_BASE) != 0) {
680 // "this is the version of the file itself. It must not be used for
681 // matching a symbol. It can be used to match references."
682 //
683 // http://www.akkadia.org/drepper/symbol-versioning
684 continue;
685 }
686
687 if (verdef->vd_cnt == 0) {
688 DL_ERR("invalid verdef[%zd] vd_cnt == 0 (version without a name)", i);
689 return false;
690 }
691
692 const ElfW(Verdaux)* verdaux = reinterpret_cast<ElfW(Verdaux)*>(verdef_ptr + verdaux_offset);
693
694 if (functor(i, verdef, verdaux) == true) {
695 break;
696 }
697 }
698
699 return true;
700 }
701
find_verdef_version_index(const version_info * vi,ElfW (Versym)* versym) const702 bool soinfo::find_verdef_version_index(const version_info* vi, ElfW(Versym)* versym) const {
703 if (vi == nullptr) {
704 *versym = kVersymNotNeeded;
705 return true;
706 }
707
708 *versym = kVersymGlobal;
709
710 return for_each_verdef(this,
711 [&](size_t, const ElfW(Verdef)* verdef, const ElfW(Verdaux)* verdaux) {
712 if (verdef->vd_hash == vi->elf_hash &&
713 strcmp(vi->name, get_string(verdaux->vda_name)) == 0) {
714 *versym = verdef->vd_ndx;
715 return true;
716 }
717
718 return false;
719 }
720 );
721 }
722
find_symbol_by_name(SymbolName & symbol_name,const version_info * vi,const ElfW (Sym)** symbol) const723 bool soinfo::find_symbol_by_name(SymbolName& symbol_name,
724 const version_info* vi,
725 const ElfW(Sym)** symbol) const {
726 uint32_t symbol_index;
727 bool success =
728 is_gnu_hash() ?
729 gnu_lookup(symbol_name, vi, &symbol_index) :
730 elf_lookup(symbol_name, vi, &symbol_index);
731
732 if (success) {
733 *symbol = symbol_index == 0 ? nullptr : symtab_ + symbol_index;
734 }
735
736 return success;
737 }
738
is_symbol_global_and_defined(const soinfo * si,const ElfW (Sym)* s)739 static bool is_symbol_global_and_defined(const soinfo* si, const ElfW(Sym)* s) {
740 if (ELF_ST_BIND(s->st_info) == STB_GLOBAL ||
741 ELF_ST_BIND(s->st_info) == STB_WEAK) {
742 return s->st_shndx != SHN_UNDEF;
743 } else if (ELF_ST_BIND(s->st_info) != STB_LOCAL) {
744 DL_WARN("unexpected ST_BIND value: %d for \"%s\" in \"%s\"",
745 ELF_ST_BIND(s->st_info), si->get_string(s->st_name), si->get_realpath());
746 }
747
748 return false;
749 }
750
751 static const ElfW(Versym) kVersymHiddenBit = 0x8000;
752
is_versym_hidden(const ElfW (Versym)* versym)753 static inline bool is_versym_hidden(const ElfW(Versym)* versym) {
754 // the symbol is hidden if bit 15 of versym is set.
755 return versym != nullptr && (*versym & kVersymHiddenBit) != 0;
756 }
757
check_symbol_version(const ElfW (Versym)verneed,const ElfW (Versym)* verdef)758 static inline bool check_symbol_version(const ElfW(Versym) verneed,
759 const ElfW(Versym)* verdef) {
760 return verneed == kVersymNotNeeded ||
761 verdef == nullptr ||
762 verneed == (*verdef & ~kVersymHiddenBit);
763 }
764
gnu_lookup(SymbolName & symbol_name,const version_info * vi,uint32_t * symbol_index) const765 bool soinfo::gnu_lookup(SymbolName& symbol_name,
766 const version_info* vi,
767 uint32_t* symbol_index) const {
768 uint32_t hash = symbol_name.gnu_hash();
769 uint32_t h2 = hash >> gnu_shift2_;
770
771 uint32_t bloom_mask_bits = sizeof(ElfW(Addr))*8;
772 uint32_t word_num = (hash / bloom_mask_bits) & gnu_maskwords_;
773 ElfW(Addr) bloom_word = gnu_bloom_filter_[word_num];
774
775 *symbol_index = 0;
776
777 TRACE_TYPE(LOOKUP, "SEARCH %s in %s@%p (gnu)",
778 symbol_name.get_name(), get_realpath(), reinterpret_cast<void*>(base));
779
780 // test against bloom filter
781 if ((1 & (bloom_word >> (hash % bloom_mask_bits)) & (bloom_word >> (h2 % bloom_mask_bits))) == 0) {
782 TRACE_TYPE(LOOKUP, "NOT FOUND %s in %s@%p",
783 symbol_name.get_name(), get_realpath(), reinterpret_cast<void*>(base));
784
785 return true;
786 }
787
788 // bloom test says "probably yes"...
789 uint32_t n = gnu_bucket_[hash % gnu_nbucket_];
790
791 if (n == 0) {
792 TRACE_TYPE(LOOKUP, "NOT FOUND %s in %s@%p",
793 symbol_name.get_name(), get_realpath(), reinterpret_cast<void*>(base));
794
795 return true;
796 }
797
798 // lookup versym for the version definition in this library
799 // note the difference between "version is not requested" (vi == nullptr)
800 // and "version not found". In the first case verneed is kVersymNotNeeded
801 // which implies that the default version can be accepted; the second case results in
802 // verneed = 1 (kVersymGlobal) and implies that we should ignore versioned symbols
803 // for this library and consider only *global* ones.
804 ElfW(Versym) verneed = 0;
805 if (!find_verdef_version_index(vi, &verneed)) {
806 return false;
807 }
808
809 do {
810 ElfW(Sym)* s = symtab_ + n;
811 const ElfW(Versym)* verdef = get_versym(n);
812 // skip hidden versions when verneed == kVersymNotNeeded (0)
813 if (verneed == kVersymNotNeeded && is_versym_hidden(verdef)) {
814 continue;
815 }
816 if (((gnu_chain_[n] ^ hash) >> 1) == 0 &&
817 check_symbol_version(verneed, verdef) &&
818 strcmp(get_string(s->st_name), symbol_name.get_name()) == 0 &&
819 is_symbol_global_and_defined(this, s)) {
820 TRACE_TYPE(LOOKUP, "FOUND %s in %s (%p) %zd",
821 symbol_name.get_name(), get_realpath(), reinterpret_cast<void*>(s->st_value),
822 static_cast<size_t>(s->st_size));
823 *symbol_index = n;
824 return true;
825 }
826 } while ((gnu_chain_[n++] & 1) == 0);
827
828 TRACE_TYPE(LOOKUP, "NOT FOUND %s in %s@%p",
829 symbol_name.get_name(), get_realpath(), reinterpret_cast<void*>(base));
830
831 return true;
832 }
833
elf_lookup(SymbolName & symbol_name,const version_info * vi,uint32_t * symbol_index) const834 bool soinfo::elf_lookup(SymbolName& symbol_name,
835 const version_info* vi,
836 uint32_t* symbol_index) const {
837 uint32_t hash = symbol_name.elf_hash();
838
839 TRACE_TYPE(LOOKUP, "SEARCH %s in %s@%p h=%x(elf) %zd",
840 symbol_name.get_name(), get_realpath(),
841 reinterpret_cast<void*>(base), hash, hash % nbucket_);
842
843 ElfW(Versym) verneed = 0;
844 if (!find_verdef_version_index(vi, &verneed)) {
845 return false;
846 }
847
848 for (uint32_t n = bucket_[hash % nbucket_]; n != 0; n = chain_[n]) {
849 ElfW(Sym)* s = symtab_ + n;
850 const ElfW(Versym)* verdef = get_versym(n);
851
852 // skip hidden versions when verneed == 0
853 if (verneed == kVersymNotNeeded && is_versym_hidden(verdef)) {
854 continue;
855 }
856
857 if (check_symbol_version(verneed, verdef) &&
858 strcmp(get_string(s->st_name), symbol_name.get_name()) == 0 &&
859 is_symbol_global_and_defined(this, s)) {
860 TRACE_TYPE(LOOKUP, "FOUND %s in %s (%p) %zd",
861 symbol_name.get_name(), get_realpath(),
862 reinterpret_cast<void*>(s->st_value),
863 static_cast<size_t>(s->st_size));
864 *symbol_index = n;
865 return true;
866 }
867 }
868
869 TRACE_TYPE(LOOKUP, "NOT FOUND %s in %s@%p %x %zd",
870 symbol_name.get_name(), get_realpath(),
871 reinterpret_cast<void*>(base), hash, hash % nbucket_);
872
873 *symbol_index = 0;
874 return true;
875 }
876
soinfo(android_namespace_t * ns,const char * realpath,const struct stat * file_stat,off64_t file_offset,int rtld_flags)877 soinfo::soinfo(android_namespace_t* ns, const char* realpath,
878 const struct stat* file_stat, off64_t file_offset,
879 int rtld_flags) {
880 memset(this, 0, sizeof(*this));
881
882 if (realpath != nullptr) {
883 realpath_ = realpath;
884 }
885
886 flags_ = FLAG_NEW_SOINFO;
887 version_ = SOINFO_VERSION;
888
889 if (file_stat != nullptr) {
890 this->st_dev_ = file_stat->st_dev;
891 this->st_ino_ = file_stat->st_ino;
892 this->file_offset_ = file_offset;
893 }
894
895 this->rtld_flags_ = rtld_flags;
896 this->primary_namespace_ = ns;
897 }
898
~soinfo()899 soinfo::~soinfo() {
900 g_soinfo_handles_map.erase(handle_);
901 }
902
calculate_elf_hash(const char * name)903 static uint32_t calculate_elf_hash(const char* name) {
904 const uint8_t* name_bytes = reinterpret_cast<const uint8_t*>(name);
905 uint32_t h = 0, g;
906
907 while (*name_bytes) {
908 h = (h << 4) + *name_bytes++;
909 g = h & 0xf0000000;
910 h ^= g;
911 h ^= g >> 24;
912 }
913
914 return h;
915 }
916
elf_hash()917 uint32_t SymbolName::elf_hash() {
918 if (!has_elf_hash_) {
919 elf_hash_ = calculate_elf_hash(name_);
920 has_elf_hash_ = true;
921 }
922
923 return elf_hash_;
924 }
925
gnu_hash()926 uint32_t SymbolName::gnu_hash() {
927 if (!has_gnu_hash_) {
928 uint32_t h = 5381;
929 const uint8_t* name = reinterpret_cast<const uint8_t*>(name_);
930 while (*name != 0) {
931 h += (h << 5) + *name++; // h*33 + c = h + h * 32 + c = h + h << 5 + c
932 }
933
934 gnu_hash_ = h;
935 has_gnu_hash_ = true;
936 }
937
938 return gnu_hash_;
939 }
940
soinfo_do_lookup(soinfo * si_from,const char * name,const version_info * vi,soinfo ** si_found_in,const soinfo::soinfo_list_t & global_group,const soinfo::soinfo_list_t & local_group,const ElfW (Sym)** symbol)941 bool soinfo_do_lookup(soinfo* si_from, const char* name, const version_info* vi,
942 soinfo** si_found_in, const soinfo::soinfo_list_t& global_group,
943 const soinfo::soinfo_list_t& local_group, const ElfW(Sym)** symbol) {
944 SymbolName symbol_name(name);
945 const ElfW(Sym)* s = nullptr;
946
947 /* "This element's presence in a shared object library alters the dynamic linker's
948 * symbol resolution algorithm for references within the library. Instead of starting
949 * a symbol search with the executable file, the dynamic linker starts from the shared
950 * object itself. If the shared object fails to supply the referenced symbol, the
951 * dynamic linker then searches the executable file and other shared objects as usual."
952 *
953 * http://www.sco.com/developers/gabi/2012-12-31/ch5.dynamic.html
954 *
955 * Note that this is unlikely since static linker avoids generating
956 * relocations for -Bsymbolic linked dynamic executables.
957 */
958 if (si_from->has_DT_SYMBOLIC) {
959 DEBUG("%s: looking up %s in local scope (DT_SYMBOLIC)", si_from->get_realpath(), name);
960 if (!si_from->find_symbol_by_name(symbol_name, vi, &s)) {
961 return false;
962 }
963
964 if (s != nullptr) {
965 *si_found_in = si_from;
966 }
967 }
968
969 // 1. Look for it in global_group
970 if (s == nullptr) {
971 bool error = false;
972 global_group.visit([&](soinfo* global_si) {
973 DEBUG("%s: looking up %s in %s (from global group)",
974 si_from->get_realpath(), name, global_si->get_realpath());
975 if (!global_si->find_symbol_by_name(symbol_name, vi, &s)) {
976 error = true;
977 return false;
978 }
979
980 if (s != nullptr) {
981 *si_found_in = global_si;
982 return false;
983 }
984
985 return true;
986 });
987
988 if (error) {
989 return false;
990 }
991 }
992
993 // 2. Look for it in the local group
994 if (s == nullptr) {
995 bool error = false;
996 local_group.visit([&](soinfo* local_si) {
997 if (local_si == si_from && si_from->has_DT_SYMBOLIC) {
998 // we already did this - skip
999 return true;
1000 }
1001
1002 DEBUG("%s: looking up %s in %s (from local group)",
1003 si_from->get_realpath(), name, local_si->get_realpath());
1004 if (!local_si->find_symbol_by_name(symbol_name, vi, &s)) {
1005 error = true;
1006 return false;
1007 }
1008
1009 if (s != nullptr) {
1010 *si_found_in = local_si;
1011 return false;
1012 }
1013
1014 return true;
1015 });
1016
1017 if (error) {
1018 return false;
1019 }
1020 }
1021
1022 if (s != nullptr) {
1023 TRACE_TYPE(LOOKUP, "si %s sym %s s->st_value = %p, "
1024 "found in %s, base = %p, load bias = %p",
1025 si_from->get_realpath(), name, reinterpret_cast<void*>(s->st_value),
1026 (*si_found_in)->get_realpath(), reinterpret_cast<void*>((*si_found_in)->base),
1027 reinterpret_cast<void*>((*si_found_in)->load_bias));
1028 }
1029
1030 *symbol = s;
1031 return true;
1032 }
1033
1034 class ProtectedDataGuard {
1035 public:
ProtectedDataGuard()1036 ProtectedDataGuard() {
1037 if (ref_count_++ == 0) {
1038 protect_data(PROT_READ | PROT_WRITE);
1039 }
1040 }
1041
~ProtectedDataGuard()1042 ~ProtectedDataGuard() {
1043 if (ref_count_ == 0) { // overflow
1044 __libc_fatal("Too many nested calls to dlopen()");
1045 }
1046
1047 if (--ref_count_ == 0) {
1048 protect_data(PROT_READ);
1049 }
1050 }
1051 private:
protect_data(int protection)1052 void protect_data(int protection) {
1053 g_soinfo_allocator.protect_all(protection);
1054 g_soinfo_links_allocator.protect_all(protection);
1055 g_namespace_allocator.protect_all(protection);
1056 g_namespace_list_allocator.protect_all(protection);
1057 }
1058
1059 static size_t ref_count_;
1060 };
1061
1062 size_t ProtectedDataGuard::ref_count_ = 0;
1063
1064 // Each size has it's own allocator.
1065 template<size_t size>
1066 class SizeBasedAllocator {
1067 public:
alloc()1068 static void* alloc() {
1069 return allocator_.alloc();
1070 }
1071
free(void * ptr)1072 static void free(void* ptr) {
1073 allocator_.free(ptr);
1074 }
1075
1076 private:
1077 static LinkerBlockAllocator allocator_;
1078 };
1079
1080 template<size_t size>
1081 LinkerBlockAllocator SizeBasedAllocator<size>::allocator_(size);
1082
1083 template<typename T>
1084 class TypeBasedAllocator {
1085 public:
alloc()1086 static T* alloc() {
1087 return reinterpret_cast<T*>(SizeBasedAllocator<sizeof(T)>::alloc());
1088 }
1089
free(T * ptr)1090 static void free(T* ptr) {
1091 SizeBasedAllocator<sizeof(T)>::free(ptr);
1092 }
1093 };
1094
1095 class LoadTask {
1096 public:
1097 struct deleter_t {
operator ()LoadTask::deleter_t1098 void operator()(LoadTask* t) {
1099 t->~LoadTask();
1100 TypeBasedAllocator<LoadTask>::free(t);
1101 }
1102 };
1103
1104 static deleter_t deleter;
1105
create(const char * name,soinfo * needed_by,std::unordered_map<const soinfo *,ElfReader> * readers_map)1106 static LoadTask* create(const char* name, soinfo* needed_by,
1107 std::unordered_map<const soinfo*, ElfReader>* readers_map) {
1108 LoadTask* ptr = TypeBasedAllocator<LoadTask>::alloc();
1109 return new (ptr) LoadTask(name, needed_by, readers_map);
1110 }
1111
get_name() const1112 const char* get_name() const {
1113 return name_;
1114 }
1115
get_needed_by() const1116 soinfo* get_needed_by() const {
1117 return needed_by_;
1118 }
1119
get_soinfo() const1120 soinfo* get_soinfo() const {
1121 return si_;
1122 }
1123
set_soinfo(soinfo * si)1124 void set_soinfo(soinfo* si) {
1125 si_ = si;
1126 }
1127
get_file_offset() const1128 off64_t get_file_offset() const {
1129 return file_offset_;
1130 }
1131
set_file_offset(off64_t offset)1132 void set_file_offset(off64_t offset) {
1133 file_offset_ = offset;
1134 }
1135
get_fd() const1136 int get_fd() const {
1137 return fd_;
1138 }
1139
set_fd(int fd,bool assume_ownership)1140 void set_fd(int fd, bool assume_ownership) {
1141 fd_ = fd;
1142 close_fd_ = assume_ownership;
1143 }
1144
get_extinfo() const1145 const android_dlextinfo* get_extinfo() const {
1146 return extinfo_;
1147 }
1148
set_extinfo(const android_dlextinfo * extinfo)1149 void set_extinfo(const android_dlextinfo* extinfo) {
1150 extinfo_ = extinfo;
1151 }
1152
is_dt_needed() const1153 bool is_dt_needed() const {
1154 return is_dt_needed_;
1155 }
1156
set_dt_needed(bool is_dt_needed)1157 void set_dt_needed(bool is_dt_needed) {
1158 is_dt_needed_ = is_dt_needed;
1159 }
1160
get_elf_reader() const1161 const ElfReader& get_elf_reader() const {
1162 CHECK(si_ != nullptr);
1163 return (*elf_readers_map_)[si_];
1164 }
1165
get_elf_reader()1166 ElfReader& get_elf_reader() {
1167 CHECK(si_ != nullptr);
1168 return (*elf_readers_map_)[si_];
1169 }
1170
get_readers_map()1171 std::unordered_map<const soinfo*, ElfReader>* get_readers_map() {
1172 return elf_readers_map_;
1173 }
1174
read(const char * realpath,off64_t file_size)1175 bool read(const char* realpath, off64_t file_size) {
1176 ElfReader& elf_reader = get_elf_reader();
1177 return elf_reader.Read(realpath, fd_, file_offset_, file_size);
1178 }
1179
load()1180 bool load() {
1181 ElfReader& elf_reader = get_elf_reader();
1182 if (!elf_reader.Load(extinfo_)) {
1183 return false;
1184 }
1185
1186 si_->base = elf_reader.load_start();
1187 si_->size = elf_reader.load_size();
1188 si_->set_mapped_by_caller(elf_reader.is_mapped_by_caller());
1189 si_->load_bias = elf_reader.load_bias();
1190 si_->phnum = elf_reader.phdr_count();
1191 si_->phdr = elf_reader.loaded_phdr();
1192
1193 return true;
1194 }
1195
1196 private:
LoadTask(const char * name,soinfo * needed_by,std::unordered_map<const soinfo *,ElfReader> * readers_map)1197 LoadTask(const char* name, soinfo* needed_by,
1198 std::unordered_map<const soinfo*, ElfReader>* readers_map)
1199 : name_(name), needed_by_(needed_by), si_(nullptr),
1200 fd_(-1), close_fd_(false), file_offset_(0), elf_readers_map_(readers_map),
1201 is_dt_needed_(false) {}
1202
~LoadTask()1203 ~LoadTask() {
1204 if (fd_ != -1 && close_fd_) {
1205 close(fd_);
1206 }
1207 }
1208
1209 const char* name_;
1210 soinfo* needed_by_;
1211 soinfo* si_;
1212 const android_dlextinfo* extinfo_;
1213 int fd_;
1214 bool close_fd_;
1215 off64_t file_offset_;
1216 std::unordered_map<const soinfo*, ElfReader>* elf_readers_map_;
1217 // TODO(dimitry): needed by workaround for http://b/26394120 (the grey-list)
1218 bool is_dt_needed_;
1219 // END OF WORKAROUND
1220
1221 DISALLOW_IMPLICIT_CONSTRUCTORS(LoadTask);
1222 };
1223
1224 LoadTask::deleter_t LoadTask::deleter;
1225
1226 template <typename T>
1227 using linked_list_t = LinkedList<T, TypeBasedAllocator<LinkedListEntry<T>>>;
1228
1229 typedef linked_list_t<soinfo> SoinfoLinkedList;
1230 typedef linked_list_t<const char> StringLinkedList;
1231 typedef std::vector<LoadTask*> LoadTaskList;
1232
1233
1234 // This function walks down the tree of soinfo dependencies
1235 // in breadth-first order and
1236 // * calls action(soinfo* si) for each node, and
1237 // * terminates walk if action returns false.
1238 //
1239 // walk_dependencies_tree returns false if walk was terminated
1240 // by the action and true otherwise.
1241 template<typename F>
walk_dependencies_tree(soinfo * root_soinfos[],size_t root_soinfos_size,F action)1242 static bool walk_dependencies_tree(soinfo* root_soinfos[], size_t root_soinfos_size, F action) {
1243 SoinfoLinkedList visit_list;
1244 SoinfoLinkedList visited;
1245
1246 for (size_t i = 0; i < root_soinfos_size; ++i) {
1247 visit_list.push_back(root_soinfos[i]);
1248 }
1249
1250 soinfo* si;
1251 while ((si = visit_list.pop_front()) != nullptr) {
1252 if (visited.contains(si)) {
1253 continue;
1254 }
1255
1256 if (!action(si)) {
1257 return false;
1258 }
1259
1260 visited.push_back(si);
1261
1262 si->get_children().for_each([&](soinfo* child) {
1263 visit_list.push_back(child);
1264 });
1265 }
1266
1267 return true;
1268 }
1269
1270
ElfW(Sym)1271 static const ElfW(Sym)* dlsym_handle_lookup(soinfo* root, soinfo* skip_until,
1272 soinfo** found, SymbolName& symbol_name,
1273 const version_info* vi) {
1274 const ElfW(Sym)* result = nullptr;
1275 bool skip_lookup = skip_until != nullptr;
1276
1277 walk_dependencies_tree(&root, 1, [&](soinfo* current_soinfo) {
1278 if (skip_lookup) {
1279 skip_lookup = current_soinfo != skip_until;
1280 return true;
1281 }
1282
1283 if (!current_soinfo->find_symbol_by_name(symbol_name, vi, &result)) {
1284 result = nullptr;
1285 return false;
1286 }
1287
1288 if (result != nullptr) {
1289 *found = current_soinfo;
1290 return false;
1291 }
1292
1293 return true;
1294 });
1295
1296 return result;
1297 }
1298
1299 static const ElfW(Sym)* dlsym_linear_lookup(android_namespace_t* ns,
1300 const char* name,
1301 const version_info* vi,
1302 soinfo** found,
1303 soinfo* caller,
1304 void* handle);
1305
1306 // This is used by dlsym(3). It performs symbol lookup only within the
1307 // specified soinfo object and its dependencies in breadth first order.
ElfW(Sym)1308 static const ElfW(Sym)* dlsym_handle_lookup(soinfo* si, soinfo** found,
1309 const char* name, const version_info* vi) {
1310 // According to man dlopen(3) and posix docs in the case when si is handle
1311 // of the main executable we need to search not only in the executable and its
1312 // dependencies but also in all libraries loaded with RTLD_GLOBAL.
1313 //
1314 // Since RTLD_GLOBAL is always set for the main executable and all dt_needed shared
1315 // libraries and they are loaded in breath-first (correct) order we can just execute
1316 // dlsym(RTLD_DEFAULT, ...); instead of doing two stage lookup.
1317 if (si == somain) {
1318 return dlsym_linear_lookup(&g_default_namespace, name, vi, found, nullptr, RTLD_DEFAULT);
1319 }
1320
1321 SymbolName symbol_name(name);
1322 return dlsym_handle_lookup(si, nullptr, found, symbol_name, vi);
1323 }
1324
1325 /* This is used by dlsym(3) to performs a global symbol lookup. If the
1326 start value is null (for RTLD_DEFAULT), the search starts at the
1327 beginning of the global solist. Otherwise the search starts at the
1328 specified soinfo (for RTLD_NEXT).
1329 */
ElfW(Sym)1330 static const ElfW(Sym)* dlsym_linear_lookup(android_namespace_t* ns,
1331 const char* name,
1332 const version_info* vi,
1333 soinfo** found,
1334 soinfo* caller,
1335 void* handle) {
1336 SymbolName symbol_name(name);
1337
1338 auto& soinfo_list = ns->soinfo_list();
1339 auto start = soinfo_list.begin();
1340
1341 if (handle == RTLD_NEXT) {
1342 if (caller == nullptr) {
1343 return nullptr;
1344 } else {
1345 auto it = soinfo_list.find(caller);
1346 CHECK (it != soinfo_list.end());
1347 start = ++it;
1348 }
1349 }
1350
1351 const ElfW(Sym)* s = nullptr;
1352 for (auto it = start, end = soinfo_list.end(); it != end; ++it) {
1353 soinfo* si = *it;
1354 // Do not skip RTLD_LOCAL libraries in dlsym(RTLD_DEFAULT, ...)
1355 // if the library is opened by application with target api level <= 22
1356 // See http://b/21565766
1357 if ((si->get_rtld_flags() & RTLD_GLOBAL) == 0 && si->get_target_sdk_version() > 22) {
1358 continue;
1359 }
1360
1361 if (!si->find_symbol_by_name(symbol_name, vi, &s)) {
1362 return nullptr;
1363 }
1364
1365 if (s != nullptr) {
1366 *found = si;
1367 break;
1368 }
1369 }
1370
1371 // If not found - use dlsym_handle_lookup for caller's
1372 // local_group unless it is part of the global group in which
1373 // case we already did it.
1374 if (s == nullptr && caller != nullptr &&
1375 (caller->get_rtld_flags() & RTLD_GLOBAL) == 0) {
1376 return dlsym_handle_lookup(caller->get_local_group_root(),
1377 (handle == RTLD_NEXT) ? caller : nullptr, found, symbol_name, vi);
1378 }
1379
1380 if (s != nullptr) {
1381 TRACE_TYPE(LOOKUP, "%s s->st_value = %p, found->base = %p",
1382 name, reinterpret_cast<void*>(s->st_value), reinterpret_cast<void*>((*found)->base));
1383 }
1384
1385 return s;
1386 }
1387
find_containing_library(const void * p)1388 soinfo* find_containing_library(const void* p) {
1389 ElfW(Addr) address = reinterpret_cast<ElfW(Addr)>(p);
1390 for (soinfo* si = solist; si != nullptr; si = si->next) {
1391 if (address >= si->base && address - si->base < si->size) {
1392 return si;
1393 }
1394 }
1395 return nullptr;
1396 }
1397
ElfW(Sym)1398 ElfW(Sym)* soinfo::find_symbol_by_address(const void* addr) {
1399 return is_gnu_hash() ? gnu_addr_lookup(addr) : elf_addr_lookup(addr);
1400 }
1401
symbol_matches_soaddr(const ElfW (Sym)* sym,ElfW (Addr)soaddr)1402 static bool symbol_matches_soaddr(const ElfW(Sym)* sym, ElfW(Addr) soaddr) {
1403 return sym->st_shndx != SHN_UNDEF &&
1404 soaddr >= sym->st_value &&
1405 soaddr < sym->st_value + sym->st_size;
1406 }
1407
ElfW(Sym)1408 ElfW(Sym)* soinfo::gnu_addr_lookup(const void* addr) {
1409 ElfW(Addr) soaddr = reinterpret_cast<ElfW(Addr)>(addr) - load_bias;
1410
1411 for (size_t i = 0; i < gnu_nbucket_; ++i) {
1412 uint32_t n = gnu_bucket_[i];
1413
1414 if (n == 0) {
1415 continue;
1416 }
1417
1418 do {
1419 ElfW(Sym)* sym = symtab_ + n;
1420 if (symbol_matches_soaddr(sym, soaddr)) {
1421 return sym;
1422 }
1423 } while ((gnu_chain_[n++] & 1) == 0);
1424 }
1425
1426 return nullptr;
1427 }
1428
ElfW(Sym)1429 ElfW(Sym)* soinfo::elf_addr_lookup(const void* addr) {
1430 ElfW(Addr) soaddr = reinterpret_cast<ElfW(Addr)>(addr) - load_bias;
1431
1432 // Search the library's symbol table for any defined symbol which
1433 // contains this address.
1434 for (size_t i = 0; i < nchain_; ++i) {
1435 ElfW(Sym)* sym = symtab_ + i;
1436 if (symbol_matches_soaddr(sym, soaddr)) {
1437 return sym;
1438 }
1439 }
1440
1441 return nullptr;
1442 }
1443
1444 class ZipArchiveCache {
1445 public:
ZipArchiveCache()1446 ZipArchiveCache() {}
1447 ~ZipArchiveCache();
1448
1449 bool get_or_open(const char* zip_path, ZipArchiveHandle* handle);
1450 private:
1451 DISALLOW_COPY_AND_ASSIGN(ZipArchiveCache);
1452
1453 std::unordered_map<std::string, ZipArchiveHandle> cache_;
1454 };
1455
get_or_open(const char * zip_path,ZipArchiveHandle * handle)1456 bool ZipArchiveCache::get_or_open(const char* zip_path, ZipArchiveHandle* handle) {
1457 std::string key(zip_path);
1458
1459 auto it = cache_.find(key);
1460 if (it != cache_.end()) {
1461 *handle = it->second;
1462 return true;
1463 }
1464
1465 int fd = TEMP_FAILURE_RETRY(open(zip_path, O_RDONLY | O_CLOEXEC));
1466 if (fd == -1) {
1467 return false;
1468 }
1469
1470 if (OpenArchiveFd(fd, "", handle) != 0) {
1471 // invalid zip-file (?)
1472 CloseArchive(handle);
1473 close(fd);
1474 return false;
1475 }
1476
1477 cache_[key] = *handle;
1478 return true;
1479 }
1480
~ZipArchiveCache()1481 ZipArchiveCache::~ZipArchiveCache() {
1482 for (const auto& it : cache_) {
1483 CloseArchive(it.second);
1484 }
1485 }
1486
open_library_in_zipfile(ZipArchiveCache * zip_archive_cache,const char * const input_path,off64_t * file_offset,std::string * realpath)1487 static int open_library_in_zipfile(ZipArchiveCache* zip_archive_cache,
1488 const char* const input_path,
1489 off64_t* file_offset, std::string* realpath) {
1490 std::string normalized_path;
1491 if (!normalize_path(input_path, &normalized_path)) {
1492 return -1;
1493 }
1494
1495 const char* const path = normalized_path.c_str();
1496 TRACE("Trying zip file open from path \"%s\" -> normalized \"%s\"", input_path, path);
1497
1498 // Treat an '!/' separator inside a path as the separator between the name
1499 // of the zip file on disk and the subdirectory to search within it.
1500 // For example, if path is "foo.zip!/bar/bas/x.so", then we search for
1501 // "bar/bas/x.so" within "foo.zip".
1502 const char* const separator = strstr(path, kZipFileSeparator);
1503 if (separator == nullptr) {
1504 return -1;
1505 }
1506
1507 char buf[512];
1508 if (strlcpy(buf, path, sizeof(buf)) >= sizeof(buf)) {
1509 PRINT("Warning: ignoring very long library path: %s", path);
1510 return -1;
1511 }
1512
1513 buf[separator - path] = '\0';
1514
1515 const char* zip_path = buf;
1516 const char* file_path = &buf[separator - path + 2];
1517 int fd = TEMP_FAILURE_RETRY(open(zip_path, O_RDONLY | O_CLOEXEC));
1518 if (fd == -1) {
1519 return -1;
1520 }
1521
1522 ZipArchiveHandle handle;
1523 if (!zip_archive_cache->get_or_open(zip_path, &handle)) {
1524 // invalid zip-file (?)
1525 close(fd);
1526 return -1;
1527 }
1528
1529 ZipEntry entry;
1530
1531 if (FindEntry(handle, ZipString(file_path), &entry) != 0) {
1532 // Entry was not found.
1533 close(fd);
1534 return -1;
1535 }
1536
1537 // Check if it is properly stored
1538 if (entry.method != kCompressStored || (entry.offset % PAGE_SIZE) != 0) {
1539 close(fd);
1540 return -1;
1541 }
1542
1543 *file_offset = entry.offset;
1544
1545 if (realpath_fd(fd, realpath)) {
1546 *realpath += separator;
1547 } else {
1548 PRINT("warning: unable to get realpath for the library \"%s\". Will use given path.",
1549 normalized_path.c_str());
1550 *realpath = normalized_path;
1551 }
1552
1553 return fd;
1554 }
1555
format_path(char * buf,size_t buf_size,const char * path,const char * name)1556 static bool format_path(char* buf, size_t buf_size, const char* path, const char* name) {
1557 int n = __libc_format_buffer(buf, buf_size, "%s/%s", path, name);
1558 if (n < 0 || n >= static_cast<int>(buf_size)) {
1559 PRINT("Warning: ignoring very long library path: %s/%s", path, name);
1560 return false;
1561 }
1562
1563 return true;
1564 }
1565
open_library_on_paths(ZipArchiveCache * zip_archive_cache,const char * name,off64_t * file_offset,const std::vector<std::string> & paths,std::string * realpath)1566 static int open_library_on_paths(ZipArchiveCache* zip_archive_cache,
1567 const char* name, off64_t* file_offset,
1568 const std::vector<std::string>& paths,
1569 std::string* realpath) {
1570 for (const auto& path : paths) {
1571 char buf[512];
1572 if (!format_path(buf, sizeof(buf), path.c_str(), name)) {
1573 continue;
1574 }
1575
1576 int fd = -1;
1577 if (strstr(buf, kZipFileSeparator) != nullptr) {
1578 fd = open_library_in_zipfile(zip_archive_cache, buf, file_offset, realpath);
1579 }
1580
1581 if (fd == -1) {
1582 fd = TEMP_FAILURE_RETRY(open(buf, O_RDONLY | O_CLOEXEC));
1583 if (fd != -1) {
1584 *file_offset = 0;
1585 if (!realpath_fd(fd, realpath)) {
1586 PRINT("warning: unable to get realpath for the library \"%s\". Will use given path.", buf);
1587 *realpath = buf;
1588 }
1589 }
1590 }
1591
1592 if (fd != -1) {
1593 return fd;
1594 }
1595 }
1596
1597 return -1;
1598 }
1599
open_library(android_namespace_t * ns,ZipArchiveCache * zip_archive_cache,const char * name,soinfo * needed_by,off64_t * file_offset,std::string * realpath)1600 static int open_library(android_namespace_t* ns,
1601 ZipArchiveCache* zip_archive_cache,
1602 const char* name, soinfo *needed_by,
1603 off64_t* file_offset, std::string* realpath) {
1604 TRACE("[ opening %s ]", name);
1605
1606 // If the name contains a slash, we should attempt to open it directly and not search the paths.
1607 if (strchr(name, '/') != nullptr) {
1608 int fd = -1;
1609
1610 if (strstr(name, kZipFileSeparator) != nullptr) {
1611 fd = open_library_in_zipfile(zip_archive_cache, name, file_offset, realpath);
1612 }
1613
1614 if (fd == -1) {
1615 fd = TEMP_FAILURE_RETRY(open(name, O_RDONLY | O_CLOEXEC));
1616 if (fd != -1) {
1617 *file_offset = 0;
1618 if (!realpath_fd(fd, realpath)) {
1619 PRINT("warning: unable to get realpath for the library \"%s\". Will use given path.", name);
1620 *realpath = name;
1621 }
1622 }
1623 }
1624
1625 return fd;
1626 }
1627
1628 // Otherwise we try LD_LIBRARY_PATH first, and fall back to the default library path
1629 int fd = open_library_on_paths(zip_archive_cache, name, file_offset, ns->get_ld_library_paths(), realpath);
1630 if (fd == -1 && needed_by != nullptr) {
1631 fd = open_library_on_paths(zip_archive_cache, name, file_offset, needed_by->get_dt_runpath(), realpath);
1632 // Check if the library is accessible
1633 if (fd != -1 && !ns->is_accessible(*realpath)) {
1634 fd = -1;
1635 }
1636 }
1637
1638 if (fd == -1) {
1639 fd = open_library_on_paths(zip_archive_cache, name, file_offset, ns->get_default_library_paths(), realpath);
1640 }
1641
1642 // TODO(dimitry): workaround for http://b/26394120 (the grey-list)
1643 if (fd == -1 && ns != &g_default_namespace && is_greylisted(name, needed_by)) {
1644 // try searching for it on default_namespace default_library_path
1645 fd = open_library_on_paths(zip_archive_cache, name, file_offset,
1646 g_default_namespace.get_default_library_paths(), realpath);
1647 }
1648 // END OF WORKAROUND
1649
1650 return fd;
1651 }
1652
fix_dt_needed(const char * dt_needed,const char * sopath __unused)1653 static const char* fix_dt_needed(const char* dt_needed, const char* sopath __unused) {
1654 #if !defined(__LP64__)
1655 // Work around incorrect DT_NEEDED entries for old apps: http://b/21364029
1656 if (get_application_target_sdk_version() <= 22) {
1657 const char* bname = basename(dt_needed);
1658 if (bname != dt_needed) {
1659 DL_WARN("library \"%s\" has invalid DT_NEEDED entry \"%s\"", sopath, dt_needed);
1660 add_dlwarning(sopath, "invalid DT_NEEDED entry", dt_needed);
1661 }
1662
1663 return bname;
1664 }
1665 #endif
1666 return dt_needed;
1667 }
1668
1669 template<typename F>
for_each_dt_needed(const soinfo * si,F action)1670 static void for_each_dt_needed(const soinfo* si, F action) {
1671 for (const ElfW(Dyn)* d = si->dynamic; d->d_tag != DT_NULL; ++d) {
1672 if (d->d_tag == DT_NEEDED) {
1673 action(fix_dt_needed(si->get_string(d->d_un.d_val), si->get_realpath()));
1674 }
1675 }
1676 }
1677
1678 template<typename F>
for_each_dt_needed(const ElfReader & elf_reader,F action)1679 static void for_each_dt_needed(const ElfReader& elf_reader, F action) {
1680 for (const ElfW(Dyn)* d = elf_reader.dynamic(); d->d_tag != DT_NULL; ++d) {
1681 if (d->d_tag == DT_NEEDED) {
1682 action(fix_dt_needed(elf_reader.get_string(d->d_un.d_val), elf_reader.name()));
1683 }
1684 }
1685 }
1686
load_library(android_namespace_t * ns,LoadTask * task,LoadTaskList * load_tasks,int rtld_flags,const std::string & realpath)1687 static bool load_library(android_namespace_t* ns,
1688 LoadTask* task,
1689 LoadTaskList* load_tasks,
1690 int rtld_flags,
1691 const std::string& realpath) {
1692 off64_t file_offset = task->get_file_offset();
1693 const char* name = task->get_name();
1694 const android_dlextinfo* extinfo = task->get_extinfo();
1695
1696 if ((file_offset % PAGE_SIZE) != 0) {
1697 DL_ERR("file offset for the library \"%s\" is not page-aligned: %" PRId64, name, file_offset);
1698 return false;
1699 }
1700 if (file_offset < 0) {
1701 DL_ERR("file offset for the library \"%s\" is negative: %" PRId64, name, file_offset);
1702 return false;
1703 }
1704
1705 struct stat file_stat;
1706 if (TEMP_FAILURE_RETRY(fstat(task->get_fd(), &file_stat)) != 0) {
1707 DL_ERR("unable to stat file for the library \"%s\": %s", name, strerror(errno));
1708 return false;
1709 }
1710 if (file_offset >= file_stat.st_size) {
1711 DL_ERR("file offset for the library \"%s\" >= file size: %" PRId64 " >= %" PRId64,
1712 name, file_offset, file_stat.st_size);
1713 return false;
1714 }
1715
1716 // Check for symlink and other situations where
1717 // file can have different names, unless ANDROID_DLEXT_FORCE_LOAD is set
1718 if (extinfo == nullptr || (extinfo->flags & ANDROID_DLEXT_FORCE_LOAD) == 0) {
1719 auto predicate = [&](soinfo* si) {
1720 return si->get_st_dev() != 0 &&
1721 si->get_st_ino() != 0 &&
1722 si->get_st_dev() == file_stat.st_dev &&
1723 si->get_st_ino() == file_stat.st_ino &&
1724 si->get_file_offset() == file_offset;
1725 };
1726
1727 soinfo* si = ns->soinfo_list().find_if(predicate);
1728
1729 // check public namespace
1730 if (si == nullptr) {
1731 si = g_public_namespace.find_if(predicate);
1732 if (si != nullptr) {
1733 ns->add_soinfo(si);
1734 }
1735 }
1736
1737 if (si != nullptr) {
1738 TRACE("library \"%s\" is already loaded under different name/path \"%s\" - "
1739 "will return existing soinfo", name, si->get_realpath());
1740 task->set_soinfo(si);
1741 return true;
1742 }
1743 }
1744
1745 if ((rtld_flags & RTLD_NOLOAD) != 0) {
1746 DL_ERR("library \"%s\" wasn't loaded and RTLD_NOLOAD prevented it", name);
1747 return false;
1748 }
1749
1750 if (!ns->is_accessible(realpath)) {
1751 // TODO(dimitry): workaround for http://b/26394120 - the grey-list
1752 const soinfo* needed_by = task->is_dt_needed() ? task->get_needed_by() : nullptr;
1753 if (is_greylisted(name, needed_by)) {
1754 // print warning only if needed by non-system library
1755 if (needed_by == nullptr || !is_system_library(needed_by->get_realpath())) {
1756 const soinfo* needed_or_dlopened_by = task->get_needed_by();
1757 const char* sopath = needed_or_dlopened_by == nullptr ? "(unknown)" :
1758 needed_or_dlopened_by->get_realpath();
1759 DL_WARN("library \"%s\" (\"%s\") needed or dlopened by \"%s\" is not accessible for the namespace \"%s\""
1760 " - the access is temporarily granted as a workaround for http://b/26394120, note that the access"
1761 " will be removed in future releases of Android.",
1762 name, realpath.c_str(), sopath, ns->get_name());
1763 add_dlwarning(sopath, "unauthorized access to", name);
1764 }
1765 } else {
1766 // do not load libraries if they are not accessible for the specified namespace.
1767 const char* needed_or_dlopened_by = task->get_needed_by() == nullptr ?
1768 "(unknown)" :
1769 task->get_needed_by()->get_realpath();
1770
1771 DL_ERR("library \"%s\" needed or dlopened by \"%s\" is not accessible for the namespace \"%s\"",
1772 name, needed_or_dlopened_by, ns->get_name());
1773
1774 PRINT("library \"%s\" (\"%s\") needed or dlopened by \"%s\" is not accessible for the"
1775 " namespace: [name=\"%s\", ld_library_paths=\"%s\", default_library_paths=\"%s\","
1776 " permitted_paths=\"%s\"]",
1777 name, realpath.c_str(),
1778 needed_or_dlopened_by,
1779 ns->get_name(),
1780 android::base::Join(ns->get_ld_library_paths(), ':').c_str(),
1781 android::base::Join(ns->get_default_library_paths(), ':').c_str(),
1782 android::base::Join(ns->get_permitted_paths(), ':').c_str());
1783 return false;
1784 }
1785 }
1786
1787 soinfo* si = soinfo_alloc(ns, realpath.c_str(), &file_stat, file_offset, rtld_flags);
1788 if (si == nullptr) {
1789 return false;
1790 }
1791
1792 task->set_soinfo(si);
1793
1794 // Read the ELF header and some of the segments.
1795 if (!task->read(realpath.c_str(), file_stat.st_size)) {
1796 soinfo_free(si);
1797 task->set_soinfo(nullptr);
1798 return false;
1799 }
1800
1801 // find and set DT_RUNPATH and dt_soname
1802 // Note that these field values are temporary and are
1803 // going to be overwritten on soinfo::prelink_image
1804 // with values from PT_LOAD segments.
1805 const ElfReader& elf_reader = task->get_elf_reader();
1806 for (const ElfW(Dyn)* d = elf_reader.dynamic(); d->d_tag != DT_NULL; ++d) {
1807 if (d->d_tag == DT_RUNPATH) {
1808 si->set_dt_runpath(elf_reader.get_string(d->d_un.d_val));
1809 }
1810 if (d->d_tag == DT_SONAME) {
1811 si->set_soname(elf_reader.get_string(d->d_un.d_val));
1812 }
1813 }
1814
1815 for_each_dt_needed(task->get_elf_reader(), [&](const char* name) {
1816 load_tasks->push_back(LoadTask::create(name, si, task->get_readers_map()));
1817 });
1818
1819 return true;
1820 }
1821
load_library(android_namespace_t * ns,LoadTask * task,ZipArchiveCache * zip_archive_cache,LoadTaskList * load_tasks,int rtld_flags)1822 static bool load_library(android_namespace_t* ns,
1823 LoadTask* task,
1824 ZipArchiveCache* zip_archive_cache,
1825 LoadTaskList* load_tasks,
1826 int rtld_flags) {
1827 const char* name = task->get_name();
1828 soinfo* needed_by = task->get_needed_by();
1829 const android_dlextinfo* extinfo = task->get_extinfo();
1830
1831 off64_t file_offset;
1832 std::string realpath;
1833 if (extinfo != nullptr && (extinfo->flags & ANDROID_DLEXT_USE_LIBRARY_FD) != 0) {
1834 file_offset = 0;
1835 if ((extinfo->flags & ANDROID_DLEXT_USE_LIBRARY_FD_OFFSET) != 0) {
1836 file_offset = extinfo->library_fd_offset;
1837 }
1838
1839 if (!realpath_fd(extinfo->library_fd, &realpath)) {
1840 PRINT("warning: unable to get realpath for the library \"%s\" by extinfo->library_fd. "
1841 "Will use given name.", name);
1842 realpath = name;
1843 }
1844
1845 task->set_fd(extinfo->library_fd, false);
1846 task->set_file_offset(file_offset);
1847 return load_library(ns, task, load_tasks, rtld_flags, realpath);
1848 }
1849
1850 // Open the file.
1851 int fd = open_library(ns, zip_archive_cache, name, needed_by, &file_offset, &realpath);
1852 if (fd == -1) {
1853 DL_ERR("library \"%s\" not found", name);
1854 return false;
1855 }
1856
1857 task->set_fd(fd, true);
1858 task->set_file_offset(file_offset);
1859
1860 return load_library(ns, task, load_tasks, rtld_flags, realpath);
1861 }
1862
1863 // Returns true if library was found and false in 2 cases
1864 // 1. (for default namespace only) The library was found but loaded under different
1865 // target_sdk_version (*candidate != nullptr)
1866 // 2. The library was not found by soname (*candidate is nullptr)
find_loaded_library_by_soname(android_namespace_t * ns,const char * name,soinfo ** candidate)1867 static bool find_loaded_library_by_soname(android_namespace_t* ns,
1868 const char* name, soinfo** candidate) {
1869 *candidate = nullptr;
1870
1871 // Ignore filename with path.
1872 if (strchr(name, '/') != nullptr) {
1873 return false;
1874 }
1875
1876 uint32_t target_sdk_version = get_application_target_sdk_version();
1877
1878 return !ns->soinfo_list().visit([&](soinfo* si) {
1879 const char* soname = si->get_soname();
1880 if (soname != nullptr && (strcmp(name, soname) == 0)) {
1881 // If the library was opened under different target sdk version
1882 // skip this step and try to reopen it. The exceptions are
1883 // "libdl.so" and global group. There is no point in skipping
1884 // them because relocation process is going to use them
1885 // in any case.
1886 bool is_libdl = si == solist;
1887 if (is_libdl || (si->get_dt_flags_1() & DF_1_GLOBAL) != 0 ||
1888 !si->is_linked() || si->get_target_sdk_version() == target_sdk_version ||
1889 ns != &g_default_namespace) {
1890 *candidate = si;
1891 return false;
1892 } else if (*candidate == nullptr) {
1893 // for the different sdk version in the default namespace
1894 // remember the first library.
1895 *candidate = si;
1896 }
1897 }
1898
1899 return true;
1900 });
1901 }
1902
find_library_internal(android_namespace_t * ns,LoadTask * task,ZipArchiveCache * zip_archive_cache,LoadTaskList * load_tasks,int rtld_flags)1903 static bool find_library_internal(android_namespace_t* ns,
1904 LoadTask* task,
1905 ZipArchiveCache* zip_archive_cache,
1906 LoadTaskList* load_tasks,
1907 int rtld_flags) {
1908 soinfo* candidate;
1909
1910 if (find_loaded_library_by_soname(ns, task->get_name(), &candidate)) {
1911 task->set_soinfo(candidate);
1912 return true;
1913 }
1914
1915 if (ns != &g_default_namespace) {
1916 // check public namespace
1917 candidate = g_public_namespace.find_if([&](soinfo* si) {
1918 return strcmp(task->get_name(), si->get_soname()) == 0;
1919 });
1920
1921 if (candidate != nullptr) {
1922 ns->add_soinfo(candidate);
1923 task->set_soinfo(candidate);
1924 return true;
1925 }
1926 }
1927
1928 // Library might still be loaded, the accurate detection
1929 // of this fact is done by load_library.
1930 TRACE("[ \"%s\" find_loaded_library_by_soname failed (*candidate=%s@%p). Trying harder...]",
1931 task->get_name(), candidate == nullptr ? "n/a" : candidate->get_realpath(), candidate);
1932
1933 if (load_library(ns, task, zip_archive_cache, load_tasks, rtld_flags)) {
1934 return true;
1935 } else {
1936 // In case we were unable to load the library but there
1937 // is a candidate loaded under the same soname but different
1938 // sdk level - return it anyways.
1939 if (candidate != nullptr) {
1940 task->set_soinfo(candidate);
1941 return true;
1942 }
1943 }
1944
1945 return false;
1946 }
1947
1948 static void soinfo_unload(soinfo* si);
1949 static void soinfo_unload(soinfo* soinfos[], size_t count);
1950
1951 // TODO: this is slightly unusual way to construct
1952 // the global group for relocation. Not every RTLD_GLOBAL
1953 // library is included in this group for backwards-compatibility
1954 // reasons.
1955 //
1956 // This group consists of the main executable, LD_PRELOADs
1957 // and libraries with the DF_1_GLOBAL flag set.
make_global_group(android_namespace_t * ns)1958 static soinfo::soinfo_list_t make_global_group(android_namespace_t* ns) {
1959 soinfo::soinfo_list_t global_group;
1960 ns->soinfo_list().for_each([&](soinfo* si) {
1961 if ((si->get_dt_flags_1() & DF_1_GLOBAL) != 0) {
1962 global_group.push_back(si);
1963 }
1964 });
1965
1966 return global_group;
1967 }
1968
1969 // This function provides a list of libraries to be shared
1970 // by the namespace. For the default namespace this is the global
1971 // group (see make_global_group). For all others this is a group
1972 // of RTLD_GLOBAL libraries (which includes the global group from
1973 // the default namespace).
get_shared_group(android_namespace_t * ns)1974 static soinfo::soinfo_list_t get_shared_group(android_namespace_t* ns) {
1975 if (ns == &g_default_namespace) {
1976 return make_global_group(ns);
1977 }
1978
1979 soinfo::soinfo_list_t shared_group;
1980 ns->soinfo_list().for_each([&](soinfo* si) {
1981 if ((si->get_rtld_flags() & RTLD_GLOBAL) != 0) {
1982 shared_group.push_back(si);
1983 }
1984 });
1985
1986 return shared_group;
1987 }
1988
shuffle(std::vector<LoadTask * > * v)1989 static void shuffle(std::vector<LoadTask*>* v) {
1990 for (size_t i = 0, size = v->size(); i < size; ++i) {
1991 size_t n = size - i;
1992 size_t r = arc4random_uniform(n);
1993 std::swap((*v)[n-1], (*v)[r]);
1994 }
1995 }
1996
1997 // add_as_children - add first-level loaded libraries (i.e. library_names[], but
1998 // not their transitive dependencies) as children of the start_with library.
1999 // This is false when find_libraries is called for dlopen(), when newly loaded
2000 // libraries must form a disjoint tree.
find_libraries(android_namespace_t * ns,soinfo * start_with,const char * const library_names[],size_t library_names_count,soinfo * soinfos[],std::vector<soinfo * > * ld_preloads,size_t ld_preloads_count,int rtld_flags,const android_dlextinfo * extinfo,bool add_as_children)2001 static bool find_libraries(android_namespace_t* ns,
2002 soinfo* start_with,
2003 const char* const library_names[],
2004 size_t library_names_count, soinfo* soinfos[],
2005 std::vector<soinfo*>* ld_preloads,
2006 size_t ld_preloads_count, int rtld_flags,
2007 const android_dlextinfo* extinfo,
2008 bool add_as_children) {
2009 // Step 0: prepare.
2010 LoadTaskList load_tasks;
2011 std::unordered_map<const soinfo*, ElfReader> readers_map;
2012
2013 for (size_t i = 0; i < library_names_count; ++i) {
2014 const char* name = library_names[i];
2015 load_tasks.push_back(LoadTask::create(name, start_with, &readers_map));
2016 }
2017
2018 // Construct global_group.
2019 soinfo::soinfo_list_t global_group = make_global_group(ns);
2020
2021 // If soinfos array is null allocate one on stack.
2022 // The array is needed in case of failure; for example
2023 // when library_names[] = {libone.so, libtwo.so} and libone.so
2024 // is loaded correctly but libtwo.so failed for some reason.
2025 // In this case libone.so should be unloaded on return.
2026 // See also implementation of failure_guard below.
2027
2028 if (soinfos == nullptr) {
2029 size_t soinfos_size = sizeof(soinfo*)*library_names_count;
2030 soinfos = reinterpret_cast<soinfo**>(alloca(soinfos_size));
2031 memset(soinfos, 0, soinfos_size);
2032 }
2033
2034 // list of libraries to link - see step 2.
2035 size_t soinfos_count = 0;
2036
2037 auto scope_guard = make_scope_guard([&]() {
2038 for (LoadTask* t : load_tasks) {
2039 LoadTask::deleter(t);
2040 }
2041 });
2042
2043 auto failure_guard = make_scope_guard([&]() {
2044 // Housekeeping
2045 soinfo_unload(soinfos, soinfos_count);
2046 });
2047
2048 ZipArchiveCache zip_archive_cache;
2049
2050 // Step 1: expand the list of load_tasks to include
2051 // all DT_NEEDED libraries (do not load them just yet)
2052 for (size_t i = 0; i<load_tasks.size(); ++i) {
2053 LoadTask* task = load_tasks[i];
2054 soinfo* needed_by = task->get_needed_by();
2055
2056 bool is_dt_needed = needed_by != nullptr && (needed_by != start_with || add_as_children);
2057 task->set_extinfo(is_dt_needed ? nullptr : extinfo);
2058 task->set_dt_needed(is_dt_needed);
2059
2060 if(!find_library_internal(ns, task, &zip_archive_cache, &load_tasks, rtld_flags)) {
2061 return false;
2062 }
2063
2064 soinfo* si = task->get_soinfo();
2065
2066 if (is_dt_needed) {
2067 needed_by->add_child(si);
2068 }
2069
2070 if (si->is_linked()) {
2071 si->increment_ref_count();
2072 }
2073
2074 // When ld_preloads is not null, the first
2075 // ld_preloads_count libs are in fact ld_preloads.
2076 if (ld_preloads != nullptr && soinfos_count < ld_preloads_count) {
2077 ld_preloads->push_back(si);
2078 }
2079
2080 if (soinfos_count < library_names_count) {
2081 soinfos[soinfos_count++] = si;
2082 }
2083 }
2084
2085 // Step 2: Load libraries in random order (see b/24047022)
2086 LoadTaskList load_list;
2087 for (auto&& task : load_tasks) {
2088 soinfo* si = task->get_soinfo();
2089 auto pred = [&](const LoadTask* t) {
2090 return t->get_soinfo() == si;
2091 };
2092
2093 if (!si->is_linked() &&
2094 std::find_if(load_list.begin(), load_list.end(), pred) == load_list.end() ) {
2095 load_list.push_back(task);
2096 }
2097 }
2098 shuffle(&load_list);
2099
2100 for (auto&& task : load_list) {
2101 if (!task->load()) {
2102 return false;
2103 }
2104 }
2105
2106 // Step 3: pre-link all DT_NEEDED libraries in breadth first order.
2107 for (auto&& task : load_tasks) {
2108 soinfo* si = task->get_soinfo();
2109 if (!si->is_linked() && !si->prelink_image()) {
2110 return false;
2111 }
2112 }
2113
2114 // Step 4: Add LD_PRELOADed libraries to the global group for
2115 // future runs. There is no need to explicitly add them to
2116 // the global group for this run because they are going to
2117 // appear in the local group in the correct order.
2118 if (ld_preloads != nullptr) {
2119 for (auto&& si : *ld_preloads) {
2120 si->set_dt_flags_1(si->get_dt_flags_1() | DF_1_GLOBAL);
2121 }
2122 }
2123
2124
2125 // Step 5: link libraries.
2126 soinfo::soinfo_list_t local_group;
2127 walk_dependencies_tree(
2128 (start_with != nullptr && add_as_children) ? &start_with : soinfos,
2129 (start_with != nullptr && add_as_children) ? 1 : soinfos_count,
2130 [&] (soinfo* si) {
2131 local_group.push_back(si);
2132 return true;
2133 });
2134
2135 // We need to increment ref_count in case
2136 // the root of the local group was not linked.
2137 bool was_local_group_root_linked = local_group.front()->is_linked();
2138
2139 bool linked = local_group.visit([&](soinfo* si) {
2140 if (!si->is_linked()) {
2141 if (!si->link_image(global_group, local_group, extinfo)) {
2142 return false;
2143 }
2144 }
2145
2146 return true;
2147 });
2148
2149 if (linked) {
2150 local_group.for_each([](soinfo* si) {
2151 if (!si->is_linked()) {
2152 si->set_linked();
2153 }
2154 });
2155
2156 failure_guard.disable();
2157 }
2158
2159 if (!was_local_group_root_linked) {
2160 local_group.front()->increment_ref_count();
2161 }
2162
2163 return linked;
2164 }
2165
find_library(android_namespace_t * ns,const char * name,int rtld_flags,const android_dlextinfo * extinfo,soinfo * needed_by)2166 static soinfo* find_library(android_namespace_t* ns,
2167 const char* name, int rtld_flags,
2168 const android_dlextinfo* extinfo,
2169 soinfo* needed_by) {
2170 soinfo* si;
2171
2172 if (name == nullptr) {
2173 si = somain;
2174 } else if (!find_libraries(ns, needed_by, &name, 1, &si, nullptr, 0, rtld_flags,
2175 extinfo, /* add_as_children */ false)) {
2176 return nullptr;
2177 }
2178
2179 return si;
2180 }
2181
soinfo_unload(soinfo * root)2182 static void soinfo_unload(soinfo* root) {
2183 if (root->is_linked()) {
2184 root = root->get_local_group_root();
2185 }
2186
2187 if (!root->can_unload()) {
2188 TRACE("not unloading \"%s\" - the binary is flagged with NODELETE", root->get_realpath());
2189 return;
2190 }
2191
2192 soinfo_unload(&root, 1);
2193 }
2194
soinfo_unload(soinfo * soinfos[],size_t count)2195 static void soinfo_unload(soinfo* soinfos[], size_t count) {
2196 // Note that the library can be loaded but not linked;
2197 // in which case there is no root but we still need
2198 // to walk the tree and unload soinfos involved.
2199 //
2200 // This happens on unsuccessful dlopen, when one of
2201 // the DT_NEEDED libraries could not be linked/found.
2202 if (count == 0) {
2203 return;
2204 }
2205
2206 soinfo::soinfo_list_t unload_list;
2207 for (size_t i = 0; i < count; ++i) {
2208 soinfo* si = soinfos[i];
2209
2210 if (si->can_unload()) {
2211 size_t ref_count = si->is_linked() ? si->decrement_ref_count() : 0;
2212 if (ref_count == 0) {
2213 unload_list.push_back(si);
2214 } else {
2215 TRACE("not unloading '%s' group, decrementing ref_count to %zd",
2216 si->get_realpath(), ref_count);
2217 }
2218 } else {
2219 TRACE("not unloading '%s' - the binary is flagged with NODELETE", si->get_realpath());
2220 return;
2221 }
2222 }
2223
2224 // This is used to identify soinfos outside of the load-group
2225 // note that we cannot have > 1 in the array and have any of them
2226 // linked. This is why we can safely use the first one.
2227 soinfo* root = soinfos[0];
2228
2229 soinfo::soinfo_list_t local_unload_list;
2230 soinfo::soinfo_list_t external_unload_list;
2231 soinfo* si = nullptr;
2232
2233 while ((si = unload_list.pop_front()) != nullptr) {
2234 if (local_unload_list.contains(si)) {
2235 continue;
2236 }
2237
2238 local_unload_list.push_back(si);
2239
2240 if (si->has_min_version(0)) {
2241 soinfo* child = nullptr;
2242 while ((child = si->get_children().pop_front()) != nullptr) {
2243 TRACE("%s@%p needs to unload %s@%p", si->get_realpath(), si,
2244 child->get_realpath(), child);
2245
2246 if (local_unload_list.contains(child)) {
2247 continue;
2248 } else if (child->is_linked() && child->get_local_group_root() != root) {
2249 child->get_parents().remove_if([&] (const soinfo* parent) {
2250 return parent == si;
2251 });
2252 external_unload_list.push_back(child);
2253 } else {
2254 unload_list.push_front(child);
2255 }
2256 }
2257 } else {
2258 #if !defined(__work_around_b_24465209__)
2259 __libc_fatal("soinfo for \"%s\"@%p has no version", si->get_realpath(), si);
2260 #else
2261 PRINT("warning: soinfo for \"%s\"@%p has no version", si->get_realpath(), si);
2262 for_each_dt_needed(si, [&] (const char* library_name) {
2263 TRACE("deprecated (old format of soinfo): %s needs to unload %s",
2264 si->get_realpath(), library_name);
2265
2266 soinfo* needed = find_library(si->get_primary_namespace(),
2267 library_name, RTLD_NOLOAD, nullptr, nullptr);
2268
2269 if (needed != nullptr) {
2270 // Not found: for example if symlink was deleted between dlopen and dlclose
2271 // Since we cannot really handle errors at this point - print and continue.
2272 PRINT("warning: couldn't find %s needed by %s on unload.",
2273 library_name, si->get_realpath());
2274 return;
2275 } else if (local_unload_list.contains(needed)) {
2276 // already visited
2277 return;
2278 } else if (needed->is_linked() && needed->get_local_group_root() != root) {
2279 // external group
2280 external_unload_list.push_back(needed);
2281 } else {
2282 // local group
2283 unload_list.push_front(needed);
2284 }
2285 });
2286 #endif
2287 }
2288 }
2289
2290 local_unload_list.for_each([](soinfo* si) {
2291 si->call_destructors();
2292 });
2293
2294 while ((si = local_unload_list.pop_front()) != nullptr) {
2295 notify_gdb_of_unload(si);
2296 soinfo_free(si);
2297 }
2298
2299 while ((si = external_unload_list.pop_front()) != nullptr) {
2300 soinfo_unload(si);
2301 }
2302 }
2303
symbol_display_name(const char * sym_name,const char * sym_ver)2304 static std::string symbol_display_name(const char* sym_name, const char* sym_ver) {
2305 if (sym_ver == nullptr) {
2306 return sym_name;
2307 }
2308
2309 return std::string(sym_name) + ", version " + sym_ver;
2310 }
2311
get_caller_namespace(soinfo * caller)2312 static android_namespace_t* get_caller_namespace(soinfo* caller) {
2313 return caller != nullptr ? caller->get_primary_namespace() : g_anonymous_namespace;
2314 }
2315
do_android_get_LD_LIBRARY_PATH(char * buffer,size_t buffer_size)2316 void do_android_get_LD_LIBRARY_PATH(char* buffer, size_t buffer_size) {
2317 // Use basic string manipulation calls to avoid snprintf.
2318 // snprintf indirectly calls pthread_getspecific to get the size of a buffer.
2319 // When debug malloc is enabled, this call returns 0. This in turn causes
2320 // snprintf to do nothing, which causes libraries to fail to load.
2321 // See b/17302493 for further details.
2322 // Once the above bug is fixed, this code can be modified to use
2323 // snprintf again.
2324 size_t required_len = 0;
2325 for (size_t i = 0; g_default_ld_paths[i] != nullptr; ++i) {
2326 required_len += strlen(g_default_ld_paths[i]) + 1;
2327 }
2328 if (buffer_size < required_len) {
2329 __libc_fatal("android_get_LD_LIBRARY_PATH failed, buffer too small: "
2330 "buffer len %zu, required len %zu", buffer_size, required_len);
2331 }
2332 char* end = buffer;
2333 for (size_t i = 0; g_default_ld_paths[i] != nullptr; ++i) {
2334 if (i > 0) *end++ = ':';
2335 end = stpcpy(end, g_default_ld_paths[i]);
2336 }
2337 }
2338
do_android_update_LD_LIBRARY_PATH(const char * ld_library_path)2339 void do_android_update_LD_LIBRARY_PATH(const char* ld_library_path) {
2340 parse_LD_LIBRARY_PATH(ld_library_path);
2341 }
2342
do_dlopen(const char * name,int flags,const android_dlextinfo * extinfo,void * caller_addr)2343 void* do_dlopen(const char* name, int flags, const android_dlextinfo* extinfo,
2344 void* caller_addr) {
2345 soinfo* const caller = find_containing_library(caller_addr);
2346
2347 if ((flags & ~(RTLD_NOW|RTLD_LAZY|RTLD_LOCAL|RTLD_GLOBAL|RTLD_NODELETE|RTLD_NOLOAD)) != 0) {
2348 DL_ERR("invalid flags to dlopen: %x", flags);
2349 return nullptr;
2350 }
2351
2352 android_namespace_t* ns = get_caller_namespace(caller);
2353
2354 if (extinfo != nullptr) {
2355 if ((extinfo->flags & ~(ANDROID_DLEXT_VALID_FLAG_BITS)) != 0) {
2356 DL_ERR("invalid extended flags to android_dlopen_ext: 0x%" PRIx64, extinfo->flags);
2357 return nullptr;
2358 }
2359
2360 if ((extinfo->flags & ANDROID_DLEXT_USE_LIBRARY_FD) == 0 &&
2361 (extinfo->flags & ANDROID_DLEXT_USE_LIBRARY_FD_OFFSET) != 0) {
2362 DL_ERR("invalid extended flag combination (ANDROID_DLEXT_USE_LIBRARY_FD_OFFSET without "
2363 "ANDROID_DLEXT_USE_LIBRARY_FD): 0x%" PRIx64, extinfo->flags);
2364 return nullptr;
2365 }
2366
2367 if ((extinfo->flags & ANDROID_DLEXT_LOAD_AT_FIXED_ADDRESS) != 0 &&
2368 (extinfo->flags & (ANDROID_DLEXT_RESERVED_ADDRESS | ANDROID_DLEXT_RESERVED_ADDRESS_HINT)) != 0) {
2369 DL_ERR("invalid extended flag combination: ANDROID_DLEXT_LOAD_AT_FIXED_ADDRESS is not "
2370 "compatible with ANDROID_DLEXT_RESERVED_ADDRESS/ANDROID_DLEXT_RESERVED_ADDRESS_HINT");
2371 return nullptr;
2372 }
2373
2374 if ((extinfo->flags & ANDROID_DLEXT_USE_NAMESPACE) != 0) {
2375 if (extinfo->library_namespace == nullptr) {
2376 DL_ERR("ANDROID_DLEXT_USE_NAMESPACE is set but extinfo->library_namespace is null");
2377 return nullptr;
2378 }
2379 ns = extinfo->library_namespace;
2380 }
2381 }
2382
2383 std::string asan_name_holder;
2384
2385 const char* translated_name = name;
2386 if (g_is_asan) {
2387 if (file_is_in_dir(name, kSystemLibDir)) {
2388 asan_name_holder = std::string(kAsanSystemLibDir) + "/" + basename(name);
2389 if (file_exists(asan_name_holder.c_str())) {
2390 translated_name = asan_name_holder.c_str();
2391 PRINT("linker_asan dlopen translating \"%s\" -> \"%s\"", name, translated_name);
2392 }
2393 } else if (file_is_in_dir(name, kVendorLibDir)) {
2394 asan_name_holder = std::string(kAsanVendorLibDir) + "/" + basename(name);
2395 if (file_exists(asan_name_holder.c_str())) {
2396 translated_name = asan_name_holder.c_str();
2397 PRINT("linker_asan dlopen translating \"%s\" -> \"%s\"", name, translated_name);
2398 }
2399 }
2400 }
2401
2402 ProtectedDataGuard guard;
2403 soinfo* si = find_library(ns, translated_name, flags, extinfo, caller);
2404 if (si != nullptr) {
2405 si->call_constructors();
2406 return si->to_handle();
2407 }
2408
2409 return nullptr;
2410 }
2411
do_dladdr(const void * addr,Dl_info * info)2412 int do_dladdr(const void* addr, Dl_info* info) {
2413 // Determine if this address can be found in any library currently mapped.
2414 soinfo* si = find_containing_library(addr);
2415 if (si == nullptr) {
2416 return 0;
2417 }
2418
2419 memset(info, 0, sizeof(Dl_info));
2420
2421 info->dli_fname = si->get_realpath();
2422 // Address at which the shared object is loaded.
2423 info->dli_fbase = reinterpret_cast<void*>(si->base);
2424
2425 // Determine if any symbol in the library contains the specified address.
2426 ElfW(Sym)* sym = si->find_symbol_by_address(addr);
2427 if (sym != nullptr) {
2428 info->dli_sname = si->get_string(sym->st_name);
2429 info->dli_saddr = reinterpret_cast<void*>(si->resolve_symbol_address(sym));
2430 }
2431
2432 return 1;
2433 }
2434
soinfo_from_handle(void * handle)2435 static soinfo* soinfo_from_handle(void* handle) {
2436 if ((reinterpret_cast<uintptr_t>(handle) & 1) != 0) {
2437 auto it = g_soinfo_handles_map.find(reinterpret_cast<uintptr_t>(handle));
2438 if (it == g_soinfo_handles_map.end()) {
2439 return nullptr;
2440 } else {
2441 return it->second;
2442 }
2443 }
2444
2445 return static_cast<soinfo*>(handle);
2446 }
2447
do_dlsym(void * handle,const char * sym_name,const char * sym_ver,void * caller_addr,void ** symbol)2448 bool do_dlsym(void* handle, const char* sym_name, const char* sym_ver,
2449 void* caller_addr, void** symbol) {
2450 #if !defined(__LP64__)
2451 if (handle == nullptr) {
2452 DL_ERR("dlsym failed: library handle is null");
2453 return false;
2454 }
2455 #endif
2456
2457 if (sym_name == nullptr) {
2458 DL_ERR("dlsym failed: symbol name is null");
2459 return false;
2460 }
2461
2462 soinfo* found = nullptr;
2463 const ElfW(Sym)* sym = nullptr;
2464 soinfo* caller = find_containing_library(caller_addr);
2465 android_namespace_t* ns = get_caller_namespace(caller);
2466
2467 version_info vi_instance;
2468 version_info* vi = nullptr;
2469
2470 if (sym_ver != nullptr) {
2471 vi_instance.name = sym_ver;
2472 vi_instance.elf_hash = calculate_elf_hash(sym_ver);
2473 vi = &vi_instance;
2474 }
2475
2476 if (handle == RTLD_DEFAULT || handle == RTLD_NEXT) {
2477 sym = dlsym_linear_lookup(ns, sym_name, vi, &found, caller, handle);
2478 } else {
2479 soinfo* si = soinfo_from_handle(handle);
2480 if (si == nullptr) {
2481 DL_ERR("dlsym failed: invalid handle: %p", handle);
2482 return false;
2483 }
2484 sym = dlsym_handle_lookup(si, &found, sym_name, vi);
2485 }
2486
2487 if (sym != nullptr) {
2488 uint32_t bind = ELF_ST_BIND(sym->st_info);
2489
2490 if ((bind == STB_GLOBAL || bind == STB_WEAK) && sym->st_shndx != 0) {
2491 *symbol = reinterpret_cast<void*>(found->resolve_symbol_address(sym));
2492 return true;
2493 }
2494
2495 DL_ERR("symbol \"%s\" found but not global", symbol_display_name(sym_name, sym_ver).c_str());
2496 return false;
2497 }
2498
2499 DL_ERR("undefined symbol: %s", symbol_display_name(sym_name, sym_ver).c_str());
2500 return false;
2501 }
2502
do_dlclose(void * handle)2503 int do_dlclose(void* handle) {
2504 ProtectedDataGuard guard;
2505 soinfo* si = soinfo_from_handle(handle);
2506 if (si == nullptr) {
2507 DL_ERR("invalid handle: %p", handle);
2508 return -1;
2509 }
2510
2511 soinfo_unload(si);
2512 return 0;
2513 }
2514
init_namespaces(const char * public_ns_sonames,const char * anon_ns_library_path)2515 bool init_namespaces(const char* public_ns_sonames, const char* anon_ns_library_path) {
2516 CHECK(public_ns_sonames != nullptr);
2517 if (g_public_namespace_initialized) {
2518 DL_ERR("public namespace has already been initialized.");
2519 return false;
2520 }
2521
2522 std::vector<std::string> sonames = android::base::Split(public_ns_sonames, ":");
2523
2524 ProtectedDataGuard guard;
2525
2526 auto failure_guard = make_scope_guard([&]() {
2527 g_public_namespace.clear();
2528 });
2529
2530 for (const auto& soname : sonames) {
2531 soinfo* candidate = nullptr;
2532
2533 find_loaded_library_by_soname(&g_default_namespace, soname.c_str(), &candidate);
2534
2535 if (candidate == nullptr) {
2536 DL_ERR("error initializing public namespace: a library with soname \"%s\""
2537 " was not found in the default namespace", soname.c_str());
2538 return false;
2539 }
2540
2541 candidate->set_nodelete();
2542 g_public_namespace.push_back(candidate);
2543 }
2544
2545 g_public_namespace_initialized = true;
2546
2547 // create anonymous namespace
2548 // When the caller is nullptr - create_namespace will take global group
2549 // from the anonymous namespace, which is fine because anonymous namespace
2550 // is still pointing to the default one.
2551 android_namespace_t* anon_ns =
2552 create_namespace(nullptr, "(anonymous)", nullptr, anon_ns_library_path,
2553 ANDROID_NAMESPACE_TYPE_REGULAR, nullptr, &g_default_namespace);
2554
2555 if (anon_ns == nullptr) {
2556 g_public_namespace_initialized = false;
2557 return false;
2558 }
2559 g_anonymous_namespace = anon_ns;
2560 failure_guard.disable();
2561 return true;
2562 }
2563
create_namespace(const void * caller_addr,const char * name,const char * ld_library_path,const char * default_library_path,uint64_t type,const char * permitted_when_isolated_path,android_namespace_t * parent_namespace)2564 android_namespace_t* create_namespace(const void* caller_addr,
2565 const char* name,
2566 const char* ld_library_path,
2567 const char* default_library_path,
2568 uint64_t type,
2569 const char* permitted_when_isolated_path,
2570 android_namespace_t* parent_namespace) {
2571 if (!g_public_namespace_initialized) {
2572 DL_ERR("cannot create namespace: public namespace is not initialized.");
2573 return nullptr;
2574 }
2575
2576 if (parent_namespace == nullptr) {
2577 // if parent_namespace is nullptr -> set it to the caller namespace
2578 soinfo* caller_soinfo = find_containing_library(caller_addr);
2579
2580 parent_namespace = caller_soinfo != nullptr ?
2581 caller_soinfo->get_primary_namespace() :
2582 g_anonymous_namespace;
2583 }
2584
2585 ProtectedDataGuard guard;
2586 std::vector<std::string> ld_library_paths;
2587 std::vector<std::string> default_library_paths;
2588 std::vector<std::string> permitted_paths;
2589
2590 parse_path(ld_library_path, ":", &ld_library_paths);
2591 parse_path(default_library_path, ":", &default_library_paths);
2592 parse_path(permitted_when_isolated_path, ":", &permitted_paths);
2593
2594 android_namespace_t* ns = new (g_namespace_allocator.alloc()) android_namespace_t();
2595 ns->set_name(name);
2596 ns->set_isolated((type & ANDROID_NAMESPACE_TYPE_ISOLATED) != 0);
2597 ns->set_ld_library_paths(std::move(ld_library_paths));
2598 ns->set_default_library_paths(std::move(default_library_paths));
2599 ns->set_permitted_paths(std::move(permitted_paths));
2600
2601 if ((type & ANDROID_NAMESPACE_TYPE_SHARED) != 0) {
2602 // If shared - clone the parent namespace
2603 ns->add_soinfos(parent_namespace->soinfo_list());
2604 } else {
2605 // If not shared - copy only the shared group
2606 ns->add_soinfos(get_shared_group(parent_namespace));
2607 }
2608
2609 return ns;
2610 }
2611
call_ifunc_resolver(ElfW (Addr)resolver_addr)2612 static ElfW(Addr) call_ifunc_resolver(ElfW(Addr) resolver_addr) {
2613 typedef ElfW(Addr) (*ifunc_resolver_t)(void);
2614 ifunc_resolver_t ifunc_resolver = reinterpret_cast<ifunc_resolver_t>(resolver_addr);
2615 ElfW(Addr) ifunc_addr = ifunc_resolver();
2616 TRACE_TYPE(RELO, "Called ifunc_resolver@%p. The result is %p",
2617 ifunc_resolver, reinterpret_cast<void*>(ifunc_addr));
2618
2619 return ifunc_addr;
2620 }
2621
get_version_info(ElfW (Versym)source_symver) const2622 const version_info* VersionTracker::get_version_info(ElfW(Versym) source_symver) const {
2623 if (source_symver < 2 ||
2624 source_symver >= version_infos.size() ||
2625 version_infos[source_symver].name == nullptr) {
2626 return nullptr;
2627 }
2628
2629 return &version_infos[source_symver];
2630 }
2631
add_version_info(size_t source_index,ElfW (Word)elf_hash,const char * ver_name,const soinfo * target_si)2632 void VersionTracker::add_version_info(size_t source_index,
2633 ElfW(Word) elf_hash,
2634 const char* ver_name,
2635 const soinfo* target_si) {
2636 if (source_index >= version_infos.size()) {
2637 version_infos.resize(source_index+1);
2638 }
2639
2640 version_infos[source_index].elf_hash = elf_hash;
2641 version_infos[source_index].name = ver_name;
2642 version_infos[source_index].target_si = target_si;
2643 }
2644
init_verneed(const soinfo * si_from)2645 bool VersionTracker::init_verneed(const soinfo* si_from) {
2646 uintptr_t verneed_ptr = si_from->get_verneed_ptr();
2647
2648 if (verneed_ptr == 0) {
2649 return true;
2650 }
2651
2652 size_t verneed_cnt = si_from->get_verneed_cnt();
2653
2654 for (size_t i = 0, offset = 0; i<verneed_cnt; ++i) {
2655 const ElfW(Verneed)* verneed = reinterpret_cast<ElfW(Verneed)*>(verneed_ptr + offset);
2656 size_t vernaux_offset = offset + verneed->vn_aux;
2657 offset += verneed->vn_next;
2658
2659 if (verneed->vn_version != 1) {
2660 DL_ERR("unsupported verneed[%zd] vn_version: %d (expected 1)", i, verneed->vn_version);
2661 return false;
2662 }
2663
2664 const char* target_soname = si_from->get_string(verneed->vn_file);
2665 // find it in dependencies
2666 soinfo* target_si = si_from->get_children().find_if([&](const soinfo* si) {
2667 return si->get_soname() != nullptr && strcmp(si->get_soname(), target_soname) == 0;
2668 });
2669
2670 if (target_si == nullptr) {
2671 DL_ERR("cannot find \"%s\" from verneed[%zd] in DT_NEEDED list for \"%s\"",
2672 target_soname, i, si_from->get_realpath());
2673 return false;
2674 }
2675
2676 for (size_t j = 0; j<verneed->vn_cnt; ++j) {
2677 const ElfW(Vernaux)* vernaux = reinterpret_cast<ElfW(Vernaux)*>(verneed_ptr + vernaux_offset);
2678 vernaux_offset += vernaux->vna_next;
2679
2680 const ElfW(Word) elf_hash = vernaux->vna_hash;
2681 const char* ver_name = si_from->get_string(vernaux->vna_name);
2682 ElfW(Half) source_index = vernaux->vna_other;
2683
2684 add_version_info(source_index, elf_hash, ver_name, target_si);
2685 }
2686 }
2687
2688 return true;
2689 }
2690
init_verdef(const soinfo * si_from)2691 bool VersionTracker::init_verdef(const soinfo* si_from) {
2692 return for_each_verdef(si_from,
2693 [&](size_t, const ElfW(Verdef)* verdef, const ElfW(Verdaux)* verdaux) {
2694 add_version_info(verdef->vd_ndx, verdef->vd_hash,
2695 si_from->get_string(verdaux->vda_name), si_from);
2696 return false;
2697 }
2698 );
2699 }
2700
init(const soinfo * si_from)2701 bool VersionTracker::init(const soinfo* si_from) {
2702 if (!si_from->has_min_version(2)) {
2703 return true;
2704 }
2705
2706 return init_verneed(si_from) && init_verdef(si_from);
2707 }
2708
lookup_version_info(const VersionTracker & version_tracker,ElfW (Word)sym,const char * sym_name,const version_info ** vi)2709 bool soinfo::lookup_version_info(const VersionTracker& version_tracker, ElfW(Word) sym,
2710 const char* sym_name, const version_info** vi) {
2711 const ElfW(Versym)* sym_ver_ptr = get_versym(sym);
2712 ElfW(Versym) sym_ver = sym_ver_ptr == nullptr ? 0 : *sym_ver_ptr;
2713
2714 if (sym_ver != VER_NDX_LOCAL && sym_ver != VER_NDX_GLOBAL) {
2715 *vi = version_tracker.get_version_info(sym_ver);
2716
2717 if (*vi == nullptr) {
2718 DL_ERR("cannot find verneed/verdef for version index=%d "
2719 "referenced by symbol \"%s\" at \"%s\"", sym_ver, sym_name, get_realpath());
2720 return false;
2721 }
2722 } else {
2723 // there is no version info
2724 *vi = nullptr;
2725 }
2726
2727 return true;
2728 }
2729
2730 #if !defined(__mips__)
2731 #if defined(USE_RELA)
get_addend(ElfW (Rela)* rela,ElfW (Addr)reloc_addr __unused)2732 static ElfW(Addr) get_addend(ElfW(Rela)* rela, ElfW(Addr) reloc_addr __unused) {
2733 return rela->r_addend;
2734 }
2735 #else
get_addend(ElfW (Rel)* rel,ElfW (Addr)reloc_addr)2736 static ElfW(Addr) get_addend(ElfW(Rel)* rel, ElfW(Addr) reloc_addr) {
2737 if (ELFW(R_TYPE)(rel->r_info) == R_GENERIC_RELATIVE ||
2738 ELFW(R_TYPE)(rel->r_info) == R_GENERIC_IRELATIVE) {
2739 return *reinterpret_cast<ElfW(Addr)*>(reloc_addr);
2740 }
2741 return 0;
2742 }
2743 #endif
2744
2745 template<typename ElfRelIteratorT>
relocate(const VersionTracker & version_tracker,ElfRelIteratorT && rel_iterator,const soinfo_list_t & global_group,const soinfo_list_t & local_group)2746 bool soinfo::relocate(const VersionTracker& version_tracker, ElfRelIteratorT&& rel_iterator,
2747 const soinfo_list_t& global_group, const soinfo_list_t& local_group) {
2748 for (size_t idx = 0; rel_iterator.has_next(); ++idx) {
2749 const auto rel = rel_iterator.next();
2750 if (rel == nullptr) {
2751 return false;
2752 }
2753
2754 ElfW(Word) type = ELFW(R_TYPE)(rel->r_info);
2755 ElfW(Word) sym = ELFW(R_SYM)(rel->r_info);
2756
2757 ElfW(Addr) reloc = static_cast<ElfW(Addr)>(rel->r_offset + load_bias);
2758 ElfW(Addr) sym_addr = 0;
2759 const char* sym_name = nullptr;
2760 ElfW(Addr) addend = get_addend(rel, reloc);
2761
2762 DEBUG("Processing \"%s\" relocation at index %zd", get_realpath(), idx);
2763 if (type == R_GENERIC_NONE) {
2764 continue;
2765 }
2766
2767 const ElfW(Sym)* s = nullptr;
2768 soinfo* lsi = nullptr;
2769
2770 if (sym != 0) {
2771 sym_name = get_string(symtab_[sym].st_name);
2772 const version_info* vi = nullptr;
2773
2774 if (!lookup_version_info(version_tracker, sym, sym_name, &vi)) {
2775 return false;
2776 }
2777
2778 if (!soinfo_do_lookup(this, sym_name, vi, &lsi, global_group, local_group, &s)) {
2779 return false;
2780 }
2781
2782 if (s == nullptr) {
2783 // We only allow an undefined symbol if this is a weak reference...
2784 s = &symtab_[sym];
2785 if (ELF_ST_BIND(s->st_info) != STB_WEAK) {
2786 DL_ERR("cannot locate symbol \"%s\" referenced by \"%s\"...", sym_name, get_realpath());
2787 return false;
2788 }
2789
2790 /* IHI0044C AAELF 4.5.1.1:
2791
2792 Libraries are not searched to resolve weak references.
2793 It is not an error for a weak reference to remain unsatisfied.
2794
2795 During linking, the value of an undefined weak reference is:
2796 - Zero if the relocation type is absolute
2797 - The address of the place if the relocation is pc-relative
2798 - The address of nominal base address if the relocation
2799 type is base-relative.
2800 */
2801
2802 switch (type) {
2803 case R_GENERIC_JUMP_SLOT:
2804 case R_GENERIC_GLOB_DAT:
2805 case R_GENERIC_RELATIVE:
2806 case R_GENERIC_IRELATIVE:
2807 #if defined(__aarch64__)
2808 case R_AARCH64_ABS64:
2809 case R_AARCH64_ABS32:
2810 case R_AARCH64_ABS16:
2811 #elif defined(__x86_64__)
2812 case R_X86_64_32:
2813 case R_X86_64_64:
2814 #elif defined(__arm__)
2815 case R_ARM_ABS32:
2816 #elif defined(__i386__)
2817 case R_386_32:
2818 #endif
2819 /*
2820 * The sym_addr was initialized to be zero above, or the relocation
2821 * code below does not care about value of sym_addr.
2822 * No need to do anything.
2823 */
2824 break;
2825 #if defined(__x86_64__)
2826 case R_X86_64_PC32:
2827 sym_addr = reloc;
2828 break;
2829 #elif defined(__i386__)
2830 case R_386_PC32:
2831 sym_addr = reloc;
2832 break;
2833 #endif
2834 default:
2835 DL_ERR("unknown weak reloc type %d @ %p (%zu)", type, rel, idx);
2836 return false;
2837 }
2838 } else { // We got a definition.
2839 #if !defined(__LP64__)
2840 // When relocating dso with text_relocation .text segment is
2841 // not executable. We need to restore elf flags before resolving
2842 // STT_GNU_IFUNC symbol.
2843 bool protect_segments = has_text_relocations &&
2844 lsi == this &&
2845 ELF_ST_TYPE(s->st_info) == STT_GNU_IFUNC;
2846 if (protect_segments) {
2847 if (phdr_table_protect_segments(phdr, phnum, load_bias) < 0) {
2848 DL_ERR("can't protect segments for \"%s\": %s",
2849 get_realpath(), strerror(errno));
2850 return false;
2851 }
2852 }
2853 #endif
2854 sym_addr = lsi->resolve_symbol_address(s);
2855 #if !defined(__LP64__)
2856 if (protect_segments) {
2857 if (phdr_table_unprotect_segments(phdr, phnum, load_bias) < 0) {
2858 DL_ERR("can't unprotect loadable segments for \"%s\": %s",
2859 get_realpath(), strerror(errno));
2860 return false;
2861 }
2862 }
2863 #endif
2864 }
2865 count_relocation(kRelocSymbol);
2866 }
2867
2868 switch (type) {
2869 case R_GENERIC_JUMP_SLOT:
2870 count_relocation(kRelocAbsolute);
2871 MARK(rel->r_offset);
2872 TRACE_TYPE(RELO, "RELO JMP_SLOT %16p <- %16p %s\n",
2873 reinterpret_cast<void*>(reloc),
2874 reinterpret_cast<void*>(sym_addr + addend), sym_name);
2875
2876 *reinterpret_cast<ElfW(Addr)*>(reloc) = (sym_addr + addend);
2877 break;
2878 case R_GENERIC_GLOB_DAT:
2879 count_relocation(kRelocAbsolute);
2880 MARK(rel->r_offset);
2881 TRACE_TYPE(RELO, "RELO GLOB_DAT %16p <- %16p %s\n",
2882 reinterpret_cast<void*>(reloc),
2883 reinterpret_cast<void*>(sym_addr + addend), sym_name);
2884 *reinterpret_cast<ElfW(Addr)*>(reloc) = (sym_addr + addend);
2885 break;
2886 case R_GENERIC_RELATIVE:
2887 count_relocation(kRelocRelative);
2888 MARK(rel->r_offset);
2889 TRACE_TYPE(RELO, "RELO RELATIVE %16p <- %16p\n",
2890 reinterpret_cast<void*>(reloc),
2891 reinterpret_cast<void*>(load_bias + addend));
2892 *reinterpret_cast<ElfW(Addr)*>(reloc) = (load_bias + addend);
2893 break;
2894 case R_GENERIC_IRELATIVE:
2895 count_relocation(kRelocRelative);
2896 MARK(rel->r_offset);
2897 TRACE_TYPE(RELO, "RELO IRELATIVE %16p <- %16p\n",
2898 reinterpret_cast<void*>(reloc),
2899 reinterpret_cast<void*>(load_bias + addend));
2900 {
2901 #if !defined(__LP64__)
2902 // When relocating dso with text_relocation .text segment is
2903 // not executable. We need to restore elf flags for this
2904 // particular call.
2905 if (has_text_relocations) {
2906 if (phdr_table_protect_segments(phdr, phnum, load_bias) < 0) {
2907 DL_ERR("can't protect segments for \"%s\": %s",
2908 get_realpath(), strerror(errno));
2909 return false;
2910 }
2911 }
2912 #endif
2913 ElfW(Addr) ifunc_addr = call_ifunc_resolver(load_bias + addend);
2914 #if !defined(__LP64__)
2915 // Unprotect it afterwards...
2916 if (has_text_relocations) {
2917 if (phdr_table_unprotect_segments(phdr, phnum, load_bias) < 0) {
2918 DL_ERR("can't unprotect loadable segments for \"%s\": %s",
2919 get_realpath(), strerror(errno));
2920 return false;
2921 }
2922 }
2923 #endif
2924 *reinterpret_cast<ElfW(Addr)*>(reloc) = ifunc_addr;
2925 }
2926 break;
2927
2928 #if defined(__aarch64__)
2929 case R_AARCH64_ABS64:
2930 count_relocation(kRelocAbsolute);
2931 MARK(rel->r_offset);
2932 TRACE_TYPE(RELO, "RELO ABS64 %16llx <- %16llx %s\n",
2933 reloc, sym_addr + addend, sym_name);
2934 *reinterpret_cast<ElfW(Addr)*>(reloc) = sym_addr + addend;
2935 break;
2936 case R_AARCH64_ABS32:
2937 count_relocation(kRelocAbsolute);
2938 MARK(rel->r_offset);
2939 TRACE_TYPE(RELO, "RELO ABS32 %16llx <- %16llx %s\n",
2940 reloc, sym_addr + addend, sym_name);
2941 {
2942 const ElfW(Addr) min_value = static_cast<ElfW(Addr)>(INT32_MIN);
2943 const ElfW(Addr) max_value = static_cast<ElfW(Addr)>(UINT32_MAX);
2944 if ((min_value <= (sym_addr + addend)) &&
2945 ((sym_addr + addend) <= max_value)) {
2946 *reinterpret_cast<ElfW(Addr)*>(reloc) = sym_addr + addend;
2947 } else {
2948 DL_ERR("0x%016llx out of range 0x%016llx to 0x%016llx",
2949 sym_addr + addend, min_value, max_value);
2950 return false;
2951 }
2952 }
2953 break;
2954 case R_AARCH64_ABS16:
2955 count_relocation(kRelocAbsolute);
2956 MARK(rel->r_offset);
2957 TRACE_TYPE(RELO, "RELO ABS16 %16llx <- %16llx %s\n",
2958 reloc, sym_addr + addend, sym_name);
2959 {
2960 const ElfW(Addr) min_value = static_cast<ElfW(Addr)>(INT16_MIN);
2961 const ElfW(Addr) max_value = static_cast<ElfW(Addr)>(UINT16_MAX);
2962 if ((min_value <= (sym_addr + addend)) &&
2963 ((sym_addr + addend) <= max_value)) {
2964 *reinterpret_cast<ElfW(Addr)*>(reloc) = (sym_addr + addend);
2965 } else {
2966 DL_ERR("0x%016llx out of range 0x%016llx to 0x%016llx",
2967 sym_addr + addend, min_value, max_value);
2968 return false;
2969 }
2970 }
2971 break;
2972 case R_AARCH64_PREL64:
2973 count_relocation(kRelocRelative);
2974 MARK(rel->r_offset);
2975 TRACE_TYPE(RELO, "RELO REL64 %16llx <- %16llx - %16llx %s\n",
2976 reloc, sym_addr + addend, rel->r_offset, sym_name);
2977 *reinterpret_cast<ElfW(Addr)*>(reloc) = sym_addr + addend - rel->r_offset;
2978 break;
2979 case R_AARCH64_PREL32:
2980 count_relocation(kRelocRelative);
2981 MARK(rel->r_offset);
2982 TRACE_TYPE(RELO, "RELO REL32 %16llx <- %16llx - %16llx %s\n",
2983 reloc, sym_addr + addend, rel->r_offset, sym_name);
2984 {
2985 const ElfW(Addr) min_value = static_cast<ElfW(Addr)>(INT32_MIN);
2986 const ElfW(Addr) max_value = static_cast<ElfW(Addr)>(UINT32_MAX);
2987 if ((min_value <= (sym_addr + addend - rel->r_offset)) &&
2988 ((sym_addr + addend - rel->r_offset) <= max_value)) {
2989 *reinterpret_cast<ElfW(Addr)*>(reloc) = sym_addr + addend - rel->r_offset;
2990 } else {
2991 DL_ERR("0x%016llx out of range 0x%016llx to 0x%016llx",
2992 sym_addr + addend - rel->r_offset, min_value, max_value);
2993 return false;
2994 }
2995 }
2996 break;
2997 case R_AARCH64_PREL16:
2998 count_relocation(kRelocRelative);
2999 MARK(rel->r_offset);
3000 TRACE_TYPE(RELO, "RELO REL16 %16llx <- %16llx - %16llx %s\n",
3001 reloc, sym_addr + addend, rel->r_offset, sym_name);
3002 {
3003 const ElfW(Addr) min_value = static_cast<ElfW(Addr)>(INT16_MIN);
3004 const ElfW(Addr) max_value = static_cast<ElfW(Addr)>(UINT16_MAX);
3005 if ((min_value <= (sym_addr + addend - rel->r_offset)) &&
3006 ((sym_addr + addend - rel->r_offset) <= max_value)) {
3007 *reinterpret_cast<ElfW(Addr)*>(reloc) = sym_addr + addend - rel->r_offset;
3008 } else {
3009 DL_ERR("0x%016llx out of range 0x%016llx to 0x%016llx",
3010 sym_addr + addend - rel->r_offset, min_value, max_value);
3011 return false;
3012 }
3013 }
3014 break;
3015
3016 case R_AARCH64_COPY:
3017 /*
3018 * ET_EXEC is not supported so this should not happen.
3019 *
3020 * http://infocenter.arm.com/help/topic/com.arm.doc.ihi0056b/IHI0056B_aaelf64.pdf
3021 *
3022 * Section 4.6.11 "Dynamic relocations"
3023 * R_AARCH64_COPY may only appear in executable objects where e_type is
3024 * set to ET_EXEC.
3025 */
3026 DL_ERR("%s R_AARCH64_COPY relocations are not supported", get_realpath());
3027 return false;
3028 case R_AARCH64_TLS_TPREL64:
3029 TRACE_TYPE(RELO, "RELO TLS_TPREL64 *** %16llx <- %16llx - %16llx\n",
3030 reloc, (sym_addr + addend), rel->r_offset);
3031 break;
3032 case R_AARCH64_TLS_DTPREL32:
3033 TRACE_TYPE(RELO, "RELO TLS_DTPREL32 *** %16llx <- %16llx - %16llx\n",
3034 reloc, (sym_addr + addend), rel->r_offset);
3035 break;
3036 #elif defined(__x86_64__)
3037 case R_X86_64_32:
3038 count_relocation(kRelocRelative);
3039 MARK(rel->r_offset);
3040 TRACE_TYPE(RELO, "RELO R_X86_64_32 %08zx <- +%08zx %s", static_cast<size_t>(reloc),
3041 static_cast<size_t>(sym_addr), sym_name);
3042 *reinterpret_cast<Elf32_Addr*>(reloc) = sym_addr + addend;
3043 break;
3044 case R_X86_64_64:
3045 count_relocation(kRelocRelative);
3046 MARK(rel->r_offset);
3047 TRACE_TYPE(RELO, "RELO R_X86_64_64 %08zx <- +%08zx %s", static_cast<size_t>(reloc),
3048 static_cast<size_t>(sym_addr), sym_name);
3049 *reinterpret_cast<Elf64_Addr*>(reloc) = sym_addr + addend;
3050 break;
3051 case R_X86_64_PC32:
3052 count_relocation(kRelocRelative);
3053 MARK(rel->r_offset);
3054 TRACE_TYPE(RELO, "RELO R_X86_64_PC32 %08zx <- +%08zx (%08zx - %08zx) %s",
3055 static_cast<size_t>(reloc), static_cast<size_t>(sym_addr - reloc),
3056 static_cast<size_t>(sym_addr), static_cast<size_t>(reloc), sym_name);
3057 *reinterpret_cast<Elf32_Addr*>(reloc) = sym_addr + addend - reloc;
3058 break;
3059 #elif defined(__arm__)
3060 case R_ARM_ABS32:
3061 count_relocation(kRelocAbsolute);
3062 MARK(rel->r_offset);
3063 TRACE_TYPE(RELO, "RELO ABS %08x <- %08x %s", reloc, sym_addr, sym_name);
3064 *reinterpret_cast<ElfW(Addr)*>(reloc) += sym_addr;
3065 break;
3066 case R_ARM_REL32:
3067 count_relocation(kRelocRelative);
3068 MARK(rel->r_offset);
3069 TRACE_TYPE(RELO, "RELO REL32 %08x <- %08x - %08x %s",
3070 reloc, sym_addr, rel->r_offset, sym_name);
3071 *reinterpret_cast<ElfW(Addr)*>(reloc) += sym_addr - rel->r_offset;
3072 break;
3073 case R_ARM_COPY:
3074 /*
3075 * ET_EXEC is not supported so this should not happen.
3076 *
3077 * http://infocenter.arm.com/help/topic/com.arm.doc.ihi0044d/IHI0044D_aaelf.pdf
3078 *
3079 * Section 4.6.1.10 "Dynamic relocations"
3080 * R_ARM_COPY may only appear in executable objects where e_type is
3081 * set to ET_EXEC.
3082 */
3083 DL_ERR("%s R_ARM_COPY relocations are not supported", get_realpath());
3084 return false;
3085 #elif defined(__i386__)
3086 case R_386_32:
3087 count_relocation(kRelocRelative);
3088 MARK(rel->r_offset);
3089 TRACE_TYPE(RELO, "RELO R_386_32 %08x <- +%08x %s", reloc, sym_addr, sym_name);
3090 *reinterpret_cast<ElfW(Addr)*>(reloc) += sym_addr;
3091 break;
3092 case R_386_PC32:
3093 count_relocation(kRelocRelative);
3094 MARK(rel->r_offset);
3095 TRACE_TYPE(RELO, "RELO R_386_PC32 %08x <- +%08x (%08x - %08x) %s",
3096 reloc, (sym_addr - reloc), sym_addr, reloc, sym_name);
3097 *reinterpret_cast<ElfW(Addr)*>(reloc) += (sym_addr - reloc);
3098 break;
3099 #endif
3100 default:
3101 DL_ERR("unknown reloc type %d @ %p (%zu)", type, rel, idx);
3102 return false;
3103 }
3104 }
3105 return true;
3106 }
3107 #endif // !defined(__mips__)
3108
call_array(const char * array_name __unused,linker_function_t * functions,size_t count,bool reverse)3109 void soinfo::call_array(const char* array_name __unused, linker_function_t* functions,
3110 size_t count, bool reverse) {
3111 if (functions == nullptr) {
3112 return;
3113 }
3114
3115 TRACE("[ Calling %s (size %zd) @ %p for \"%s\" ]", array_name, count, functions, get_realpath());
3116
3117 int begin = reverse ? (count - 1) : 0;
3118 int end = reverse ? -1 : count;
3119 int step = reverse ? -1 : 1;
3120
3121 for (int i = begin; i != end; i += step) {
3122 TRACE("[ %s[%d] == %p ]", array_name, i, functions[i]);
3123 call_function("function", functions[i]);
3124 }
3125
3126 TRACE("[ Done calling %s for \"%s\" ]", array_name, get_realpath());
3127 }
3128
call_function(const char * function_name __unused,linker_function_t function)3129 void soinfo::call_function(const char* function_name __unused, linker_function_t function) {
3130 if (function == nullptr || reinterpret_cast<uintptr_t>(function) == static_cast<uintptr_t>(-1)) {
3131 return;
3132 }
3133
3134 TRACE("[ Calling %s @ %p for \"%s\" ]", function_name, function, get_realpath());
3135 function();
3136 TRACE("[ Done calling %s @ %p for \"%s\" ]", function_name, function, get_realpath());
3137 }
3138
call_pre_init_constructors()3139 void soinfo::call_pre_init_constructors() {
3140 // DT_PREINIT_ARRAY functions are called before any other constructors for executables,
3141 // but ignored in a shared library.
3142 call_array("DT_PREINIT_ARRAY", preinit_array_, preinit_array_count_, false);
3143 }
3144
call_constructors()3145 void soinfo::call_constructors() {
3146 if (constructors_called) {
3147 return;
3148 }
3149
3150 // We set constructors_called before actually calling the constructors, otherwise it doesn't
3151 // protect against recursive constructor calls. One simple example of constructor recursion
3152 // is the libc debug malloc, which is implemented in libc_malloc_debug_leak.so:
3153 // 1. The program depends on libc, so libc's constructor is called here.
3154 // 2. The libc constructor calls dlopen() to load libc_malloc_debug_leak.so.
3155 // 3. dlopen() calls the constructors on the newly created
3156 // soinfo for libc_malloc_debug_leak.so.
3157 // 4. The debug .so depends on libc, so CallConstructors is
3158 // called again with the libc soinfo. If it doesn't trigger the early-
3159 // out above, the libc constructor will be called again (recursively!).
3160 constructors_called = true;
3161
3162 if (!is_main_executable() && preinit_array_ != nullptr) {
3163 // The GNU dynamic linker silently ignores these, but we warn the developer.
3164 PRINT("\"%s\": ignoring DT_PREINIT_ARRAY in shared library!", get_realpath());
3165 }
3166
3167 get_children().for_each([] (soinfo* si) {
3168 si->call_constructors();
3169 });
3170
3171 TRACE("\"%s\": calling constructors", get_realpath());
3172
3173 // DT_INIT should be called before DT_INIT_ARRAY if both are present.
3174 call_function("DT_INIT", init_func_);
3175 call_array("DT_INIT_ARRAY", init_array_, init_array_count_, false);
3176 }
3177
call_destructors()3178 void soinfo::call_destructors() {
3179 if (!constructors_called) {
3180 return;
3181 }
3182 TRACE("\"%s\": calling destructors", get_realpath());
3183
3184 // DT_FINI_ARRAY must be parsed in reverse order.
3185 call_array("DT_FINI_ARRAY", fini_array_, fini_array_count_, true);
3186
3187 // DT_FINI should be called after DT_FINI_ARRAY if both are present.
3188 call_function("DT_FINI", fini_func_);
3189
3190 // This is needed on second call to dlopen
3191 // after library has been unloaded with RTLD_NODELETE
3192 constructors_called = false;
3193 }
3194
add_child(soinfo * child)3195 void soinfo::add_child(soinfo* child) {
3196 if (has_min_version(0)) {
3197 child->parents_.push_back(this);
3198 this->children_.push_back(child);
3199 }
3200 }
3201
remove_all_links()3202 void soinfo::remove_all_links() {
3203 if (!has_min_version(0)) {
3204 return;
3205 }
3206
3207 // 1. Untie connected soinfos from 'this'.
3208 children_.for_each([&] (soinfo* child) {
3209 child->parents_.remove_if([&] (const soinfo* parent) {
3210 return parent == this;
3211 });
3212 });
3213
3214 parents_.for_each([&] (soinfo* parent) {
3215 parent->children_.remove_if([&] (const soinfo* child) {
3216 return child == this;
3217 });
3218 });
3219
3220 // 2. Remove from the primary namespace
3221 primary_namespace_->remove_soinfo(this);
3222 primary_namespace_ = nullptr;
3223
3224 // 3. Remove from secondary namespaces
3225 secondary_namespaces_.for_each([&](android_namespace_t* ns) {
3226 ns->remove_soinfo(this);
3227 });
3228
3229
3230 // 4. Once everything untied - clear local lists.
3231 parents_.clear();
3232 children_.clear();
3233 secondary_namespaces_.clear();
3234 }
3235
get_st_dev() const3236 dev_t soinfo::get_st_dev() const {
3237 if (has_min_version(0)) {
3238 return st_dev_;
3239 }
3240
3241 return 0;
3242 };
3243
get_st_ino() const3244 ino_t soinfo::get_st_ino() const {
3245 if (has_min_version(0)) {
3246 return st_ino_;
3247 }
3248
3249 return 0;
3250 }
3251
get_file_offset() const3252 off64_t soinfo::get_file_offset() const {
3253 if (has_min_version(1)) {
3254 return file_offset_;
3255 }
3256
3257 return 0;
3258 }
3259
get_rtld_flags() const3260 uint32_t soinfo::get_rtld_flags() const {
3261 if (has_min_version(1)) {
3262 return rtld_flags_;
3263 }
3264
3265 return 0;
3266 }
3267
get_dt_flags_1() const3268 uint32_t soinfo::get_dt_flags_1() const {
3269 if (has_min_version(1)) {
3270 return dt_flags_1_;
3271 }
3272
3273 return 0;
3274 }
3275
set_dt_flags_1(uint32_t dt_flags_1)3276 void soinfo::set_dt_flags_1(uint32_t dt_flags_1) {
3277 if (has_min_version(1)) {
3278 if ((dt_flags_1 & DF_1_GLOBAL) != 0) {
3279 rtld_flags_ |= RTLD_GLOBAL;
3280 }
3281
3282 if ((dt_flags_1 & DF_1_NODELETE) != 0) {
3283 rtld_flags_ |= RTLD_NODELETE;
3284 }
3285
3286 dt_flags_1_ = dt_flags_1;
3287 }
3288 }
3289
set_nodelete()3290 void soinfo::set_nodelete() {
3291 rtld_flags_ |= RTLD_NODELETE;
3292 }
3293
get_realpath() const3294 const char* soinfo::get_realpath() const {
3295 #if defined(__work_around_b_24465209__)
3296 if (has_min_version(2)) {
3297 return realpath_.c_str();
3298 } else {
3299 return old_name_;
3300 }
3301 #else
3302 return realpath_.c_str();
3303 #endif
3304 }
3305
set_soname(const char * soname)3306 void soinfo::set_soname(const char* soname) {
3307 #if defined(__work_around_b_24465209__)
3308 if (has_min_version(2)) {
3309 soname_ = soname;
3310 }
3311 strlcpy(old_name_, soname_, sizeof(old_name_));
3312 #else
3313 soname_ = soname;
3314 #endif
3315 }
3316
get_soname() const3317 const char* soinfo::get_soname() const {
3318 #if defined(__work_around_b_24465209__)
3319 if (has_min_version(2)) {
3320 return soname_;
3321 } else {
3322 return old_name_;
3323 }
3324 #else
3325 return soname_;
3326 #endif
3327 }
3328
3329 // This is a return on get_children()/get_parents() if
3330 // 'this->flags' does not have FLAG_NEW_SOINFO set.
3331 static soinfo::soinfo_list_t g_empty_list;
3332
get_children()3333 soinfo::soinfo_list_t& soinfo::get_children() {
3334 if (has_min_version(0)) {
3335 return children_;
3336 }
3337
3338 return g_empty_list;
3339 }
3340
get_children() const3341 const soinfo::soinfo_list_t& soinfo::get_children() const {
3342 if (has_min_version(0)) {
3343 return children_;
3344 }
3345
3346 return g_empty_list;
3347 }
3348
get_parents()3349 soinfo::soinfo_list_t& soinfo::get_parents() {
3350 if (has_min_version(0)) {
3351 return parents_;
3352 }
3353
3354 return g_empty_list;
3355 }
3356
3357 static std::vector<std::string> g_empty_runpath;
3358
get_dt_runpath() const3359 const std::vector<std::string>& soinfo::get_dt_runpath() const {
3360 if (has_min_version(3)) {
3361 return dt_runpath_;
3362 }
3363
3364 return g_empty_runpath;
3365 }
3366
get_primary_namespace()3367 android_namespace_t* soinfo::get_primary_namespace() {
3368 if (has_min_version(3)) {
3369 return primary_namespace_;
3370 }
3371
3372 return &g_default_namespace;
3373 }
3374
add_secondary_namespace(android_namespace_t * secondary_ns)3375 void soinfo::add_secondary_namespace(android_namespace_t* secondary_ns) {
3376 CHECK(has_min_version(3));
3377 secondary_namespaces_.push_back(secondary_ns);
3378 }
3379
ElfW(Addr)3380 ElfW(Addr) soinfo::resolve_symbol_address(const ElfW(Sym)* s) const {
3381 if (ELF_ST_TYPE(s->st_info) == STT_GNU_IFUNC) {
3382 return call_ifunc_resolver(s->st_value + load_bias);
3383 }
3384
3385 return static_cast<ElfW(Addr)>(s->st_value + load_bias);
3386 }
3387
get_string(ElfW (Word)index) const3388 const char* soinfo::get_string(ElfW(Word) index) const {
3389 if (has_min_version(1) && (index >= strtab_size_)) {
3390 __libc_fatal("%s: strtab out of bounds error; STRSZ=%zd, name=%d",
3391 get_realpath(), strtab_size_, index);
3392 }
3393
3394 return strtab_ + index;
3395 }
3396
is_gnu_hash() const3397 bool soinfo::is_gnu_hash() const {
3398 return (flags_ & FLAG_GNU_HASH) != 0;
3399 }
3400
can_unload() const3401 bool soinfo::can_unload() const {
3402 return !is_linked() || ((get_rtld_flags() & (RTLD_NODELETE | RTLD_GLOBAL)) == 0);
3403 }
3404
is_linked() const3405 bool soinfo::is_linked() const {
3406 return (flags_ & FLAG_LINKED) != 0;
3407 }
3408
is_main_executable() const3409 bool soinfo::is_main_executable() const {
3410 return (flags_ & FLAG_EXE) != 0;
3411 }
3412
is_linker() const3413 bool soinfo::is_linker() const {
3414 return (flags_ & FLAG_LINKER) != 0;
3415 }
3416
set_linked()3417 void soinfo::set_linked() {
3418 flags_ |= FLAG_LINKED;
3419 }
3420
set_linker_flag()3421 void soinfo::set_linker_flag() {
3422 flags_ |= FLAG_LINKER;
3423 }
3424
set_main_executable()3425 void soinfo::set_main_executable() {
3426 flags_ |= FLAG_EXE;
3427 }
3428
increment_ref_count()3429 void soinfo::increment_ref_count() {
3430 local_group_root_->ref_count_++;
3431 }
3432
decrement_ref_count()3433 size_t soinfo::decrement_ref_count() {
3434 return --local_group_root_->ref_count_;
3435 }
3436
get_local_group_root() const3437 soinfo* soinfo::get_local_group_root() const {
3438 return local_group_root_;
3439 }
3440
3441
set_mapped_by_caller(bool mapped_by_caller)3442 void soinfo::set_mapped_by_caller(bool mapped_by_caller) {
3443 if (mapped_by_caller) {
3444 flags_ |= FLAG_MAPPED_BY_CALLER;
3445 } else {
3446 flags_ &= ~FLAG_MAPPED_BY_CALLER;
3447 }
3448 }
3449
is_mapped_by_caller() const3450 bool soinfo::is_mapped_by_caller() const {
3451 return (flags_ & FLAG_MAPPED_BY_CALLER) != 0;
3452 }
3453
3454 // This function returns api-level at the time of
3455 // dlopen/load. Note that libraries opened by system
3456 // will always have 'current' api level.
get_target_sdk_version() const3457 uint32_t soinfo::get_target_sdk_version() const {
3458 if (!has_min_version(2)) {
3459 return __ANDROID_API__;
3460 }
3461
3462 return local_group_root_->target_sdk_version_;
3463 }
3464
get_handle() const3465 uintptr_t soinfo::get_handle() const {
3466 CHECK(has_min_version(3));
3467 CHECK(handle_ != 0);
3468 return handle_;
3469 }
3470
to_handle()3471 void* soinfo::to_handle() {
3472 if (get_application_target_sdk_version() <= 23 || !has_min_version(3)) {
3473 return this;
3474 }
3475
3476 return reinterpret_cast<void*>(get_handle());
3477 }
3478
generate_handle()3479 void soinfo::generate_handle() {
3480 CHECK(has_min_version(3));
3481 CHECK(handle_ == 0); // Make sure this is the first call
3482
3483 // Make sure the handle is unique and does not collide
3484 // with special values which are RTLD_DEFAULT and RTLD_NEXT.
3485 do {
3486 arc4random_buf(&handle_, sizeof(handle_));
3487 // the least significant bit for the handle is always 1
3488 // making it easy to test the type of handle passed to
3489 // dl* functions.
3490 handle_ = handle_ | 1;
3491 } while (handle_ == reinterpret_cast<uintptr_t>(RTLD_DEFAULT) ||
3492 handle_ == reinterpret_cast<uintptr_t>(RTLD_NEXT) ||
3493 g_soinfo_handles_map.find(handle_) != g_soinfo_handles_map.end());
3494
3495 g_soinfo_handles_map[handle_] = this;
3496 }
3497
prelink_image()3498 bool soinfo::prelink_image() {
3499 /* Extract dynamic section */
3500 ElfW(Word) dynamic_flags = 0;
3501 phdr_table_get_dynamic_section(phdr, phnum, load_bias, &dynamic, &dynamic_flags);
3502
3503 /* We can't log anything until the linker is relocated */
3504 bool relocating_linker = (flags_ & FLAG_LINKER) != 0;
3505 if (!relocating_linker) {
3506 INFO("[ Linking \"%s\" ]", get_realpath());
3507 DEBUG("si->base = %p si->flags = 0x%08x", reinterpret_cast<void*>(base), flags_);
3508 }
3509
3510 if (dynamic == nullptr) {
3511 if (!relocating_linker) {
3512 DL_ERR("missing PT_DYNAMIC in \"%s\"", get_realpath());
3513 }
3514 return false;
3515 } else {
3516 if (!relocating_linker) {
3517 DEBUG("dynamic = %p", dynamic);
3518 }
3519 }
3520
3521 #if defined(__arm__)
3522 (void) phdr_table_get_arm_exidx(phdr, phnum, load_bias,
3523 &ARM_exidx, &ARM_exidx_count);
3524 #endif
3525
3526 // Extract useful information from dynamic section.
3527 // Note that: "Except for the DT_NULL element at the end of the array,
3528 // and the relative order of DT_NEEDED elements, entries may appear in any order."
3529 //
3530 // source: http://www.sco.com/developers/gabi/1998-04-29/ch5.dynamic.html
3531 uint32_t needed_count = 0;
3532 for (ElfW(Dyn)* d = dynamic; d->d_tag != DT_NULL; ++d) {
3533 DEBUG("d = %p, d[0](tag) = %p d[1](val) = %p",
3534 d, reinterpret_cast<void*>(d->d_tag), reinterpret_cast<void*>(d->d_un.d_val));
3535 switch (d->d_tag) {
3536 case DT_SONAME:
3537 // this is parsed after we have strtab initialized (see below).
3538 break;
3539
3540 case DT_HASH:
3541 nbucket_ = reinterpret_cast<uint32_t*>(load_bias + d->d_un.d_ptr)[0];
3542 nchain_ = reinterpret_cast<uint32_t*>(load_bias + d->d_un.d_ptr)[1];
3543 bucket_ = reinterpret_cast<uint32_t*>(load_bias + d->d_un.d_ptr + 8);
3544 chain_ = reinterpret_cast<uint32_t*>(load_bias + d->d_un.d_ptr + 8 + nbucket_ * 4);
3545 break;
3546
3547 case DT_GNU_HASH:
3548 gnu_nbucket_ = reinterpret_cast<uint32_t*>(load_bias + d->d_un.d_ptr)[0];
3549 // skip symndx
3550 gnu_maskwords_ = reinterpret_cast<uint32_t*>(load_bias + d->d_un.d_ptr)[2];
3551 gnu_shift2_ = reinterpret_cast<uint32_t*>(load_bias + d->d_un.d_ptr)[3];
3552
3553 gnu_bloom_filter_ = reinterpret_cast<ElfW(Addr)*>(load_bias + d->d_un.d_ptr + 16);
3554 gnu_bucket_ = reinterpret_cast<uint32_t*>(gnu_bloom_filter_ + gnu_maskwords_);
3555 // amend chain for symndx = header[1]
3556 gnu_chain_ = gnu_bucket_ + gnu_nbucket_ -
3557 reinterpret_cast<uint32_t*>(load_bias + d->d_un.d_ptr)[1];
3558
3559 if (!powerof2(gnu_maskwords_)) {
3560 DL_ERR("invalid maskwords for gnu_hash = 0x%x, in \"%s\" expecting power to two",
3561 gnu_maskwords_, get_realpath());
3562 return false;
3563 }
3564 --gnu_maskwords_;
3565
3566 flags_ |= FLAG_GNU_HASH;
3567 break;
3568
3569 case DT_STRTAB:
3570 strtab_ = reinterpret_cast<const char*>(load_bias + d->d_un.d_ptr);
3571 break;
3572
3573 case DT_STRSZ:
3574 strtab_size_ = d->d_un.d_val;
3575 break;
3576
3577 case DT_SYMTAB:
3578 symtab_ = reinterpret_cast<ElfW(Sym)*>(load_bias + d->d_un.d_ptr);
3579 break;
3580
3581 case DT_SYMENT:
3582 if (d->d_un.d_val != sizeof(ElfW(Sym))) {
3583 DL_ERR("invalid DT_SYMENT: %zd in \"%s\"",
3584 static_cast<size_t>(d->d_un.d_val), get_realpath());
3585 return false;
3586 }
3587 break;
3588
3589 case DT_PLTREL:
3590 #if defined(USE_RELA)
3591 if (d->d_un.d_val != DT_RELA) {
3592 DL_ERR("unsupported DT_PLTREL in \"%s\"; expected DT_RELA", get_realpath());
3593 return false;
3594 }
3595 #else
3596 if (d->d_un.d_val != DT_REL) {
3597 DL_ERR("unsupported DT_PLTREL in \"%s\"; expected DT_REL", get_realpath());
3598 return false;
3599 }
3600 #endif
3601 break;
3602
3603 case DT_JMPREL:
3604 #if defined(USE_RELA)
3605 plt_rela_ = reinterpret_cast<ElfW(Rela)*>(load_bias + d->d_un.d_ptr);
3606 #else
3607 plt_rel_ = reinterpret_cast<ElfW(Rel)*>(load_bias + d->d_un.d_ptr);
3608 #endif
3609 break;
3610
3611 case DT_PLTRELSZ:
3612 #if defined(USE_RELA)
3613 plt_rela_count_ = d->d_un.d_val / sizeof(ElfW(Rela));
3614 #else
3615 plt_rel_count_ = d->d_un.d_val / sizeof(ElfW(Rel));
3616 #endif
3617 break;
3618
3619 case DT_PLTGOT:
3620 #if defined(__mips__)
3621 // Used by mips and mips64.
3622 plt_got_ = reinterpret_cast<ElfW(Addr)**>(load_bias + d->d_un.d_ptr);
3623 #endif
3624 // Ignore for other platforms... (because RTLD_LAZY is not supported)
3625 break;
3626
3627 case DT_DEBUG:
3628 // Set the DT_DEBUG entry to the address of _r_debug for GDB
3629 // if the dynamic table is writable
3630 // FIXME: not working currently for N64
3631 // The flags for the LOAD and DYNAMIC program headers do not agree.
3632 // The LOAD section containing the dynamic table has been mapped as
3633 // read-only, but the DYNAMIC header claims it is writable.
3634 #if !(defined(__mips__) && defined(__LP64__))
3635 if ((dynamic_flags & PF_W) != 0) {
3636 d->d_un.d_val = reinterpret_cast<uintptr_t>(&_r_debug);
3637 }
3638 #endif
3639 break;
3640 #if defined(USE_RELA)
3641 case DT_RELA:
3642 rela_ = reinterpret_cast<ElfW(Rela)*>(load_bias + d->d_un.d_ptr);
3643 break;
3644
3645 case DT_RELASZ:
3646 rela_count_ = d->d_un.d_val / sizeof(ElfW(Rela));
3647 break;
3648
3649 case DT_ANDROID_RELA:
3650 android_relocs_ = reinterpret_cast<uint8_t*>(load_bias + d->d_un.d_ptr);
3651 break;
3652
3653 case DT_ANDROID_RELASZ:
3654 android_relocs_size_ = d->d_un.d_val;
3655 break;
3656
3657 case DT_ANDROID_REL:
3658 DL_ERR("unsupported DT_ANDROID_REL in \"%s\"", get_realpath());
3659 return false;
3660
3661 case DT_ANDROID_RELSZ:
3662 DL_ERR("unsupported DT_ANDROID_RELSZ in \"%s\"", get_realpath());
3663 return false;
3664
3665 case DT_RELAENT:
3666 if (d->d_un.d_val != sizeof(ElfW(Rela))) {
3667 DL_ERR("invalid DT_RELAENT: %zd", static_cast<size_t>(d->d_un.d_val));
3668 return false;
3669 }
3670 break;
3671
3672 // ignored (see DT_RELCOUNT comments for details)
3673 case DT_RELACOUNT:
3674 break;
3675
3676 case DT_REL:
3677 DL_ERR("unsupported DT_REL in \"%s\"", get_realpath());
3678 return false;
3679
3680 case DT_RELSZ:
3681 DL_ERR("unsupported DT_RELSZ in \"%s\"", get_realpath());
3682 return false;
3683
3684 #else
3685 case DT_REL:
3686 rel_ = reinterpret_cast<ElfW(Rel)*>(load_bias + d->d_un.d_ptr);
3687 break;
3688
3689 case DT_RELSZ:
3690 rel_count_ = d->d_un.d_val / sizeof(ElfW(Rel));
3691 break;
3692
3693 case DT_RELENT:
3694 if (d->d_un.d_val != sizeof(ElfW(Rel))) {
3695 DL_ERR("invalid DT_RELENT: %zd", static_cast<size_t>(d->d_un.d_val));
3696 return false;
3697 }
3698 break;
3699
3700 case DT_ANDROID_REL:
3701 android_relocs_ = reinterpret_cast<uint8_t*>(load_bias + d->d_un.d_ptr);
3702 break;
3703
3704 case DT_ANDROID_RELSZ:
3705 android_relocs_size_ = d->d_un.d_val;
3706 break;
3707
3708 case DT_ANDROID_RELA:
3709 DL_ERR("unsupported DT_ANDROID_RELA in \"%s\"", get_realpath());
3710 return false;
3711
3712 case DT_ANDROID_RELASZ:
3713 DL_ERR("unsupported DT_ANDROID_RELASZ in \"%s\"", get_realpath());
3714 return false;
3715
3716 // "Indicates that all RELATIVE relocations have been concatenated together,
3717 // and specifies the RELATIVE relocation count."
3718 //
3719 // TODO: Spec also mentions that this can be used to optimize relocation process;
3720 // Not currently used by bionic linker - ignored.
3721 case DT_RELCOUNT:
3722 break;
3723
3724 case DT_RELA:
3725 DL_ERR("unsupported DT_RELA in \"%s\"", get_realpath());
3726 return false;
3727
3728 case DT_RELASZ:
3729 DL_ERR("unsupported DT_RELASZ in \"%s\"", get_realpath());
3730 return false;
3731
3732 #endif
3733 case DT_INIT:
3734 init_func_ = reinterpret_cast<linker_function_t>(load_bias + d->d_un.d_ptr);
3735 DEBUG("%s constructors (DT_INIT) found at %p", get_realpath(), init_func_);
3736 break;
3737
3738 case DT_FINI:
3739 fini_func_ = reinterpret_cast<linker_function_t>(load_bias + d->d_un.d_ptr);
3740 DEBUG("%s destructors (DT_FINI) found at %p", get_realpath(), fini_func_);
3741 break;
3742
3743 case DT_INIT_ARRAY:
3744 init_array_ = reinterpret_cast<linker_function_t*>(load_bias + d->d_un.d_ptr);
3745 DEBUG("%s constructors (DT_INIT_ARRAY) found at %p", get_realpath(), init_array_);
3746 break;
3747
3748 case DT_INIT_ARRAYSZ:
3749 init_array_count_ = static_cast<uint32_t>(d->d_un.d_val) / sizeof(ElfW(Addr));
3750 break;
3751
3752 case DT_FINI_ARRAY:
3753 fini_array_ = reinterpret_cast<linker_function_t*>(load_bias + d->d_un.d_ptr);
3754 DEBUG("%s destructors (DT_FINI_ARRAY) found at %p", get_realpath(), fini_array_);
3755 break;
3756
3757 case DT_FINI_ARRAYSZ:
3758 fini_array_count_ = static_cast<uint32_t>(d->d_un.d_val) / sizeof(ElfW(Addr));
3759 break;
3760
3761 case DT_PREINIT_ARRAY:
3762 preinit_array_ = reinterpret_cast<linker_function_t*>(load_bias + d->d_un.d_ptr);
3763 DEBUG("%s constructors (DT_PREINIT_ARRAY) found at %p", get_realpath(), preinit_array_);
3764 break;
3765
3766 case DT_PREINIT_ARRAYSZ:
3767 preinit_array_count_ = static_cast<uint32_t>(d->d_un.d_val) / sizeof(ElfW(Addr));
3768 break;
3769
3770 case DT_TEXTREL:
3771 #if defined(__LP64__)
3772 DL_ERR("text relocations (DT_TEXTREL) found in 64-bit ELF file \"%s\"", get_realpath());
3773 return false;
3774 #else
3775 has_text_relocations = true;
3776 break;
3777 #endif
3778
3779 case DT_SYMBOLIC:
3780 has_DT_SYMBOLIC = true;
3781 break;
3782
3783 case DT_NEEDED:
3784 ++needed_count;
3785 break;
3786
3787 case DT_FLAGS:
3788 if (d->d_un.d_val & DF_TEXTREL) {
3789 #if defined(__LP64__)
3790 DL_ERR("text relocations (DF_TEXTREL) found in 64-bit ELF file \"%s\"", get_realpath());
3791 return false;
3792 #else
3793 has_text_relocations = true;
3794 #endif
3795 }
3796 if (d->d_un.d_val & DF_SYMBOLIC) {
3797 has_DT_SYMBOLIC = true;
3798 }
3799 break;
3800
3801 case DT_FLAGS_1:
3802 set_dt_flags_1(d->d_un.d_val);
3803
3804 if ((d->d_un.d_val & ~SUPPORTED_DT_FLAGS_1) != 0) {
3805 DL_WARN("%s: unsupported flags DT_FLAGS_1=%p", get_realpath(), reinterpret_cast<void*>(d->d_un.d_val));
3806 }
3807 break;
3808 #if defined(__mips__)
3809 case DT_MIPS_RLD_MAP:
3810 // Set the DT_MIPS_RLD_MAP entry to the address of _r_debug for GDB.
3811 {
3812 r_debug** dp = reinterpret_cast<r_debug**>(load_bias + d->d_un.d_ptr);
3813 *dp = &_r_debug;
3814 }
3815 break;
3816 case DT_MIPS_RLD_MAP2:
3817 // Set the DT_MIPS_RLD_MAP2 entry to the address of _r_debug for GDB.
3818 {
3819 r_debug** dp = reinterpret_cast<r_debug**>(
3820 reinterpret_cast<ElfW(Addr)>(d) + d->d_un.d_val);
3821 *dp = &_r_debug;
3822 }
3823 break;
3824
3825 case DT_MIPS_RLD_VERSION:
3826 case DT_MIPS_FLAGS:
3827 case DT_MIPS_BASE_ADDRESS:
3828 case DT_MIPS_UNREFEXTNO:
3829 break;
3830
3831 case DT_MIPS_SYMTABNO:
3832 mips_symtabno_ = d->d_un.d_val;
3833 break;
3834
3835 case DT_MIPS_LOCAL_GOTNO:
3836 mips_local_gotno_ = d->d_un.d_val;
3837 break;
3838
3839 case DT_MIPS_GOTSYM:
3840 mips_gotsym_ = d->d_un.d_val;
3841 break;
3842 #endif
3843 // Ignored: "Its use has been superseded by the DF_BIND_NOW flag"
3844 case DT_BIND_NOW:
3845 break;
3846
3847 case DT_VERSYM:
3848 versym_ = reinterpret_cast<ElfW(Versym)*>(load_bias + d->d_un.d_ptr);
3849 break;
3850
3851 case DT_VERDEF:
3852 verdef_ptr_ = load_bias + d->d_un.d_ptr;
3853 break;
3854 case DT_VERDEFNUM:
3855 verdef_cnt_ = d->d_un.d_val;
3856 break;
3857
3858 case DT_VERNEED:
3859 verneed_ptr_ = load_bias + d->d_un.d_ptr;
3860 break;
3861
3862 case DT_VERNEEDNUM:
3863 verneed_cnt_ = d->d_un.d_val;
3864 break;
3865
3866 case DT_RUNPATH:
3867 // this is parsed after we have strtab initialized (see below).
3868 break;
3869
3870 default:
3871 if (!relocating_linker) {
3872 DL_WARN("%s: unused DT entry: type %p arg %p", get_realpath(),
3873 reinterpret_cast<void*>(d->d_tag), reinterpret_cast<void*>(d->d_un.d_val));
3874 }
3875 break;
3876 }
3877 }
3878
3879 #if defined(__mips__) && !defined(__LP64__)
3880 if (!mips_check_and_adjust_fp_modes()) {
3881 return false;
3882 }
3883 #endif
3884
3885 DEBUG("si->base = %p, si->strtab = %p, si->symtab = %p",
3886 reinterpret_cast<void*>(base), strtab_, symtab_);
3887
3888 // Sanity checks.
3889 if (relocating_linker && needed_count != 0) {
3890 DL_ERR("linker cannot have DT_NEEDED dependencies on other libraries");
3891 return false;
3892 }
3893 if (nbucket_ == 0 && gnu_nbucket_ == 0) {
3894 DL_ERR("empty/missing DT_HASH/DT_GNU_HASH in \"%s\" "
3895 "(new hash type from the future?)", get_realpath());
3896 return false;
3897 }
3898 if (strtab_ == 0) {
3899 DL_ERR("empty/missing DT_STRTAB in \"%s\"", get_realpath());
3900 return false;
3901 }
3902 if (symtab_ == 0) {
3903 DL_ERR("empty/missing DT_SYMTAB in \"%s\"", get_realpath());
3904 return false;
3905 }
3906
3907 // second pass - parse entries relying on strtab
3908 for (ElfW(Dyn)* d = dynamic; d->d_tag != DT_NULL; ++d) {
3909 switch (d->d_tag) {
3910 case DT_SONAME:
3911 set_soname(get_string(d->d_un.d_val));
3912 break;
3913 case DT_RUNPATH:
3914 set_dt_runpath(get_string(d->d_un.d_val));
3915 break;
3916 }
3917 }
3918
3919 // Before M release linker was using basename in place of soname.
3920 // In the case when dt_soname is absent some apps stop working
3921 // because they can't find dt_needed library by soname.
3922 // This workaround should keep them working. (applies only
3923 // for apps targeting sdk version <=22). Make an exception for
3924 // the main executable and linker; they do not need to have dt_soname
3925 if (soname_ == nullptr && this != somain && (flags_ & FLAG_LINKER) == 0 &&
3926 get_application_target_sdk_version() <= 22) {
3927 soname_ = basename(realpath_.c_str());
3928 DL_WARN("%s: is missing DT_SONAME will use basename as a replacement: \"%s\"",
3929 get_realpath(), soname_);
3930 // Don't call add_dlwarning because a missing DT_SONAME isn't important enough to show in the UI
3931 }
3932 return true;
3933 }
3934
link_image(const soinfo_list_t & global_group,const soinfo_list_t & local_group,const android_dlextinfo * extinfo)3935 bool soinfo::link_image(const soinfo_list_t& global_group, const soinfo_list_t& local_group,
3936 const android_dlextinfo* extinfo) {
3937
3938 local_group_root_ = local_group.front();
3939 if (local_group_root_ == nullptr) {
3940 local_group_root_ = this;
3941 }
3942
3943 if ((flags_ & FLAG_LINKER) == 0 && local_group_root_ == this) {
3944 target_sdk_version_ = get_application_target_sdk_version();
3945 }
3946
3947 VersionTracker version_tracker;
3948
3949 if (!version_tracker.init(this)) {
3950 return false;
3951 }
3952
3953 #if !defined(__LP64__)
3954 if (has_text_relocations) {
3955 // Fail if app is targeting sdk version > 22
3956 if (get_application_target_sdk_version() > 22) {
3957 PRINT("%s: has text relocations", get_realpath());
3958 DL_ERR("%s: has text relocations", get_realpath());
3959 return false;
3960 }
3961 // Make segments writable to allow text relocations to work properly. We will later call
3962 // phdr_table_protect_segments() after all of them are applied.
3963 DL_WARN("%s has text relocations. This is wasting memory and prevents "
3964 "security hardening. Please fix.", get_realpath());
3965 add_dlwarning(get_realpath(), "text relocations");
3966 if (phdr_table_unprotect_segments(phdr, phnum, load_bias) < 0) {
3967 DL_ERR("can't unprotect loadable segments for \"%s\": %s",
3968 get_realpath(), strerror(errno));
3969 return false;
3970 }
3971 }
3972 #endif
3973
3974 if (android_relocs_ != nullptr) {
3975 // check signature
3976 if (android_relocs_size_ > 3 &&
3977 android_relocs_[0] == 'A' &&
3978 android_relocs_[1] == 'P' &&
3979 android_relocs_[2] == 'S' &&
3980 android_relocs_[3] == '2') {
3981 DEBUG("[ android relocating %s ]", get_realpath());
3982
3983 bool relocated = false;
3984 const uint8_t* packed_relocs = android_relocs_ + 4;
3985 const size_t packed_relocs_size = android_relocs_size_ - 4;
3986
3987 relocated = relocate(
3988 version_tracker,
3989 packed_reloc_iterator<sleb128_decoder>(
3990 sleb128_decoder(packed_relocs, packed_relocs_size)),
3991 global_group, local_group);
3992
3993 if (!relocated) {
3994 return false;
3995 }
3996 } else {
3997 DL_ERR("bad android relocation header.");
3998 return false;
3999 }
4000 }
4001
4002 #if defined(USE_RELA)
4003 if (rela_ != nullptr) {
4004 DEBUG("[ relocating %s ]", get_realpath());
4005 if (!relocate(version_tracker,
4006 plain_reloc_iterator(rela_, rela_count_), global_group, local_group)) {
4007 return false;
4008 }
4009 }
4010 if (plt_rela_ != nullptr) {
4011 DEBUG("[ relocating %s plt ]", get_realpath());
4012 if (!relocate(version_tracker,
4013 plain_reloc_iterator(plt_rela_, plt_rela_count_), global_group, local_group)) {
4014 return false;
4015 }
4016 }
4017 #else
4018 if (rel_ != nullptr) {
4019 DEBUG("[ relocating %s ]", get_realpath());
4020 if (!relocate(version_tracker,
4021 plain_reloc_iterator(rel_, rel_count_), global_group, local_group)) {
4022 return false;
4023 }
4024 }
4025 if (plt_rel_ != nullptr) {
4026 DEBUG("[ relocating %s plt ]", get_realpath());
4027 if (!relocate(version_tracker,
4028 plain_reloc_iterator(plt_rel_, plt_rel_count_), global_group, local_group)) {
4029 return false;
4030 }
4031 }
4032 #endif
4033
4034 #if defined(__mips__)
4035 if (!mips_relocate_got(version_tracker, global_group, local_group)) {
4036 return false;
4037 }
4038 #endif
4039
4040 DEBUG("[ finished linking %s ]", get_realpath());
4041
4042 #if !defined(__LP64__)
4043 if (has_text_relocations) {
4044 // All relocations are done, we can protect our segments back to read-only.
4045 if (phdr_table_protect_segments(phdr, phnum, load_bias) < 0) {
4046 DL_ERR("can't protect segments for \"%s\": %s",
4047 get_realpath(), strerror(errno));
4048 return false;
4049 }
4050 }
4051 #endif
4052
4053 // We can also turn on GNU RELRO protection if we're not linking the dynamic linker
4054 // itself --- it can't make system calls yet, and will have to call protect_relro later.
4055 if (!is_linker() && !protect_relro()) {
4056 return false;
4057 }
4058
4059 /* Handle serializing/sharing the RELRO segment */
4060 if (extinfo && (extinfo->flags & ANDROID_DLEXT_WRITE_RELRO)) {
4061 if (phdr_table_serialize_gnu_relro(phdr, phnum, load_bias,
4062 extinfo->relro_fd) < 0) {
4063 DL_ERR("failed serializing GNU RELRO section for \"%s\": %s",
4064 get_realpath(), strerror(errno));
4065 return false;
4066 }
4067 } else if (extinfo && (extinfo->flags & ANDROID_DLEXT_USE_RELRO)) {
4068 if (phdr_table_map_gnu_relro(phdr, phnum, load_bias,
4069 extinfo->relro_fd) < 0) {
4070 DL_ERR("failed mapping GNU RELRO section for \"%s\": %s",
4071 get_realpath(), strerror(errno));
4072 return false;
4073 }
4074 }
4075
4076 notify_gdb_of_load(this);
4077 return true;
4078 }
4079
protect_relro()4080 bool soinfo::protect_relro() {
4081 if (phdr_table_protect_gnu_relro(phdr, phnum, load_bias) < 0) {
4082 DL_ERR("can't enable GNU RELRO protection for \"%s\": %s",
4083 get_realpath(), strerror(errno));
4084 return false;
4085 }
4086 return true;
4087 }
4088
4089 /*
4090 * This function add vdso to internal dso list.
4091 * It helps to stack unwinding through signal handlers.
4092 * Also, it makes bionic more like glibc.
4093 */
add_vdso(KernelArgumentBlock & args __unused)4094 static void add_vdso(KernelArgumentBlock& args __unused) {
4095 #if defined(AT_SYSINFO_EHDR)
4096 ElfW(Ehdr)* ehdr_vdso = reinterpret_cast<ElfW(Ehdr)*>(args.getauxval(AT_SYSINFO_EHDR));
4097 if (ehdr_vdso == nullptr) {
4098 return;
4099 }
4100
4101 soinfo* si = soinfo_alloc(&g_default_namespace, "[vdso]", nullptr, 0, 0);
4102
4103 si->phdr = reinterpret_cast<ElfW(Phdr)*>(reinterpret_cast<char*>(ehdr_vdso) + ehdr_vdso->e_phoff);
4104 si->phnum = ehdr_vdso->e_phnum;
4105 si->base = reinterpret_cast<ElfW(Addr)>(ehdr_vdso);
4106 si->size = phdr_table_get_load_size(si->phdr, si->phnum);
4107 si->load_bias = get_elf_exec_load_bias(ehdr_vdso);
4108
4109 si->prelink_image();
4110 si->link_image(g_empty_list, soinfo::soinfo_list_t::make_list(si), nullptr);
4111 #endif
4112 }
4113
4114 /* gdb expects the linker to be in the debug shared object list.
4115 * Without this, gdb has trouble locating the linker's ".text"
4116 * and ".plt" sections. Gdb could also potentially use this to
4117 * relocate the offset of our exported 'rtld_db_dlactivity' symbol.
4118 * Note that the linker shouldn't be on the soinfo list.
4119 */
init_linker_info_for_gdb(ElfW (Addr)linker_base)4120 static void init_linker_info_for_gdb(ElfW(Addr) linker_base) {
4121 static link_map linker_link_map_for_gdb;
4122 #if defined(__LP64__)
4123 static char kLinkerPath[] = "/system/bin/linker64";
4124 #else
4125 static char kLinkerPath[] = "/system/bin/linker";
4126 #endif
4127
4128 linker_link_map_for_gdb.l_addr = linker_base;
4129 linker_link_map_for_gdb.l_name = kLinkerPath;
4130
4131 /*
4132 * Set the dynamic field in the link map otherwise gdb will complain with
4133 * the following:
4134 * warning: .dynamic section for "/system/bin/linker" is not at the
4135 * expected address (wrong library or version mismatch?)
4136 */
4137 ElfW(Ehdr)* elf_hdr = reinterpret_cast<ElfW(Ehdr)*>(linker_base);
4138 ElfW(Phdr)* phdr = reinterpret_cast<ElfW(Phdr)*>(linker_base + elf_hdr->e_phoff);
4139 phdr_table_get_dynamic_section(phdr, elf_hdr->e_phnum, linker_base,
4140 &linker_link_map_for_gdb.l_ld, nullptr);
4141
4142 insert_link_map_into_debug_map(&linker_link_map_for_gdb);
4143 }
4144
init_default_namespace()4145 static void init_default_namespace() {
4146 g_default_namespace.set_name("(default)");
4147 g_default_namespace.set_isolated(false);
4148
4149 const char *interp = phdr_table_get_interpreter_name(somain->phdr, somain->phnum,
4150 somain->load_bias);
4151 const char* bname = basename(interp);
4152 if (bname && (strcmp(bname, "linker_asan") == 0 || strcmp(bname, "linker_asan64") == 0)) {
4153 g_default_ld_paths = kAsanDefaultLdPaths;
4154 g_is_asan = true;
4155 } else {
4156 g_default_ld_paths = kDefaultLdPaths;
4157 }
4158
4159 char real_path[PATH_MAX];
4160 std::vector<std::string> ld_default_paths;
4161 for (size_t i = 0; g_default_ld_paths[i] != nullptr; ++i) {
4162 if (realpath(g_default_ld_paths[i], real_path) != nullptr) {
4163 ld_default_paths.push_back(real_path);
4164 } else {
4165 ld_default_paths.push_back(g_default_ld_paths[i]);
4166 }
4167 }
4168
4169 g_default_namespace.set_default_library_paths(std::move(ld_default_paths));
4170 };
4171
4172 extern "C" int __system_properties_init(void);
4173
get_executable_path()4174 static const char* get_executable_path() {
4175 static std::string executable_path;
4176 if (executable_path.empty()) {
4177 char path[PATH_MAX];
4178 ssize_t path_len = readlink("/proc/self/exe", path, sizeof(path));
4179 if (path_len == -1 || path_len >= static_cast<ssize_t>(sizeof(path))) {
4180 __libc_fatal("readlink('/proc/self/exe') failed: %s", strerror(errno));
4181 }
4182 executable_path = std::string(path, path_len);
4183 }
4184
4185 return executable_path.c_str();
4186 }
4187
4188 /*
4189 * This code is called after the linker has linked itself and
4190 * fixed it's own GOT. It is safe to make references to externs
4191 * and other non-local data at this point.
4192 */
__linker_init_post_relocation(KernelArgumentBlock & args,ElfW (Addr)linker_base)4193 static ElfW(Addr) __linker_init_post_relocation(KernelArgumentBlock& args, ElfW(Addr) linker_base) {
4194 #if TIMING
4195 struct timeval t0, t1;
4196 gettimeofday(&t0, 0);
4197 #endif
4198
4199 // Sanitize the environment.
4200 __libc_init_AT_SECURE(args);
4201
4202 // Initialize system properties
4203 __system_properties_init(); // may use 'environ'
4204
4205 debuggerd_init();
4206
4207 // Get a few environment variables.
4208 const char* LD_DEBUG = getenv("LD_DEBUG");
4209 if (LD_DEBUG != nullptr) {
4210 g_ld_debug_verbosity = atoi(LD_DEBUG);
4211 }
4212
4213 #if defined(__LP64__)
4214 INFO("[ Android dynamic linker (64-bit) ]");
4215 #else
4216 INFO("[ Android dynamic linker (32-bit) ]");
4217 #endif
4218
4219 // These should have been sanitized by __libc_init_AT_SECURE, but the test
4220 // doesn't cost us anything.
4221 const char* ldpath_env = nullptr;
4222 const char* ldpreload_env = nullptr;
4223 if (!getauxval(AT_SECURE)) {
4224 ldpath_env = getenv("LD_LIBRARY_PATH");
4225 if (ldpath_env != nullptr) {
4226 INFO("[ LD_LIBRARY_PATH set to \"%s\" ]", ldpath_env);
4227 }
4228 ldpreload_env = getenv("LD_PRELOAD");
4229 if (ldpreload_env != nullptr) {
4230 INFO("[ LD_PRELOAD set to \"%s\" ]", ldpreload_env);
4231 }
4232 }
4233
4234 struct stat file_stat;
4235 // Stat "/proc/self/exe" instead of executable_path because
4236 // the executable could be unlinked by this point and it should
4237 // not cause a crash (see http://b/31084669)
4238 if (TEMP_FAILURE_RETRY(stat("/proc/self/exe", &file_stat)) != 0) {
4239 __libc_fatal("unable to stat \"/proc/self/exe\": %s", strerror(errno));
4240 }
4241
4242 const char* executable_path = get_executable_path();
4243 soinfo* si = soinfo_alloc(&g_default_namespace, executable_path, &file_stat, 0, RTLD_GLOBAL);
4244 if (si == nullptr) {
4245 __libc_fatal("Couldn't allocate soinfo: out of memory?");
4246 }
4247
4248 /* bootstrap the link map, the main exe always needs to be first */
4249 si->set_main_executable();
4250 link_map* map = &(si->link_map_head);
4251
4252 // Register the main executable and the linker upfront to have
4253 // gdb aware of them before loading the rest of the dependency
4254 // tree.
4255 map->l_addr = 0;
4256 map->l_name = const_cast<char*>(executable_path);
4257 insert_link_map_into_debug_map(map);
4258 init_linker_info_for_gdb(linker_base);
4259
4260 // Extract information passed from the kernel.
4261 si->phdr = reinterpret_cast<ElfW(Phdr)*>(args.getauxval(AT_PHDR));
4262 si->phnum = args.getauxval(AT_PHNUM);
4263 si->entry = args.getauxval(AT_ENTRY);
4264
4265 /* Compute the value of si->base. We can't rely on the fact that
4266 * the first entry is the PHDR because this will not be true
4267 * for certain executables (e.g. some in the NDK unit test suite)
4268 */
4269 si->base = 0;
4270 si->size = phdr_table_get_load_size(si->phdr, si->phnum);
4271 si->load_bias = 0;
4272 for (size_t i = 0; i < si->phnum; ++i) {
4273 if (si->phdr[i].p_type == PT_PHDR) {
4274 si->load_bias = reinterpret_cast<ElfW(Addr)>(si->phdr) - si->phdr[i].p_vaddr;
4275 si->base = reinterpret_cast<ElfW(Addr)>(si->phdr) - si->phdr[i].p_offset;
4276 break;
4277 }
4278 }
4279 si->dynamic = nullptr;
4280
4281 ElfW(Ehdr)* elf_hdr = reinterpret_cast<ElfW(Ehdr)*>(si->base);
4282 if (elf_hdr->e_type != ET_DYN) {
4283 __libc_fatal("\"%s\": error: only position independent executables (PIE) are supported.",
4284 args.argv[0]);
4285 }
4286
4287 // Use LD_LIBRARY_PATH and LD_PRELOAD (but only if we aren't setuid/setgid).
4288 parse_LD_LIBRARY_PATH(ldpath_env);
4289 parse_LD_PRELOAD(ldpreload_env);
4290
4291 somain = si;
4292
4293 init_default_namespace();
4294
4295 if (!si->prelink_image()) {
4296 __libc_fatal("CANNOT LINK EXECUTABLE \"%s\": %s", args.argv[0], linker_get_error_buffer());
4297 }
4298
4299 // add somain to global group
4300 si->set_dt_flags_1(si->get_dt_flags_1() | DF_1_GLOBAL);
4301
4302 // Load ld_preloads and dependencies.
4303 StringLinkedList needed_library_name_list;
4304 size_t needed_libraries_count = 0;
4305 size_t ld_preloads_count = 0;
4306
4307 for (const auto& ld_preload_name : g_ld_preload_names) {
4308 needed_library_name_list.push_back(ld_preload_name.c_str());
4309 ++needed_libraries_count;
4310 ++ld_preloads_count;
4311 }
4312
4313 for_each_dt_needed(si, [&](const char* name) {
4314 needed_library_name_list.push_back(name);
4315 ++needed_libraries_count;
4316 });
4317
4318 const char* needed_library_names[needed_libraries_count];
4319
4320 memset(needed_library_names, 0, sizeof(needed_library_names));
4321 needed_library_name_list.copy_to_array(needed_library_names, needed_libraries_count);
4322
4323 if (needed_libraries_count > 0 &&
4324 !find_libraries(&g_default_namespace, si, needed_library_names, needed_libraries_count,
4325 nullptr, &g_ld_preloads, ld_preloads_count, RTLD_GLOBAL, nullptr,
4326 /* add_as_children */ true)) {
4327 __libc_fatal("CANNOT LINK EXECUTABLE \"%s\": %s", args.argv[0], linker_get_error_buffer());
4328 } else if (needed_libraries_count == 0) {
4329 if (!si->link_image(g_empty_list, soinfo::soinfo_list_t::make_list(si), nullptr)) {
4330 __libc_fatal("CANNOT LINK EXECUTABLE \"%s\": %s", args.argv[0], linker_get_error_buffer());
4331 }
4332 si->increment_ref_count();
4333 }
4334
4335 add_vdso(args);
4336
4337 {
4338 ProtectedDataGuard guard;
4339
4340 si->call_pre_init_constructors();
4341
4342 /* After the prelink_image, the si->load_bias is initialized.
4343 * For so lib, the map->l_addr will be updated in notify_gdb_of_load.
4344 * We need to update this value for so exe here. So Unwind_Backtrace
4345 * for some arch like x86 could work correctly within so exe.
4346 */
4347 map->l_addr = si->load_bias;
4348 si->call_constructors();
4349 }
4350
4351 #if TIMING
4352 gettimeofday(&t1, nullptr);
4353 PRINT("LINKER TIME: %s: %d microseconds", args.argv[0], (int) (
4354 (((long long)t1.tv_sec * 1000000LL) + (long long)t1.tv_usec) -
4355 (((long long)t0.tv_sec * 1000000LL) + (long long)t0.tv_usec)));
4356 #endif
4357 #if STATS
4358 PRINT("RELO STATS: %s: %d abs, %d rel, %d copy, %d symbol", args.argv[0],
4359 linker_stats.count[kRelocAbsolute],
4360 linker_stats.count[kRelocRelative],
4361 linker_stats.count[kRelocCopy],
4362 linker_stats.count[kRelocSymbol]);
4363 #endif
4364 #if COUNT_PAGES
4365 {
4366 unsigned n;
4367 unsigned i;
4368 unsigned count = 0;
4369 for (n = 0; n < 4096; n++) {
4370 if (bitmask[n]) {
4371 unsigned x = bitmask[n];
4372 #if defined(__LP64__)
4373 for (i = 0; i < 32; i++) {
4374 #else
4375 for (i = 0; i < 8; i++) {
4376 #endif
4377 if (x & 1) {
4378 count++;
4379 }
4380 x >>= 1;
4381 }
4382 }
4383 }
4384 PRINT("PAGES MODIFIED: %s: %d (%dKB)", args.argv[0], count, count * 4);
4385 }
4386 #endif
4387
4388 #if TIMING || STATS || COUNT_PAGES
4389 fflush(stdout);
4390 #endif
4391
4392 TRACE("[ Ready to execute \"%s\" @ %p ]", si->get_realpath(), reinterpret_cast<void*>(si->entry));
4393 return si->entry;
4394 }
4395
4396 /* Compute the load-bias of an existing executable. This shall only
4397 * be used to compute the load bias of an executable or shared library
4398 * that was loaded by the kernel itself.
4399 *
4400 * Input:
4401 * elf -> address of ELF header, assumed to be at the start of the file.
4402 * Return:
4403 * load bias, i.e. add the value of any p_vaddr in the file to get
4404 * the corresponding address in memory.
4405 */
4406 static ElfW(Addr) get_elf_exec_load_bias(const ElfW(Ehdr)* elf) {
4407 ElfW(Addr) offset = elf->e_phoff;
4408 const ElfW(Phdr)* phdr_table =
4409 reinterpret_cast<const ElfW(Phdr)*>(reinterpret_cast<uintptr_t>(elf) + offset);
4410 const ElfW(Phdr)* phdr_end = phdr_table + elf->e_phnum;
4411
4412 for (const ElfW(Phdr)* phdr = phdr_table; phdr < phdr_end; phdr++) {
4413 if (phdr->p_type == PT_LOAD) {
4414 return reinterpret_cast<ElfW(Addr)>(elf) + phdr->p_offset - phdr->p_vaddr;
4415 }
4416 }
4417 return 0;
4418 }
4419
4420 static void __linker_cannot_link(KernelArgumentBlock& args) {
4421 __libc_fatal("CANNOT LINK EXECUTABLE \"%s\": %s", args.argv[0], linker_get_error_buffer());
4422 }
4423
4424 /*
4425 * This is the entry point for the linker, called from begin.S. This
4426 * method is responsible for fixing the linker's own relocations, and
4427 * then calling __linker_init_post_relocation().
4428 *
4429 * Because this method is called before the linker has fixed it's own
4430 * relocations, any attempt to reference an extern variable, extern
4431 * function, or other GOT reference will generate a segfault.
4432 */
4433 extern "C" ElfW(Addr) __linker_init(void* raw_args) {
4434 KernelArgumentBlock args(raw_args);
4435
4436 ElfW(Addr) linker_addr = args.getauxval(AT_BASE);
4437 ElfW(Addr) entry_point = args.getauxval(AT_ENTRY);
4438 ElfW(Ehdr)* elf_hdr = reinterpret_cast<ElfW(Ehdr)*>(linker_addr);
4439 ElfW(Phdr)* phdr = reinterpret_cast<ElfW(Phdr)*>(linker_addr + elf_hdr->e_phoff);
4440
4441 soinfo linker_so(nullptr, nullptr, nullptr, 0, 0);
4442
4443 // If the linker is not acting as PT_INTERP entry_point is equal to
4444 // _start. Which means that the linker is running as an executable and
4445 // already linked by PT_INTERP.
4446 //
4447 // This happens when user tries to run 'adb shell /system/bin/linker'
4448 // see also https://code.google.com/p/android/issues/detail?id=63174
4449 if (reinterpret_cast<ElfW(Addr)>(&_start) == entry_point) {
4450 __libc_format_fd(STDOUT_FILENO,
4451 "This is %s, the helper program for shared library executables.\n",
4452 args.argv[0]);
4453 exit(0);
4454 }
4455
4456 linker_so.base = linker_addr;
4457 linker_so.size = phdr_table_get_load_size(phdr, elf_hdr->e_phnum);
4458 linker_so.load_bias = get_elf_exec_load_bias(elf_hdr);
4459 linker_so.dynamic = nullptr;
4460 linker_so.phdr = phdr;
4461 linker_so.phnum = elf_hdr->e_phnum;
4462 linker_so.set_linker_flag();
4463
4464 // Prelink the linker so we can access linker globals.
4465 if (!linker_so.prelink_image()) __linker_cannot_link(args);
4466
4467 // This might not be obvious... The reasons why we pass g_empty_list
4468 // in place of local_group here are (1) we do not really need it, because
4469 // linker is built with DT_SYMBOLIC and therefore relocates its symbols against
4470 // itself without having to look into local_group and (2) allocators
4471 // are not yet initialized, and therefore we cannot use linked_list.push_*
4472 // functions at this point.
4473 if (!linker_so.link_image(g_empty_list, g_empty_list, nullptr)) __linker_cannot_link(args);
4474
4475 #if defined(__i386__)
4476 // On x86, we can't make system calls before this point.
4477 // We can't move this up because this needs to assign to a global.
4478 // Note that until we call __libc_init_main_thread below we have
4479 // no TLS, so you shouldn't make a system call that can fail, because
4480 // it will SEGV when it tries to set errno.
4481 __libc_init_sysinfo(args);
4482 #endif
4483
4484 // Initialize the main thread (including TLS, so system calls really work).
4485 __libc_init_main_thread(args);
4486
4487 // We didn't protect the linker's RELRO pages in link_image because we
4488 // couldn't make system calls on x86 at that point, but we can now...
4489 if (!linker_so.protect_relro()) __linker_cannot_link(args);
4490
4491 // Initialize the linker's static libc's globals
4492 __libc_init_globals(args);
4493
4494 // Initialize the linker's own global variables
4495 linker_so.call_constructors();
4496
4497 // Initialize static variables. Note that in order to
4498 // get correct libdl_info we need to call constructors
4499 // before get_libdl_info().
4500 solist = get_libdl_info();
4501 sonext = get_libdl_info();
4502 g_default_namespace.add_soinfo(get_libdl_info());
4503
4504 // We have successfully fixed our own relocations. It's safe to run
4505 // the main part of the linker now.
4506 args.abort_message_ptr = &g_abort_message;
4507 ElfW(Addr) start_address = __linker_init_post_relocation(args, linker_addr);
4508
4509 INFO("[ Jumping to _start (%p)... ]", reinterpret_cast<void*>(start_address));
4510
4511 // Return the address that the calling assembly stub should jump to.
4512 return start_address;
4513 }
4514