This is a rather clumsy patch to make prederef mode work without
needing to be compiled as a shared library. In fact, it prevents it
from being used as a shared library (but it's trivial to revert to the
former behavior; see the patch.)

Anyone who wishes is welcome to figure out exactly what's going on
with shared oplibs. I believe prederef mode contains a valiant start
at them, but at the moment the inability to compare all three
different modes of operation with a single binary is just an
annoyance. (And that 3 should really be 4; the computed goto should
just be another option IMHO.)

Index: config_h.in
===================================================================
RCS file: /home/perlcvs/parrot/config_h.in,v
retrieving revision 1.26
diff -u -r1.26 config_h.in
--- config_h.in 22 Mar 2002 18:06:46 -0000      1.26
+++ config_h.in 24 Apr 2002 03:32:37 -0000
@@ -55,6 +55,7 @@
 
 #define PARROT_CORE_OPLIB_NAME "core"
 #define PARROT_CORE_OPLIB_INIT Parrot_DynOp_core_${MAJOR}_${MINOR}_${PATCH}
+#define PARROT_CORE_PREDEREF_OPLIB_INIT 
+Parrot_DynOp_core_prederef_${MAJOR}_${MINOR}_${PATCH}
 
 #define INTVAL_FMT "${intvalfmt}"
 #define FLOATVAL_FMT "${floatvalfmt}"
Index: interpreter.c
===================================================================
RCS file: /home/perlcvs/parrot/interpreter.c,v
retrieving revision 1.84
diff -u -r1.84 interpreter.c
--- interpreter.c       15 Apr 2002 18:05:18 -0000      1.84
+++ interpreter.c       24 Apr 2002 03:32:38 -0000
@@ -104,7 +104,7 @@
 static op_func_t *prederef_op_func = NULL;
 
 static void
-init_prederef(struct Parrot_Interp *interpreter)
+init_prederef(struct Parrot_Interp *interpreter, BOOLVAL dynamic)
 {
     char file_name[50];
     char func_name[50];
@@ -122,9 +122,9 @@
      * Get a handle to the library file:
      */
 
-    prederef_oplib_handle = Parrot_dlopen(file_name);
+    if (dynamic) prederef_oplib_handle = Parrot_dlopen(file_name);
 
-    if (!prederef_oplib_handle) {
+    if (dynamic && !prederef_oplib_handle) {
         internal_exception(PREDEREF_LOAD_ERROR,
                            "Unable to dynamically load oplib file '%s' for oplib 
'%s_prederef' version %s!\n",
                            file_name, PARROT_CORE_OPLIB_NAME, PARROT_VERSION);
@@ -134,9 +134,14 @@
      * Look up the init function:
      */
 
-    prederef_oplib_init =
-        (oplib_init_f)(ptrcast_t)Parrot_dlsym(prederef_oplib_handle,
-                                              func_name);
+    if (dynamic) {
+        prederef_oplib_init =
+            (oplib_init_f)(ptrcast_t)Parrot_dlsym(prederef_oplib_handle,
+                                                  func_name);
+    } else {
+        extern op_lib_t * PARROT_CORE_PREDEREF_OPLIB_INIT(void);
+        prederef_oplib_init = PARROT_CORE_PREDEREF_OPLIB_INIT;
+    }
 
     if (!prederef_oplib_init) {
         internal_exception(PREDEREF_LOAD_ERROR,
@@ -202,13 +207,13 @@
  */
 
 static void
-stop_prederef(void)
+stop_prederef(BOOLVAL dynamic)
 {
     prederef_op_func = NULL;
     prederef_op_info = NULL;
     prederef_op_count = 0;
 
-    Parrot_dlclose(prederef_oplib_handle);
+    if (dynamic) Parrot_dlclose(prederef_oplib_handle);
 
     prederef_oplib = NULL;
     prederef_oplib_init = (oplib_init_f)NULLfunc;
@@ -371,7 +376,7 @@
 
     code_start_prederef = pc_prederef;
 
-    init_prederef(interpreter);
+    init_prederef(interpreter, 0);
 
     while (pc_prederef) {
         pc_prederef =
@@ -379,7 +384,7 @@
                                                            interpreter);
     }
 
-    stop_prederef();
+    stop_prederef(0);
 
     if (pc_prederef == 0) {
         pc = 0;
Index: docs/running.pod
===================================================================
RCS file: /home/perlcvs/parrot/docs/running.pod,v
retrieving revision 1.7
diff -u -r1.7 running.pod
--- docs/running.pod    25 Mar 2002 18:41:51 -0000      1.7
+++ docs/running.pod    24 Apr 2002 03:32:38 -0000
@@ -27,8 +27,12 @@
 That's because we use fixed address for registers, this problem will
 be solved soon.
 
-Prederef mode only works as a shared library. For example, on most
-Unix platforms:
+Prederef mode should work for all programs.
+
+It previously only worked as a shared library. To revert to that
+state, find the calls to init_prederef and stop_prederef in
+interpreter.c, and pass a true value instead of zero as the sole
+argument. Then, on most Unix platforms:
 
   make clean
   make shared

Reply via email to