1 /*-------------------------------------------------------------------------
2 * drawElements Utility Library
3 * ----------------------------
4 *
5 * Copyright 2014 The Android Open Source Project
6 *
7 * Licensed under the Apache License, Version 2.0 (the "License");
8 * you may not use this file except in compliance with the License.
9 * You may obtain a copy of the License at
10 *
11 * http://www.apache.org/licenses/LICENSE-2.0
12 *
13 * Unless required by applicable law or agreed to in writing, software
14 * distributed under the License is distributed on an "AS IS" BASIS,
15 * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
16 * See the License for the specific language governing permissions and
17 * limitations under the License.
18 *
19 *//*!
20 * \file
21 * \brief Dynamic link library abstraction.
22 *//*--------------------------------------------------------------------*/
23
24 #include "deDynamicLibrary.h"
25 #include "deMemory.h"
26
27 #if (DE_OS == DE_OS_UNIX) || (DE_OS == DE_OS_ANDROID) || (DE_OS == DE_OS_OSX) || (DE_OS == DE_OS_SYMBIAN) || \
28 (DE_OS == DE_OS_IOS) || (DE_OS == DE_OS_QNX) || (DE_OS == DE_OS_FUCHSIA)
29 /* Posix implementation. */
30
31 #include <dlfcn.h>
32 #include <libgen.h>
33 #include <stdlib.h>
34
35 struct deDynamicLibrary_s
36 {
37 void *libHandle;
38 };
39
deDynamicLibrary_open(const char * fileName)40 deDynamicLibrary *deDynamicLibrary_open(const char *fileName)
41 {
42 deDynamicLibrary *library = (deDynamicLibrary *)deCalloc(sizeof(deDynamicLibrary));
43 if (!library)
44 return DE_NULL;
45
46 if (getenv("LD_LIBRARY_PATH"))
47 {
48 // basename() requires a non-const string because it may modify the its contents, so we cannot pass fileName to
49 // it directly. The string may be coming from statically allocated memory. E.g. this segfaulted in FreeBSD.
50 char *aux = deStrdup(fileName);
51 if (!aux)
52 return NULL;
53 library->libHandle = dlopen(basename(aux), RTLD_LAZY);
54 deFree(aux);
55 }
56 else
57 library->libHandle = dlopen(fileName, RTLD_LAZY);
58
59 if (!library->libHandle)
60 {
61 deFree(library);
62 return DE_NULL;
63 }
64
65 return library;
66 }
67
deDynamicLibrary_close(deDynamicLibrary * library)68 void deDynamicLibrary_close(deDynamicLibrary *library)
69 {
70 if (library && library->libHandle)
71 dlclose(library->libHandle);
72 deFree(library);
73 }
74
deDynamicLibrary_getFunction(const deDynamicLibrary * library,const char * symbolName)75 deFunctionPtr deDynamicLibrary_getFunction(const deDynamicLibrary *library, const char *symbolName)
76 {
77 /* C forbids direct cast from object pointer to function pointer */
78 union
79 {
80 deFunctionPtr funcPtr;
81 void *objPtr;
82 } ptr;
83
84 DE_ASSERT(library && library->libHandle && symbolName);
85 ptr.objPtr = dlsym(library->libHandle, symbolName);
86 return ptr.funcPtr;
87 }
88
89 #elif (DE_OS == DE_OS_WIN32)
90 /* Win32 implementation. */
91
92 #define WIN32_LEAN_AND_MEAN
93 #define VC_EXTRALEAN
94 #include <windows.h>
95
96 struct deDynamicLibrary_s
97 {
98 HINSTANCE handle;
99 };
100
deDynamicLibrary_open(const char * fileName)101 deDynamicLibrary *deDynamicLibrary_open(const char *fileName)
102 {
103 deDynamicLibrary *library = (deDynamicLibrary *)deCalloc(sizeof(deDynamicLibrary));
104 if (!library)
105 return DE_NULL;
106
107 library->handle = LoadLibrary(fileName);
108 if (!library->handle)
109 {
110 deFree(library);
111 return DE_NULL;
112 }
113
114 return library;
115 }
116
deDynamicLibrary_close(deDynamicLibrary * library)117 void deDynamicLibrary_close(deDynamicLibrary *library)
118 {
119 if (library && library->handle)
120 FreeLibrary(library->handle);
121 deFree(library);
122 }
123
deDynamicLibrary_getFunction(const deDynamicLibrary * library,const char * symbolName)124 deFunctionPtr deDynamicLibrary_getFunction(const deDynamicLibrary *library, const char *symbolName)
125 {
126 DE_ASSERT(library && library->handle && symbolName);
127 return (deFunctionPtr)GetProcAddress(library->handle, symbolName);
128 }
129
130 #else
131 #error deDynamicLibrary is not implemented on this OS
132 #endif
133