Esempio n. 1
0
struct pvm_object
pvm_copy_object( struct pvm_object in_object )
{
    // TODO ERROR throw!
    if(in_object.data->_flags & PHANTOM_OBJECT_STORAGE_FLAG_IS_INTERNAL)
        panic("internal object copy?!");

    //ref_inc_o( in_object.data->_class );  //increment if class is refcounted
    struct pvm_object in_class = in_object.data->_class;
    int da_size = in_object.data->_da_size;

    struct pvm_object out = pvm_object_create_dynamic( in_class, da_size );

    int i = da_size/sizeof(struct pvm_object);
    for(; i >= 0; i-- )
    {
        if(da_po_ptr((in_object.data)->da)[i].data)
            ref_inc_o( da_po_ptr((in_object.data)->da)[i] );
    }

    memcpy( out.data->da, in_object.data->da, da_size );
    // TODO: check for special cases - copy c'tor?

    return out;
}
Esempio n. 2
0
void
pvm_set_ofield( struct pvm_object op, unsigned int slot, struct pvm_object value )
{
    verify_o(op);
    verify_o(value);
    if( PHANTOM_OBJECT_STORAGE_FLAG_IS_INTERNAL & ((op.data)->_flags) )
    {
        if( PHANTOM_OBJECT_STORAGE_FLAG_IS_RESIZEABLE & ((op.data)->_flags) )
        {
            pvm_set_array_ofield( op.data, slot, value );
            return;
        }
        pvm_exec_panic( "attempt to save to internal" );
    }

    if( PHANTOM_OBJECT_STORAGE_FLAG_IS_IMMUTABLE &  (op.data->_flags) )
        pvm_exec_panic( "attempt to set_ofield for immutable" );


    if( slot >= da_po_limit(op.data) )
    {
        pvm_exec_panic( "slot index out of bounds" );
    }

    if(da_po_ptr((op.data)->da)[slot].data) ref_dec_o(da_po_ptr((op.data)->da)[slot]);  //decr old value
    da_po_ptr((op.data)->da)[slot] = value;
}
Esempio n. 3
0
void pvm_pop_array(struct pvm_object_storage *array, struct pvm_object value_to_pop )
{
    struct data_area_4_array *da = (struct data_area_4_array *)&(array->da);

    verify_p(array);
    if(
       !(PHANTOM_OBJECT_STORAGE_FLAG_IS_INTERNAL & (array->_flags) ) ||
       !( PHANTOM_OBJECT_STORAGE_FLAG_IS_RESIZEABLE & (array->_flags) )
      )
        pvm_exec_panic( "attempt to do an array op to non-array" );

    if( PHANTOM_OBJECT_STORAGE_FLAG_IS_IMMUTABLE &  (array->_flags) )
        pvm_exec_panic( "attempt to pop_array for immutable" );

    //swap with last and decrement used_slots
    struct pvm_object *p = da_po_ptr((da->page.data)->da);
    unsigned int slot;
    for( slot = 0; slot < da->used_slots; slot++ )
    {
        if ( ( p[slot] ).data == value_to_pop.data )  //please don't leak refcnt
        {
            if (slot != da->used_slots-1) {
                p[slot] = p[da->used_slots-1];
            }
            da->used_slots--;
            return;
        }
    }

    pvm_exec_panic( "attempt to remove non existing element from array" );
}
Esempio n. 4
0
struct pvm_object     pvm_create_interface_object( int n_methods, struct pvm_object parent_class )
{
    struct pvm_object	ret = create_interface_worker( n_methods );
    struct pvm_object * data_area = (struct pvm_object *)ret.data->da;

    if(pvm_is_null( parent_class ))
        pvm_exec_panic( "create interface: parent is null" );

    struct pvm_object_storage *base_i =  ((struct data_area_4_class*)parent_class.data->da)->object_default_interface.data;

    int base_icount = da_po_limit(base_i);

    if(base_icount > n_methods)
    {
        // root classes have N_SYS_METHODS slots in interface, don't cry about that
        if( n_methods > N_SYS_METHODS )
            printf( " create interface: child has less methods (%d) than parent (%d)\n", n_methods, base_icount );
        base_icount = n_methods;
    }

    int i = 0;
    // copy methods from parent
    for( ; i < base_icount; i++ )
    {
        pvm_object_t baseMethod = (da_po_ptr(base_i->da))[i];
        ref_inc_o(baseMethod);
        data_area[i] = baseMethod;
    }

    // fill others with nulls
    for( ; i < n_methods; i++ )
        data_area[i] = pvm_get_null_object(); // null

    return ret;
}
Esempio n. 5
0
// TODO BUG XXX - races possible, read obj, then other thread writes
// to slot (derements refctr and kills object), then we attempt to
// use it (even increment refctr) -> death. Need atomic (to slot write? to refcnt dec?)
// refcnt incr here
struct pvm_object
pvm_get_ofield( struct pvm_object op, unsigned int slot )
{
    verify_o(op);
    if( PHANTOM_OBJECT_STORAGE_FLAG_IS_INTERNAL & ((op.data)->_flags) )
    {
        if( PHANTOM_OBJECT_STORAGE_FLAG_IS_RESIZEABLE & ((op.data)->_flags) )
        {
            return pvm_get_array_ofield( op.data, slot );
        }
        pvm_exec_panic( "attempt to load from internal" );
    }

    if( slot >= da_po_limit(op.data) )
    {
        pvm_exec_panic( "load: slot index out of bounds" );
    }

    verify_o(da_po_ptr((op.data)->da)[slot]);
    return da_po_ptr((op.data)->da)[slot];
}