Panda3D
Loading...
Searching...
No Matches
load_dso.cxx
Go to the documentation of this file.
1/**
2 * PANDA 3D SOFTWARE
3 * Copyright (c) Carnegie Mellon University. All rights reserved.
4 *
5 * All use of this software is subject to the terms of the revised BSD
6 * license. You should have received a copy of this license along
7 * with this source code in a file named "LICENSE."
8 *
9 * @file load_dso.cxx
10 * @author drose
11 * @date 2000-05-12
12 */
13
14#include "load_dso.h"
16
17using std::string;
18
19static Filename resolve_dso(const DSearchPath &path, const Filename &filename) {
20 if (filename.is_local()) {
21 if ((path.get_num_directories()==1)&&(path.get_directory(0)=="<auto>")) {
22 // This is a special case, meaning to search in the same directory in
23 // which libp3dtool.dll, or the exe, was started from.
25 DSearchPath spath(dtoolpath.get_dirname());
26 return spath.find_file(filename);
27 } else {
28 return path.find_file(filename);
29 }
30 } else {
31 return filename;
32 }
33}
34
35#if defined(WIN32)
36/* begin Win32-specific code */
37
38#define WINDOWS_LEAN_AND_MEAN
39#include <windows.h>
40#undef WINDOWS_LEAN_AND_MEAN
41
42// Loads in a dynamic library like an .so or .dll. Returns NULL if failure,
43// otherwise on success. If the filename is not absolute, searches the path.
44// If the path is empty, searches the dtool directory.
45
46void *
47load_dso(const DSearchPath &path, const Filename &filename) {
48 Filename abspath = resolve_dso(path, filename);
49 if (!abspath.is_regular_file()) {
50 return nullptr;
51 }
52 std::wstring os_specific_w = abspath.to_os_specific_w();
53
54 // Try using LoadLibraryEx, if possible.
55 typedef HMODULE (WINAPI *tLoadLibraryEx)(LPCWSTR, HANDLE, DWORD);
56 tLoadLibraryEx pLoadLibraryEx;
57 HINSTANCE hLib = LoadLibrary("kernel32.dll");
58 if (hLib) {
59 pLoadLibraryEx = (tLoadLibraryEx)GetProcAddress(hLib, "LoadLibraryExW");
60 if (pLoadLibraryEx) {
61 return pLoadLibraryEx(os_specific_w.c_str(), nullptr, LOAD_WITH_ALTERED_SEARCH_PATH);
62 }
63 }
64
65 return LoadLibraryW(os_specific_w.c_str());
66}
67
68bool
69unload_dso(void *dso_handle) {
70 HMODULE dll_handle = (HMODULE) dso_handle;
71
72 // true indicates success
73 return (FreeLibrary(dll_handle)!=0);
74}
75
76string
77load_dso_error() {
78 DWORD last_error = GetLastError();
79
80 /*
81 LPVOID ptr;
82 if (FormatMessage( FORMAT_MESSAGE_ALLOCATE_BUFFER |
83 FORMAT_MESSAGE_FROM_SYSTEM,
84 NULL,
85 last_error,
86 MAKELANGID( LANG_ENGLISH, SUBLANG_ENGLISH_US ),
87 (LPTSTR)&ptr,
88 0, NULL))
89 {
90 cout << "ERROR: " << " result = " << (char*) ptr << "\n";
91 LocalFree( ptr );
92 }
93 */
94
95 switch (last_error) {
96 case 2: return "File not found";
97 case 3: return "Path not found";
98 case 4: return "Too many open files";
99 case 5: return "Access denied";
100 case 14: return "Out of memory";
101 case 18: return "No more files";
102 case 126: return "Module not found";
103 case 127: return "The specified procedure could not be found";
104 case 193: return "Not a valid Win32 application";
105 case 998: return "Invalid access to memory location";
106 }
107
108 // Some unknown error code.
109 std::ostringstream errmsg;
110 errmsg << "Unknown error " << last_error;
111 return errmsg.str();
112}
113
114void *
115get_dso_symbol(void *handle, const string &name) {
116 // Windows puts a leading underscore in front of the symbol name.
117 return (void *)GetProcAddress((HMODULE)handle, name.c_str());
118}
119
120/* end Win32-specific code */
121
122#else
123/* begin Posix code */
124
125#if defined(IS_OSX)
126#include <mach-o/dyld.h>
127#endif
128
129#include <dlfcn.h>
130
131void *
132load_dso(const DSearchPath &path, const Filename &filename) {
133 Filename abspath = resolve_dso(path, filename);
134 if (!abspath.is_regular_file()) {
135 // Make sure the error flag is cleared, to prevent a subsequent call to
136 // load_dso_error() from returning a previously stored error.
137 dlerror();
138 return nullptr;
139 }
140 string os_specific = abspath.to_os_specific();
141 return dlopen(os_specific.c_str(), RTLD_NOW | RTLD_GLOBAL);
142}
143
144bool
145unload_dso(void *dso_handle) {
146 return dlclose(dso_handle)==0;
147}
148
149string
150load_dso_error() {
151 const char *message = dlerror();
152 if (message != nullptr) {
153 return std::string(message);
154 }
155 return "No error.";
156}
157
158void *
159get_dso_symbol(void *handle, const string &name) {
160 return dlsym(handle, name.c_str());
161}
162
163#endif
This class stores a list of directories that can be searched, in order, to locate a particular file.
Definition dSearchPath.h:28
Filename find_file(const Filename &filename) const
Searches all the directories in the search list for the indicated file, in order.
get_num_directories
Returns the number of directories on the search list.
Definition dSearchPath.h:76
get_directory
Returns the nth directory on the search list.
Definition dSearchPath.h:76
get_dtool_name
Returns the name of the libdtool DLL that is used in this program, if it can be determined.
The name of a file, such as a texture file or an Egg file.
Definition filename.h:44
bool is_regular_file() const
Returns true if the filename exists on the physical disk and is the name of a regular file (i....
std::string to_os_specific() const
Converts the filename from our generic Unix-like convention (forward slashes starting with the root a...
std::wstring to_os_specific_w() const
The wide-string variant on to_os_specific().
bool is_local() const
Returns true if the filename is local, e.g.
Definition filename.I:549
std::string get_dirname() const
Returns the directory part of the filename.
Definition filename.I:358
PANDA 3D SOFTWARE Copyright (c) Carnegie Mellon University.
PANDA 3D SOFTWARE Copyright (c) Carnegie Mellon University.