Author: jonathan
Date: Fri Jun  8 05:23:38 2007
New Revision: 18873

Modified:
   trunk/include/parrot/pmc.h
   trunk/lib/Parrot/Pmc2c.pm
   trunk/src/global_setup.c
   trunk/src/pmc.c
   trunk/src/pmc/pmcproxy.pmc
   trunk/t/pmc/pmcproxy.t

Log:
[PDD17] Make each PMC create a PMC Proxy object and put it in the list. Also 
attach each of these to the NameSpace that the PMC is attached to. This means 
you can now get_class, just as you would with PDD15 classes, for PMCs. However, 
it returns a PMC Proxy object rather than a Class. Added a test for this.

Modified: trunk/include/parrot/pmc.h
==============================================================================
--- trunk/include/parrot/pmc.h  (original)
+++ trunk/include/parrot/pmc.h  Fri Jun  8 05:23:38 2007
@@ -45,6 +45,8 @@
         __attribute__warn_unused_result__;
 
 PARROT_API INTVAL pmc_type_p( Interp* interp, PMC *name );
+
+PARROT_API void Parrot_create_pmc_proxy( Interp* interp, int type_num );
 /* HEADERIZER END: src/pmc.c */
 
 /* Internal use */
@@ -58,6 +60,19 @@
 
 /* &end_gen */
 
+/* This is the underlying structure for a PMC Proxy object; we need to set it
+ * up from outside of the PMC. */
+typedef struct Parrot_PMCProxy {
+    int id;               /* The type number of the PMC. */
+    STRING *name;         /* The name of the PMC. */
+    PMC *_namespace;      /* The namespace it's linked to, if any. */
+    PMC *parents;         /* Proxy PMCs of any immediate parent classes. */
+    PMC *all_parents;     /* Cached list of ourself and all parents, in MRO 
order. */
+} Parrot_PMCProxy;
+
+/* Macro to access underlying structure of a PMCProxy PMC. */
+#define PARROT_PMCPROXY(o) ((Parrot_PMCProxy *) PMC_data(o))
+
 #endif /* PARROT_PMC_H_GUARD */
 
 /*

Modified: trunk/lib/Parrot/Pmc2c.pm
==============================================================================
--- trunk/lib/Parrot/Pmc2c.pm   (original)
+++ trunk/lib/Parrot/Pmc2c.pm   Fri Jun  8 05:23:38 2007
@@ -1013,6 +1013,8 @@
     $cout .= <<"EOC";
         /* setup MRO and _namespace */
         Parrot_create_mro(interp, entry);
+        /* create PMC Proxy object */
+        Parrot_create_pmc_proxy(interp, entry);
 EOC
 
     # declare each nci method for this class

Modified: trunk/src/global_setup.c
==============================================================================
--- trunk/src/global_setup.c    (original)
+++ trunk/src/global_setup.c    Fri Jun  8 05:23:38 2007
@@ -114,6 +114,7 @@
 {
     PMC *iglobals;
     PMC *self, *pmc;
+    int i;
 
 #ifdef PARROT_HAS_PLATFORM_INIT_CODE
     Parrot_platform_init_code();
@@ -124,6 +125,14 @@
     /* Call base vtable class constructor methods */
     Parrot_initialize_core_pmcs(interp);
 
+    /* We have a Proxy PMC for each of the PMCs; now need to attach that to
+     * the class slot for the namespace each of the PMCs reference. */
+    for (i = 0; i <= interp->n_vtable_max; i++)
+        if (interp->vtables[i])
+            Parrot_PCCINVOKE(interp, interp->vtables[i]->_namespace,
+                string_from_const_cstring(interp, "set_class", 0), "P->",
+                VTABLE_get_pmc_keyed_int(interp, interp->pmc_proxies, i));
+
     iglobals = interp->iglobals;
     VTABLE_set_pmc_keyed_int(interp, iglobals,
             (INTVAL)IGLOBALS_CLASSNAME_HASH, interp->class_hash);

Modified: trunk/src/pmc.c
==============================================================================
--- trunk/src/pmc.c     (original)
+++ trunk/src/pmc.c     Fri Jun  8 05:23:38 2007
@@ -545,6 +545,44 @@
     VTABLE_delete_keyed(interp, interp->DOD_registry, pmc);
 }
 
+
+/*
+
+=head2 PMC Proxy related things
+
+FUNCDOC: Parrot_create_pmc_proxy
+Creates a PMC Proxy for the supplied class number and puts it into the array
+of proxies.
+
+*/
+
+PARROT_API
+void
+Parrot_create_pmc_proxy(Interp* interp, int type_num)
+{
+    PMC *proxy;
+    Parrot_PMCProxy *proxy_info;
+
+    /* Ensure that it's a valid type number. */
+    if (type_num > interp->n_vtable_max || type_num < 0)
+        internal_exception(1, 
+            "Attempt to create PMC Proxy for invalid type number!");
+
+    /* Create PMC proxy object and set up number, name and namespcae. */
+    proxy = pmc_new(interp, enum_class_PMCProxy);
+    proxy_info = PARROT_PMCPROXY(proxy);
+    proxy_info->id = type_num;
+    proxy_info->name = interp->vtables[type_num]->whoami;
+    proxy_info->_namespace = interp->vtables[type_num]->_namespace;
+
+    /* XXX Parents and MRO still todo. */
+        
+    /* Enter it in the list of proxy objects. */
+    VTABLE_set_pmc_keyed_int(interp, interp->pmc_proxies, type_num, proxy);    
+}
+
+
+
 /*
 
 =head1 SEE ALSO

Modified: trunk/src/pmc/pmcproxy.pmc
==============================================================================
--- trunk/src/pmc/pmcproxy.pmc  (original)
+++ trunk/src/pmc/pmcproxy.pmc  Fri Jun  8 05:23:38 2007
@@ -51,17 +51,6 @@
 
 #include "parrot/parrot.h"
 
-typedef struct Parrot_PMCProxy {
-    int id;               /* The type number of the PMC. */
-    STRING *name;         /* The name of the PMC. */
-    PMC *_namespace;      /* The namespace it's linked to, if any. */
-    PMC *parents;         /* Proxy PMCs of any immediate parent classes. */
-    PMC *all_parents;     /* Cached list of ourself and all parents, in MRO 
order. */
-} Parrot_PMCProxy;
-
-/* Macro to access underlying structure of a PMCProxy PMC. */
-#define PARROT_PMCPROXY(o) ((Parrot_PMCProxy *) PMC_data(o))
-
 /*
 
 =head2 Functions

Modified: trunk/t/pmc/pmcproxy.t
==============================================================================
--- trunk/t/pmc/pmcproxy.t      (original)
+++ trunk/t/pmc/pmcproxy.t      Fri Jun  8 05:23:38 2007
@@ -6,7 +6,7 @@
 use warnings;
 use lib qw( . lib ../lib ../../lib );
 use Test::More;
-use Parrot::Test tests => 1;
+use Parrot::Test tests => 2;
 
 =head1 NAME
 
@@ -38,6 +38,28 @@
 ok 2 - isa $P0, 'PMCProxy'
 OUT
 
+pir_output_is( <<'CODE', <<'OUT', 'get_class gives back Proxy PMC' );
+.sub 'test' :main
+push_eh nok_1
+    $P0 = get_class 'NameSpace'
+    clear_eh
+    goto ok_1
+nok_1:
+    print "not "
+ok_1:
+    print "ok 1 - get_class returned something\n"
+
+    $I0 = isa $P0, 'PMCProxy'
+    if $I0 goto ok_2
+    print 'not '
+  ok_2:
+    say "ok 2 - isa $P0, 'PMCProxy'"
+.end
+CODE
+ok 1 - get_class returned something
+ok 2 - isa $P0, 'PMCProxy'
+OUT
+
 # Local Variables:
 #   mode: cperl
 #   cperl-indent-level: 4

Reply via email to