blob: af47619907da128092913527ea17dfdb060a4691 [file] [log] [blame]
Dimitry Ivanov3f660572016-09-09 10:00:39 -07001/*
2 * Copyright (C) 2016 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 "linker_main.h"
30
31#include "linker_debug.h"
Evgenii Stepanov0a3637d2016-07-06 13:20:59 -070032#include "linker_cfi.h"
Dimitry Ivanov3f660572016-09-09 10:00:39 -070033#include "linker_gdb_support.h"
34#include "linker_globals.h"
35#include "linker_phdr.h"
36#include "linker_utils.h"
37
38#include "private/bionic_globals.h"
39#include "private/bionic_tls.h"
40#include "private/KernelArgumentBlock.h"
41
42#include "android-base/strings.h"
43#include "android-base/stringprintf.h"
Dan Willemsen7ec52b12016-11-28 17:02:25 -080044#ifdef __ANDROID__
Josh Gao2a3b4fa2016-10-26 17:55:49 -070045#include "debuggerd/handler.h"
Dan Willemsen7ec52b12016-11-28 17:02:25 -080046#endif
Dimitry Ivanov3f660572016-09-09 10:00:39 -070047
Christopher Ferris7a3681e2017-04-24 17:48:32 -070048#include <async_safe/log.h>
49
Dimitry Ivanov3f660572016-09-09 10:00:39 -070050#include <vector>
51
52extern void __libc_init_globals(KernelArgumentBlock&);
53extern void __libc_init_AT_SECURE(KernelArgumentBlock&);
54
55extern "C" void _start();
56
57static ElfW(Addr) get_elf_exec_load_bias(const ElfW(Ehdr)* elf);
58
Ryan Prichard9729f352018-07-13 22:40:26 -070059static void get_elf_base_from_phdr(const ElfW(Phdr)* phdr_table, size_t phdr_count,
60 ElfW(Addr)* base, ElfW(Addr)* load_bias);
61
Dimitry Ivanov3f660572016-09-09 10:00:39 -070062// These should be preserved static to avoid emitting
63// RELATIVE relocations for the part of the code running
64// before linker links itself.
65
66// TODO (dimtiry): remove somain, rename solist to solist_head
67static soinfo* solist;
68static soinfo* sonext;
69static soinfo* somain; // main process, always the one after libdl_info
dimitry8b142562018-05-09 15:22:38 +020070static soinfo* vdso; // vdso if present
Dimitry Ivanov3f660572016-09-09 10:00:39 -070071
72void solist_add_soinfo(soinfo* si) {
73 sonext->next = si;
74 sonext = si;
75}
76
77bool solist_remove_soinfo(soinfo* si) {
78 soinfo *prev = nullptr, *trav;
79 for (trav = solist; trav != nullptr; trav = trav->next) {
80 if (trav == si) {
81 break;
82 }
83 prev = trav;
84 }
85
86 if (trav == nullptr) {
87 // si was not in solist
88 PRINT("name \"%s\"@%p is not in solist!", si->get_realpath(), si);
89 return false;
90 }
91
92 // prev will never be null, because the first entry in solist is
93 // always the static libdl_info.
George Burgess IV70591002017-06-27 16:23:45 -070094 CHECK(prev != nullptr);
Dimitry Ivanov3f660572016-09-09 10:00:39 -070095 prev->next = si->next;
96 if (si == sonext) {
97 sonext = prev;
98 }
99
100 return true;
101}
102
103soinfo* solist_get_head() {
104 return solist;
105}
106
107soinfo* solist_get_somain() {
108 return somain;
109}
110
dimitry8b142562018-05-09 15:22:38 +0200111soinfo* solist_get_vdso() {
112 return vdso;
113}
114
Dimitry Ivanov3f660572016-09-09 10:00:39 -0700115int g_ld_debug_verbosity;
116abort_msg_t* g_abort_message = nullptr; // For debuggerd.
117
118static std::vector<std::string> g_ld_preload_names;
119
120static std::vector<soinfo*> g_ld_preloads;
121
122static void parse_path(const char* path, const char* delimiters,
123 std::vector<std::string>* resolved_paths) {
124 std::vector<std::string> paths;
125 split_path(path, delimiters, &paths);
126 resolve_paths(paths, resolved_paths);
127}
128
129static void parse_LD_LIBRARY_PATH(const char* path) {
130 std::vector<std::string> ld_libary_paths;
131 parse_path(path, ":", &ld_libary_paths);
132 g_default_namespace.set_ld_library_paths(std::move(ld_libary_paths));
133}
134
135static void parse_LD_PRELOAD(const char* path) {
136 g_ld_preload_names.clear();
137 if (path != nullptr) {
138 // We have historically supported ':' as well as ' ' in LD_PRELOAD.
139 g_ld_preload_names = android::base::Split(path, " :");
Josh Gao44f6e182017-10-18 17:25:24 -0700140 g_ld_preload_names.erase(std::remove_if(g_ld_preload_names.begin(), g_ld_preload_names.end(),
Josh Gao27242c62017-10-20 17:45:13 -0700141 [](const std::string& s) { return s.empty(); }),
142 g_ld_preload_names.end());
Dimitry Ivanov3f660572016-09-09 10:00:39 -0700143 }
144}
145
146// An empty list of soinfos
147static soinfo_list_t g_empty_list;
148
dimitryf9abbf62017-07-06 12:17:14 +0200149static void add_vdso(KernelArgumentBlock& args) {
Dimitry Ivanov3f660572016-09-09 10:00:39 -0700150 ElfW(Ehdr)* ehdr_vdso = reinterpret_cast<ElfW(Ehdr)*>(args.getauxval(AT_SYSINFO_EHDR));
151 if (ehdr_vdso == nullptr) {
152 return;
153 }
154
155 soinfo* si = soinfo_alloc(&g_default_namespace, "[vdso]", nullptr, 0, 0);
156
157 si->phdr = reinterpret_cast<ElfW(Phdr)*>(reinterpret_cast<char*>(ehdr_vdso) + ehdr_vdso->e_phoff);
158 si->phnum = ehdr_vdso->e_phnum;
159 si->base = reinterpret_cast<ElfW(Addr)>(ehdr_vdso);
160 si->size = phdr_table_get_load_size(si->phdr, si->phnum);
161 si->load_bias = get_elf_exec_load_bias(ehdr_vdso);
162
163 si->prelink_image();
164 si->link_image(g_empty_list, soinfo_list_t::make_list(si), nullptr);
dimitryc18de1b2017-09-26 14:31:35 +0200165 // prevents accidental unloads...
166 si->set_dt_flags_1(si->get_dt_flags_1() | DF_1_NODELETE);
167 si->set_linked();
168 si->call_constructors();
dimitry8b142562018-05-09 15:22:38 +0200169
170 vdso = si;
Dimitry Ivanov3f660572016-09-09 10:00:39 -0700171}
172
173/* gdb expects the linker to be in the debug shared object list.
174 * Without this, gdb has trouble locating the linker's ".text"
175 * and ".plt" sections. Gdb could also potentially use this to
176 * relocate the offset of our exported 'rtld_db_dlactivity' symbol.
177 * Note that the linker shouldn't be on the soinfo list.
178 */
Dimitry Ivanovcd510cb2017-05-31 15:07:41 -0700179static link_map linker_link_map;
Dimitry Ivanov3f660572016-09-09 10:00:39 -0700180
Dimitry Ivanovcd510cb2017-05-31 15:07:41 -0700181static void init_linker_info_for_gdb(ElfW(Addr) linker_base, char* linker_path) {
182 linker_link_map.l_addr = linker_base;
183 linker_link_map.l_name = linker_path;
Dimitry Ivanov3f660572016-09-09 10:00:39 -0700184
185 /*
186 * Set the dynamic field in the link map otherwise gdb will complain with
187 * the following:
188 * warning: .dynamic section for "/system/bin/linker" is not at the
189 * expected address (wrong library or version mismatch?)
190 */
191 ElfW(Ehdr)* elf_hdr = reinterpret_cast<ElfW(Ehdr)*>(linker_base);
192 ElfW(Phdr)* phdr = reinterpret_cast<ElfW(Phdr)*>(linker_base + elf_hdr->e_phoff);
193 phdr_table_get_dynamic_section(phdr, elf_hdr->e_phnum, linker_base,
Dimitry Ivanovcd510cb2017-05-31 15:07:41 -0700194 &linker_link_map.l_ld, nullptr);
Dimitry Ivanov3f660572016-09-09 10:00:39 -0700195
Dimitry Ivanov3f660572016-09-09 10:00:39 -0700196}
197
198extern "C" int __system_properties_init(void);
199
200static const char* get_executable_path() {
201 static std::string executable_path;
202 if (executable_path.empty()) {
Jiyong Park31cd08f2018-06-01 19:18:56 +0900203 if (!is_init()) {
204 char path[PATH_MAX];
205 ssize_t path_len = readlink("/proc/self/exe", path, sizeof(path));
206 if (path_len == -1 || path_len >= static_cast<ssize_t>(sizeof(path))) {
207 async_safe_fatal("readlink('/proc/self/exe') failed: %s", strerror(errno));
208 }
209 executable_path = std::string(path, path_len);
210 } else {
211 executable_path = "/init";
Dimitry Ivanov3f660572016-09-09 10:00:39 -0700212 }
Dimitry Ivanov3f660572016-09-09 10:00:39 -0700213 }
214
215 return executable_path.c_str();
216}
217
Dimitry Ivanovd9e427c2016-11-22 16:55:25 -0800218#if defined(__LP64__)
219static char kLinkerPath[] = "/system/bin/linker64";
220#else
221static char kLinkerPath[] = "/system/bin/linker";
222#endif
223
Elliott Hughesad2d0382017-07-31 11:43:34 -0700224static void __linker_cannot_link(const char* argv0) {
dimitry04f7a792017-09-29 11:52:17 +0200225 async_safe_format_fd(STDERR_FILENO,
226 "CANNOT LINK EXECUTABLE \"%s\": %s\n",
227 argv0,
228 linker_get_error_buffer());
229
230 async_safe_format_log(ANDROID_LOG_FATAL,
231 "linker",
232 "CANNOT LINK EXECUTABLE \"%s\": %s",
233 argv0,
234 linker_get_error_buffer());
235 _exit(EXIT_FAILURE);
Elliott Hughesad2d0382017-07-31 11:43:34 -0700236}
237
Ryan Prichard742982d2018-05-30 22:32:17 -0700238static ElfW(Addr) linker_main(KernelArgumentBlock& args) {
Dimitry Ivanov4cabfaa2017-03-07 11:19:05 -0800239 ProtectedDataGuard guard;
240
Dimitry Ivanov3f660572016-09-09 10:00:39 -0700241#if TIMING
242 struct timeval t0, t1;
243 gettimeofday(&t0, 0);
244#endif
245
246 // Sanitize the environment.
247 __libc_init_AT_SECURE(args);
248
249 // Initialize system properties
250 __system_properties_init(); // may use 'environ'
251
252 // Register the debuggerd signal handler.
Dan Willemsen7ec52b12016-11-28 17:02:25 -0800253#ifdef __ANDROID__
Dimitry Ivanov3f660572016-09-09 10:00:39 -0700254 debuggerd_callbacks_t callbacks = {
255 .get_abort_message = []() {
256 return g_abort_message;
257 },
258 .post_dump = &notify_gdb_of_libraries,
259 };
260 debuggerd_init(&callbacks);
Dan Willemsen7ec52b12016-11-28 17:02:25 -0800261#endif
Dimitry Ivanov3f660572016-09-09 10:00:39 -0700262
263 g_linker_logger.ResetState();
264
265 // Get a few environment variables.
266 const char* LD_DEBUG = getenv("LD_DEBUG");
267 if (LD_DEBUG != nullptr) {
268 g_ld_debug_verbosity = atoi(LD_DEBUG);
269 }
270
271#if defined(__LP64__)
272 INFO("[ Android dynamic linker (64-bit) ]");
273#else
274 INFO("[ Android dynamic linker (32-bit) ]");
275#endif
276
277 // These should have been sanitized by __libc_init_AT_SECURE, but the test
278 // doesn't cost us anything.
279 const char* ldpath_env = nullptr;
280 const char* ldpreload_env = nullptr;
281 if (!getauxval(AT_SECURE)) {
282 ldpath_env = getenv("LD_LIBRARY_PATH");
283 if (ldpath_env != nullptr) {
284 INFO("[ LD_LIBRARY_PATH set to \"%s\" ]", ldpath_env);
285 }
286 ldpreload_env = getenv("LD_PRELOAD");
287 if (ldpreload_env != nullptr) {
288 INFO("[ LD_PRELOAD set to \"%s\" ]", ldpreload_env);
289 }
290 }
291
292 struct stat file_stat;
293 // Stat "/proc/self/exe" instead of executable_path because
294 // the executable could be unlinked by this point and it should
295 // not cause a crash (see http://b/31084669)
Jiyong Park31cd08f2018-06-01 19:18:56 +0900296 if (!is_init()) {
297 if (TEMP_FAILURE_RETRY(stat("/proc/self/exe", &file_stat)) != 0) {
298 async_safe_fatal("unable to stat \"/proc/self/exe\": %s", strerror(errno));
299 }
300 } else {
301 // /proc fs is not mounted when init starts. Therefore we can't use
302 // /proc/self/exe for init.
303 stat("/init", &file_stat);
Dimitry Ivanov3f660572016-09-09 10:00:39 -0700304 }
305
306 const char* executable_path = get_executable_path();
307 soinfo* si = soinfo_alloc(&g_default_namespace, executable_path, &file_stat, 0, RTLD_GLOBAL);
Dimitry Ivanov3f660572016-09-09 10:00:39 -0700308
Elliott Hughes7b0af7a2017-09-15 16:09:22 -0700309 // Bootstrap the link map, the main exe always needs to be first.
Dimitry Ivanov3f660572016-09-09 10:00:39 -0700310 si->set_main_executable();
311 link_map* map = &(si->link_map_head);
312
313 // Register the main executable and the linker upfront to have
314 // gdb aware of them before loading the rest of the dependency
315 // tree.
316 map->l_addr = 0;
317 map->l_name = const_cast<char*>(executable_path);
318 insert_link_map_into_debug_map(map);
Dimitry Ivanovcd510cb2017-05-31 15:07:41 -0700319 insert_link_map_into_debug_map(&linker_link_map);
Dimitry Ivanov3f660572016-09-09 10:00:39 -0700320
Ryan Prichard14dd9922018-08-20 17:43:44 -0700321 add_vdso(args);
322
Dimitry Ivanov3f660572016-09-09 10:00:39 -0700323 // Extract information passed from the kernel.
324 si->phdr = reinterpret_cast<ElfW(Phdr)*>(args.getauxval(AT_PHDR));
325 si->phnum = args.getauxval(AT_PHNUM);
326
Ryan Prichard9729f352018-07-13 22:40:26 -0700327 get_elf_base_from_phdr(si->phdr, si->phnum, &si->base, &si->load_bias);
Dimitry Ivanov3f660572016-09-09 10:00:39 -0700328 si->size = phdr_table_get_load_size(si->phdr, si->phnum);
George Burgess IV70591002017-06-27 16:23:45 -0700329
Dimitry Ivanov3f660572016-09-09 10:00:39 -0700330 si->dynamic = nullptr;
331
332 ElfW(Ehdr)* elf_hdr = reinterpret_cast<ElfW(Ehdr)*>(si->base);
Elliott Hughes3bdb31b2017-01-07 10:38:20 -0800333
334 // We haven't supported non-PIE since Lollipop for security reasons.
Dimitry Ivanov3f660572016-09-09 10:00:39 -0700335 if (elf_hdr->e_type != ET_DYN) {
Elliott Hughesad2d0382017-07-31 11:43:34 -0700336 // We don't use async_safe_fatal here because we don't want a tombstone:
337 // even after several years we still find ourselves on app compatibility
Elliott Hughes3bdb31b2017-01-07 10:38:20 -0800338 // investigations because some app's trying to launch an executable that
339 // hasn't worked in at least three years, and we've "helpfully" dropped a
340 // tombstone for them. The tombstone never provided any detail relevant to
341 // fixing the problem anyway, and the utility of drawing extra attention
342 // to the problem is non-existent at this late date.
Christopher Ferris7a3681e2017-04-24 17:48:32 -0700343 async_safe_format_fd(STDERR_FILENO,
Elliott Hughesad2d0382017-07-31 11:43:34 -0700344 "\"%s\": error: Android 5.0 and later only support "
345 "position-independent executables (-fPIE).\n",
346 g_argv[0]);
Dan Albert95e2e6f2017-01-31 16:02:43 -0800347 exit(EXIT_FAILURE);
Dimitry Ivanov3f660572016-09-09 10:00:39 -0700348 }
349
350 // Use LD_LIBRARY_PATH and LD_PRELOAD (but only if we aren't setuid/setgid).
351 parse_LD_LIBRARY_PATH(ldpath_env);
352 parse_LD_PRELOAD(ldpreload_env);
353
354 somain = si;
355
Jiyong Park02586a22017-05-20 01:01:24 +0900356 std::vector<android_namespace_t*> namespaces = init_default_namespaces(executable_path);
Dimitry Ivanov3f660572016-09-09 10:00:39 -0700357
Elliott Hughesad2d0382017-07-31 11:43:34 -0700358 if (!si->prelink_image()) __linker_cannot_link(g_argv[0]);
Dimitry Ivanov3f660572016-09-09 10:00:39 -0700359
360 // add somain to global group
361 si->set_dt_flags_1(si->get_dt_flags_1() | DF_1_GLOBAL);
Jiyong Park02586a22017-05-20 01:01:24 +0900362 // ... and add it to all other linked namespaces
363 for (auto linked_ns : namespaces) {
364 if (linked_ns != &g_default_namespace) {
365 linked_ns->add_soinfo(somain);
366 somain->add_secondary_namespace(linked_ns);
367 }
368 }
Dimitry Ivanov3f660572016-09-09 10:00:39 -0700369
370 // Load ld_preloads and dependencies.
371 std::vector<const char*> needed_library_name_list;
372 size_t ld_preloads_count = 0;
373
374 for (const auto& ld_preload_name : g_ld_preload_names) {
375 needed_library_name_list.push_back(ld_preload_name.c_str());
376 ++ld_preloads_count;
377 }
378
379 for_each_dt_needed(si, [&](const char* name) {
380 needed_library_name_list.push_back(name);
381 });
382
383 const char** needed_library_names = &needed_library_name_list[0];
384 size_t needed_libraries_count = needed_library_name_list.size();
385
386 if (needed_libraries_count > 0 &&
Dimitry Ivanov7d429d32017-02-01 15:28:52 -0800387 !find_libraries(&g_default_namespace,
388 si,
389 needed_library_names,
390 needed_libraries_count,
391 nullptr,
392 &g_ld_preloads,
393 ld_preloads_count,
394 RTLD_GLOBAL,
395 nullptr,
396 true /* add_as_children */,
Jiyong Park02586a22017-05-20 01:01:24 +0900397 true /* search_linked_namespaces */,
Jiyong Park02586a22017-05-20 01:01:24 +0900398 &namespaces)) {
Elliott Hughesad2d0382017-07-31 11:43:34 -0700399 __linker_cannot_link(g_argv[0]);
Dimitry Ivanov3f660572016-09-09 10:00:39 -0700400 } else if (needed_libraries_count == 0) {
401 if (!si->link_image(g_empty_list, soinfo_list_t::make_list(si), nullptr)) {
Elliott Hughesad2d0382017-07-31 11:43:34 -0700402 __linker_cannot_link(g_argv[0]);
Dimitry Ivanov3f660572016-09-09 10:00:39 -0700403 }
404 si->increment_ref_count();
405 }
406
Elliott Hughesad2d0382017-07-31 11:43:34 -0700407 if (!get_cfi_shadow()->InitialLinkDone(solist)) __linker_cannot_link(g_argv[0]);
Evgenii Stepanov0a3637d2016-07-06 13:20:59 -0700408
Ryan Prichard6631f9b2018-04-30 18:29:32 -0700409 // Store a pointer to the kernel argument block in a TLS slot to be
410 // picked up by the libc constructor.
411 __get_tls()[TLS_SLOT_BIONIC_PREINIT] = &args;
412
Dimitry Ivanov4cabfaa2017-03-07 11:19:05 -0800413 si->call_pre_init_constructors();
Dimitry Ivanov3f660572016-09-09 10:00:39 -0700414
Dimitry Ivanov4cabfaa2017-03-07 11:19:05 -0800415 /* After the prelink_image, the si->load_bias is initialized.
416 * For so lib, the map->l_addr will be updated in notify_gdb_of_load.
417 * We need to update this value for so exe here. So Unwind_Backtrace
418 * for some arch like x86 could work correctly within so exe.
419 */
420 map->l_addr = si->load_bias;
421 si->call_constructors();
Dimitry Ivanov3f660572016-09-09 10:00:39 -0700422
423#if TIMING
424 gettimeofday(&t1, nullptr);
425 PRINT("LINKER TIME: %s: %d microseconds", g_argv[0], (int) (
426 (((long long)t1.tv_sec * 1000000LL) + (long long)t1.tv_usec) -
427 (((long long)t0.tv_sec * 1000000LL) + (long long)t0.tv_usec)));
428#endif
429#if STATS
430 PRINT("RELO STATS: %s: %d abs, %d rel, %d copy, %d symbol", g_argv[0],
431 linker_stats.count[kRelocAbsolute],
432 linker_stats.count[kRelocRelative],
433 linker_stats.count[kRelocCopy],
434 linker_stats.count[kRelocSymbol]);
435#endif
436#if COUNT_PAGES
437 {
438 unsigned n;
439 unsigned i;
440 unsigned count = 0;
441 for (n = 0; n < 4096; n++) {
442 if (bitmask[n]) {
443 unsigned x = bitmask[n];
444#if defined(__LP64__)
445 for (i = 0; i < 32; i++) {
446#else
447 for (i = 0; i < 8; i++) {
448#endif
449 if (x & 1) {
450 count++;
451 }
452 x >>= 1;
453 }
454 }
455 }
456 PRINT("PAGES MODIFIED: %s: %d (%dKB)", g_argv[0], count, count * 4);
457 }
458#endif
459
460#if TIMING || STATS || COUNT_PAGES
461 fflush(stdout);
462#endif
463
464 ElfW(Addr) entry = args.getauxval(AT_ENTRY);
465 TRACE("[ Ready to execute \"%s\" @ %p ]", si->get_realpath(), reinterpret_cast<void*>(entry));
466 return entry;
467}
468
469/* Compute the load-bias of an existing executable. This shall only
470 * be used to compute the load bias of an executable or shared library
471 * that was loaded by the kernel itself.
472 *
473 * Input:
474 * elf -> address of ELF header, assumed to be at the start of the file.
475 * Return:
476 * load bias, i.e. add the value of any p_vaddr in the file to get
477 * the corresponding address in memory.
478 */
479static ElfW(Addr) get_elf_exec_load_bias(const ElfW(Ehdr)* elf) {
480 ElfW(Addr) offset = elf->e_phoff;
481 const ElfW(Phdr)* phdr_table =
482 reinterpret_cast<const ElfW(Phdr)*>(reinterpret_cast<uintptr_t>(elf) + offset);
483 const ElfW(Phdr)* phdr_end = phdr_table + elf->e_phnum;
484
485 for (const ElfW(Phdr)* phdr = phdr_table; phdr < phdr_end; phdr++) {
486 if (phdr->p_type == PT_LOAD) {
487 return reinterpret_cast<ElfW(Addr)>(elf) + phdr->p_offset - phdr->p_vaddr;
488 }
489 }
490 return 0;
491}
492
Ryan Prichard9729f352018-07-13 22:40:26 -0700493/* Find the load bias and base address of an executable or shared object loaded
494 * by the kernel. The ELF file's PHDR table must have a PT_PHDR entry.
495 *
496 * A VDSO doesn't have a PT_PHDR entry in its PHDR table.
497 */
498static void get_elf_base_from_phdr(const ElfW(Phdr)* phdr_table, size_t phdr_count,
499 ElfW(Addr)* base, ElfW(Addr)* load_bias) {
500 for (size_t i = 0; i < phdr_count; ++i) {
501 if (phdr_table[i].p_type == PT_PHDR) {
502 *load_bias = reinterpret_cast<ElfW(Addr)>(phdr_table) - phdr_table[i].p_vaddr;
503 *base = reinterpret_cast<ElfW(Addr)>(phdr_table) - phdr_table[i].p_offset;
504 return;
505 }
506 }
507 async_safe_fatal("Could not find a PHDR: broken executable?");
508}
509
Ryan Prichard742982d2018-05-30 22:32:17 -0700510static ElfW(Addr) __attribute__((noinline))
511__linker_init_post_relocation(KernelArgumentBlock& args,
512 ElfW(Addr) linker_addr,
513 soinfo& linker_so);
514
Dimitry Ivanov3f660572016-09-09 10:00:39 -0700515/*
516 * This is the entry point for the linker, called from begin.S. This
517 * method is responsible for fixing the linker's own relocations, and
518 * then calling __linker_init_post_relocation().
519 *
520 * Because this method is called before the linker has fixed it's own
521 * relocations, any attempt to reference an extern variable, extern
522 * function, or other GOT reference will generate a segfault.
523 */
524extern "C" ElfW(Addr) __linker_init(void* raw_args) {
525 KernelArgumentBlock args(raw_args);
526
Ryan Prichard27475b52018-05-17 17:14:18 -0700527#if defined(__i386__)
528 __libc_init_sysinfo(args);
529#endif
530
Ryan Prichard9729f352018-07-13 22:40:26 -0700531 ElfW(Addr) linker_addr = args.getauxval(AT_BASE);
532 if (linker_addr == 0) {
533 // When the linker is run by itself (rather than as an interpreter for
534 // another program), AT_BASE is 0. In that case, the AT_PHDR and AT_PHNUM
535 // aux values describe the linker, so use the phdr to find the linker's
536 // base address.
537 ElfW(Addr) load_bias;
538 get_elf_base_from_phdr(
539 reinterpret_cast<ElfW(Phdr)*>(args.getauxval(AT_PHDR)), args.getauxval(AT_PHNUM),
540 &linker_addr, &load_bias);
541 }
George Burgess IV70591002017-06-27 16:23:45 -0700542
Dimitry Ivanov3f660572016-09-09 10:00:39 -0700543 ElfW(Ehdr)* elf_hdr = reinterpret_cast<ElfW(Ehdr)*>(linker_addr);
544 ElfW(Phdr)* phdr = reinterpret_cast<ElfW(Phdr)*>(linker_addr + elf_hdr->e_phoff);
545
546 soinfo linker_so(nullptr, nullptr, nullptr, 0, 0);
547
Dimitry Ivanov3f660572016-09-09 10:00:39 -0700548 linker_so.base = linker_addr;
549 linker_so.size = phdr_table_get_load_size(phdr, elf_hdr->e_phnum);
550 linker_so.load_bias = get_elf_exec_load_bias(elf_hdr);
551 linker_so.dynamic = nullptr;
552 linker_so.phdr = phdr;
553 linker_so.phnum = elf_hdr->e_phnum;
554 linker_so.set_linker_flag();
555
556 // Prelink the linker so we can access linker globals.
557 if (!linker_so.prelink_image()) __linker_cannot_link(args.argv[0]);
558
559 // This might not be obvious... The reasons why we pass g_empty_list
560 // in place of local_group here are (1) we do not really need it, because
561 // linker is built with DT_SYMBOLIC and therefore relocates its symbols against
562 // itself without having to look into local_group and (2) allocators
563 // are not yet initialized, and therefore we cannot use linked_list.push_*
564 // functions at this point.
565 if (!linker_so.link_image(g_empty_list, g_empty_list, nullptr)) __linker_cannot_link(args.argv[0]);
566
Ryan Prichard742982d2018-05-30 22:32:17 -0700567 return __linker_init_post_relocation(args, linker_addr, linker_so);
568}
569
570/*
571 * This code is called after the linker has linked itself and fixed its own
572 * GOT. It is safe to make references to externs and other non-local data at
573 * this point. The compiler sometimes moves GOT references earlier in a
574 * function, so avoid inlining this function (http://b/80503879).
575 */
576static ElfW(Addr) __attribute__((noinline))
577__linker_init_post_relocation(KernelArgumentBlock& args,
578 ElfW(Addr) linker_addr,
579 soinfo& linker_so) {
Dimitry Ivanov3f660572016-09-09 10:00:39 -0700580 // Initialize the main thread (including TLS, so system calls really work).
581 __libc_init_main_thread(args);
582
583 // We didn't protect the linker's RELRO pages in link_image because we
584 // couldn't make system calls on x86 at that point, but we can now...
585 if (!linker_so.protect_relro()) __linker_cannot_link(args.argv[0]);
586
Josh Gaof6e5b582018-06-01 15:30:54 -0700587 // Initialize the linker/libc.so shared global inside the linker.
588 static libc_shared_globals shared_globals;
589 __libc_shared_globals = &shared_globals;
590 __libc_init_shared_globals(&shared_globals);
591 args.shared_globals = __libc_shared_globals;
592
Dimitry Ivanov3f660572016-09-09 10:00:39 -0700593 // Initialize the linker's static libc's globals
594 __libc_init_globals(args);
595
596 // store argc/argv/envp to use them for calling constructors
597 g_argc = args.argc;
598 g_argv = args.argv;
599 g_envp = args.envp;
600
601 // Initialize the linker's own global variables
602 linker_so.call_constructors();
603
Dimitry Ivanov9b1cc4b2017-03-23 16:17:15 -0700604 // If the linker is not acting as PT_INTERP entry_point is equal to
605 // _start. Which means that the linker is running as an executable and
606 // already linked by PT_INTERP.
607 //
608 // This happens when user tries to run 'adb shell /system/bin/linker'
609 // see also https://code.google.com/p/android/issues/detail?id=63174
Ryan Prichard742982d2018-05-30 22:32:17 -0700610 ElfW(Addr) entry_point = args.getauxval(AT_ENTRY);
Dimitry Ivanov9b1cc4b2017-03-23 16:17:15 -0700611 if (reinterpret_cast<ElfW(Addr)>(&_start) == entry_point) {
Christopher Ferris7a3681e2017-04-24 17:48:32 -0700612 async_safe_format_fd(STDOUT_FILENO,
Dimitry Ivanov9b1cc4b2017-03-23 16:17:15 -0700613 "This is %s, the helper program for dynamic executables.\n",
614 args.argv[0]);
615 exit(0);
616 }
617
Dimitry Ivanovcd510cb2017-05-31 15:07:41 -0700618 init_linker_info_for_gdb(linker_addr, kLinkerPath);
619
Dimitry Ivanov3f660572016-09-09 10:00:39 -0700620 // Initialize static variables. Note that in order to
621 // get correct libdl_info we need to call constructors
622 // before get_libdl_info().
dimitry7abea572017-08-29 18:14:49 +0200623 sonext = solist = get_libdl_info(kLinkerPath, linker_so, linker_link_map);
Dimitry Ivanovd9e427c2016-11-22 16:55:25 -0800624 g_default_namespace.add_soinfo(solist);
Dimitry Ivanov3f660572016-09-09 10:00:39 -0700625
Dimitry Ivanov3f660572016-09-09 10:00:39 -0700626 args.abort_message_ptr = &g_abort_message;
Ryan Prichard742982d2018-05-30 22:32:17 -0700627 ElfW(Addr) start_address = linker_main(args);
Dimitry Ivanov3f660572016-09-09 10:00:39 -0700628
629 INFO("[ Jumping to _start (%p)... ]", reinterpret_cast<void*>(start_address));
630
631 // Return the address that the calling assembly stub should jump to.
632 return start_address;
633}