1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
27
28
29
30
31
32
|
/*
* tclLoadDyld.c --
*
* This procedure provides a version of the TclLoadFile that
* works with NeXT/Apple's dyld dynamic loading. This file
* provided by Wilfredo Sanchez (wsanchez@apple.com).
* The works on Mac OS X and Mac OS X Server.
* It should work with OpenStep, but it's not been tried.
*
* Copyright (c) 1995 Apple Computer, Inc.
*
* See the file "license.terms" for information on usage and redistribution
* of this file, and for a DISCLAIMER OF ALL WARRANTIES.
*
* RCS: @(#) $Id: tclLoadDyld.c,v 1.2.2.1 2001/04/06 18:42:39 hobbs Exp $
*/
#include "tclInt.h"
#include <mach-o/dyld.h>
/* For compatibility with older API. */
#ifndef NSLINKMODULE_OPTION_PRIVATE
#define NSLINKMODULE_OPTION_PRIVATE TRUE
#endif
/*
*----------------------------------------------------------------------
*
* TclpLoadFile --
*
* Dynamically loads a binary code file into memory and returns
* the addresses of two procedures within that file, if they
|
|
|
<
|
<
<
<
<
<
|
1
2
3
4
5
6
7
8
9
10
11
12
13
14
15
16
17
18
19
20
21
22
23
24
25
26
|
/*
* tclLoadDyld.c --
*
* This procedure provides a version of the TclLoadFile that
* works with Apple's dyld dynamic loading. This file
* provided by Wilfredo Sanchez (wsanchez@apple.com).
* This works on Mac OS X.
*
* Copyright (c) 1995 Apple Computer, Inc.
*
* See the file "license.terms" for information on usage and redistribution
* of this file, and for a DISCLAIMER OF ALL WARRANTIES.
*
* RCS: @(#) $Id: tclLoadDyld.c,v 1.2.2.2 2001/10/16 06:44:09 das Exp $
*/
#include "tclInt.h"
#include <mach-o/dyld.h>
/*
*----------------------------------------------------------------------
*
* TclpLoadFile --
*
* Dynamically loads a binary code file into memory and returns
* the addresses of two procedures within that file, if they
|
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
109
110
111
112
113
114
115
116
117
118
119
120
121
122
123
124
125
126
127
128
129
130
|
Tcl_PackageInitProc **proc1Ptr, **proc2Ptr;
/* Where to return the addresses corresponding
* to sym1 and sym2. */
ClientData *clientDataPtr; /* Filled with token for dynamically loaded
* file which will be passed back to
* TclpUnloadFile() to unload the file. */
{
NSObjectFileImageReturnCode err;
NSObjectFileImage image;
NSModule module;
NSSymbol symbol;
char *name;
err = NSCreateObjectFileImageFromFile(fileName, &image);
if (err != NSObjectFileImageSuccess) {
switch (err) {
case NSObjectFileImageFailure:
Tcl_SetResult(interp, "dyld: general failure", TCL_STATIC);
break;
case NSObjectFileImageInappropriateFile:
Tcl_SetResult(interp, "dyld: inappropriate Mach-O file",
TCL_STATIC);
break;
case NSObjectFileImageArch:
Tcl_SetResult(interp,
"dyld: inappropriate Mach-O architecture", TCL_STATIC);
break;
case NSObjectFileImageFormat:
Tcl_SetResult(interp, "dyld: invalid Mach-O file format",
TCL_STATIC);
break;
case NSObjectFileImageAccess:
Tcl_SetResult(interp, "dyld: permission denied", TCL_STATIC);
break;
default:
Tcl_SetResult(interp, "dyld: unknown failure", TCL_STATIC);
break;
}
return TCL_ERROR;
}
module = NSLinkModule(image, fileName, NSLINKMODULE_OPTION_PRIVATE);
if (module == NULL) {
Tcl_SetResult(interp, "dyld: falied to link module", TCL_STATIC);
return TCL_ERROR;
}
name = (char*)malloc(sizeof(char)*(strlen(sym1)+2));
sprintf(name, "_%s", sym1);
#ifdef NSLINKMODULE_OPTION_PRIVATE
symbol = NSLookupSymbolInModule(module, name);
#else
symbol = NSLookupAndBindSymbol(name);
#endif
free(name);
*proc1Ptr = NSAddressOfSymbol(symbol);
name = (char*)malloc(sizeof(char)*(strlen(sym2)+2));
sprintf(name, "_%s", sym2);
#ifdef NSLINKMODULE_OPTION_PRIVATE
symbol = NSLookupSymbolInModule(module, name);
#else
symbol = NSLookupAndBindSymbol(name);
#endif
free(name);
*proc2Ptr = NSAddressOfSymbol(symbol);
*clientDataPtr = module;
return TCL_OK;
}
/*
*----------------------------------------------------------------------
*
* TclpUnloadFile --
|
<
<
<
|
>
>
|
<
<
<
<
<
<
<
<
<
<
<
|
<
|
<
<
<
|
<
<
<
<
<
<
|
>
>
>
<
|
<
<
<
>
>
|
|
<
>
|
<
>
|
<
|
<
<
|
>
>
>
>
|
>
>
|
>
>
|
<
>
|
<
|
<
<
|
>
>
|
<
>
>
|
|
48
49
50
51
52
53
54
55
56
57
58
59
60
61
62
63
64
65
66
67
68
69
70
71
72
73
74
75
76
77
78
79
80
81
82
83
84
85
86
87
88
89
90
91
92
93
94
95
96
97
98
99
100
101
102
103
104
105
106
107
108
|
Tcl_PackageInitProc **proc1Ptr, **proc2Ptr;
/* Where to return the addresses corresponding
* to sym1 and sym2. */
ClientData *clientDataPtr; /* Filled with token for dynamically loaded
* file which will be passed back to
* TclpUnloadFile() to unload the file. */
{
NSSymbol symbol;
enum DYLD_BOOL dyld_return;
Tcl_DString newName, ds;
char *native;
native = Tcl_UtfToExternalDString(NULL, fileName, -1, &ds);
dyld_return = NSAddLibrary(native);
Tcl_DStringFree(&ds);
if (dyld_return != TRUE) {
Tcl_AppendResult(interp, "dyld: couldn't add library \"", fileName,
"\": ", Tcl_PosixError(interp), (char *) NULL);
return TCL_ERROR;
}
/*
* dyld adds an underscore to the beginning of symbol names.
*/
native = Tcl_UtfToExternalDString(NULL, sym1, -1, &ds);
Tcl_DStringInit(&newName);
Tcl_DStringAppend(&newName, "_", 1);
native = Tcl_DStringAppend(&newName, native, -1);
if(NSIsSymbolNameDefined(native)) {
symbol = NSLookupAndBindSymbol(native);
*proc1Ptr = NSAddressOfSymbol(symbol);
*clientDataPtr = NSModuleForSymbol(symbol);
} else {
*proc1Ptr=NULL;
*clientDataPtr=NULL;
}
Tcl_DStringFree(&newName);
Tcl_DStringFree(&ds);
native = Tcl_UtfToExternalDString(NULL, sym2, -1, &ds);
Tcl_DStringInit(&newName);
Tcl_DStringAppend(&newName, "_", 1);
native = Tcl_DStringAppend(&newName, native, -1);
if(NSIsSymbolNameDefined(native)) {
symbol = NSLookupAndBindSymbol(native);
*proc2Ptr = NSAddressOfSymbol(symbol);
} else {
*proc2Ptr=NULL;
}
Tcl_DStringFree(&newName);
Tcl_DStringFree(&ds);
return TCL_OK;
}
/*
*----------------------------------------------------------------------
*
* TclpUnloadFile --
|