1 /*
2  * Copyright (C) 2016 The Android Open Source Project
3  *
4  * Licensed under the Apache License, Version 2.0 (the "License");
5  * you may not use this file except in compliance with the License.
6  * You may obtain a copy of the License at
7  *
8  *      http://www.apache.org/licenses/LICENSE-2.0
9  *
10  * Unless required by applicable law or agreed to in writing, software
11  * distributed under the License is distributed on an "AS IS" BASIS,
12  * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
13  * See the License for the specific language governing permissions and
14  * limitations under the License.
15  */
16 
17 #include "component_loader/DllLoader.h"
18 
19 #include <android-base/logging.h>
20 #include <dlfcn.h>
21 
22 namespace android {
23 namespace vts {
24 
DllLoader()25 DllLoader::DllLoader() : handle_(NULL) {}
26 
~DllLoader()27 DllLoader::~DllLoader() {
28   if (!handle_) {
29     dlclose(handle_);
30     handle_ = NULL;
31   }
32 }
33 
Load(const char * file_path)34 void* DllLoader::Load(const char* file_path) {
35   if (!file_path) {
36     LOG(ERROR) << "file_path is NULL";
37     return NULL;
38   }
39 
40   // consider using the load mechanism in hardware/libhardware/hardware.c
41   handle_ = dlopen(file_path, RTLD_LAZY);
42   if (!handle_) {
43     LOG(ERROR) << "Can't load a shared library, " << file_path
44                << ", error: " << dlerror();
45     return NULL;
46   }
47   LOG(DEBUG) << "DLL loaded " << file_path;
48   return handle_;
49 }
50 
GetLoaderFunction(const char * function_name) const51 loader_function DllLoader::GetLoaderFunction(const char* function_name) const {
52   return (loader_function)LoadSymbol(function_name);
53 }
54 
GetLoaderFunctionWithArg(const char * function_name) const55 loader_function_with_arg DllLoader::GetLoaderFunctionWithArg(
56     const char* function_name) const {
57   return (loader_function_with_arg)LoadSymbol(function_name);
58 }
59 
SancovResetCoverage()60 bool DllLoader::SancovResetCoverage() {
61   void (*func)() = (void (*)())LoadSymbol("__sanitizer_reset_coverage");
62   if (func == NULL) {
63     return false;
64   }
65   func();
66   return true;
67 }
68 
GcovInit(writeout_fn wfn,flush_fn ffn)69 bool DllLoader::GcovInit(writeout_fn wfn, flush_fn ffn) {
70   void (*func)(writeout_fn, flush_fn) =
71       (void (*)(writeout_fn, flush_fn))LoadSymbol("llvm_gcov_init");
72   if (func == NULL) {
73     return false;
74   }
75   func(wfn, ffn);
76   return true;
77 }
78 
GcovFlush()79 bool DllLoader::GcovFlush() {
80   void (*func)() = (void (*)()) LoadSymbol("__gcov_flush");
81   if (func == NULL) {
82     return false;
83   }
84   func();
85   return true;
86 }
87 
LoadSymbol(const char * symbol_name) const88 void* DllLoader::LoadSymbol(const char* symbol_name) const {
89   const char* error = dlerror();
90   if (error != NULL) {
91     LOG(ERROR) << "Existing error message " << error << "before loading "
92                << symbol_name;
93   }
94   void* sym = dlsym(handle_, symbol_name);
95   if ((error = dlerror()) != NULL) {
96     LOG(ERROR) << "Can't find " << symbol_name << " error: " << error;
97     return NULL;
98   }
99   return sym;
100 }
101 
102 }  // namespace vts
103 }  // namespace android
104