Skip to content

Commit

Permalink
Browse files Browse the repository at this point in the history
Refactor {bind,at}_pos_ref to follow the new native access scheme.
I think we're most of the way there now. Some cleanup left to do, but the hard
work should be done.
  • Loading branch information
arnsholt committed Feb 2, 2013
1 parent 65c6ac0 commit 59a19e2
Show file tree
Hide file tree
Showing 4 changed files with 77 additions and 31 deletions.
8 changes: 4 additions & 4 deletions src/6model/repr_registry.c
Expand Up @@ -81,13 +81,13 @@ static void die_no_idx(PARROT_INTERP, STRING *repr_name) {
Parrot_ex_throw_from_c_args(interp, NULL, EXCEPTION_INVALID_OPERATION,
"%Ss representation does not support indexed storage", repr_name);
}
static void * default_at_pos_ref(PARROT_INTERP, STable *st, void *data, INTVAL index) {
static void default_at_pos_native(PARROT_INTERP, STable *st, void *data, INTVAL index, NativeValue *value) {
die_no_idx(interp, st->REPR->name);
}
static PMC * default_at_pos_boxed(PARROT_INTERP, STable *st, void *data, INTVAL index) {
die_no_idx(interp, st->REPR->name);
}
static void default_bind_pos_ref(PARROT_INTERP, STable *st, void *data, INTVAL index, void *addr) {
static void default_bind_pos_native(PARROT_INTERP, STable *st, void *data, INTVAL index, NativeValue *value) {
die_no_idx(interp, st->REPR->name);
}
static void default_bind_pos_boxed(PARROT_INTERP, STable *st, void *data, INTVAL index, PMC *obj) {
Expand Down Expand Up @@ -138,9 +138,9 @@ static void add_default_box_funcs(PARROT_INTERP, REPROps *repr) {
/* Set default indexing functions on a REPR that lacks them. */
static void add_default_idx_funcs(PARROT_INTERP, REPROps *repr) {
repr->idx_funcs = mem_allocate_typed(REPROps_Indexing);
repr->idx_funcs->at_pos_ref = default_at_pos_ref;
repr->idx_funcs->at_pos_native = default_at_pos_native;
repr->idx_funcs->at_pos_boxed = default_at_pos_boxed;
repr->idx_funcs->bind_pos_ref = default_bind_pos_ref;
repr->idx_funcs->bind_pos_native = default_bind_pos_native;
repr->idx_funcs->bind_pos_boxed = default_bind_pos_boxed;
repr->idx_funcs->elems = default_elems;
repr->idx_funcs->preallocate = default_preallocate;
Expand Down
52 changes: 43 additions & 9 deletions src/6model/reprs/CArray.c
Expand Up @@ -221,17 +221,35 @@ static void expand(PARROT_INTERP, CArrayREPRData *repr_data, CArrayBody *body, I
body->child_objs = (PMC **) mem_sys_realloc_zeroed(body->child_objs, next_size * sizeof(PMC *), body->allocated * sizeof(PMC *));
body->allocated = next_size;
}
static void * at_pos_ref(PARROT_INTERP, STable *st, void *data, INTVAL index) {
static void at_pos_native(PARROT_INTERP, STable *st, void *data, INTVAL index, NativeValue *value) {
CArrayREPRData *repr_data = (CArrayREPRData *)st->REPR_data;
CArrayBody *body = (CArrayBody *)data;
STable *type_st = STABLE(repr_data->elem_type);
void *ptr = ((char *)body->storage) + index * repr_data->elem_size;
/* XXX: What to do here now? Used to return NULL pointer, but that's not
* an option anymore. */
if (body->managed && index >= body->elems)
return NULL;
return;
switch (repr_data->elem_kind) {
case CARRAY_ELEM_KIND_NUMERIC:
return ((char *)body->storage) + index * repr_data->elem_size;
switch (value->type) {
case NATIVE_VALUE_INT:
value->value.intval = type_st->REPR->box_funcs->get_int(interp, type_st, ptr);
break;
case NATIVE_VALUE_FLOAT:
value->value.floatval = type_st->REPR->box_funcs->get_num(interp, type_st, ptr);
break;
case NATIVE_VALUE_STRING:
value->value.stringval = type_st->REPR->box_funcs->get_str(interp, type_st, ptr);
break;
default:
Parrot_ex_throw_from_c_args(interp, NULL, EXCEPTION_INVALID_OPERATION,
"Bad value of NativeValue.type: %d", value->type);
}
break;
default:
Parrot_ex_throw_from_c_args(interp, NULL, EXCEPTION_INVALID_OPERATION,
"at_pos_ref on CArray REPR only usable with numeric element types");
"at_pos_native on CArray REPR only usable with numeric element types");
}
}
static PMC * make_object(PARROT_INTERP, STable *st, void *data) {
Expand Down Expand Up @@ -326,21 +344,37 @@ static PMC * at_pos_boxed(PARROT_INTERP, STable *st, void *data, INTVAL index) {
}
}
}
static void bind_pos_ref(PARROT_INTERP, STable *st, void *data, INTVAL index, void *value) {
static void bind_pos_native(PARROT_INTERP, STable *st, void *data, INTVAL index, NativeValue *value) {
CArrayREPRData *repr_data = (CArrayREPRData *)st->REPR_data;
CArrayBody *body = (CArrayBody *)data;
STable *type_st = STABLE(repr_data->elem_type);
void *ptr = ((char *)body->storage) + index * repr_data->elem_size;
if (body->managed && index >= body->allocated)
expand(interp, repr_data, body, index + 1);
if (index >= body->elems)
body->elems = index + 1;
switch (repr_data->elem_kind) {
case CARRAY_ELEM_KIND_NUMERIC:
type_st->REPR->copy_to(interp, type_st, value, ((char *)body->storage) + index * repr_data->elem_size);
/* XXX: Dispatch to REPR here. */
/*type_st->REPR->copy_to(interp, type_st, value, ((char *)body->storage) + index * repr_data->elem_size);*/
switch (value->type) {
case NATIVE_VALUE_INT:
type_st->REPR->box_funcs->set_int(interp, type_st, ptr, value->value.intval);
break;
case NATIVE_VALUE_FLOAT:
type_st->REPR->box_funcs->set_num(interp, type_st, ptr, value->value.floatval);
break;
case NATIVE_VALUE_STRING:
type_st->REPR->box_funcs->set_str(interp, type_st, ptr, value->value.stringval);
break;
default:
Parrot_ex_throw_from_c_args(interp, NULL, EXCEPTION_INVALID_OPERATION,
"Bad value of NativeValue.type: %d", value->type);
}
break;
default:
Parrot_ex_throw_from_c_args(interp, NULL, EXCEPTION_INVALID_OPERATION,
"bind_pos_ref on CArray REPR only usable with numeric element types");
"bind_pos_native on CArray REPR only usable with numeric element types");
}
}
static void bind_pos_boxed(PARROT_INTERP, STable *st, void *data, INTVAL index, PMC *obj) {
Expand Down Expand Up @@ -465,9 +499,9 @@ REPROps * CArray_initialize(PARROT_INTERP,
this_repr->gc_mark = gc_mark;
this_repr->get_storage_spec = get_storage_spec;
this_repr->idx_funcs = mem_allocate_zeroed_typed(REPROps_Indexing);
this_repr->idx_funcs->at_pos_ref = at_pos_ref;
this_repr->idx_funcs->at_pos_native = at_pos_native;
this_repr->idx_funcs->at_pos_boxed = at_pos_boxed;
this_repr->idx_funcs->bind_pos_ref = bind_pos_ref;
this_repr->idx_funcs->bind_pos_native = bind_pos_native;
this_repr->idx_funcs->bind_pos_boxed = bind_pos_boxed;
this_repr->idx_funcs->elems = elems;
this_repr->idx_funcs->preallocate = preallocate;
Expand Down
14 changes: 6 additions & 8 deletions src/6model/sixmodelobject.h
Expand Up @@ -229,19 +229,17 @@ typedef struct SixModel_REPROps_Boxing {
void * (*get_boxed_ref) (PARROT_INTERP, STable *st, void *data, INTVAL repr_id);
} REPROps_Boxing;
typedef struct SixModel_REPROps_Indexing {
/* Get the address of the element at the specified position. May return null if
* nothing is there, or throw to indicate out of bounds, or vivify. If
* bits is a non-NULL pointer, the pointed-to INTVAL will contain the
* bit-width of the attribute. */
void * (*at_pos_ref) (PARROT_INTERP, STable *st, void *data, INTVAL index);
/* Get a flattened native value, of the type specified in value->type. It
* is the caller's responsibility to make sure the stored data is of the
* appropriate type. May throw to indicate out of bounds, or vivify. */
void (*at_pos_native) (PARROT_INTERP, STable *st, void *data, INTVAL index, NativeValue *value);

/* Get a boxed object representing the element at the specified position. If the
* object is already a reference type, simply returns that. */
PMC * (*at_pos_boxed) (PARROT_INTERP, STable *st, void *data, INTVAL index);

/* Binds the value at the specified address into the array at the specified index.
* may auto-vivify or throw. */
void (*bind_pos_ref) (PARROT_INTERP, STable *st, void *data, INTVAL index, void *addr);
/* Sets the value at the specified index of the array. May auto-vivify or throw. */
void (*bind_pos_native) (PARROT_INTERP, STable *st, void *data, INTVAL index, NativeValue *value);

/* Binds the object at the specified address into the array at the specified index.
* For arrays of non-reference types, expects a compatible type. */
Expand Down
34 changes: 24 additions & 10 deletions src/ops/nqp.ops
Expand Up @@ -1138,9 +1138,12 @@ inline op repr_at_pos_int(out INT, invar PMC, in INT) :base_core {
PMC *obj = decontainerize(interp, $2);
if (obj->vtable->base_type == smo_id) {
STable *elem_st = REPR(obj)->idx_funcs->get_elem_stable(interp, STABLE(obj));
if (IS_CONCRETE(obj))
$1 = elem_st->REPR->box_funcs->get_int(interp, elem_st,
REPR(obj)->idx_funcs->at_pos_ref(interp, STABLE(obj), OBJECT_BODY(obj), $3));
if (IS_CONCRETE(obj)) {
NativeValue value;
value.type = NATIVE_VALUE_INT;
REPR(obj)->idx_funcs->at_pos_native(interp, STABLE(obj), OBJECT_BODY(obj), $3, &value);
$1 = value.value.intval;
}
else
Parrot_ex_throw_from_c_args(interp, NULL, EXCEPTION_INVALID_OPERATION,
"Cannot do at_pos on a type object");
Expand All @@ -1164,9 +1167,12 @@ inline op repr_at_pos_num(out NUM, invar PMC, in INT) :base_core {
PMC *obj = decontainerize(interp, $2);
if (obj->vtable->base_type == smo_id) {
STable *elem_st = REPR(obj)->idx_funcs->get_elem_stable(interp, STABLE(obj));
if (IS_CONCRETE(obj))
$1 = elem_st->REPR->box_funcs->get_num(interp, elem_st,
REPR(obj)->idx_funcs->at_pos_ref(interp, STABLE(obj), OBJECT_BODY(obj), $3));
if (IS_CONCRETE(obj)) {
NativeValue value;
value.type = NATIVE_VALUE_FLOAT;
REPR(obj)->idx_funcs->at_pos_native(interp, STABLE(obj), OBJECT_BODY(obj), $3, &value);
$1 = value.value.floatval;
}
else
Parrot_ex_throw_from_c_args(interp, NULL, EXCEPTION_INVALID_OPERATION,
"Cannot do at_pos on a type object");
Expand Down Expand Up @@ -1215,8 +1221,12 @@ Sets the element at the specified position to an integer.
inline op repr_bind_pos_int(invar PMC, in INT, in INT) :base_core {
PMC *obj = decontainerize(interp, $1);
if (obj->vtable->base_type == smo_id) {
if (IS_CONCRETE(obj))
REPR(obj)->idx_funcs->bind_pos_ref(interp, STABLE(obj), OBJECT_BODY(obj), $2, &$3);
if (IS_CONCRETE(obj)) {
NativeValue value;
value.type = NATIVE_VALUE_INT;
value.value.intval = $3;
REPR(obj)->idx_funcs->bind_pos_native(interp, STABLE(obj), OBJECT_BODY(obj), $2, &value);
}
else
Parrot_ex_throw_from_c_args(interp, NULL, EXCEPTION_INVALID_OPERATION,
"Cannot do bind_pos on a type object");
Expand All @@ -1240,8 +1250,12 @@ Sets the element at the specified position to a floating point number.
inline op repr_bind_pos_num(invar PMC, in INT, in NUM) :base_core {
PMC *obj = decontainerize(interp, $1);
if (obj->vtable->base_type == smo_id) {
if (IS_CONCRETE(obj))
REPR(obj)->idx_funcs->bind_pos_ref(interp, STABLE(obj), OBJECT_BODY(obj), $2, &$3);
if (IS_CONCRETE(obj)) {
NativeValue value;
value.type = NATIVE_VALUE_FLOAT;
value.value.floatval = $3;
REPR(obj)->idx_funcs->bind_pos_native(interp, STABLE(obj), OBJECT_BODY(obj), $2, &value);
}
else
Parrot_ex_throw_from_c_args(interp, NULL, EXCEPTION_INVALID_OPERATION,
"Cannot do bind_pos on a type object");
Expand Down

0 comments on commit 59a19e2

Please sign in to comment.