mirror of
https://gitlab.freedesktop.org/cairo/cairo.git
synced 2025-12-25 18:50:09 +01:00
[script] Improve array construction.
Limit the memory allocation to the initial array size and perform a direct copy from the operand stack to the array.
This commit is contained in:
parent
ecb8dce27c
commit
fd96cea4fe
5 changed files with 41 additions and 36 deletions
|
|
@ -38,26 +38,30 @@
|
|||
|
||||
csi_status_t
|
||||
csi_array_new (csi_t *ctx,
|
||||
csi_integer_t initial_size,
|
||||
csi_object_t *obj)
|
||||
|
||||
{
|
||||
csi_array_t *array;
|
||||
|
||||
if (ctx->free_array != NULL) {
|
||||
array = ctx->free_array;
|
||||
ctx->free_array = NULL;
|
||||
} else {
|
||||
if (ctx->free_array == NULL ||
|
||||
ctx->free_array->stack.size <= initial_size)
|
||||
{
|
||||
csi_status_t status;
|
||||
|
||||
array = _csi_slab_alloc (ctx, sizeof (csi_array_t));
|
||||
if (_csi_unlikely (array == NULL))
|
||||
return _csi_error (CSI_STATUS_NO_MEMORY);
|
||||
|
||||
status = _csi_stack_init (ctx, &array->stack, 32);
|
||||
status = _csi_stack_init (ctx, &array->stack,
|
||||
initial_size ? initial_size : 32);
|
||||
if (_csi_unlikely (status)) {
|
||||
_csi_slab_free (ctx, array, sizeof (csi_array_t));
|
||||
return status;
|
||||
}
|
||||
} else {
|
||||
array = ctx->free_array;
|
||||
ctx->free_array = NULL;
|
||||
}
|
||||
|
||||
array->base.type = CSI_OBJECT_TYPE_ARRAY;
|
||||
|
|
@ -153,16 +157,25 @@ void
|
|||
csi_array_free (csi_t *ctx, csi_array_t *array)
|
||||
{
|
||||
if (ctx->free_array != NULL) {
|
||||
if (array->stack.size > ctx->free_array->stack.size) {
|
||||
csi_array_t *tmp = ctx->free_array;
|
||||
ctx->free_array = array;
|
||||
array = tmp;
|
||||
}
|
||||
|
||||
_csi_stack_fini (ctx, &array->stack);
|
||||
_csi_slab_free (ctx, array, sizeof (csi_array_t));
|
||||
} else {
|
||||
csi_integer_t n;
|
||||
|
||||
ctx->free_array = array;
|
||||
|
||||
for (n = 0; n < array->stack.len; n++)
|
||||
csi_object_free (ctx, &array->stack.objects[n]);
|
||||
array->stack.len = 0;
|
||||
|
||||
if (ctx->free_array == NULL)
|
||||
ctx->free_array = array;
|
||||
else
|
||||
csi_array_free (ctx, array);
|
||||
}
|
||||
}
|
||||
|
||||
|
|
|
|||
|
|
@ -567,44 +567,35 @@ static csi_status_t
|
|||
end_array_construction (csi_t *ctx)
|
||||
{
|
||||
csi_object_t obj;
|
||||
csi_array_t *array;
|
||||
csi_status_t status;
|
||||
int len = 0;
|
||||
|
||||
status = csi_array_new (ctx, &obj);
|
||||
if (_csi_unlikely (status))
|
||||
return status;
|
||||
|
||||
array = obj.datum.array;
|
||||
do {
|
||||
csi_object_t *value;
|
||||
check (len + 1);
|
||||
|
||||
check (1);
|
||||
|
||||
value = _csi_peek_ostack (ctx, 0);
|
||||
if (csi_object_get_type (value) == CSI_OBJECT_TYPE_MARK) {
|
||||
pop (1);
|
||||
if (csi_object_get_type (_csi_peek_ostack (ctx, len)) ==
|
||||
CSI_OBJECT_TYPE_MARK)
|
||||
{
|
||||
break;
|
||||
}
|
||||
|
||||
status = csi_array_append (ctx, array, value);
|
||||
if (_csi_unlikely (status))
|
||||
return status;
|
||||
|
||||
pop (1);
|
||||
len++;
|
||||
} while (TRUE);
|
||||
|
||||
/* and reverse */
|
||||
if (array->stack.len) {
|
||||
unsigned int i, j;
|
||||
status = csi_array_new (ctx, len, &obj);
|
||||
if (_csi_unlikely (status))
|
||||
return status;
|
||||
|
||||
for (i = 0, j = array->stack.len; i < --j; i++) {
|
||||
csi_object_t tmp;
|
||||
if (len != 0) {
|
||||
csi_array_t *array;
|
||||
|
||||
tmp = array->stack.objects[i];
|
||||
array->stack.objects[i] = array->stack.objects[j];
|
||||
array->stack.objects[j] = tmp;
|
||||
}
|
||||
array = obj.datum.array;
|
||||
memcpy (array->stack.objects,
|
||||
_csi_peek_ostack (ctx, len - 1),
|
||||
sizeof (csi_object_t) * len);
|
||||
array->stack.len = len;
|
||||
}
|
||||
ctx->ostack.len -= len + 1;
|
||||
|
||||
return push (&obj);
|
||||
}
|
||||
|
|
@ -824,7 +815,7 @@ _array (csi_t *ctx)
|
|||
csi_object_t obj;
|
||||
csi_status_t status;
|
||||
|
||||
status = csi_array_new (ctx, &obj);
|
||||
status = csi_array_new (ctx, 0, &obj);
|
||||
if (_csi_unlikely (status))
|
||||
return status;
|
||||
|
||||
|
|
|
|||
|
|
@ -618,6 +618,7 @@ _csi_error (csi_status_t status);
|
|||
|
||||
csi_private csi_status_t
|
||||
csi_array_new (csi_t *ctx,
|
||||
csi_integer_t initial_size,
|
||||
csi_object_t *obj);
|
||||
|
||||
csi_private csi_status_t
|
||||
|
|
|
|||
|
|
@ -350,7 +350,7 @@ token_end (csi_t *ctx, csi_scanner_t *scan, csi_file_t *src)
|
|||
&scan->procedure_stack,
|
||||
&scan->build_procedure);
|
||||
|
||||
scan->status = csi_array_new (ctx, &scan->build_procedure);
|
||||
scan->status = csi_array_new (ctx, 0, &scan->build_procedure);
|
||||
scan->build_procedure.type |= CSI_OBJECT_ATTR_EXECUTABLE;
|
||||
reset (scan);
|
||||
return;
|
||||
|
|
|
|||
|
|
@ -44,7 +44,7 @@ _csi_stack_init (csi_t *ctx, csi_stack_t *stack, csi_integer_t size)
|
|||
stack->len = 0;
|
||||
stack->size = size;
|
||||
/* assert ((unsigned) size < INT32_MAX / sizeof (csi_object_t)); */
|
||||
stack->objects = _csi_alloc (ctx, stack->size * sizeof (csi_object_t));
|
||||
stack->objects = _csi_alloc (ctx, size * sizeof (csi_object_t));
|
||||
if (_csi_unlikely (stack->objects == NULL))
|
||||
status = _csi_error (CSI_STATUS_NO_MEMORY);
|
||||
|
||||
|
|
|
|||
Loading…
Add table
Reference in a new issue