1 /* HDL.H        (c) Copyright Jan Jaeger, 2003-2009                  */
2 /*              Hercules Dynamic Loader                              */
3 
4 #ifndef _HDL_H
5 #define _HDL_H
6 
7 #include "hercules.h"
8 
9 #if !defined(_MSVC_)
10   #define _HDL_UNUSED __attribute__ ((unused))
11 #else
12   #define _HDL_UNUSED
13 #endif
14 
15 #ifndef _HDL_C_
16 #ifndef _HUTIL_DLL_
17 #define HDL_DLL_IMPORT DLL_IMPORT
18 #else   /* _HUTIL_DLL_ */
19 #define HDL_DLL_IMPORT extern
20 #endif  /* _HUTIL_DLL_ */
21 #else
22 #define HDL_DLL_IMPORT DLL_EXPORT
23 #endif
24 
25 #ifndef _HDLMAIN_C_
26 #ifndef _HENGINE_DLL_
27 #define HDM_DLL_IMPORT DLL_IMPORT
28 #else   /* _HENGINE_DLL_ */
29 #define HDM_DLL_IMPORT extern
30 #endif  /* _HENGINE_DLL_ */
31 #else
32 #define HDM_DLL_IMPORT DLL_EXPORT
33 #endif
34 
35 /*********************************************************************/
36 
37 #define STRING_M( _string ) #_string
38 #define STRING_Q( _string ) STRING_M( _string )
39 
40 struct _HDLSHD;
41 typedef struct _HDLSHD {
42     struct _HDLSHD *next;
43     char* shdname;                      /* identifying name          */
44     void (*shdcall) (void *);           /* Entry to be called        */
45     void *shdarg;                       /* Optional argument         */
46 } HDLSHD;
47 
48 HDL_DLL_IMPORT void    hdl_adsc(char*, void *, void *);/* Add shutdown routine      */
49 HDL_DLL_IMPORT int     hdl_rmsc(void *, void *);       /* Remove shutdown routine   */
50 HDL_DLL_IMPORT void    hdl_shut(void);                 /* Call all shutdown routines*/
51 DLL_EXPORT DEVHND *hdl_ghnd(const char *devname);        /* Get device handler        */
52 
53 /*********************************************************************/
54 
55 #if !defined(OPTION_DYNAMIC_LOAD)
56 
57 #define HDL_DEVICE_SECTION                              \
58 DLL_EXPORT DEVHND *hdl_ghnd(const char *devtype)                         \
59 {
60 
61 #define HDL_DEVICE( _devname, _devhnd )                 \
62     if(!strcasecmp( STRING_Q(_devname), devtype ))      \
63         return &(_devhnd);
64 
65 #define END_DEVICE_SECTION                              \
66     return NULL;                                        \
67 }
68 
69 #else /* defined(OPTION_DYNAMIC_LOAD) */
70 
71 /*********************************************************************/
72 
73 #if !defined(HDL_USE_LIBTOOL)
74   #define dlinit()
75 #else
76   #define dlinit()                lt_dlinit()
77   #define dlopen(_name, _flags)   lt_dlopen(_name)
78   #define dlsym(_handle, _symbol) lt_dlsym(_handle, _symbol)
79   #define dlclose(_handle)        lt_dlclose(_handle)
80   #define dlerror()               lt_dlerror()
81   #define RTLD_NOW                0
82 #endif
83 
84 // extern char *(*hdl_device_type_equates)(char *);
85 
86 typedef struct _HDLDEV {                /* Device entry              */
87     char *name;                         /* Device type name          */
88     DEVHND *hnd;                        /* Device handlers           */
89     struct _HDLDEV *next;               /* Next entry                */
90 } HDLDEV;
91 
92 
93 typedef struct _HDLINS {                /* Instruction entry         */
94     int  opcode;                        /* Opcode                    */
95     int  archflags;                     /* Architecture flags        */
96     char *instname;                     /* Instruction name          */
97     void *instruction;                  /* Instruction routine       */
98     void *original;                     /* Original instruction      */
99     struct _HDLINS *next;               /* Next entry                */
100 } HDLINS;
101 
102 
103 struct _HDLDEP;
104 typedef struct _HDLDEP {                /* Dependency entry          */
105     char *name;                         /* Dependency name           */
106     char *version;                      /* Version                   */
107     int  size;                          /* Structure/module size     */
108     struct _HDLDEP *next;               /* Next entry                */
109 } HDLDEP;
110 
111 
112 typedef struct _HDLPRE {                /* Preload list entry        */
113     char *name;                         /* Module name               */
114     int  flag;                          /* Load flags                */
115 } HDLPRE;
116 
117 
118 struct _MODENT;
119 typedef struct _MODENT {                /* External Symbol entry     */
120     void (*fep)();                      /* Function entry point      */
121     char *name;                         /* Function symbol name      */
122     int  count;                         /* Symbol load count         */
123     struct _MODENT *modnext;            /* Next entry in chain       */
124 } MODENT;
125 
126 
127 struct _DLLENT;
128 typedef struct _DLLENT {                /* DLL entry                 */
129     char *name;                         /* load module name          */
130     void *dll;                          /* DLL handle (dlopen)       */
131     int flags;                          /* load flags                */
132     int (*hdldepc)(void *);             /* hdl_depc                  */
133     int (*hdlreso)(void *);             /* hdl_reso                  */
134     int (*hdlinit)(void *);             /* hdl_init                  */
135     int (*hdlddev)(void *);             /* hdl_ddev                  */
136     int (*hdldins)(void *);             /* hdl_dins                  */
137     int (*hdlfini)();                   /* hdl_fini                  */
138     struct _MODENT *modent;             /* First symbol entry        */
139     struct _HDLDEV *hndent;             /* First device entry        */
140     struct _HDLINS *insent;             /* First instruction entry   */
141     struct _DLLENT *dllnext;            /* Next entry in chain       */
142 } DLLENT;
143 
144 
145 #if defined(MODULESDIR)
146 #define HDL_DEFAULT_PATH     MODULESDIR
147 #else
148 #define HDL_DEFAULT_PATH     "hercules"
149 #endif
150 
151 /* SHLIBEXT defined by ISW in configure.ac/config.h */
152 #if defined( HDL_BUILD_SHARED ) && defined( LTDL_SHLIB_EXT )
153   #define   HDL_MODULE_SUFFIX   LTDL_SHLIB_EXT
154 #else
155   #if defined(LT_MODULE_EXT)
156     #define HDL_MODULE_SUFFIX LT_MODULE_EXT
157   #elif defined(_MSVC_)
158     #define HDL_MODULE_SUFFIX   ".dll"
159   #else
160     #define HDL_MODULE_SUFFIX   ".la"
161   #endif
162 #endif
163 
164 
165 #if defined( HDL_MODULE_SUFFIX )
166  #define HDL_SUFFIX_LENGTH (sizeof(HDL_MODULE_SUFFIX) - 1)
167 #else
168  #define HDL_SUFFIX_LENGTH 0
169 #endif
170 
171 
172 DLL_EXPORT
173 int hdl_load(char *, int);              /* load dll                  */
174 #define HDL_LOAD_DEFAULT     0x00000000
175 #define HDL_LOAD_MAIN        0x00000001 /* Hercules MAIN module flag */
176 #define HDL_LOAD_NOUNLOAD    0x00000002 /* Module cannot be unloaded */
177 #define HDL_LOAD_FORCE       0x00000004 /* Override dependency check */
178 #define HDL_LOAD_NOMSG       0x00000008 /* Do not issue not found msg*/
179 #define HDL_LOAD_WAS_FORCED  0x00000010 /* Module load was forced    */
180 
181 #define HDL_INSTARCH_370     0x00000001
182 #define HDL_INSTARCH_390     0x00000002
183 #define HDL_INSTARCH_900     0x00000004
184 #define HDL_INSTARCH_ALL     (HDL_INSTARCH_370|HDL_INSTARCH_390|HDL_INSTARCH_900)
185 
186 DLL_EXPORT
187 int hdl_dele(char *);                   /* Unload dll                */
188 DLL_EXPORT
189 void hdl_list(int);                     /* list all loaded modules   */
190 #define HDL_LIST_DEFAULT     0x00000000
191 #define HDL_LIST_ALL         0x00000001 /* list all references       */
192 DLL_EXPORT
193 void hdl_dlst();                        /* list all dependencies     */
194 
195 DLL_EXPORT
196 void hdl_main();                        /* Main initialization rtn   */
197 
198 DLL_EXPORT
199 void hdl_setpath(char *);               /* Set module path           */
200 
201 DLL_EXPORT
202 void * hdl_fent(char *);                /* Find entry name           */
203 DLL_EXPORT
204 void * hdl_nent(void *);                /* Find next in chain        */
205 
206 /* The following statement should be void *(*unresolved)(void) = NULL*/
207 static void **unresolved _HDL_UNUSED = NULL;
208 #define UNRESOLVED *unresolved
209 
210 
211 #define HDL_DEPC hdl_depc
212 #define HDL_RESO hdl_reso
213 #define HDL_INIT hdl_init
214 #define HDL_FINI hdl_fini
215 #define HDL_DDEV hdl_ddev
216 #define HDL_DINS hdl_dins
217 
218 #define HDL_HDTP hdt
219 
220 #define HDL_DEPC_Q STRING_Q(HDL_DEPC)
221 #define HDL_RESO_Q STRING_Q(HDL_RESO)
222 #define HDL_INIT_Q STRING_Q(HDL_INIT)
223 #define HDL_FINI_Q STRING_Q(HDL_FINI)
224 #define HDL_DDEV_Q STRING_Q(HDL_DDEV)
225 #define HDL_DINS_Q STRING_Q(HDL_DINS)
226 
227 #define HDL_HDTP_Q STRING_Q(HDL_HDTP)
228 
229 
230 #define HDL_FINDSYM(_name)                              \
231     hdl_fent( (_name) )
232 
233 #define HDL_FINDNXT(_ep)                                \
234     hdl_nent( &(_ep) )
235 
236 
237 #define HDL_DEPENDENCY_SECTION \
238 DLL_EXPORT int HDL_DEPC(int (*hdl_depc_vers)(char *, char *, int) _HDL_UNUSED ) \
239 { \
240 int hdl_depc_rc = 0
241 
242 #define HDL_DEPENDENCY(_comp) \
243     if (hdl_depc_vers( STRING_Q(_comp), HDL_VERS_ ## _comp, HDL_SIZE_ ## _comp)) \
244         hdl_depc_rc = 1
245 
246 #define END_DEPENDENCY_SECTION                            \
247 return hdl_depc_rc; }
248 
249 
250 #define HDL_REGISTER_SECTION                            \
251 DLL_EXPORT void HDL_INIT(int (*hdl_init_regi)(char *, void *) _HDL_UNUSED ) \
252 {
253 
254 /*       register this epname, as ep = addr of this var or func...   */
255 #define HDL_REGISTER( _epname, _varname )               \
256     (hdl_init_regi)( STRING_Q(_epname), &(_varname) )
257 
258 #define END_REGISTER_SECTION                            \
259 }
260 
261 
262 #define HDL_DEVICE_SECTION                              \
263 DLL_EXPORT void HDL_DDEV(int (*hdl_init_ddev)(char *, void *) _HDL_UNUSED ) \
264 {
265 
266 #define HDL_DEVICE( _devname, _devhnd )                 \
267     (hdl_init_ddev)( STRING_Q(_devname), &(_devhnd) )
268 
269 #define END_DEVICE_SECTION                              \
270 }
271 
272 
273 #define HDL_INSTRUCTION_SECTION                         \
274 DLL_EXPORT void HDL_DINS(int (*hdl_init_dins)(int, int, void *, void *) _HDL_UNUSED ) \
275 {
276 
277 #if defined(_370)
278  #define HDL_370_DEFINST( _arch, _opcode, _instruction)                                  \
279 do {                                                                                     \
280   if( (_arch) & HDL_INSTARCH_370 )                                                       \
281     (hdl_init_dins)( _arch, _opcode, STRING_Q(_instruction), &(s370_ ## _instruction) ); \
282 } while(0)
283 #else
284  #define HDL_370_DEFINST( _arch, _opcode, _instruction)
285 #endif
286 
287 #if defined(_390)
288  #define HDL_390_DEFINST( _arch, _opcode, _instruction)                                  \
289 do {                                                                                     \
290   if( (_arch) & HDL_INSTARCH_390 )                                                       \
291     (hdl_init_dins)( _arch, _opcode, STRING_Q(_instruction), &(s390_ ## _instruction) ); \
292 } while(0)
293 #else
294  #define HDL_390_DEFINST( _arch, _opcode, _instruction)
295 #endif
296 
297 #if defined(_900)
298  #define HDL_900_DEFINST( _arch, _opcode, _instruction)                                  \
299 do {                                                                                     \
300   if( (_arch) & HDL_INSTARCH_900 )                                                       \
301     (hdl_init_dins)( _arch, _opcode, STRING_Q(_instruction), &(z900_ ## _instruction) ); \
302 } while(0)
303 #else
304  #define HDL_900_DEFINST( _arch, _opcode, _instruction)
305 #endif
306 
307 #define HDL_DEFINST( _arch, _opcode, _instruction )                        \
308 do {                                                                       \
309     HDL_370_DEFINST(( (_arch) & HDL_INSTARCH_370), _opcode, _instruction); \
310     HDL_390_DEFINST(( (_arch) & HDL_INSTARCH_390), _opcode, _instruction); \
311     HDL_900_DEFINST(( (_arch) & HDL_INSTARCH_900), _opcode, _instruction); \
312 } while(0)
313 
314 #define END_INSTRUCTION_SECTION                              \
315 }
316 
317 #define HDL_RESOLVER_SECTION                                          \
318 DLL_EXPORT void HDL_RESO(void *(*hdl_reso_fent)(char *) _HDL_UNUSED ) \
319 {
320 
321 #define HDL_RESOLVE(_name)                              \
322     (_name) = (hdl_reso_fent)(STRING_Q(_name))
323 
324 /*                  set this ptrvar, to this ep value...             */
325 #define HDL_RESOLVE_PTRVAR( _ptrvar, _epname )          \
326     (_ptrvar) = (hdl_reso_fent)( STRING_Q(_epname) )
327 
328 #define END_RESOLVER_SECTION                            \
329 }
330 
331 
332 #define HDL_FINAL_SECTION                               \
333 DLL_EXPORT int HDL_FINI()                                          \
334 {
335 
336 #define END_FINAL_SECTION                               \
337 return 0; }
338 
339 #endif /* defined(OPTION_DYNAMIC_LOAD) */
340 
341 /*********************************************************************/
342 
343 #endif /* _HDL_H */
344