Dan Sugalski <[EMAIL PROTECTED]> wrote:
> Okay, we've a long-running discussion between Leo and I about the
> keyed  variants for all the binary vtable entries.

Another long running discussion: do we need duplicate mmd tables.
Here is a proof of concept to avoid it:

#v+
--- parrot/src/mmd.c    Thu Apr 29 07:49:31 2004
+++ parrot-leo/src/mmd.c        Thu Apr 29 15:40:58 2004
@@ -81,14 +81,21 @@
             right_type + left_type;
         real_function = 
(pmc_mmd_f)*(interpreter->binop_mmd_funcs->mmd_funcs[function] + offset);
     }
-    if (real_function) {
+    if ((UINTVAL)real_function & 1) {
+        sub = (PMC*)((UINTVAL)real_function & ~1);
+        Parrot_runops_fromc_args_save(interpreter, sub, "vPPP",
+                left, right, dest);
+    }
+    else
         (*real_function)(interpreter, left, right, dest);
+#if 0
     } else {
         /* Didn't find it. Go look for a bytecode version */
         offset = interpreter->binop_mmd_funcs->x[function] *
             right_type + left_type;
         sub = 
(void*)((pmc_mmd_f)*(interpreter->bytecode_binop_mmd_funcs->mmd_funcs[function] + 
offset));
     }
+#endif
 }

 /*
@@ -473,6 +480,16 @@

     offset = interpreter->binop_mmd_funcs->x[type] * right_type + left_type;
     *(interpreter->binop_mmd_funcs->mmd_funcs[type] + offset) = funcptr;
+}
+
+void
+mmd_register_sub(Interp *interpreter,
+             INTVAL type,
+             INTVAL left_type, INTVAL right_type,
+             PMC *sub)
+{
+    PMC *fake = (PMC*)((UINTVAL) sub | 1);
+    mmd_register(interpreter, type, left_type, right_type, D2FPTR(fake));
 }

 /*

#v-

This wouldn't really slow down MMD in C. The current if(func) isn't
really necessary as empty slots are filled with the default function ptr.

I don't think that we need a (23 * 56 * 56 * 4 + some bytes) table
duplication (this is for current types only ...).

.sub _main
.include "pmctypes.pasm"
.include "vtable_constants.pasm"

# fake mmd_vtregister / mmdfunc opcode
    .local pmc NULL
    null NULL
    .local pmc mmd_register
    mmd_register = dlfunc NULL, "mmd_register_sub", "vIiiiP"
    .local pmc divide
    divide = global "Integer_divide_PerlInt"
    .pcc_begin prototyped
    .arg .VTABLE_DIVIDE
    .arg .Integer
    .arg .PerlInt
    .arg divide
    .nci_call mmd_register
    .pcc_end
# done

    $P0 = new PerlInt
    $P1 = new Integer
    $P2 = new PerlInt
    $P1 = 10
    $P2 = 3
    $P0 = $P1 / $P2
    print $P0
    print "\n"
    end
.end

.sub Integer_divide_PerlInt
    .param pmc left
    .param pmc right
    .param pmc lhs
    $P0 = new PerlInt
    $I0 = left
    $P0 = $I0
    lhs = $P0/right   # don't call divide Integer/PerlInt here
    $N0 = lhs
    floor $N0
    lhs = $N0
.end

leo

Reply via email to