Merge Chromium + Blink git repositories
[chromium-blink-merge.git] / third_party / android_crazy_linker / src / tests / bench_load_library.cpp
blob1a544ff833eb4d4692f7163d17c340ee5aae9752
1 // Copyright 2014 The Chromium Authors. All rights reserved.
2 // Use of this source code is governed by a BSD-style license that can be
3 // found in the LICENSE file.
5 // A crazy linker test to:
6 // - Load a library (libfoo.so) with the linker.
7 // - Find the address of the "Foo" function in it.
8 // - Call the function.
9 // - Close the library.
11 #include <crazy_linker.h>
13 #include <stdarg.h>
14 #include <stdio.h>
15 #include <stdlib.h>
16 #include <time.h>
17 #include <unistd.h>
18 #include <fcntl.h>
20 static void Panic(const char* fmt, ...) {
21 va_list args;
22 fprintf(stderr, "PANIC: ");
23 va_start(args, fmt);
24 vfprintf(stderr, fmt, args);
25 va_end(args);
26 exit(1);
29 static double now_ms() {
30 struct timespec ts;
31 clock_gettime(CLOCK_MONOTONIC, &ts);
32 return (ts.tv_sec * 1000.) + (ts.tv_nsec / 1000000.);
35 static void drop_caches() {
36 int fd = open("/proc/sys/vm/drop_caches", O_RDWR);
37 if (fd < 0) {
38 fprintf(stderr,
39 "Could not drop caches! Please run this program as root!\n");
40 return;
42 write(fd, "3\n", 2);
43 close(fd);
46 class ScopedTimer {
47 public:
48 ScopedTimer(const char* name) {
49 name_ = name;
50 start_ms_ = now_ms();
53 ~ScopedTimer() {
54 double elapsed_ms = now_ms() - start_ms_;
55 printf("Timer %s: %.1f\n", name_, elapsed_ms);
58 private:
59 const char* name_;
60 double start_ms_;
63 int main(int argc, char** argv) {
64 const char* library_path = "libfoo.so";
65 if (argc >= 2)
66 library_path = argv[1];
68 { ScopedTimer null_timer("empty"); }
70 // Load the library with dlopen().
71 void* lib;
72 drop_caches();
74 ScopedTimer timer("dlopen");
75 lib = dlopen(library_path, RTLD_NOW);
77 if (!lib)
78 Panic("Could not load library with dlopen(): %s\n", dlerror());
80 dlclose(lib);
82 crazy_library_t* library;
83 crazy_context_t* context = crazy_context_create();
85 // Ensure the program looks in its own directory too.
86 crazy_context_add_search_path_for_address(context,
87 reinterpret_cast<void*>(&main));
89 // Load the library with the crazy linker.
90 drop_caches();
92 ScopedTimer timer("crazy_linker");
93 // Load libfoo.so
94 if (!crazy_library_open(&library, library_path, context)) {
95 Panic("Could not open library: %s\n", crazy_context_get_error(context));
98 crazy_library_close(library);
100 // Load the library with the crazy linker. Preload libOpenSLES.so
101 drop_caches();
102 void* sles_lib = dlopen("libOpenSLES.so", RTLD_NOW);
104 ScopedTimer timer("crazy_linker (preload libOpenSLES.so)");
105 // Load libfoo.so
106 if (!crazy_library_open(&library, library_path, context)) {
107 Panic("Could not open library: %s\n", crazy_context_get_error(context));
110 crazy_library_close(library);
111 dlclose(sles_lib);
113 // Load the library with the crazy linker. Preload libOpenSLES.so
115 drop_caches();
116 void* sys1_lib = dlopen("libandroid.so", RTLD_NOW);
117 void* sys2_lib = dlopen("libjnigraphics.so", RTLD_NOW);
118 void* sys3_lib = dlopen("libOpenSLES.so", RTLD_NOW);
120 ScopedTimer timer("crazy_linker (preload 3 system libs)");
121 // Load libfoo.so
122 if (!crazy_library_open(&library, library_path, context)) {
123 Panic("Could not open library: %s\n", crazy_context_get_error(context));
126 crazy_library_close(library);
127 dlclose(sys3_lib);
128 dlclose(sys2_lib);
129 dlclose(sys1_lib);
132 // Load the library with the crazy linker. Create a shared RELRO as well.
133 drop_caches();
135 ScopedTimer timer("crazy_linker (with RELRO)");
136 // Load libfoo.so
137 if (!crazy_library_open(&library, library_path, context)) {
138 Panic("Could not open library: %s\n", crazy_context_get_error(context));
141 if (!crazy_library_enable_relro_sharing(library, context)) {
142 Panic("Could not create shared RELRO: %s\n",
143 crazy_context_get_error(context));
146 crazy_library_close(library);
148 printf("OK\n");
149 return 0;