annotate src/loadso/macosx/SDL_loadso.c @ 1312:c9b51268668f

Updated copyright information and removed rcs id lines (problematic in branch merges) I batch edited these files, so please let me know if I've accidentally removed anybody's credit here.
author Sam Lantinga <slouken@libsdl.org>
date Wed, 01 Feb 2006 06:32:25 +0000
parents 173c063d4f55
children 3692456e7b0f
rev   line source
1173
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1 /*
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
2 SDL - Simple DirectMedia Layer
1312
c9b51268668f Updated copyright information and removed rcs id lines (problematic in branch merges)
Sam Lantinga <slouken@libsdl.org>
parents: 1190
diff changeset
3 Copyright (C) 1997-2006 Sam Lantinga
1173
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
4
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
5 This library is free software; you can redistribute it and/or
1312
c9b51268668f Updated copyright information and removed rcs id lines (problematic in branch merges)
Sam Lantinga <slouken@libsdl.org>
parents: 1190
diff changeset
6 modify it under the terms of the GNU Lesser General Public
1173
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
7 License as published by the Free Software Foundation; either
1312
c9b51268668f Updated copyright information and removed rcs id lines (problematic in branch merges)
Sam Lantinga <slouken@libsdl.org>
parents: 1190
diff changeset
8 version 2.1 of the License, or (at your option) any later version.
1173
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
9
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
10 This library is distributed in the hope that it will be useful,
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU
1312
c9b51268668f Updated copyright information and removed rcs id lines (problematic in branch merges)
Sam Lantinga <slouken@libsdl.org>
parents: 1190
diff changeset
13 Lesser General Public License for more details.
1173
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
14
1312
c9b51268668f Updated copyright information and removed rcs id lines (problematic in branch merges)
Sam Lantinga <slouken@libsdl.org>
parents: 1190
diff changeset
15 You should have received a copy of the GNU Lesser General Public
c9b51268668f Updated copyright information and removed rcs id lines (problematic in branch merges)
Sam Lantinga <slouken@libsdl.org>
parents: 1190
diff changeset
16 License along with this library; if not, write to the Free Software
c9b51268668f Updated copyright information and removed rcs id lines (problematic in branch merges)
Sam Lantinga <slouken@libsdl.org>
parents: 1190
diff changeset
17 Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301 USA
1173
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
18
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
19 Sam Lantinga
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
20 slouken@libsdl.org
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
21 */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
22
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
23 /* Please note that dlcompat apparently ships in current Mac OS X versions
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
24 * as a system library that provides compatibility with the Unix "dlopen"
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
25 * interface. In order to allow SDL to work on older OS X releases and also
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
26 * not conflict with the system lib on newer versions, we include dlcompat
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
27 * in SDL and change the symbols to prevent symbol clash with any existing
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
28 * system libraries. --ryan.
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
29 */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
30
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
31 /* here is the dlcompat license: */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
32
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
33 /*
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
34 Copyright (c) 2002 Jorge Acereda <jacereda@users.sourceforge.net> &
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
35 Peter O'Gorman <ogorman@users.sourceforge.net>
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
36
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
37 Portions may be copyright others, see the AUTHORS file included with this
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
38 distribution.
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
39
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
40 Maintained by Peter O'Gorman <ogorman@users.sourceforge.net>
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
41
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
42 Bug Reports and other queries should go to <ogorman@users.sourceforge.net>
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
43
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
44 Permission is hereby granted, free of charge, to any person obtaining
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
45 a copy of this software and associated documentation files (the
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
46 "Software"), to deal in the Software without restriction, including
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
47 without limitation the rights to use, copy, modify, merge, publish,
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
48 distribute, sublicense, and/or sell copies of the Software, and to
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
49 permit persons to whom the Software is furnished to do so, subject to
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
50 the following conditions:
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
51
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
52 The above copyright notice and this permission notice shall be
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
53 included in all copies or substantial portions of the Software.
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
54
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
55 THE SOFTWARE IS PROVIDED "AS IS", WITHOUT WARRANTY OF ANY KIND,
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
56 EXPRESS OR IMPLIED, INCLUDING BUT NOT LIMITED TO THE WARRANTIES OF
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
57 MERCHANTABILITY, FITNESS FOR A PARTICULAR PURPOSE AND
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
58 NONINFRINGEMENT. IN NO EVENT SHALL THE AUTHORS OR COPYRIGHT HOLDERS BE
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
59 LIABLE FOR ANY CLAIM, DAMAGES OR OTHER LIABILITY, WHETHER IN AN ACTION
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
60 OF CONTRACT, TORT OR OTHERWISE, ARISING FROM, OUT OF OR IN CONNECTION
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
61 WITH THE SOFTWARE OR THE USE OR OTHER DEALINGS IN THE SOFTWARE.
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
62 */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
63
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
64 #include <pthread.h>
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
65 #include <stdio.h>
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
66 #include <stdlib.h>
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
67 #include <string.h>
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
68 #include <sys/types.h>
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
69 #include <sys/stat.h>
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
70 #include <stdarg.h>
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
71 #include <limits.h>
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
72 #include <mach-o/dyld.h>
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
73 #include <mach-o/nlist.h>
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
74 #include <mach-o/getsect.h>
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
75
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
76 /* Just playing to see if it would compile with the freebsd headers, it does,
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
77 * but because of the different values for RTLD_LOCAL etc, it would break binary
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
78 * compat... oh well
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
79 */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
80 #ifndef __BSD_VISIBLE
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
81 #define __BSD_VISIBLE 1
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
82 #endif
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
83
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
84 /*include "dlfcn.h"*/
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
85 #ifdef __cplusplus
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
86 extern "C" {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
87 #endif
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
88
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
89 #if defined (__GNUC__) && __GNUC__ > 3
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
90 #define dl_restrict __restrict
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
91 #else
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
92 #define dl_restrict
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
93 #endif
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
94
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
95 #ifndef _POSIX_SOURCE
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
96 /*
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
97 * Structure filled in by dladdr().
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
98 */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
99 typedef struct SDL_OSX_dl_info {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
100 const char *dli_fname; /* Pathname of shared object */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
101 void *dli_fbase; /* Base address of shared object */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
102 const char *dli_sname; /* Name of nearest symbol */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
103 void *dli_saddr; /* Address of nearest symbol */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
104 } SDL_OSX_Dl_info;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
105
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
106 static int SDL_OSX_dladdr(const void * dl_restrict, SDL_OSX_Dl_info * dl_restrict);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
107 #endif /* ! _POSIX_SOURCE */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
108
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
109 static int SDL_OSX_dlclose(void * handle);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
110 static char * SDL_OSX_dlerror(void);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
111 static void * SDL_OSX_dlopen(const char *path, int mode);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
112 static void * SDL_OSX_dlsym(void * dl_restrict handle, const char * dl_restrict symbol);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
113
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
114 #define RTLD_LAZY 0x1
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
115 #define RTLD_NOW 0x2
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
116 #define RTLD_LOCAL 0x4
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
117 #define RTLD_GLOBAL 0x8
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
118
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
119 #ifndef _POSIX_SOURCE
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
120 #define RTLD_NOLOAD 0x10
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
121 #define RTLD_NODELETE 0x80
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
122
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
123 /*
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
124 * Special handle arguments for SDL_OSX_dlsym().
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
125 */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
126 #define RTLD_NEXT ((void *) -1) /* Search subsequent objects. */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
127 #define RTLD_DEFAULT ((void *) -2) /* Use default search algorithm. */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
128 #endif /* ! _POSIX_SOURCE */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
129
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
130 #ifdef __cplusplus
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
131 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
132 #endif
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
133
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
134 #ifndef dl_restrict
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
135 #define dl_restrict __restrict
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
136 #endif
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
137 /* This is not available on 10.1 */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
138 #ifndef LC_LOAD_WEAK_DYLIB
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
139 #define LC_LOAD_WEAK_DYLIB (0x18 | LC_REQ_DYLD)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
140 #endif
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
141
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
142 /* With this stuff here, this thing may actually compile/run on 10.0 systems
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
143 * Not that I have a 10.0 system to test it on anylonger
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
144 */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
145 #ifndef LC_REQ_DYLD
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
146 #define LC_REQ_DYLD 0x80000000
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
147 #endif
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
148 #ifndef NSADDIMAGE_OPTION_RETURN_ONLY_IF_LOADED
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
149 #define NSADDIMAGE_OPTION_RETURN_ONLY_IF_LOADED 0x4
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
150 #endif
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
151 #ifndef NSADDIMAGE_OPTION_RETURN_ON_ERROR
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
152 #define NSADDIMAGE_OPTION_RETURN_ON_ERROR 0x1
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
153 #endif
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
154 #ifndef NSLOOKUPSYMBOLINIMAGE_OPTION_BIND
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
155 #define NSLOOKUPSYMBOLINIMAGE_OPTION_BIND 0x0
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
156 #endif
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
157 #ifndef NSLOOKUPSYMBOLINIMAGE_OPTION_RETURN_ON_ERROR
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
158 #define NSLOOKUPSYMBOLINIMAGE_OPTION_RETURN_ON_ERROR 0x4
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
159 #endif
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
160 /* These symbols will be looked for in dyld */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
161 static const struct mach_header *(*dyld_NSAddImage) (const char *, unsigned long) = 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
162 static int (*dyld_NSIsSymbolNameDefinedInImage) (const struct mach_header *, const char *) = 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
163 static NSSymbol(*dyld_NSLookupSymbolInImage)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
164 (const struct mach_header *, const char *, unsigned long) = 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
165
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
166 /* Define this to make dlcompat reuse data block. This way in theory we save
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
167 * a little bit of overhead. However we then couldn't correctly catch excess
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
168 * calls to SDL_OSX_dlclose(). Hence we don't use this feature
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
169 */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
170 #undef REUSE_STATUS
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
171
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
172 /* Size of the internal error message buffer (used by dlerror()) */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
173 #define ERR_STR_LEN 251
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
174
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
175 /* Maximum number of search paths supported by getSearchPath */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
176 #define MAX_SEARCH_PATHS 32
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
177
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
178
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
179 #define MAGIC_DYLIB_OFI ((NSObjectFileImage) 'DYOF')
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
180 #define MAGIC_DYLIB_MOD ((NSModule) 'DYMO')
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
181
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
182 /* internal flags */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
183 #define DL_IN_LIST 0x01
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
184
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
185 /* our mutex */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
186 static pthread_mutex_t dlcompat_mutex;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
187 /* Our thread specific storage
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
188 */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
189 static pthread_key_t dlerror_key;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
190
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
191 struct dlthread
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
192 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
193 int lockcnt;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
194 unsigned char errset;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
195 char errstr[ERR_STR_LEN];
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
196 };
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
197
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
198 /* This is our central data structure. Whenever a module is loaded via
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
199 * SDL_OSX_dlopen(), we create such a struct.
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
200 */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
201 struct dlstatus
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
202 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
203 struct dlstatus *next; /* pointer to next element in the linked list */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
204 NSModule module;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
205 const struct mach_header *lib;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
206 int refs; /* reference count */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
207 int mode; /* mode in which this module was loaded */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
208 dev_t device;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
209 ino_t inode;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
210 int flags; /* Any internal flags we may need */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
211 };
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
212
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
213 /* Head node of the dlstatus list */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
214 static struct dlstatus mainStatus = { 0, MAGIC_DYLIB_MOD, NULL, -1, RTLD_GLOBAL, 0, 0, 0 };
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
215 static struct dlstatus *stqueue = &mainStatus;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
216
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
217
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
218 /* Storage for the last error message (used by dlerror()) */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
219 /* static char err_str[ERR_STR_LEN]; */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
220 /* static int err_filled = 0; */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
221
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
222 /* Prototypes to internal functions */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
223 static void debug(const char *fmt, ...);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
224 static void error(const char *str, ...);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
225 static const char *safegetenv(const char *s);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
226 static const char *searchList(void);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
227 static const char *getSearchPath(int i);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
228 static const char *getFullPath(int i, const char *file);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
229 static const struct stat *findFile(const char *file, const char **fullPath);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
230 static int isValidStatus(struct dlstatus *status);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
231 static inline int isFlagSet(int mode, int flag);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
232 static struct dlstatus *lookupStatus(const struct stat *sbuf);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
233 static void insertStatus(struct dlstatus *dls, const struct stat *sbuf);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
234 static int promoteLocalToGlobal(struct dlstatus *dls);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
235 static void *reference(struct dlstatus *dls, int mode);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
236 static void *dlsymIntern(struct dlstatus *dls, const char *symbol, int canSetError);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
237 static struct dlstatus *allocStatus(void);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
238 static struct dlstatus *loadModule(const char *path, const struct stat *sbuf, int mode);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
239 static NSSymbol *search_linked_libs(const struct mach_header *mh, const char *symbol);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
240 static const char *get_lib_name(const struct mach_header *mh);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
241 static const struct mach_header *get_mach_header_from_NSModule(NSModule * mod);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
242 static void dlcompat_init_func(void);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
243 static inline void dlcompat_init_check(void);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
244 static inline void dolock(void);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
245 static inline void dounlock(void);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
246 static void dlerrorfree(void *data);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
247 static void resetdlerror(void);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
248 static const struct mach_header *my_find_image(const char *name);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
249 static const struct mach_header *image_for_address(const void *address);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
250 static inline const char *dyld_error_str(void);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
251
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
252 #if FINK_BUILD
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
253 /* Two Global Functions */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
254 static void *dlsym_prepend_underscore(void *handle, const char *symbol);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
255 static void *dlsym_auto_underscore(void *handle, const char *symbol);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
256
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
257 /* And their _intern counterparts */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
258 static void *dlsym_prepend_underscore_intern(void *handle, const char *symbol);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
259 static void *dlsym_auto_underscore_intern(void *handle, const char *symbol);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
260 #endif
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
261
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
262 /* Functions */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
263
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
264 static void debug(const char *fmt, ...)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
265 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
266 #if DEBUG > 1
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
267 va_list arg;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
268 va_start(arg, fmt);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
269 fprintf(stderr, "DLDEBUG: ");
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
270 vfprintf(stderr, fmt, arg);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
271 fprintf(stderr, "\n");
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
272 fflush(stderr);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
273 va_end(arg);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
274 #endif
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
275 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
276
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
277 static void error(const char *str, ...)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
278 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
279 va_list arg;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
280 struct dlthread *tss;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
281 char * err_str;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
282 va_start(arg, str);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
283 tss = pthread_getspecific(dlerror_key);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
284 err_str = tss->errstr;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
285 strncpy(err_str, "dlcompat: ", ERR_STR_LEN);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
286 vsnprintf(err_str + 10, ERR_STR_LEN - 10, str, arg);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
287 va_end(arg);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
288 debug("ERROR: %s\n", err_str);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
289 tss->errset = 1;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
290 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
291
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
292 static void warning(const char *str)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
293 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
294 #if DEBUG > 0
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
295 fprintf(stderr, "WARNING: dlcompat: %s\n", str);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
296 #endif
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
297 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
298
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
299 static const char *safegetenv(const char *s)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
300 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
301 const char *ss = getenv(s);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
302 return ss ? ss : "";
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
303 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
304
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
305 /* because this is only used for debugging and error reporting functions, we
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
306 * don't really care about how elegant it is... it could use the load
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
307 * commands to find the install name of the library, but...
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
308 */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
309 static const char *get_lib_name(const struct mach_header *mh)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
310 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
311 unsigned long count = _dyld_image_count();
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
312 unsigned long i;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
313 const char *val = NULL;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
314 if (mh)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
315 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
316 for (i = 0; i < count; i++)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
317 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
318 if (mh == _dyld_get_image_header(i))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
319 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
320 val = _dyld_get_image_name(i);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
321 break;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
322 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
323 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
324 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
325 return val;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
326 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
327
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
328 /* Returns the mach_header for the module bu going through all the loaded images
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
329 * and finding the one with the same name as the module. There really ought to be
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
330 * an api for doing this, would be faster, but there isn't one right now
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
331 */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
332 static const struct mach_header *get_mach_header_from_NSModule(NSModule * mod)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
333 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
334 const char *mod_name = NSNameOfModule(mod);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
335 struct mach_header *mh = NULL;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
336 unsigned long count = _dyld_image_count();
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
337 unsigned long i;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
338 debug("Module name: %s", mod_name);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
339 for (i = 0; i < count; i++)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
340 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
341 if (!strcmp(mod_name, _dyld_get_image_name(i)))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
342 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
343 mh = _dyld_get_image_header(i);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
344 break;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
345 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
346 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
347 return mh;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
348 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
349
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
350
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
351 /* Compute and return a list of all directories that we should search when
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
352 * trying to locate a module. We first look at the values of LD_LIBRARY_PATH
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
353 * and DYLD_LIBRARY_PATH, and then finally fall back to looking into
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
354 * /usr/lib and /lib. Since both of the environments variables can contain a
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
355 * list of colon seperated paths, we simply concat them and the two other paths
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
356 * into one big string, which we then can easily parse.
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
357 * Splitting this string into the actual path list is done by getSearchPath()
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
358 */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
359 static const char *searchList()
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
360 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
361 size_t buf_size;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
362 static char *buf=NULL;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
363 const char *ldlp = safegetenv("LD_LIBRARY_PATH");
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
364 const char *dyldlp = safegetenv("DYLD_LIBRARY_PATH");
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
365 const char *stdpath = getenv("DYLD_FALLBACK_LIBRARY_PATH");
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
366 if (!stdpath)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
367 stdpath = "/usr/local/lib:/lib:/usr/lib";
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
368 if (!buf)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
369 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
370 buf_size = strlen(ldlp) + strlen(dyldlp) + strlen(stdpath) + 4;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
371 buf = malloc(buf_size);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
372 snprintf(buf, buf_size, "%s%s%s%s%s%c", dyldlp, (dyldlp[0] ? ":" : ""), ldlp, (ldlp[0] ? ":" : ""),
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
373 stdpath, '\0');
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
374 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
375 return buf;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
376 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
377
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
378 /* Returns the ith search path from the list as computed by searchList() */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
379 static const char *getSearchPath(int i)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
380 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
381 static const char *list = 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
382 static char **path = (char **)0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
383 static int end = 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
384 static int numsize = MAX_SEARCH_PATHS;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
385 static char **tmp;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
386 /* So we can call free() in the "destructor" we use i=-1 to return the alloc'd array */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
387 if (i == -1)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
388 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
389 return (const char*)path;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
390 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
391 if (!path)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
392 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
393 path = (char **)calloc(MAX_SEARCH_PATHS, sizeof(char **));
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
394 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
395 if (!list && !end)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
396 list = searchList();
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
397 if (i >= (numsize))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
398 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
399 debug("Increasing size for long PATH");
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
400 tmp = (char **)calloc((MAX_SEARCH_PATHS + numsize), sizeof(char **));
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
401 if (tmp)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
402 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
403 memcpy(tmp, path, sizeof(char **) * numsize);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
404 free(path);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
405 path = tmp;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
406 numsize += MAX_SEARCH_PATHS;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
407 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
408 else
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
409 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
410 return 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
411 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
412 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
413
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
414 while (!path[i] && !end)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
415 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
416 path[i] = strsep((char **)&list, ":");
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
417
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
418 if (path[i][0] == 0)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
419 path[i] = 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
420 end = (list == 0);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
421 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
422 return path[i];
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
423 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
424
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
425 static const char *getFullPath(int i, const char *file)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
426 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
427 static char buf[PATH_MAX];
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
428 const char *path = getSearchPath(i);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
429 if (path)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
430 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
431 snprintf(buf, PATH_MAX, "%s/%s", path, file);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
432 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
433 return path ? buf : 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
434 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
435
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
436 /* Given a file name, try to determine the full path for that file. Starts
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
437 * its search in the current directory, and then tries all paths in the
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
438 * search list in the order they are specified there.
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
439 */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
440 static const struct stat *findFile(const char *file, const char **fullPath)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
441 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
442 int i = 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
443 static struct stat sbuf;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
444 char *fileName;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
445 debug("finding file %s", file);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
446 *fullPath = file;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
447 if (0 == stat(file, &sbuf))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
448 return &sbuf;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
449 if (strchr(file, '/'))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
450 return 0; /* If the path had a / we don't look in env var places */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
451 fileName = NULL;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
452 if (!fileName)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
453 fileName = (char *)file;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
454 while ((*fullPath = getFullPath(i++, fileName)))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
455 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
456 if (0 == stat(*fullPath, &sbuf))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
457 return &sbuf;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
458 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
459 ;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
460 return 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
461 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
462
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
463 /* Determine whether a given dlstatus is valid or not */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
464 static int isValidStatus(struct dlstatus *status)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
465 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
466 /* Walk the list to verify status is contained in it */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
467 struct dlstatus *dls = stqueue;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
468 while (dls && status != dls)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
469 dls = dls->next;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
470 if (dls == 0)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
471 error("invalid handle");
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
472 else if ((dls->module == 0) || (dls->refs == 0))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
473 error("handle to closed library");
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
474 else
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
475 return TRUE;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
476 return FALSE;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
477 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
478
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
479 static inline int isFlagSet(int mode, int flag)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
480 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
481 return (mode & flag) == flag;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
482 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
483
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
484 static struct dlstatus *lookupStatus(const struct stat *sbuf)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
485 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
486 struct dlstatus *dls = stqueue;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
487 debug("looking for status");
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
488 while (dls && ( /* isFlagSet(dls->mode, RTLD_UNSHARED) */ 0
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
489 || sbuf->st_dev != dls->device || sbuf->st_ino != dls->inode))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
490 dls = dls->next;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
491 return dls;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
492 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
493
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
494 static void insertStatus(struct dlstatus *dls, const struct stat *sbuf)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
495 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
496 debug("inserting status");
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
497 dls->inode = sbuf->st_ino;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
498 dls->device = sbuf->st_dev;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
499 dls->refs = 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
500 dls->mode = 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
501 if ((dls->flags & DL_IN_LIST) == 0)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
502 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
503 dls->next = stqueue;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
504 stqueue = dls;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
505 dls->flags |= DL_IN_LIST;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
506 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
507 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
508
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
509 static struct dlstatus *allocStatus()
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
510 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
511 struct dlstatus *dls;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
512 #ifdef REUSE_STATUS
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
513 dls = stqueue;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
514 while (dls && dls->module)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
515 dls = dls->next;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
516 if (!dls)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
517 #endif
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
518 dls = calloc(sizeof(*dls),1);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
519 return dls;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
520 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
521
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
522 static int promoteLocalToGlobal(struct dlstatus *dls)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
523 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
524 static int (*p) (NSModule module) = 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
525 debug("promoting");
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
526 if (!p)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
527 _dyld_func_lookup("__dyld_NSMakePrivateModulePublic", (unsigned long *)&p);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
528 return (dls->module == MAGIC_DYLIB_MOD) || (p && p(dls->module));
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
529 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
530
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
531 static void *reference(struct dlstatus *dls, int mode)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
532 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
533 if (dls)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
534 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
535 if (dls->module == MAGIC_DYLIB_MOD && isFlagSet(mode, RTLD_LOCAL))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
536 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
537 warning("trying to open a .dylib with RTLD_LOCAL");
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
538 error("unable to open a .dylib with RTLD_LOCAL");
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
539 return NULL;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
540 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
541 if (isFlagSet(mode, RTLD_GLOBAL) &&
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
542 !isFlagSet(dls->mode, RTLD_GLOBAL) && !promoteLocalToGlobal(dls))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
543 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
544 error("unable to promote local module to global");
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
545 return NULL;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
546 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
547 dls->mode |= mode;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
548 dls->refs++;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
549 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
550 else
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
551 debug("reference called with NULL argument");
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
552
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
553 return dls;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
554 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
555
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
556 static const struct mach_header *my_find_image(const char *name)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
557 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
558 const struct mach_header *mh = 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
559 const char *id = NULL;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
560 int i = _dyld_image_count();
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
561 int j;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
562 mh = (struct mach_header *)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
563 dyld_NSAddImage(name, NSADDIMAGE_OPTION_RETURN_ONLY_IF_LOADED |
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
564 NSADDIMAGE_OPTION_RETURN_ON_ERROR);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
565 if (!mh)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
566 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
567 for (j = 0; j < i; j++)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
568 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
569 id = _dyld_get_image_name(j);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
570 if (!strcmp(id, name))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
571 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
572 mh = _dyld_get_image_header(j);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
573 break;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
574 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
575 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
576 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
577 return mh;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
578 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
579
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
580 /*
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
581 * dyld adds libraries by first adding the directly dependant libraries in link order, and
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
582 * then adding the dependencies for those libraries, so we should do the same... but we don't
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
583 * bother adding the extra dependencies, if the symbols are neither in the loaded image nor
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
584 * any of it's direct dependencies, then it probably isn't there.
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
585 */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
586 static NSSymbol *search_linked_libs(const struct mach_header * mh, const char *symbol)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
587 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
588 unsigned int n;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
589 struct load_command *lc = 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
590 struct mach_header *wh;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
591 NSSymbol *nssym = 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
592 if (dyld_NSAddImage && dyld_NSIsSymbolNameDefinedInImage && dyld_NSLookupSymbolInImage)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
593 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
594 lc = (struct load_command *)((char *)mh + sizeof(struct mach_header));
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
595 for (n = 0; n < mh->ncmds; n++, lc = (struct load_command *)((char *)lc + lc->cmdsize))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
596 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
597 if ((LC_LOAD_DYLIB == lc->cmd) || (LC_LOAD_WEAK_DYLIB == lc->cmd))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
598 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
599 if ((wh = (struct mach_header *)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
600 my_find_image((char *)(((struct dylib_command *)lc)->dylib.name.offset +
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
601 (char *)lc))))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
602 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
603 if (dyld_NSIsSymbolNameDefinedInImage(wh, symbol))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
604 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
605 nssym = dyld_NSLookupSymbolInImage(wh,
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
606 symbol,
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
607 NSLOOKUPSYMBOLINIMAGE_OPTION_BIND |
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
608 NSLOOKUPSYMBOLINIMAGE_OPTION_RETURN_ON_ERROR);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
609 break;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
610 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
611 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
612 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
613 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
614 if ((!nssym) && NSIsSymbolNameDefined(symbol))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
615 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
616 /* I've never seen this debug message...*/
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
617 debug("Symbol \"%s\" is defined but was not found", symbol);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
618 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
619 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
620 return nssym;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
621 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
622
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
623 /* Up to the caller to free() returned string */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
624 static inline const char *dyld_error_str()
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
625 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
626 NSLinkEditErrors dylder;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
627 int dylderno;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
628 const char *dylderrstr;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
629 const char *dyldfile;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
630 const char* retStr = NULL;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
631 NSLinkEditError(&dylder, &dylderno, &dyldfile, &dylderrstr);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
632 if (dylderrstr && strlen(dylderrstr))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
633 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
634 retStr = malloc(strlen(dylderrstr) +1);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
635 strcpy((char*)retStr,dylderrstr);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
636 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
637 return retStr;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
638 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
639
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
640 static void *dlsymIntern(struct dlstatus *dls, const char *symbol, int canSetError)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
641 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
642 NSSymbol *nssym = 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
643 #ifdef __GCC__
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
644 void *caller = __builtin_return_address(1); /* Be *very* careful about inlining */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
645 #else
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
646 void *caller = NULL;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
647 #endif
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
648 const struct mach_header *caller_mh = 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
649 const char* savedErrorStr = NULL;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
650 resetdlerror();
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
651 #ifndef RTLD_SELF
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
652 #define RTLD_SELF ((void *) -3)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
653 #endif
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
654 if (NULL == dls)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
655 dls = RTLD_SELF;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
656 if ((RTLD_NEXT == dls) || (RTLD_SELF == dls))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
657 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
658 if (dyld_NSIsSymbolNameDefinedInImage && dyld_NSLookupSymbolInImage && caller)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
659 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
660 caller_mh = image_for_address(caller);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
661 if (RTLD_SELF == dls)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
662 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
663 /* FIXME: We should be using the NSModule api, if SELF is an MH_BUNDLE
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
664 * But it appears to work anyway, and looking at the code in dyld_libfuncs.c
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
665 * this is acceptable.
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
666 */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
667 if (dyld_NSIsSymbolNameDefinedInImage(caller_mh, symbol))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
668 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
669 nssym = dyld_NSLookupSymbolInImage(caller_mh,
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
670 symbol,
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
671 NSLOOKUPSYMBOLINIMAGE_OPTION_BIND |
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
672 NSLOOKUPSYMBOLINIMAGE_OPTION_RETURN_ON_ERROR);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
673 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
674 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
675 if (!nssym)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
676 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
677 if (RTLD_SELF == dls)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
678 savedErrorStr = dyld_error_str();
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
679 nssym = search_linked_libs(caller_mh, symbol);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
680 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
681 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
682 else
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
683 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
684 if (canSetError)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
685 error("RTLD_SELF and RTLD_NEXT are not supported");
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
686 return NULL;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
687 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
688 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
689 if (!nssym)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
690 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
691
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
692 if (RTLD_DEFAULT == dls)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
693 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
694 dls = &mainStatus;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
695 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
696 if (!isValidStatus(dls))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
697 return NULL;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
698
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
699 if (dls->module != MAGIC_DYLIB_MOD)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
700 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
701 nssym = NSLookupSymbolInModule(dls->module, symbol);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
702 if (!nssym && NSIsSymbolNameDefined(symbol))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
703 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
704 debug("Searching dependencies");
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
705 savedErrorStr = dyld_error_str();
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
706 nssym = search_linked_libs(get_mach_header_from_NSModule(dls->module), symbol);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
707 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
708 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
709 else if (dls->lib && dyld_NSIsSymbolNameDefinedInImage && dyld_NSLookupSymbolInImage)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
710 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
711 if (dyld_NSIsSymbolNameDefinedInImage(dls->lib, symbol))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
712 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
713 nssym = dyld_NSLookupSymbolInImage(dls->lib,
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
714 symbol,
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
715 NSLOOKUPSYMBOLINIMAGE_OPTION_BIND |
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
716 NSLOOKUPSYMBOLINIMAGE_OPTION_RETURN_ON_ERROR);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
717 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
718 else if (NSIsSymbolNameDefined(symbol))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
719 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
720 debug("Searching dependencies");
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
721 savedErrorStr = dyld_error_str();
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
722 nssym = search_linked_libs(dls->lib, symbol);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
723 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
724 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
725 else if (dls->module == MAGIC_DYLIB_MOD)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
726 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
727 /* Global context, use NSLookupAndBindSymbol */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
728 if (NSIsSymbolNameDefined(symbol))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
729 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
730 /* There doesn't seem to be a return on error option for this call???
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
731 this is potentially broken, if binding fails, it will improperly
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
732 exit the application. */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
733 nssym = NSLookupAndBindSymbol(symbol);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
734 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
735 else
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
736 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
737 if (savedErrorStr)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
738 free((char*)savedErrorStr);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
739 savedErrorStr = malloc(256);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
740 snprintf((char*)savedErrorStr, 256, "Symbol \"%s\" not in global context",symbol);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
741 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
742 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
743 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
744 /* Error reporting */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
745 if (!nssym)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
746 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
747 if (!savedErrorStr || !strlen(savedErrorStr))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
748 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
749 if (savedErrorStr)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
750 free((char*)savedErrorStr);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
751 savedErrorStr = malloc(256);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
752 snprintf((char*)savedErrorStr, 256,"Symbol \"%s\" not found",symbol);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
753 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
754 if (canSetError)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
755 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
756 error(savedErrorStr);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
757 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
758 else
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
759 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
760 debug(savedErrorStr);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
761 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
762 if (savedErrorStr)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
763 free((char*)savedErrorStr);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
764 return NULL;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
765 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
766 return NSAddressOfSymbol(nssym);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
767 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
768
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
769 static struct dlstatus *loadModule(const char *path, const struct stat *sbuf, int mode)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
770 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
771 NSObjectFileImage ofi = 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
772 NSObjectFileImageReturnCode ofirc;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
773 struct dlstatus *dls;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
774 NSLinkEditErrors ler;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
775 int lerno;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
776 const char *errstr;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
777 const char *file;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
778 void (*init) (void);
1190
173c063d4f55 OS/2 port!
Ryan C. Gordon <icculus@icculus.org>
parents: 1173
diff changeset
779
1173
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
780 ofirc = NSCreateObjectFileImageFromFile(path, &ofi);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
781 switch (ofirc)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
782 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
783 case NSObjectFileImageSuccess:
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
784 break;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
785 case NSObjectFileImageInappropriateFile:
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
786 if (dyld_NSAddImage && dyld_NSIsSymbolNameDefinedInImage && dyld_NSLookupSymbolInImage)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
787 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
788 if (isFlagSet(mode, RTLD_LOCAL))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
789 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
790 warning("trying to open a .dylib with RTLD_LOCAL");
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
791 error("unable to open this file with RTLD_LOCAL");
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
792 return NULL;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
793 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
794 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
795 else
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
796 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
797 error("opening this file is unsupported on this system");
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
798 return NULL;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
799 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
800 break;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
801 case NSObjectFileImageFailure:
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
802 error("object file setup failure");
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
803 return NULL;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
804 case NSObjectFileImageArch:
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
805 error("no object for this architecture");
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
806 return NULL;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
807 case NSObjectFileImageFormat:
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
808 error("bad object file format");
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
809 return NULL;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
810 case NSObjectFileImageAccess:
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
811 error("can't read object file");
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
812 return NULL;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
813 default:
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
814 error("unknown error from NSCreateObjectFileImageFromFile()");
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
815 return NULL;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
816 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
817 dls = lookupStatus(sbuf);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
818 if (!dls)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
819 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
820 dls = allocStatus();
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
821 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
822 if (!dls)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
823 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
824 error("unable to allocate memory");
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
825 return NULL;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
826 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
827 // dls->lib = 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
828 if (ofirc == NSObjectFileImageInappropriateFile)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
829 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
830 if ((dls->lib = dyld_NSAddImage(path, NSADDIMAGE_OPTION_RETURN_ON_ERROR)))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
831 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
832 debug("Dynamic lib loaded at %ld", dls->lib);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
833 ofi = MAGIC_DYLIB_OFI;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
834 dls->module = MAGIC_DYLIB_MOD;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
835 ofirc = NSObjectFileImageSuccess;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
836 /* Although it is possible with a bit of work to modify this so it works and
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
837 functions with RTLD_NOW, I don't deem it necessary at the moment */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
838 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
839 if (!(dls->module))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
840 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
841 NSLinkEditError(&ler, &lerno, &file, &errstr);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
842 if (!errstr || (!strlen(errstr)))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
843 error("Can't open this file type");
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
844 else
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
845 error(errstr);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
846 if ((dls->flags & DL_IN_LIST) == 0)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
847 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
848 free(dls);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
849 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
850 return NULL;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
851 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
852 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
853 else
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
854 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
855 dls->module = NSLinkModule(ofi, path,
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
856 NSLINKMODULE_OPTION_RETURN_ON_ERROR |
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
857 NSLINKMODULE_OPTION_PRIVATE |
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
858 (isFlagSet(mode, RTLD_NOW) ? NSLINKMODULE_OPTION_BINDNOW : 0));
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
859 NSDestroyObjectFileImage(ofi);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
860 if (dls->module)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
861 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
862 dls->lib = get_mach_header_from_NSModule(dls->module);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
863 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
864 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
865 if (!dls->module)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
866 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
867 NSLinkEditError(&ler, &lerno, &file, &errstr);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
868 if ((dls->flags & DL_IN_LIST) == 0)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
869 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
870 free(dls);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
871 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
872 error(errstr);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
873 return NULL;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
874 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
875
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
876 insertStatus(dls, sbuf);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
877 dls = reference(dls, mode);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
878 if ((init = dlsymIntern(dls, "__init", 0)))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
879 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
880 debug("calling _init()");
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
881 init();
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
882 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
883 return dls;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
884 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
885
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
886 inline static void dlcompat_init_check(void)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
887 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
888 static pthread_mutex_t l = PTHREAD_MUTEX_INITIALIZER;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
889 static int init_done = 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
890
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
891 pthread_mutex_lock(&l);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
892 if (!init_done) {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
893 dlcompat_init_func();
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
894 init_done = 1;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
895 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
896 pthread_mutex_unlock(&l);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
897 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
898
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
899 static void dlcompat_init_func(void)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
900 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
901 _dyld_func_lookup("__dyld_NSAddImage", (unsigned long *)&dyld_NSAddImage);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
902 _dyld_func_lookup("__dyld_NSIsSymbolNameDefinedInImage",
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
903 (unsigned long *)&dyld_NSIsSymbolNameDefinedInImage);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
904 _dyld_func_lookup("__dyld_NSLookupSymbolInImage", (unsigned long *)&dyld_NSLookupSymbolInImage);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
905 if (pthread_mutex_init(&dlcompat_mutex, NULL))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
906 exit(1);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
907 if (pthread_key_create(&dlerror_key, &dlerrorfree))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
908 exit(1);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
909 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
910
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
911 static void resetdlerror()
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
912 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
913 struct dlthread *tss;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
914 tss = pthread_getspecific(dlerror_key);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
915 tss->errset = 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
916 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
917
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
918 static void dlerrorfree(void *data)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
919 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
920 free(data);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
921 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
922
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
923 /* We kind of want a recursive lock here, but meet a little trouble
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
924 * because they are not available pre OS X 10.2, so we fake it
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
925 * using thread specific storage to keep a lock count
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
926 */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
927 static inline void dolock(void)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
928 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
929 int err = 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
930 struct dlthread *tss;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
931 dlcompat_init_check();
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
932 tss = pthread_getspecific(dlerror_key);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
933 if (!tss)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
934 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
935 tss = malloc(sizeof(struct dlthread));
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
936 tss->lockcnt = 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
937 tss->errset = 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
938 if (pthread_setspecific(dlerror_key, tss))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
939 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
940 fprintf(stderr,"dlcompat: pthread_setspecific failed\n");
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
941 exit(1);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
942 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
943 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
944 if (!tss->lockcnt)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
945 err = pthread_mutex_lock(&dlcompat_mutex);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
946 tss->lockcnt = tss->lockcnt +1;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
947 if (err)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
948 exit(err);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
949 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
950
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
951 static inline void dounlock(void)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
952 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
953 int err = 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
954 struct dlthread *tss;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
955 tss = pthread_getspecific(dlerror_key);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
956 tss->lockcnt = tss->lockcnt -1;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
957 if (!tss->lockcnt)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
958 err = pthread_mutex_unlock(&dlcompat_mutex);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
959 if (err)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
960 exit(err);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
961 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
962
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
963 static void *SDL_OSX_dlopen(const char *path, int mode)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
964 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
965 const struct stat *sbuf;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
966 struct dlstatus *dls;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
967 const char *fullPath;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
968
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
969 dolock();
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
970 resetdlerror();
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
971 if (!path)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
972 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
973 dls = &mainStatus;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
974 goto dlopenok;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
975 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
976 if (!(sbuf = findFile(path, &fullPath)))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
977 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
978 error("file \"%s\" not found", path);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
979 goto dlopenerror;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
980 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
981 /* Now checks that it hasn't been closed already */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
982 if ((dls = lookupStatus(sbuf)) && (dls->refs > 0))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
983 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
984 /* debug("status found"); */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
985 dls = reference(dls, mode);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
986 goto dlopenok;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
987 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
988 #ifdef RTLD_NOLOAD
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
989 if (isFlagSet(mode, RTLD_NOLOAD))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
990 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
991 error("no existing handle and RTLD_NOLOAD specified");
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
992 goto dlopenerror;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
993 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
994 #endif
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
995 if (isFlagSet(mode, RTLD_LAZY) && isFlagSet(mode, RTLD_NOW))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
996 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
997 error("how can I load something both RTLD_LAZY and RTLD_NOW?");
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
998 goto dlopenerror;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
999 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1000 dls = loadModule(fullPath, sbuf, mode);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1001
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1002 dlopenok:
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1003 dounlock();
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1004 return (void *)dls;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1005 dlopenerror:
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1006 dounlock();
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1007 return NULL;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1008 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1009
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1010 #if !FINK_BUILD
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1011 static void *SDL_OSX_dlsym(void * dl_restrict handle, const char * dl_restrict symbol)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1012 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1013 int sym_len = strlen(symbol);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1014 void *value = NULL;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1015 char *malloc_sym = NULL;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1016 dolock();
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1017 malloc_sym = malloc(sym_len + 2);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1018 if (malloc_sym)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1019 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1020 sprintf(malloc_sym, "_%s", symbol);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1021 value = dlsymIntern(handle, malloc_sym, 1);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1022 free(malloc_sym);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1023 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1024 else
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1025 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1026 error("Unable to allocate memory");
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1027 goto dlsymerror;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1028 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1029 dounlock();
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1030 return value;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1031 dlsymerror:
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1032 dounlock();
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1033 return NULL;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1034 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1035 #endif
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1036
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1037 #if FINK_BUILD
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1038
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1039 static void *dlsym_prepend_underscore(void *handle, const char *symbol)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1040 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1041 void *answer;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1042 dolock();
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1043 answer = dlsym_prepend_underscore_intern(handle, symbol);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1044 dounlock();
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1045 return answer;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1046 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1047
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1048 static void *dlsym_prepend_underscore_intern(void *handle, const char *symbol)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1049 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1050 /*
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1051 * A quick and easy way for porting packages which call dlsym(handle,"sym")
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1052 * If the porter adds -Ddlsym=dlsym_prepend_underscore to the CFLAGS then
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1053 * this function will be called, and will add the required underscore.
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1054 *
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1055 * Note that I haven't figured out yet which should be "standard", prepend
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1056 * the underscore always, or not at all. These global functions need to go away
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1057 * for opendarwin.
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1058 */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1059 int sym_len = strlen(symbol);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1060 void *value = NULL;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1061 char *malloc_sym = NULL;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1062 malloc_sym = malloc(sym_len + 2);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1063 if (malloc_sym)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1064 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1065 sprintf(malloc_sym, "_%s", symbol);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1066 value = dlsymIntern(handle, malloc_sym, 1);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1067 free(malloc_sym);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1068 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1069 else
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1070 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1071 error("Unable to allocate memory");
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1072 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1073 return value;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1074 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1075
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1076 static void *dlsym_auto_underscore(void *handle, const char *symbol)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1077 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1078 void *answer;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1079 dolock();
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1080 answer = dlsym_auto_underscore_intern(handle, symbol);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1081 dounlock();
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1082 return answer;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1083
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1084 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1085 static void *dlsym_auto_underscore_intern(void *handle, const char *symbol)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1086 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1087 struct dlstatus *dls = handle;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1088 void *addr = 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1089 addr = dlsymIntern(dls, symbol, 0);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1090 if (!addr)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1091 addr = dlsym_prepend_underscore_intern(handle, symbol);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1092 return addr;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1093 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1094
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1095
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1096 static void *SDL_OSX_dlsym(void * dl_restrict handle, const char * dl_restrict symbol)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1097 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1098 struct dlstatus *dls = handle;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1099 void *addr = 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1100 dolock();
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1101 addr = dlsymIntern(dls, symbol, 1);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1102 dounlock();
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1103 return addr;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1104 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1105 #endif
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1106
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1107 static int SDL_OSX_dlclose(void *handle)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1108 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1109 struct dlstatus *dls = handle;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1110 dolock();
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1111 resetdlerror();
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1112 if (!isValidStatus(dls))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1113 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1114 goto dlcloseerror;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1115 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1116 if (dls->module == MAGIC_DYLIB_MOD)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1117 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1118 const char *name;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1119 if (!dls->lib)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1120 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1121 name = "global context";
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1122 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1123 else
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1124 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1125 name = get_lib_name(dls->lib);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1126 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1127 warning("trying to close a .dylib!");
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1128 error("Not closing \"%s\" - dynamic libraries cannot be closed", name);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1129 goto dlcloseerror;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1130 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1131 if (!dls->module)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1132 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1133 error("module already closed");
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1134 goto dlcloseerror;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1135 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1136
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1137 if (dls->refs == 1)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1138 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1139 unsigned long options = 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1140 void (*fini) (void);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1141 if ((fini = dlsymIntern(dls, "__fini", 0)))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1142 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1143 debug("calling _fini()");
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1144 fini();
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1145 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1146 options |= NSUNLINKMODULE_OPTION_RESET_LAZY_REFERENCES;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1147 #ifdef RTLD_NODELETE
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1148 if (isFlagSet(dls->mode, RTLD_NODELETE))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1149 options |= NSUNLINKMODULE_OPTION_KEEP_MEMORY_MAPPED;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1150 #endif
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1151 if (!NSUnLinkModule(dls->module, options))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1152 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1153 error("unable to unlink module");
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1154 goto dlcloseerror;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1155 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1156 dls->refs--;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1157 dls->module = 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1158 /* Note: the dlstatus struct dls is neither removed from the list
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1159 * nor is the memory it occupies freed. This shouldn't pose a
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1160 * problem in mostly all cases, though.
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1161 */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1162 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1163 dounlock();
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1164 return 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1165 dlcloseerror:
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1166 dounlock();
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1167 return 1;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1168 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1169
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1170 static char *SDL_OSX_dlerror(void)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1171 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1172 struct dlthread *tss;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1173 const char * err_str = NULL;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1174 dlcompat_init_check();
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1175 tss = pthread_getspecific(dlerror_key);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1176 if (tss != NULL && tss->errset != 0) {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1177 tss->errset = 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1178 err_str = tss->errstr;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1179 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1180 return (err_str);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1181 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1182
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1183 /* Given an address, return the mach_header for the image containing it
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1184 * or zero if the given address is not contained in any loaded images.
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1185 */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1186 static const struct mach_header *image_for_address(const void *address)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1187 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1188 unsigned long i;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1189 unsigned long j;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1190 unsigned long count = _dyld_image_count();
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1191 struct mach_header *mh = 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1192 struct load_command *lc = 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1193 unsigned long addr = NULL;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1194 for (i = 0; i < count; i++)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1195 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1196 addr = (unsigned long)address - _dyld_get_image_vmaddr_slide(i);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1197 mh = _dyld_get_image_header(i);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1198 if (mh)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1199 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1200 lc = (struct load_command *)((char *)mh + sizeof(struct mach_header));
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1201 for (j = 0; j < mh->ncmds; j++, lc = (struct load_command *)((char *)lc + lc->cmdsize))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1202 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1203 if (LC_SEGMENT == lc->cmd &&
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1204 addr >= ((struct segment_command *)lc)->vmaddr &&
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1205 addr <
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1206 ((struct segment_command *)lc)->vmaddr + ((struct segment_command *)lc)->vmsize)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1207 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1208 goto image_found;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1209 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1210 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1211 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1212 mh = 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1213 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1214 image_found:
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1215 return mh;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1216 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1217
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1218 static int SDL_OSX_dladdr(const void * dl_restrict p, SDL_OSX_Dl_info * dl_restrict info)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1219 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1220 /*
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1221 FIXME: USe the routine image_for_address.
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1222 */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1223 unsigned long i;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1224 unsigned long j;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1225 unsigned long count = _dyld_image_count();
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1226 struct mach_header *mh = 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1227 struct load_command *lc = 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1228 unsigned long addr = NULL;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1229 unsigned long table_off = (unsigned long)0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1230 int found = 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1231 if (!info)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1232 return 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1233 dolock();
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1234 resetdlerror();
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1235 info->dli_fname = 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1236 info->dli_fbase = 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1237 info->dli_sname = 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1238 info->dli_saddr = 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1239 /* Some of this was swiped from code posted by Douglas Davidson <ddavidso AT apple DOT com>
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1240 * to darwin-development AT lists DOT apple DOT com and slightly modified
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1241 */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1242 for (i = 0; i < count; i++)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1243 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1244 addr = (unsigned long)p - _dyld_get_image_vmaddr_slide(i);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1245 mh = _dyld_get_image_header(i);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1246 if (mh)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1247 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1248 lc = (struct load_command *)((char *)mh + sizeof(struct mach_header));
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1249 for (j = 0; j < mh->ncmds; j++, lc = (struct load_command *)((char *)lc + lc->cmdsize))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1250 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1251 if (LC_SEGMENT == lc->cmd &&
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1252 addr >= ((struct segment_command *)lc)->vmaddr &&
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1253 addr <
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1254 ((struct segment_command *)lc)->vmaddr + ((struct segment_command *)lc)->vmsize)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1255 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1256 info->dli_fname = _dyld_get_image_name(i);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1257 info->dli_fbase = (void *)mh;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1258 found = 1;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1259 break;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1260 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1261 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1262 if (found)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1263 break;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1264 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1265 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1266 if (!found)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1267 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1268 dounlock();
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1269 return 0;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1270 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1271 lc = (struct load_command *)((char *)mh + sizeof(struct mach_header));
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1272 for (j = 0; j < mh->ncmds; j++, lc = (struct load_command *)((char *)lc + lc->cmdsize))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1273 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1274 if (LC_SEGMENT == lc->cmd)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1275 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1276 if (!strcmp(((struct segment_command *)lc)->segname, "__LINKEDIT"))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1277 break;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1278 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1279 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1280 table_off =
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1281 ((unsigned long)((struct segment_command *)lc)->vmaddr) -
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1282 ((unsigned long)((struct segment_command *)lc)->fileoff) + _dyld_get_image_vmaddr_slide(i);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1283 debug("table off %x", table_off);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1284
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1285 lc = (struct load_command *)((char *)mh + sizeof(struct mach_header));
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1286 for (j = 0; j < mh->ncmds; j++, lc = (struct load_command *)((char *)lc + lc->cmdsize))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1287 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1288 if (LC_SYMTAB == lc->cmd)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1289 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1290
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1291 struct nlist *symtable = (struct nlist *)(((struct symtab_command *)lc)->symoff + table_off);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1292 unsigned long numsyms = ((struct symtab_command *)lc)->nsyms;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1293 struct nlist *nearest = NULL;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1294 unsigned long diff = 0xffffffff;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1295 unsigned long strtable = (unsigned long)(((struct symtab_command *)lc)->stroff + table_off);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1296 debug("symtable %x", symtable);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1297 for (i = 0; i < numsyms; i++)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1298 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1299 /* Ignore the following kinds of Symbols */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1300 if ((!symtable->n_value) /* Undefined */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1301 || (symtable->n_type >= N_PEXT) /* Debug symbol */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1302 || (!(symtable->n_type & N_EXT)) /* Local Symbol */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1303 )
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1304 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1305 symtable++;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1306 continue;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1307 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1308 if ((addr >= symtable->n_value) && (diff >= (symtable->n_value - addr)))
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1309 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1310 diff = (unsigned long)symtable->n_value - addr;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1311 nearest = symtable;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1312 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1313 symtable++;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1314 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1315 if (nearest)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1316 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1317 info->dli_saddr = nearest->n_value + ((void *)p - addr);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1318 info->dli_sname = (char *)(strtable + nearest->n_un.n_strx);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1319 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1320 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1321 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1322 dounlock();
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1323 return 1;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1324 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1325
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1326
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1327 /*
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1328 * Implement the dlfunc() interface, which behaves exactly the same as
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1329 * dlsym() except that it returns a function pointer instead of a data
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1330 * pointer. This can be used by applications to avoid compiler warnings
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1331 * about undefined behavior, and is intended as prior art for future
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1332 * POSIX standardization. This function requires that all pointer types
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1333 * have the same representation, which is true on all platforms FreeBSD
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1334 * runs on, but is not guaranteed by the C standard.
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1335 */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1336 #if 0
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1337 static dlfunc_t SDL_OSX_dlfunc(void * dl_restrict handle, const char * dl_restrict symbol)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1338 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1339 union
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1340 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1341 void *d;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1342 dlfunc_t f;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1343 } rv;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1344 int sym_len = strlen(symbol);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1345 char *malloc_sym = NULL;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1346 dolock();
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1347 malloc_sym = malloc(sym_len + 2);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1348 if (malloc_sym)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1349 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1350 sprintf(malloc_sym, "_%s", symbol);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1351 rv.d = dlsymIntern(handle, malloc_sym, 1);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1352 free(malloc_sym);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1353 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1354 else
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1355 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1356 error("Unable to allocate memory");
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1357 goto dlfuncerror;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1358 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1359 dounlock();
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1360 return rv.f;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1361 dlfuncerror:
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1362 dounlock();
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1363 return NULL;
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1364 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1365 #endif
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1366
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1367
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1368
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1369 /* dlcompat ends, here's the SDL interface... --ryan. */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1370
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1371
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1372 /* * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * * */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1373 /* System dependent library loading routines */
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1374
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1375 #if !SDL_INTERNAL_BUILDING_LOADSO
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1376 #error Do not compile directly...compile src/SDL_loadso.c instead!
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1377 #endif
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1378
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1379 #if !defined(MACOSX)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1380 #error Compiling for the wrong platform?
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1381 #elif defined(USE_DLOPEN)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1382 #error Do not use USE_DLOPEN on Mac OS X.
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1383 #endif
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1384
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1385 #include "SDL_types.h"
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1386 #include "SDL_error.h"
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1387 #include "SDL_loadso.h"
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1388
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1389 void *SDL_LoadObject(const char *sofile)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1390 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1391 void *handle = SDL_OSX_dlopen(sofile, RTLD_NOW);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1392 const char *loaderror = (char *)SDL_OSX_dlerror();
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1393 if ( handle == NULL ) {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1394 SDL_SetError("Failed loading %s: %s", sofile, loaderror);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1395 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1396 return(handle);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1397 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1398
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1399 void *SDL_LoadFunction(void *handle, const char *name)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1400 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1401 void *symbol = SDL_OSX_dlsym(handle, name);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1402 if ( symbol == NULL ) {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1403 SDL_SetError("Failed loading %s: %s", name, (const char *)SDL_OSX_dlerror());
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1404 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1405 return(symbol);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1406 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1407
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1408 void SDL_UnloadObject(void *handle)
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1409 {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1410 if ( handle != NULL ) {
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1411 SDL_OSX_dlclose(handle);
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1412 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1413 }
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1414
e9cf8c1b4590 Split up src/SDL_loadso.c into platform directories.
Ryan C. Gordon <icculus@icculus.org>
parents:
diff changeset
1415