Fix multi-dimensional arrays management.

[INTERPRETER]
* BUG: Fix multi-dimensional arrays management.
This commit is contained in:
gambas 2021-02-09 02:19:39 +01:00
parent 15135fe60b
commit 95572fb040
4 changed files with 14 additions and 203 deletions

View file

@ -179,6 +179,8 @@ void *CARRAY_get_data_multi(CARRAY *_object, GB_INTEGER *arg, int nparam)
//fprintf(stderr, "get_data_multi: nparam = %d\n", nparam);
nparam++;
if (THIS->n_dim)
{
int max;
@ -186,7 +188,6 @@ void *CARRAY_get_data_multi(CARRAY *_object, GB_INTEGER *arg, int nparam)
int d;
index = 0;
nparam--;
for (i = 0; i <= THIS->n_dim; i++)
{
@ -334,14 +335,12 @@ static void clear(CARRAY *_object)
}
}
static void *insert(CARRAY *_object, int index)
{
THIS->count++;
return ARRAY_insert(&THIS->data, index);
}
size_t CARRAY_get_static_size(CLASS *class, CLASS_ARRAY *desc)
{
uint64_t size = (uint64_t)get_count(desc->dim) * CLASS_sizeof_ctype(class, desc->ctype);
@ -382,7 +381,7 @@ CARRAY *CARRAY_create_static(CLASS *class, void *ref, CLASS_ARRAY *desc, void *d
else
{
array->dim = desc->dim;
array->n_dim = calc_dim(desc->dim);
array->n_dim = calc_dim(desc->dim) - 1;
}
size = CLASS_sizeof_ctype(class, desc->ctype);
@ -540,7 +539,10 @@ END_PROPERTY
BEGIN_METHOD_VOID(Array_free)
if (THIS->ref)
{
OBJECT_UNREF(THIS->ref);
return;
}
release(THIS, 0, -1);
@ -882,7 +884,6 @@ static void add(CARRAY *_object, GB_VALUE *value, int index)
return;
data = insert(THIS, index);
/*GB_Conv(value, THIS->type);*/
GB_Store(THIS->type, value, data);
}
@ -931,7 +932,7 @@ BEGIN_METHOD(Array_##_type##_put, GB_##_gtype value; GB_INTEGER index) \
\
if (check_not_read_only(THIS)) \
return; \
void *data = get_data_multi(THIS, ARG(index), GB_NParam() + 1); \
void *data = get_data_multi(THIS, ARG(index), GB_NParam()); \
if (!data) return; \
GB_Store(GB_T_##_gtype, (GB_VALUE *)(void *)ARG(value), data); \
\
@ -942,7 +943,7 @@ BEGIN_METHOD(Array_##_type##_put, GB_##_gtype value; GB_INTEGER index) \
\
if (check_not_read_only(THIS)) \
return; \
void *data = get_data_multi(THIS, ARG(index), GB_NParam() + 1); \
void *data = get_data_multi(THIS, ARG(index), GB_NParam()); \
if (!data) return; \
GB_Store(GB_T_##_gstore, (GB_VALUE *)(void *)ARG(value), data); \
\
@ -956,7 +957,7 @@ BEGIN_METHOD(Array_put, GB_VARIANT value; GB_INTEGER index)
if (check_not_read_only(THIS))
return;
data = get_data_multi(THIS, ARG(index), GB_NParam() + 1);
data = get_data_multi(THIS, ARG(index), GB_NParam());
if (!data) return;
value = (GB_VALUE *)(void *)ARG(value);
@ -1065,7 +1066,7 @@ END_METHOD
BEGIN_METHOD(Array_get, GB_INTEGER index)
void *data = get_data_multi(THIS, ARG(index), GB_NParam() + 1);
void *data = get_data_multi(THIS, ARG(index), GB_NParam());
if (data)
GB_ReturnPtr(THIS->type, data);
@ -1670,7 +1671,7 @@ END_METHOD
BEGIN_METHOD(ArrayOfStruct_get, GB_INTEGER index)
void *data = get_data_multi(THIS, ARG(index), GB_NParam() + 1);
void *data = get_data_multi(THIS, ARG(index), GB_NParam());
if (data)
GB_ReturnObject(CSTRUCT_create_static(THIS, (CLASS *)THIS->type, data));
@ -1709,7 +1710,7 @@ BEGIN_METHOD(ArrayOfStruct_put, GB_OBJECT value; GB_INTEGER index)
if (GB_CheckObject(object))
return;
data = get_data_multi(THIS, ARG(index), GB_NParam() + 1);
data = get_data_multi(THIS, ARG(index), GB_NParam());
if (!data)
return;

View file

@ -3668,7 +3668,7 @@ __PUSH_NATIVE_ARRAY:
for (i = 1; i <= np; i++)
VALUE_conv_integer(&val[i]);
data = CARRAY_get_data_multi((CARRAY *)object, (GB_INTEGER *)&val[1], np);
data = CARRAY_get_data_multi((CARRAY *)object, (GB_INTEGER *)&val[1], np - 1);
if (!data)
PROPAGATE();
@ -3867,7 +3867,7 @@ __POP_NATIVE_ARRAY:
for (i = 1; i < np; i++)
VALUE_conv_integer(&val[i]);
data = CARRAY_get_data_multi((CARRAY *)object, (GB_INTEGER *)&val[1], np - 1);
data = CARRAY_get_data_multi((CARRAY *)object, (GB_INTEGER *)&val[1], np - 2);
if (data == NULL)
PROPAGATE();

View file

@ -292,28 +292,3 @@ _FIN:
SP -= 2;
PC++;
}
#if 0
void EXEC_pop_array(ushort code)
{
CLASS *class;
OBJECT *object;
GET_NPARAM(np);
VALUE *val;
VALUE swap;
val = &SP[-np];
EXEC_object(val, &class, &object);
/* swap object and value to be inserted */
VALUE_copy(&swap, &val[0]);
VALUE_copy(&val[0], &val[-1]);
VALUE_copy(&val[-1], &swap);
if (EXEC_special(SPEC_PUT, class, object, np, TRUE))
THROW(E_NARRAY, CLASS_get_name(class));
POP(); /* free the object */
}
#endif

View file

@ -542,171 +542,6 @@ _FIN:
PC++;
}
#if 0
void EXEC_push_array(ushort code)
{
static const void *jump[] = { &&__PUSH_GENERIC, &&__PUSH_QUICK_ARRAY, &&__PUSH_QUICK_COLLECTION, &&__PUSH_ARRAY };
CLASS *class;
OBJECT *object;
GET_NPARAM(np);
//int dim[MAX_ARRAY_DIM];
int i;
void *data;
bool defined;
VALUE *val;
int fast;
//ARRAY_DESC *desc;
val = &SP[-np];
np--;
goto *jump[((unsigned char)code) >> 6];
__PUSH_GENERIC:
defined = EXEC_object(val, &class, &object);
fast = 3;
if (defined)
{
if (class->quick_array == CQA_ARRAY)
fast = 1;
else if (class->quick_array == CQA_COLLECTION)
fast = 2;
else
{
// Check the symbol existance, but *not virtually*
if (object && !VALUE_is_super(val))
{
CLASS *nvclass = val->_object.class;
if (nvclass->special[SPEC_GET] == NO_SYMBOL)
THROW(E_NARRAY, CLASS_get_name(nvclass));
}
}
}
*PC |= fast << 6;
goto __PUSH_ARRAY_2;
/*__PUSH_STATIC_ARRAY:
for (i = 1; i <= np; i++)
{
VALUE_conv_integer(&val[i];
dim[i - 1] = val[i]._integer.value;
}
SP = val;
desc = (ARRAY_DESC *)SP->_array.class->load->array[SP->_array.index];
data = ARRAY_get_address(desc, SP->_array.addr, np, dim);
VALUE_read(SP, data, CLASS_ctype_to_type(SP->_array.class, desc->type));
PUSH();
return;*/
__PUSH_QUICK_ARRAY:
// Optimization test
//EXEC_object_fast(val, &class, &object);
EXEC_object_array(val, class, object);
VALUE_conv_integer(&val[1]);
if (np == 1)
{
data = CARRAY_get_data((CARRAY *)object, val[1]._integer.value);
}
else
{
for (i = 2; i <= np; i++)
VALUE_conv_integer(&val[i]);
data = CARRAY_get_data_multi((CARRAY *)object, (GB_INTEGER *)&val[1], np);
}
if (!data)
PROPAGATE();
//VALUE_read(val, data, ((CARRAY *)object)->type);
if (TYPE_is_object(((CARRAY *)object)->type))
fast = T_OBJECT;
else
fast = ((CARRAY *)object)->type;
VALUE_read_inline_type(val, data, fast);
goto __PUSH_QUICK_END;
__PUSH_QUICK_COLLECTION:
EXEC_object_fast(val, &class, &object);
VALUE_conv_string(&val[1]);
//fprintf(stderr, "GB_CollectionGet: %p '%.*s'\n", val[1]._string.addr, val[1]._string.len, val[1]._string.addr + val[1]._string.start);
GB_CollectionGet((GB_COLLECTION)object, val[1]._string.addr + val[1]._string.start, val[1]._string.len, (GB_VARIANT *)val);
RELEASE_STRING(&val[1]);
__PUSH_QUICK_END:
SP = val;
PUSH();
OBJECT_UNREF(object);
return;
__PUSH_ARRAY:
defined = EXEC_object(val, &class, &object);
__PUSH_ARRAY_2:
if (EXEC_special(SPEC_GET, class, object, np, FALSE))
THROW(E_NARRAY, CLASS_get_name(class));
OBJECT_UNREF(object);
SP--;
//SP[-1] = SP[0];
VALUE_copy(&SP[-1], &SP[0]);
if (!defined)
VALUE_conv_variant(&SP[-1]);
}
#endif
#if 0
// JIT needs it
void EXEC_push_array(ushort code)
{
CLASS *class;
OBJECT *object;
GET_NPARAM(np);
bool defined;
VALUE *val;
val = &SP[-np];
np--;
defined = EXEC_object(val, &class, &object);
if (EXEC_special(SPEC_GET, class, object, np, FALSE))
THROW(E_NARRAY, CLASS_get_name(class));
OBJECT_UNREF(object);
SP--;
//SP[-1] = SP[0];
VALUE_copy(&SP[-1], &SP[0]);
if (!defined)
VALUE_conv_variant(&SP[-1]);
}
#endif
int EXEC_push_unknown_event(bool unknown)
{
int index;