1*906afcb8SAndy Fiddaman /*********************************************************************** 2*906afcb8SAndy Fiddaman * * 3*906afcb8SAndy Fiddaman * This software is part of the ast package * 4*906afcb8SAndy Fiddaman * Copyright (c) 1997-2011 AT&T Intellectual Property * 5*906afcb8SAndy Fiddaman * and is licensed under the * 6*906afcb8SAndy Fiddaman * Eclipse Public License, Version 1.0 * 7*906afcb8SAndy Fiddaman * by AT&T Intellectual Property * 8*906afcb8SAndy Fiddaman * * 9*906afcb8SAndy Fiddaman * A copy of the License is available at * 10*906afcb8SAndy Fiddaman * http://www.eclipse.org/org/documents/epl-v10.html * 11*906afcb8SAndy Fiddaman * (with md5 checksum b35adb5213ca9657e911e9befb180842) * 12*906afcb8SAndy Fiddaman * * 13*906afcb8SAndy Fiddaman * Information and Software Systems Research * 14*906afcb8SAndy Fiddaman * AT&T Research * 15*906afcb8SAndy Fiddaman * Florham Park NJ * 16*906afcb8SAndy Fiddaman * * 17*906afcb8SAndy Fiddaman * Glenn Fowler <gsf@research.att.com> * 18*906afcb8SAndy Fiddaman * * 19*906afcb8SAndy Fiddaman ***********************************************************************/ 20*906afcb8SAndy Fiddaman #pragma prototyped 21*906afcb8SAndy Fiddaman /* 22*906afcb8SAndy Fiddaman * provide dlopen/dlsym/dlerror interface 23*906afcb8SAndy Fiddaman * 24*906afcb8SAndy Fiddaman * David Korn 25*906afcb8SAndy Fiddaman * Glenn Fowler 26*906afcb8SAndy Fiddaman * AT&T Research 27*906afcb8SAndy Fiddaman */ 28*906afcb8SAndy Fiddaman 29*906afcb8SAndy Fiddaman static const char id[] = "\n@(#)$Id: dll library (AT&T Research) 2009-04-15 $\0\n"; 30*906afcb8SAndy Fiddaman 31*906afcb8SAndy Fiddaman #include <ast.h> 32*906afcb8SAndy Fiddaman #include <dlldefs.h> 33*906afcb8SAndy Fiddaman #include <error.h> 34*906afcb8SAndy Fiddaman 35*906afcb8SAndy Fiddaman #define T(x) ERROR_dictionary(x) 36*906afcb8SAndy Fiddaman 37*906afcb8SAndy Fiddaman #if _BLD_dll && defined(__EXPORT__) 38*906afcb8SAndy Fiddaman #define extern __EXPORT__ 39*906afcb8SAndy Fiddaman #endif 40*906afcb8SAndy Fiddaman 41*906afcb8SAndy Fiddaman #if _hdr_dlfcn && _lib_dlopen 42*906afcb8SAndy Fiddaman 43*906afcb8SAndy Fiddaman /* 44*906afcb8SAndy Fiddaman * standard 45*906afcb8SAndy Fiddaman */ 46*906afcb8SAndy Fiddaman 47*906afcb8SAndy Fiddaman # include <dlfcn.h> 48*906afcb8SAndy Fiddaman 49*906afcb8SAndy Fiddaman #else 50*906afcb8SAndy Fiddaman #if _hdr_dl 51*906afcb8SAndy Fiddaman 52*906afcb8SAndy Fiddaman /* 53*906afcb8SAndy Fiddaman * HP-UX 54*906afcb8SAndy Fiddaman */ 55*906afcb8SAndy Fiddaman 56*906afcb8SAndy Fiddaman # include <dl.h> 57*906afcb8SAndy Fiddaman # ifndef BIND_FIRST 58*906afcb8SAndy Fiddaman # define BIND_FIRST 0x4 59*906afcb8SAndy Fiddaman # endif 60*906afcb8SAndy Fiddaman # ifndef BIND_NOSTART 61*906afcb8SAndy Fiddaman # define BIND_NOSTART 0x10 62*906afcb8SAndy Fiddaman # endif 63*906afcb8SAndy Fiddaman 64*906afcb8SAndy Fiddaman static shl_t all; 65*906afcb8SAndy Fiddaman static int err; 66*906afcb8SAndy Fiddaman dlopen(const char * path,int mode)67*906afcb8SAndy Fiddaman extern void* dlopen(const char* path, int mode) 68*906afcb8SAndy Fiddaman { 69*906afcb8SAndy Fiddaman void* dll; 70*906afcb8SAndy Fiddaman 71*906afcb8SAndy Fiddaman if (!path) 72*906afcb8SAndy Fiddaman return (void*)&all; 73*906afcb8SAndy Fiddaman if (mode) 74*906afcb8SAndy Fiddaman mode = (BIND_IMMEDIATE|BIND_FIRST|BIND_NOSTART); 75*906afcb8SAndy Fiddaman if (!(dll = (void*)shl_load(path, mode, 0L))) 76*906afcb8SAndy Fiddaman err = errno; 77*906afcb8SAndy Fiddaman return dll; 78*906afcb8SAndy Fiddaman } 79*906afcb8SAndy Fiddaman dlclose(void * dll)80*906afcb8SAndy Fiddaman extern int dlclose(void* dll) 81*906afcb8SAndy Fiddaman { 82*906afcb8SAndy Fiddaman return 0; 83*906afcb8SAndy Fiddaman } 84*906afcb8SAndy Fiddaman dlsym(void * dll,const char * name)85*906afcb8SAndy Fiddaman extern void* dlsym(void* dll, const char* name) 86*906afcb8SAndy Fiddaman { 87*906afcb8SAndy Fiddaman shl_t handle; 88*906afcb8SAndy Fiddaman long addr; 89*906afcb8SAndy Fiddaman 90*906afcb8SAndy Fiddaman handle = dll == (void*)&all ? (shl_t)0 : (shl_t)dll; 91*906afcb8SAndy Fiddaman if (shl_findsym(&handle, name, TYPE_UNDEFINED, &addr)) 92*906afcb8SAndy Fiddaman { 93*906afcb8SAndy Fiddaman err = errno; 94*906afcb8SAndy Fiddaman return 0; 95*906afcb8SAndy Fiddaman } 96*906afcb8SAndy Fiddaman return (void*)addr; 97*906afcb8SAndy Fiddaman } 98*906afcb8SAndy Fiddaman dlerror(void)99*906afcb8SAndy Fiddaman extern char* dlerror(void) 100*906afcb8SAndy Fiddaman { 101*906afcb8SAndy Fiddaman char* msg; 102*906afcb8SAndy Fiddaman 103*906afcb8SAndy Fiddaman if (!err) 104*906afcb8SAndy Fiddaman return 0; 105*906afcb8SAndy Fiddaman msg = fmterror(err); 106*906afcb8SAndy Fiddaman err = 0; 107*906afcb8SAndy Fiddaman return msg; 108*906afcb8SAndy Fiddaman } 109*906afcb8SAndy Fiddaman 110*906afcb8SAndy Fiddaman #else 111*906afcb8SAndy Fiddaman #if _sys_ldr && _lib_loadbind 112*906afcb8SAndy Fiddaman 113*906afcb8SAndy Fiddaman /* 114*906afcb8SAndy Fiddaman * rs6000 115*906afcb8SAndy Fiddaman */ 116*906afcb8SAndy Fiddaman 117*906afcb8SAndy Fiddaman # include <sys/ldr.h> 118*906afcb8SAndy Fiddaman # include <xcoff.h> 119*906afcb8SAndy Fiddaman 120*906afcb8SAndy Fiddaman /* xcoff module header */ 121*906afcb8SAndy Fiddaman struct hdr 122*906afcb8SAndy Fiddaman { 123*906afcb8SAndy Fiddaman struct filehdr f; 124*906afcb8SAndy Fiddaman struct aouthdr a; 125*906afcb8SAndy Fiddaman struct scnhdr s[1]; 126*906afcb8SAndy Fiddaman }; 127*906afcb8SAndy Fiddaman 128*906afcb8SAndy Fiddaman static struct ld_info* ld_info; 129*906afcb8SAndy Fiddaman static unsigned int ld_info_size = 1024; 130*906afcb8SAndy Fiddaman static void* last_module; 131*906afcb8SAndy Fiddaman static int err; 132*906afcb8SAndy Fiddaman dlopen(const char * path,int mode)133*906afcb8SAndy Fiddaman extern void* dlopen(const char* path, int mode) 134*906afcb8SAndy Fiddaman { 135*906afcb8SAndy Fiddaman void* dll; 136*906afcb8SAndy Fiddaman 137*906afcb8SAndy Fiddaman if (!(dll = (void*)load((char*)path, mode, getenv("LIBPATH")))) 138*906afcb8SAndy Fiddaman err = errno; 139*906afcb8SAndy Fiddaman return dll; 140*906afcb8SAndy Fiddaman } 141*906afcb8SAndy Fiddaman dlclose(void * dll)142*906afcb8SAndy Fiddaman extern int dlclose(void* dll) 143*906afcb8SAndy Fiddaman { 144*906afcb8SAndy Fiddaman return 0; 145*906afcb8SAndy Fiddaman } 146*906afcb8SAndy Fiddaman getquery(void)147*906afcb8SAndy Fiddaman static int getquery(void) 148*906afcb8SAndy Fiddaman { 149*906afcb8SAndy Fiddaman if (!ld_info) 150*906afcb8SAndy Fiddaman ld_info = malloc(ld_info_size); 151*906afcb8SAndy Fiddaman for (;;) 152*906afcb8SAndy Fiddaman { 153*906afcb8SAndy Fiddaman if (!ld_info) 154*906afcb8SAndy Fiddaman return 1; 155*906afcb8SAndy Fiddaman if (!loadquery(L_GETINFO, ld_info, ld_info_size)) 156*906afcb8SAndy Fiddaman return 0; 157*906afcb8SAndy Fiddaman if (errno != ENOMEM) 158*906afcb8SAndy Fiddaman return 1; 159*906afcb8SAndy Fiddaman ld_info = realloc(ld_info, ld_info_size *= 2); 160*906afcb8SAndy Fiddaman } 161*906afcb8SAndy Fiddaman } 162*906afcb8SAndy Fiddaman 163*906afcb8SAndy Fiddaman /* find the loaded module whose data area contains the 164*906afcb8SAndy Fiddaman * address passed in. Remember that procedure pointers 165*906afcb8SAndy Fiddaman * are implemented as pointers to descriptors in the 166*906afcb8SAndy Fiddaman * data area of the module defining the procedure 167*906afcb8SAndy Fiddaman */ getinfo(void * module)168*906afcb8SAndy Fiddaman static struct ld_info* getinfo(void* module) 169*906afcb8SAndy Fiddaman { 170*906afcb8SAndy Fiddaman struct ld_info* info = ld_info; 171*906afcb8SAndy Fiddaman register int n = 1; 172*906afcb8SAndy Fiddaman 173*906afcb8SAndy Fiddaman if (!ld_info || module != last_module) 174*906afcb8SAndy Fiddaman { 175*906afcb8SAndy Fiddaman last_module = module; 176*906afcb8SAndy Fiddaman if (getquery()) 177*906afcb8SAndy Fiddaman return 0; 178*906afcb8SAndy Fiddaman info = ld_info; 179*906afcb8SAndy Fiddaman } 180*906afcb8SAndy Fiddaman while (n) 181*906afcb8SAndy Fiddaman { 182*906afcb8SAndy Fiddaman if ((char*)(info->ldinfo_dataorg) <= (char*)module && 183*906afcb8SAndy Fiddaman (char*)module <= ((char*)(info->ldinfo_dataorg) 184*906afcb8SAndy Fiddaman + (unsigned)(info->ldinfo_datasize))) 185*906afcb8SAndy Fiddaman return info; 186*906afcb8SAndy Fiddaman if (n=info->ldinfo_next) 187*906afcb8SAndy Fiddaman info = (void*)((char*)info + n); 188*906afcb8SAndy Fiddaman } 189*906afcb8SAndy Fiddaman return 0; 190*906afcb8SAndy Fiddaman } 191*906afcb8SAndy Fiddaman getloc(struct hdr * hdr,char * data,char * name)192*906afcb8SAndy Fiddaman static char* getloc(struct hdr* hdr, char* data, char* name) 193*906afcb8SAndy Fiddaman { 194*906afcb8SAndy Fiddaman struct ldhdr* ldhdr; 195*906afcb8SAndy Fiddaman struct ldsym* ldsym; 196*906afcb8SAndy Fiddaman ulong datareloc; 197*906afcb8SAndy Fiddaman ulong textreloc; 198*906afcb8SAndy Fiddaman int i; 199*906afcb8SAndy Fiddaman 200*906afcb8SAndy Fiddaman /* data is relocated by the difference between 201*906afcb8SAndy Fiddaman * its virtual origin and where it was 202*906afcb8SAndy Fiddaman * actually placed 203*906afcb8SAndy Fiddaman */ 204*906afcb8SAndy Fiddaman /*N.B. o_sndata etc. are one based */ 205*906afcb8SAndy Fiddaman datareloc = (ulong)data - hdr->s[hdr->a.o_sndata-1].s_vaddr; 206*906afcb8SAndy Fiddaman /*hdr is address of header, not text, so add text s_scnptr */ 207*906afcb8SAndy Fiddaman textreloc = (ulong)hdr + hdr->s[hdr->a.o_sntext-1].s_scnptr 208*906afcb8SAndy Fiddaman - hdr->s[hdr->a.o_sntext-1].s_vaddr; 209*906afcb8SAndy Fiddaman ldhdr = (void*)((char*)hdr+ hdr->s[hdr->a.o_snloader-1].s_scnptr); 210*906afcb8SAndy Fiddaman ldsym = (void*) (ldhdr+1); 211*906afcb8SAndy Fiddaman /* search the exports symbols */ 212*906afcb8SAndy Fiddaman for(i=0; i < ldhdr->l_nsyms;ldsym++,i++) 213*906afcb8SAndy Fiddaman { 214*906afcb8SAndy Fiddaman char *symname,symbuf[9]; 215*906afcb8SAndy Fiddaman char *loc; 216*906afcb8SAndy Fiddaman /* the symbol name representation is a nuisance since 217*906afcb8SAndy Fiddaman * 8 character names appear in l_name but may 218*906afcb8SAndy Fiddaman * not be null terminated. This code works around 219*906afcb8SAndy Fiddaman * that by brute force 220*906afcb8SAndy Fiddaman */ 221*906afcb8SAndy Fiddaman if (ldsym->l_zeroes) 222*906afcb8SAndy Fiddaman { 223*906afcb8SAndy Fiddaman symname = symbuf; 224*906afcb8SAndy Fiddaman memcpy(symbuf,ldsym->l_name,8); 225*906afcb8SAndy Fiddaman symbuf[8] = 0; 226*906afcb8SAndy Fiddaman } 227*906afcb8SAndy Fiddaman else 228*906afcb8SAndy Fiddaman symname = (void*)(ldsym->l_offset + (ulong)ldhdr + ldhdr->l_stoff); 229*906afcb8SAndy Fiddaman if (strcmp(symname,name)) 230*906afcb8SAndy Fiddaman continue; 231*906afcb8SAndy Fiddaman loc = (char*)ldsym->l_value; 232*906afcb8SAndy Fiddaman if ((ldsym->l_scnum==hdr->a.o_sndata) || 233*906afcb8SAndy Fiddaman (ldsym->l_scnum==hdr->a.o_snbss)) 234*906afcb8SAndy Fiddaman loc += datareloc; 235*906afcb8SAndy Fiddaman else if (ldsym->l_scnum==hdr->a.o_sntext) 236*906afcb8SAndy Fiddaman loc += textreloc; 237*906afcb8SAndy Fiddaman return loc; 238*906afcb8SAndy Fiddaman } 239*906afcb8SAndy Fiddaman return 0; 240*906afcb8SAndy Fiddaman } 241*906afcb8SAndy Fiddaman dlsym(void * handle,const char * name)242*906afcb8SAndy Fiddaman extern void* dlsym(void* handle, const char* name) 243*906afcb8SAndy Fiddaman { 244*906afcb8SAndy Fiddaman void* addr; 245*906afcb8SAndy Fiddaman struct ld_info* info; 246*906afcb8SAndy Fiddaman 247*906afcb8SAndy Fiddaman if (!(info = getinfo(handle)) || !(addr = getloc(info->ldinfo_textorg,info->ldinfo_dataorg,(char*)name))) 248*906afcb8SAndy Fiddaman { 249*906afcb8SAndy Fiddaman err = errno; 250*906afcb8SAndy Fiddaman return 0; 251*906afcb8SAndy Fiddaman } 252*906afcb8SAndy Fiddaman return addr; 253*906afcb8SAndy Fiddaman } 254*906afcb8SAndy Fiddaman dlerror(void)255*906afcb8SAndy Fiddaman extern char* dlerror(void) 256*906afcb8SAndy Fiddaman { 257*906afcb8SAndy Fiddaman char* msg; 258*906afcb8SAndy Fiddaman 259*906afcb8SAndy Fiddaman if (!err) 260*906afcb8SAndy Fiddaman return 0; 261*906afcb8SAndy Fiddaman msg = fmterror(err); 262*906afcb8SAndy Fiddaman err = 0; 263*906afcb8SAndy Fiddaman return msg; 264*906afcb8SAndy Fiddaman } 265*906afcb8SAndy Fiddaman 266*906afcb8SAndy Fiddaman #else 267*906afcb8SAndy Fiddaman #if _hdr_dll && _lib_dllload 268*906afcb8SAndy Fiddaman 269*906afcb8SAndy Fiddaman /* 270*906afcb8SAndy Fiddaman * MVS 271*906afcb8SAndy Fiddaman */ 272*906afcb8SAndy Fiddaman 273*906afcb8SAndy Fiddaman # include <dll.h> 274*906afcb8SAndy Fiddaman 275*906afcb8SAndy Fiddaman static int err; 276*906afcb8SAndy Fiddaman dlopen(const char * path,int mode)277*906afcb8SAndy Fiddaman extern void* dlopen(const char* path, int mode) 278*906afcb8SAndy Fiddaman { 279*906afcb8SAndy Fiddaman void* dll; 280*906afcb8SAndy Fiddaman 281*906afcb8SAndy Fiddaman NoP(mode); 282*906afcb8SAndy Fiddaman if (!(dll = (void*)dllload(path))) 283*906afcb8SAndy Fiddaman err = errno; 284*906afcb8SAndy Fiddaman return dll; 285*906afcb8SAndy Fiddaman } 286*906afcb8SAndy Fiddaman dlclose(void * dll)287*906afcb8SAndy Fiddaman extern int dlclose(void* dll) 288*906afcb8SAndy Fiddaman { 289*906afcb8SAndy Fiddaman return 0; 290*906afcb8SAndy Fiddaman } 291*906afcb8SAndy Fiddaman dlsym(void * handle,const char * name)292*906afcb8SAndy Fiddaman extern void* dlsym(void* handle, const char* name) 293*906afcb8SAndy Fiddaman { 294*906afcb8SAndy Fiddaman void* addr; 295*906afcb8SAndy Fiddaman 296*906afcb8SAndy Fiddaman if (!(addr = (void*)dllqueryfn(handle, (char*)name))) 297*906afcb8SAndy Fiddaman err = errno; 298*906afcb8SAndy Fiddaman return addr; 299*906afcb8SAndy Fiddaman } 300*906afcb8SAndy Fiddaman dlerror(void)301*906afcb8SAndy Fiddaman extern char* dlerror(void) 302*906afcb8SAndy Fiddaman { 303*906afcb8SAndy Fiddaman char* msg; 304*906afcb8SAndy Fiddaman 305*906afcb8SAndy Fiddaman if (!err) 306*906afcb8SAndy Fiddaman return 0; 307*906afcb8SAndy Fiddaman msg = fmterror(err); 308*906afcb8SAndy Fiddaman err = 0; 309*906afcb8SAndy Fiddaman return msg; 310*906afcb8SAndy Fiddaman } 311*906afcb8SAndy Fiddaman 312*906afcb8SAndy Fiddaman #else 313*906afcb8SAndy Fiddaman #if _hdr_mach_o_dyld 314*906afcb8SAndy Fiddaman 315*906afcb8SAndy Fiddaman /* 316*906afcb8SAndy Fiddaman * mac[h] 317*906afcb8SAndy Fiddaman */ 318*906afcb8SAndy Fiddaman 319*906afcb8SAndy Fiddaman # include <mach-o/dyld.h> 320*906afcb8SAndy Fiddaman 321*906afcb8SAndy Fiddaman typedef const struct mach_header* NSImage; 322*906afcb8SAndy Fiddaman 323*906afcb8SAndy Fiddaman typedef struct Dll_s 324*906afcb8SAndy Fiddaman { 325*906afcb8SAndy Fiddaman unsigned long magic; 326*906afcb8SAndy Fiddaman NSImage image; 327*906afcb8SAndy Fiddaman NSModule module; 328*906afcb8SAndy Fiddaman char path[1]; 329*906afcb8SAndy Fiddaman } Dll_t; 330*906afcb8SAndy Fiddaman 331*906afcb8SAndy Fiddaman #define DL_MAGIC 0x04190c04 332*906afcb8SAndy Fiddaman #define DL_NEXT ((Dll_t*)RTLD_NEXT) 333*906afcb8SAndy Fiddaman 334*906afcb8SAndy Fiddaman static const char* dlmessage = "no error"; 335*906afcb8SAndy Fiddaman 336*906afcb8SAndy Fiddaman static const char e_cover[] = T("cannot access covered library"); 337*906afcb8SAndy Fiddaman static const char e_handle[] = T("invalid handle"); 338*906afcb8SAndy Fiddaman static const char e_space[] = T("out of space"); 339*906afcb8SAndy Fiddaman static const char e_static[] = T("image statically linked"); 340*906afcb8SAndy Fiddaman static const char e_undefined[] = T("undefined symbol"); 341*906afcb8SAndy Fiddaman 342*906afcb8SAndy Fiddaman static Dll_t global = { DL_MAGIC }; 343*906afcb8SAndy Fiddaman undefined(const char * name)344*906afcb8SAndy Fiddaman static void undefined(const char* name) 345*906afcb8SAndy Fiddaman { 346*906afcb8SAndy Fiddaman } 347*906afcb8SAndy Fiddaman multiple(NSSymbol sym,NSModule om,NSModule nm)348*906afcb8SAndy Fiddaman static NSModule multiple(NSSymbol sym, NSModule om, NSModule nm) 349*906afcb8SAndy Fiddaman { 350*906afcb8SAndy Fiddaman return om; 351*906afcb8SAndy Fiddaman } 352*906afcb8SAndy Fiddaman linkedit(NSLinkEditErrors c,int n,const char * f,const char * m)353*906afcb8SAndy Fiddaman static void linkedit(NSLinkEditErrors c, int n, const char* f, const char* m) 354*906afcb8SAndy Fiddaman { 355*906afcb8SAndy Fiddaman dlmessage = m; 356*906afcb8SAndy Fiddaman } 357*906afcb8SAndy Fiddaman 358*906afcb8SAndy Fiddaman static NSLinkEditErrorHandlers handlers = 359*906afcb8SAndy Fiddaman { 360*906afcb8SAndy Fiddaman undefined, multiple, linkedit 361*906afcb8SAndy Fiddaman }; 362*906afcb8SAndy Fiddaman dlopen(const char * path,int mode)363*906afcb8SAndy Fiddaman extern void* dlopen(const char* path, int mode) 364*906afcb8SAndy Fiddaman { 365*906afcb8SAndy Fiddaman Dll_t* dll; 366*906afcb8SAndy Fiddaman int i; 367*906afcb8SAndy Fiddaman NSObjectFileImage image; 368*906afcb8SAndy Fiddaman 369*906afcb8SAndy Fiddaman static int init = 0; 370*906afcb8SAndy Fiddaman 371*906afcb8SAndy Fiddaman if (!_dyld_present()) 372*906afcb8SAndy Fiddaman { 373*906afcb8SAndy Fiddaman dlmessage = e_static; 374*906afcb8SAndy Fiddaman return 0; 375*906afcb8SAndy Fiddaman } 376*906afcb8SAndy Fiddaman if (!init) 377*906afcb8SAndy Fiddaman { 378*906afcb8SAndy Fiddaman init = 1; 379*906afcb8SAndy Fiddaman NSInstallLinkEditErrorHandlers(&handlers); 380*906afcb8SAndy Fiddaman } 381*906afcb8SAndy Fiddaman if (!path) 382*906afcb8SAndy Fiddaman dll = &global; 383*906afcb8SAndy Fiddaman else if (!(dll = newof(0, Dll_t, 1, strlen(path)))) 384*906afcb8SAndy Fiddaman { 385*906afcb8SAndy Fiddaman dlmessage = e_space; 386*906afcb8SAndy Fiddaman return 0; 387*906afcb8SAndy Fiddaman } 388*906afcb8SAndy Fiddaman else 389*906afcb8SAndy Fiddaman { 390*906afcb8SAndy Fiddaman switch (NSCreateObjectFileImageFromFile(path, &image)) 391*906afcb8SAndy Fiddaman { 392*906afcb8SAndy Fiddaman case NSObjectFileImageSuccess: 393*906afcb8SAndy Fiddaman dll->module = NSLinkModule(image, path, (mode & RTLD_LAZY) ? 0 : NSLINKMODULE_OPTION_BINDNOW); 394*906afcb8SAndy Fiddaman NSDestroyObjectFileImage(image); 395*906afcb8SAndy Fiddaman if (!dll->module) 396*906afcb8SAndy Fiddaman { 397*906afcb8SAndy Fiddaman free(dll); 398*906afcb8SAndy Fiddaman return 0; 399*906afcb8SAndy Fiddaman } 400*906afcb8SAndy Fiddaman break; 401*906afcb8SAndy Fiddaman case NSObjectFileImageInappropriateFile: 402*906afcb8SAndy Fiddaman dll->image = NSAddImage(path, 0); 403*906afcb8SAndy Fiddaman if (!dll->image) 404*906afcb8SAndy Fiddaman { 405*906afcb8SAndy Fiddaman free(dll); 406*906afcb8SAndy Fiddaman return 0; 407*906afcb8SAndy Fiddaman } 408*906afcb8SAndy Fiddaman break; 409*906afcb8SAndy Fiddaman default: 410*906afcb8SAndy Fiddaman free(dll); 411*906afcb8SAndy Fiddaman return 0; 412*906afcb8SAndy Fiddaman } 413*906afcb8SAndy Fiddaman strcpy(dll->path, path); 414*906afcb8SAndy Fiddaman dll->magic = DL_MAGIC; 415*906afcb8SAndy Fiddaman } 416*906afcb8SAndy Fiddaman return (void*)dll; 417*906afcb8SAndy Fiddaman } 418*906afcb8SAndy Fiddaman dlclose(void * handle)419*906afcb8SAndy Fiddaman extern int dlclose(void* handle) 420*906afcb8SAndy Fiddaman { 421*906afcb8SAndy Fiddaman Dll_t* dll = (Dll_t*)handle; 422*906afcb8SAndy Fiddaman 423*906afcb8SAndy Fiddaman if (!dll || dll == DL_NEXT || dll->magic != DL_MAGIC) 424*906afcb8SAndy Fiddaman { 425*906afcb8SAndy Fiddaman dlmessage = e_handle; 426*906afcb8SAndy Fiddaman return -1; 427*906afcb8SAndy Fiddaman } 428*906afcb8SAndy Fiddaman if (dll->module) 429*906afcb8SAndy Fiddaman NSUnLinkModule(dll->module, 0); 430*906afcb8SAndy Fiddaman free(dll); 431*906afcb8SAndy Fiddaman return 0; 432*906afcb8SAndy Fiddaman } 433*906afcb8SAndy Fiddaman 434*906afcb8SAndy Fiddaman static NSSymbol lookup(Dll_t * dll,const char * name)435*906afcb8SAndy Fiddaman lookup(Dll_t* dll, const char* name) 436*906afcb8SAndy Fiddaman { 437*906afcb8SAndy Fiddaman unsigned long pun; 438*906afcb8SAndy Fiddaman void* address; 439*906afcb8SAndy Fiddaman 440*906afcb8SAndy Fiddaman if (dll == DL_NEXT) 441*906afcb8SAndy Fiddaman { 442*906afcb8SAndy Fiddaman if (!_dyld_func_lookup(name, &pun)) 443*906afcb8SAndy Fiddaman return 0; 444*906afcb8SAndy Fiddaman address = (NSSymbol)pun; 445*906afcb8SAndy Fiddaman } 446*906afcb8SAndy Fiddaman else if (dll->module) 447*906afcb8SAndy Fiddaman address = NSLookupSymbolInModule(dll->module, name); 448*906afcb8SAndy Fiddaman else if (dll->image) 449*906afcb8SAndy Fiddaman { 450*906afcb8SAndy Fiddaman if (!NSIsSymbolNameDefinedInImage(dll->image, name)) 451*906afcb8SAndy Fiddaman return 0; 452*906afcb8SAndy Fiddaman address = NSLookupSymbolInImage(dll->image, name, 0); 453*906afcb8SAndy Fiddaman } 454*906afcb8SAndy Fiddaman else 455*906afcb8SAndy Fiddaman { 456*906afcb8SAndy Fiddaman if (!NSIsSymbolNameDefined(name)) 457*906afcb8SAndy Fiddaman return 0; 458*906afcb8SAndy Fiddaman address = NSLookupAndBindSymbol(name); 459*906afcb8SAndy Fiddaman } 460*906afcb8SAndy Fiddaman if (address) 461*906afcb8SAndy Fiddaman address = NSAddressOfSymbol(address); 462*906afcb8SAndy Fiddaman return address; 463*906afcb8SAndy Fiddaman } 464*906afcb8SAndy Fiddaman dlsym(void * handle,const char * name)465*906afcb8SAndy Fiddaman extern void* dlsym(void* handle, const char* name) 466*906afcb8SAndy Fiddaman { 467*906afcb8SAndy Fiddaman Dll_t* dll = (Dll_t*)handle; 468*906afcb8SAndy Fiddaman NSSymbol address; 469*906afcb8SAndy Fiddaman char buf[1024]; 470*906afcb8SAndy Fiddaman 471*906afcb8SAndy Fiddaman if (!dll || dll != DL_NEXT && (dll->magic != DL_MAGIC || !dll->image && !dll->module)) 472*906afcb8SAndy Fiddaman { 473*906afcb8SAndy Fiddaman dlmessage = e_handle; 474*906afcb8SAndy Fiddaman return 0; 475*906afcb8SAndy Fiddaman } 476*906afcb8SAndy Fiddaman if (!(address = lookup(dll, name)) && name[0] != '_' && strlen(name) < (sizeof(buf) - 1)) 477*906afcb8SAndy Fiddaman { 478*906afcb8SAndy Fiddaman buf[0] = '_'; 479*906afcb8SAndy Fiddaman strcpy(buf + 1, name); 480*906afcb8SAndy Fiddaman address = lookup(dll, buf); 481*906afcb8SAndy Fiddaman } 482*906afcb8SAndy Fiddaman if (!address) 483*906afcb8SAndy Fiddaman { 484*906afcb8SAndy Fiddaman dlmessage = dll == DL_NEXT ? e_cover : e_undefined; 485*906afcb8SAndy Fiddaman return 0; 486*906afcb8SAndy Fiddaman } 487*906afcb8SAndy Fiddaman return (void*)address; 488*906afcb8SAndy Fiddaman } 489*906afcb8SAndy Fiddaman dlerror(void)490*906afcb8SAndy Fiddaman extern char* dlerror(void) 491*906afcb8SAndy Fiddaman { 492*906afcb8SAndy Fiddaman char* msg; 493*906afcb8SAndy Fiddaman 494*906afcb8SAndy Fiddaman msg = (char*)dlmessage; 495*906afcb8SAndy Fiddaman dlmessage = 0; 496*906afcb8SAndy Fiddaman return msg; 497*906afcb8SAndy Fiddaman } 498*906afcb8SAndy Fiddaman 499*906afcb8SAndy Fiddaman #else 500*906afcb8SAndy Fiddaman /* 501*906afcb8SAndy Fiddaman * punt 502*906afcb8SAndy Fiddaman */ 503*906afcb8SAndy Fiddaman 504*906afcb8SAndy Fiddaman static int err; 505*906afcb8SAndy Fiddaman dlopen(const char * path,int mode)506*906afcb8SAndy Fiddaman extern void* dlopen(const char* path, int mode) 507*906afcb8SAndy Fiddaman { 508*906afcb8SAndy Fiddaman err = 1; 509*906afcb8SAndy Fiddaman return 0; 510*906afcb8SAndy Fiddaman } 511*906afcb8SAndy Fiddaman dlclose(void * dll)512*906afcb8SAndy Fiddaman extern int dlclose(void* dll) 513*906afcb8SAndy Fiddaman { 514*906afcb8SAndy Fiddaman err = 1; 515*906afcb8SAndy Fiddaman return 0; 516*906afcb8SAndy Fiddaman } 517*906afcb8SAndy Fiddaman dlsym(void * handle,const char * name)518*906afcb8SAndy Fiddaman extern void* dlsym(void* handle, const char* name) 519*906afcb8SAndy Fiddaman { 520*906afcb8SAndy Fiddaman err = 1; 521*906afcb8SAndy Fiddaman return 0; 522*906afcb8SAndy Fiddaman } 523*906afcb8SAndy Fiddaman dlerror(void)524*906afcb8SAndy Fiddaman extern char* dlerror(void) 525*906afcb8SAndy Fiddaman { 526*906afcb8SAndy Fiddaman if (!err) 527*906afcb8SAndy Fiddaman return 0; 528*906afcb8SAndy Fiddaman err = 0; 529*906afcb8SAndy Fiddaman return "dynamic linking not supported"; 530*906afcb8SAndy Fiddaman } 531*906afcb8SAndy Fiddaman 532*906afcb8SAndy Fiddaman #endif 533*906afcb8SAndy Fiddaman #endif 534*906afcb8SAndy Fiddaman #endif 535*906afcb8SAndy Fiddaman #endif 536*906afcb8SAndy Fiddaman #endif 537