[svn:parrot] r38009 - branches/packfile_revamp/src/pmc
bacek at svn.parrot.org
bacek at svn.parrot.org
Fri Apr 10 05:30:19 UTC 2009
Author: bacek
Date: Fri Apr 10 05:30:18 2009
New Revision: 38009
URL: https://trac.parrot.org/parrot/changeset/38009
Log:
Refactor PackfileDirectory PMC to use Hash as main storage.
Modified:
branches/packfile_revamp/src/pmc/packfiledirectory.pmc
Modified: branches/packfile_revamp/src/pmc/packfiledirectory.pmc
==============================================================================
--- branches/packfile_revamp/src/pmc/packfiledirectory.pmc Fri Apr 10 05:29:56 2009 (r38008)
+++ branches/packfile_revamp/src/pmc/packfiledirectory.pmc Fri Apr 10 05:30:18 2009 (r38009)
@@ -28,87 +28,146 @@
#include "parrot/parrot.h"
pmclass PackfileDirectory extends PackfileSegment {
+ /* Directory is a hash of Segments */
+ ATTR PMC *hash;
+/*
+
+=item C<void init()>
+
+Initialize PackfileDirectory.
+
+=cut
+
+*/
+ VTABLE void init() {
+ Parrot_PackfileDirectory_attributes * attrs =
+ mem_allocate_zeroed_typed(Parrot_PackfileDirectory_attributes);
+
+ attrs->hash = pmc_new(interp, enum_class_Hash);
+
+ PObj_custom_mark_destroy_SETALL(SELF);
+ PMC_data(SELF) = attrs;
+ }
/*
-=item C<INTVAL elements()>
+=item C<void mark()>
-Get the number of elements in the array.
+Marks the object as live.
=cut
*/
- VTABLE INTVAL elements() {
- PackFile_Directory *pfd = PMC_data_typed(SELF, PackFile_Directory *);
- return pfd->num_segments;
+
+ VTABLE void mark() {
+ Parrot_PackfileDirectory_attributes * attrs =
+ PARROT_PACKFILEDIRECTORY(SELF);
+
+ if (attrs->hash)
+ pobject_lives(interp, (PObj *)attrs->hash);
+ }
+
+/*
+
+=item C<void destroy()>
+
+Destroys the PMC and frees all allocated memory.
+
+=cut
+
+*/
+
+ VTABLE void destroy() {
+ Parrot_PackfileDirectory_attributes * attrs =
+ PARROT_PACKFILEDIRECTORY(SELF);
+
+ if (attrs) {
+ mem_sys_free(attrs);
+ PMC_data(SELF) = NULL;
+ }
}
/*
-=item C<PMC *get_pmc_keyed_int(INTVAL index)>
+=item C<void set_pointer(void *ptr)>
-Fetch a segment PMC from the array.
+Initialize PackfileDirectory from PackFile_Directory.
=cut
*/
- VTABLE PMC *get_pmc_keyed_int(INTVAL index) {
- const PackFile_Directory * const pfd = PMC_data_typed(SELF, PackFile_Directory *);
+
+ VTABLE void set_pointer(void *ptr) {
+ const PackFile_Directory * const pfd = (const PackFile_Directory *)ptr;
PackFile_Segment *pfseg;
- PMC *rv;
+ PMC *segment;
int pmc_type;
+ unsigned int i;
+ STRING *name;
+ PMC *hash = PARROT_PACKFILEDIRECTORY(SELF)->hash;
+
+ SUPER(ptr);
+
+ /* Iterate over elements and create corresponded PMCs */
+ for (i=0; i < pfd->num_segments; ++i) {
+ pfseg = pfd->segments[i];
+
+ switch (pfseg->type) {
+ case PF_DIR_SEG:
+ pmc_type = enum_class_PackfileDirectory;
+ break;
+ case PF_FIXUP_SEG:
+ pmc_type = enum_class_PackfileFixupTable;
+ break;
+ case PF_CONST_SEG:
+ pmc_type = enum_class_PackfileConstantTable;
+ break;
+ case PF_BYTEC_SEG:
+ case PF_UNKNOWN_SEG:
+ case PF_DEBUG_SEG:
+ default:
+ pmc_type = enum_class_PackfileRawSegment;
+ break;
+ }
+
+ segment = pmc_new(interp, pmc_type);
+ /* Initialize internal PMC structure */
+ VTABLE_set_pointer(interp, segment, pfseg);
- if (index < 0 || index >= (INTVAL)pfd->num_segments)
- Parrot_ex_throw_from_c_args(interp, NULL, EXCEPTION_OUT_OF_BOUNDS,
- "PackfileDirectory: index out of bounds!");
-
- pfseg = pfd->segments[index];
-
- switch (pfseg->type) {
- case PF_DIR_SEG:
- pmc_type = enum_class_PackfileDirectory;
- break;
- case PF_FIXUP_SEG:
- pmc_type = enum_class_PackfileFixupTable;
- break;
- case PF_CONST_SEG:
- pmc_type = enum_class_PackfileConstantTable;
- break;
- case PF_BYTEC_SEG:
- case PF_UNKNOWN_SEG:
- case PF_DEBUG_SEG:
- default:
- pmc_type = enum_class_PackfileRawSegment;
- break;
+ name = Parrot_str_new(interp, pfseg->name, strlen(pfseg->name));
+ VTABLE_set_pmc_keyed_str(interp, hash, name, segment);
}
+ }
+
+/*
+
+=item C<INTVAL elements()>
+
+Get the number of elements in the array.
+
+=cut
- rv = pmc_new(interp, pmc_type);
- PMC_data(rv) = pfseg;
- return rv;
+*/
+ VTABLE INTVAL elements() {
+ return VTABLE_elements(interp, PARROT_PACKFILEDIRECTORY(SELF)->hash);
}
/*
-=item C<STRING *get_string_keyed_int(INTVAL index)>
+=item C<PMC *get_iter()>
-Fetch a string containing the name of the specified segment PMC.
+Return a new iterator for the directory.
=cut
*/
- VTABLE STRING *get_string_keyed_int(INTVAL index) {
- const PackFile_Directory * const pfd = PMC_data_typed(SELF, PackFile_Directory *);
- const PackFile_Segment *pfseg;
- if (index < 0 || index >= (INTVAL)pfd->num_segments)
- Parrot_ex_throw_from_c_args(interp, NULL, EXCEPTION_OUT_OF_BOUNDS,
- "PackfileDirectory: index out of bounds!");
- pfseg = pfd->segments[index];
- return Parrot_str_new_constant(interp, pfseg->name);
- }
+ VTABLE PMC *get_iter() {
+ return VTABLE_get_iter(interp, PARROT_PACKFILEDIRECTORY(SELF)->hash);
+ }
/*
@@ -120,16 +179,8 @@
*/
VTABLE PMC *get_pmc_keyed_str(STRING *name) {
- const PackFile_Directory * const pfd = PMC_data_typed(SELF, PackFile_Directory *);
- const int total = pfd->num_segments;
- int i;
- for (i = 0; i < total; i++) {
- const PackFile_Segment * const pfseg = pfd->segments[i];
- if (!Parrot_str_compare(interp, name, Parrot_str_new_constant(interp, pfseg->name)))
- return VTABLE_get_pmc_keyed_int(interp, SELF, i);
- }
- /* the specified segment name wasn't found. */
- return PMCNULL;
+ return VTABLE_get_pmc_keyed_str(interp,
+ PARROT_PACKFILEDIRECTORY(SELF)->hash, name);
}
@@ -144,8 +195,9 @@
*/
VTABLE PMC *get_pmc_keyed(PMC *key) {
- STRING * const s = VTABLE_get_string(INTERP, key);
- return SELF.get_pmc_keyed_str(s);
+ STRING *s_key = VTABLE_get_string(interp, key);
+ return VTABLE_get_pmc_keyed_str(interp,
+ PARROT_PACKFILEDIRECTORY(SELF)->hash, s_key);
}
@@ -158,29 +210,12 @@
=cut
+TODO: check type
+
*/
VTABLE void set_pmc_keyed_str(STRING *name, PMC *segment) {
- PackFile_Directory * const pfd = PMC_data_typed(SELF, PackFile_Directory *);
- PackFile_Segment *add_seg = PMC_data_typed(segment, PackFile_Segment *);
-
- const int total = pfd->num_segments;
- int i;
-
- for (i = 0; i < total; i++) {
- const PackFile_Segment * const pfseg = pfd->segments[i];
-
- if (!Parrot_str_compare(interp, name,
- Parrot_str_new_constant(interp, pfseg->name))) {
- add_seg->pf = pfd->base.pf;
- add_seg->name = pfseg->name;
- pfd->segments[i] = add_seg;
- return;
- }
- }
-
- add_seg->name = Parrot_str_to_cstring(interp, name);
- add_seg->pf = pfd->base.pf;
- PackFile_add_segment(interp, pfd, add_seg);
+ VTABLE_set_pmc_keyed_str(interp,
+ PARROT_PACKFILEDIRECTORY(SELF)->hash, name, segment);
}
VTABLE void set_pmc_keyed(PMC *key, PMC *segment) {
More information about the parrot-commits
mailing list