@@ -189,13 +189,13 @@ void idris_doneAlloc(void) {
191int space(VM* vm, size_t size) {
191int space(VM* vm, size_t size) {
192− return (vm->heap.next + size + sizeof(size_t) < vm->heap.end);
192+ return (vm->heap.next + size) < vm->heap.end;
195void* idris_alloc(size_t size) {
195void* idris_alloc(size_t size) {
196 Closure* cl = (Closure*) allocate(sizeof(Closure)+size, 0);
196 Closure* cl = (Closure*) allocate(sizeof(Closure)+size, 0);
197 SETTY(cl, CT_RAWDATA);
197 SETTY(cl, CT_RAWDATA);
198− cl->sz = size;
198+ cl->extrasz = size;
199 return (void*)(cl+1);
199 return (void*)(cl+1);
@@ -208,8 +208,9 @@ void* idris_realloc(void* old, size_t old_size, size_t size) {
208void idris_free(void* ptr, size_t size) {
208void idris_free(void* ptr, size_t size) {
211−void* allocate(size_t size, int outerlock) {
211+void* allocate(size_t isize, int outerlock) {
212// return malloc(size);
212// return malloc(size);
213+ size_t size = aligned(isize);
214#ifdef HAS_PTHREAD
215#ifdef HAS_PTHREAD
215 VM* vm = pthread_getspecific(vm_key);
216 VM* vm = pthread_getspecific(vm_key);
@@ -222,16 +223,10 @@ void* allocate(size_t size, int outerlock) {
222 VM* vm = global_vm;
223 VM* vm = global_vm;
228− size_t chunk_size = size + sizeof(size_t);
230− if (vm->heap.next + chunk_size < vm->heap.end) {
226+ if (vm->heap.next + size < vm->heap.end) {
231− STATS_ALLOC(vm->stats, chunk_size)
227+ STATS_ALLOC(vm->stats, size)
232− void* ptr = (void*)(vm->heap.next + sizeof(size_t));
233− *((size_t*)(vm->heap.next)) = chunk_size;
228+ char* ptr = vm->heap.next;
234− vm->heap.next += chunk_size;
229+ vm->heap.next += size;
236 assert(vm->heap.next <= vm->heap.end);
231 assert(vm->heap.next <= vm->heap.end);
@@ -241,7 +236,7 @@ void* allocate(size_t size, int outerlock) {
241 pthread_mutex_unlock(&vm->alloc_lock);
236 pthread_mutex_unlock(&vm->alloc_lock);
244− return ptr;
239+ return (void*)ptr;
246 // If we're trying to allocate something bigger than the heap,
241 // If we're trying to allocate something bigger than the heap,
247 // grow the heap here so that the new heap is big enough.
242 // grow the heap here so that the new heap is big enough.
@@ -259,16 +254,12 @@ void* allocate(size_t size, int outerlock) {
262−static size_t szMax(ssize_t a, ssize_t b) {
263− return a > b? a : b;
266static Closure * allocStr(size_t len, int outer) {
257static Closure * allocStr(size_t len, int outer) {
267− size_t sz = szMax(len + 1 - 8, 0);
268− Closure * cl = allocate(sizeof(*cl) + sz, outer);
258+ Closure * cl = allocate(sizeof(Closure) + len + 1, outer);
269− SETTY(cl, CT_STRING);
259+ SETTY(cl, CT_STRING);
260+ cl->extrasz = len + 1;
270− cl->sz = len;
261+ cl->info.slen = len;
271− return cl;
262+ return cl;
274/* Now a macro
265/* Now a macro
@@ -293,8 +284,9 @@ VAL MKFLOAT(VM* vm, double val) {
294VAL MKSTRlen(VM* vm, const char * str, size_t len) {
285VAL MKSTRlen(VM* vm, const char * str, size_t len) {
295 Closure* cl = allocStr(len, 0);
286 Closure* cl = allocStr(len, 0);
296− memcpy(cl->info.str, str, len);
287+ memcpy(cl->extra.str, str, len);
297− cl->flag = str == NULL;
288+ if (str == NULL)
298 return cl;
290 return cl;
@@ -304,13 +296,13 @@ VAL MKSTR(VM* vm, const char* str) {
305char* GETSTROFF(VAL stroff) {
297char* GETSTROFF(VAL stroff) {
306 // Assume STROFF
298 // Assume STROFF
307− return stroff->info.str_offset->info.str + stroff->sz;
299+ return stroff->extra.basestr[0]->extra.str + stroff->info.soffset;
310size_t GETSTROFFLEN(VAL stroff) {
302size_t GETSTROFFLEN(VAL stroff) {
311 // Assume STROFF
303 // Assume STROFF
312 // we're working in char* here so no worries about utf8 char length
304 // we're working in char* here so no worries about utf8 char length
313− return stroff->info.str_offset->sz - stroff->sz;
305+ return stroff->extra.basestr[0]->info.slen - stroff->info.soffset;
316VAL MKCDATA(VM* vm, CHeapItem * item) {
308VAL MKCDATA(VM* vm, CHeapItem * item) {
@@ -339,8 +331,8 @@ VAL MKPTR(VM* vm, void* ptr) {
339VAL MKMPTR(VM* vm, void* ptr, size_t size) {
331VAL MKMPTR(VM* vm, void* ptr, size_t size) {
340 Closure* cl = allocate(sizeof(Closure) + size, 0);
332 Closure* cl = allocate(sizeof(Closure) + size, 0);
341 SETTY(cl, CT_MANAGEDPTR);
333 SETTY(cl, CT_MANAGEDPTR);
342− memcpy(cl->info.mptr, ptr, size);
334+ memcpy(cl->extra.mptr, ptr, size);
343− cl->sz = size;
335+ cl->extrasz = size;
344 return cl;
336 return cl;
@@ -353,7 +345,7 @@ VAL MKFLOATc(VM* vm, double val) {
354VAL MKSTRclen(VM* vm, char* str, size_t len) {
346VAL MKSTRclen(VM* vm, char* str, size_t len) {
355 Closure* cl = allocStr(len, 1);
347 Closure* cl = allocStr(len, 1);
356− memcpy(cl->info.str, str, len);
348+ memcpy(cl->extra.str, str, len);
357 return cl;
349 return cl;
@@ -371,8 +363,8 @@ VAL MKPTRc(VM* vm, void* ptr) {
371VAL MKMPTRc(VM* vm, void* ptr, size_t size) {
363VAL MKMPTRc(VM* vm, void* ptr, size_t size) {
372 Closure* cl = allocate(sizeof(Closure) + size, 1);
364 Closure* cl = allocate(sizeof(Closure) + size, 1);
373 SETTY(cl, CT_MANAGEDPTR);
365 SETTY(cl, CT_MANAGEDPTR);
374− memcpy(cl->info.mptr, ptr, size);
366+ memcpy(cl->extra.mptr, ptr, size);
375− cl->sz = size;
367+ cl->extrasz = size;
376 return cl;
368 return cl;
@@ -437,17 +429,17 @@ void dumpVal(VAL v) {
437 switch(GETTY(v)) {
429 switch(GETTY(v)) {
438 case CT_CON:
430 case CT_CON:
439 printf("%d[", (int)TAG(v));
431 printf("%d[", (int)TAG(v));
440− for(i = 0; i < ARITY(v); ++i) {
432+ for(i = 0; i < CARITY(v); ++i) {
441− dumpVal(v->info.cargs[i]);
433+ dumpVal(v->extra.cargs[i]);
443 printf("] ");
435 printf("] ");
445 case CT_STRING:
437 case CT_STRING:
446− printf("STR[%s]", v->info.str);
438+ printf("STR[%s]", v->extra.str);
448 case CT_STROFFSET:
440 case CT_STROFFSET:
449 printf("OFFSET[");
441 printf("OFFSET[");
450− dumpVal((VAL)(v->info.str_offset));
442+ dumpVal((VAL)(v->extra.basestr[0]));
451 printf("]");
443 printf("]");
453 case CT_FWD:
445 case CT_FWD:
@@ -509,7 +501,7 @@ void idris_memmove(void* dest, void* src, i_int dest_offset, i_int src_offset, i
509VAL idris_castIntStr(VM* vm, VAL i) {
501VAL idris_castIntStr(VM* vm, VAL i) {
510 int x = (int) GETINT(i);
502 int x = (int) GETINT(i);
511 Closure* cl = allocStr(16, 0);
503 Closure* cl = allocStr(16, 0);
512− cl->sz = sprintf(cl->info.str, "%d", x);
504+ cl->info.slen = sprintf(cl->extra.str, "%d", x);
513 return cl;
505 return cl;
@@ -521,22 +513,22 @@ VAL idris_castBitsStr(VM* vm, VAL i) {
521 case CT_BITS8:
513 case CT_BITS8:
522 // max length 8 bit unsigned int str 3 chars (256)
514 // max length 8 bit unsigned int str 3 chars (256)
523 cl = allocStr(4, 0);
515 cl = allocStr(4, 0);
524− cl->sz = sprintf(cl->info.str, "%" PRIu8, GETBITS8(i));
516+ cl->info.slen = sprintf(cl->extra.str, "%" PRIu8, GETBITS8(i));
526 case CT_BITS16:
518 case CT_BITS16:
527 // max length 16 bit unsigned int str 5 chars (65,535)
519 // max length 16 bit unsigned int str 5 chars (65,535)
528 cl = allocStr(6, 0);
520 cl = allocStr(6, 0);
529− cl->sz = sprintf(cl->info.str, "%" PRIu16, GETBITS16(i));
521+ cl->info.slen = sprintf(cl->extra.str, "%" PRIu16, GETBITS16(i));
531 case CT_BITS32:
523 case CT_BITS32:
532 // max length 32 bit unsigned int str 10 chars (4,294,967,295)
524 // max length 32 bit unsigned int str 10 chars (4,294,967,295)
533 cl = allocStr(11, 0);
525 cl = allocStr(11, 0);
534− cl->sz = sprintf(cl->info.str, "%" PRIu32, GETBITS32(i));
526+ cl->info.slen = sprintf(cl->extra.str, "%" PRIu32, GETBITS32(i));
536 case CT_BITS64:
528 case CT_BITS64:
537 // max length 64 bit unsigned int str 20 chars (18,446,744,073,709,551,615)
529 // max length 64 bit unsigned int str 20 chars (18,446,744,073,709,551,615)
538 cl = allocStr(21, 0);
530 cl = allocStr(21, 0);
539− cl->sz = sprintf(cl->info.str, "%" PRIu64, GETBITS64(i));
531+ cl->info.slen = sprintf(cl->extra.str, "%" PRIu64, GETBITS64(i));
542 fprintf(stderr, "Fatal Error: ClosureType %d, not an integer type", ty);
534 fprintf(stderr, "Fatal Error: ClosureType %d, not an integer type", ty);
@@ -556,7 +548,7 @@ VAL idris_castStrInt(VM* vm, VAL i) {
557VAL idris_castFloatStr(VM* vm, VAL i) {
549VAL idris_castFloatStr(VM* vm, VAL i) {
558 Closure* cl = allocStr(32, 0);
550 Closure* cl = allocStr(32, 0);
559− cl->sz = snprintf(cl->info.str, 32, "%.16g", GETFLOAT(i));
551+ cl->info.slen = snprintf(cl->extra.str, 32, "%.16g", GETFLOAT(i));
560 return cl;
552 return cl;
@@ -571,8 +563,8 @@ VAL idris_concat(VM* vm, VAL l, VAL r) {
571 size_t rlen = GETSTRLEN(r);
563 size_t rlen = GETSTRLEN(r);
573 Closure* cl = allocStr(llen + rlen, 0);
565 Closure* cl = allocStr(llen + rlen, 0);
574− memcpy(cl->info.str, ls, llen);
566+ memcpy(cl->extra.str, ls, llen);
575− memcpy(cl->info.str + llen, rs, rlen);
567+ memcpy(cl->extra.str + llen, rs, rlen);
576 return cl;
568 return cl;
@@ -634,12 +626,11 @@ VAL idris_strHead(VM* vm, VAL str) {
634 return idris_strIndex(vm, str, 0);
626 return idris_strIndex(vm, str, 0);
637−VAL MKSTROFFc(VM* vm, VAL off) {
629+VAL MKSTROFFc(VM* vm, VAL basestr) {
638− Closure* cl = allocate(sizeof(Closure), 1);
630+ Closure* cl = allocate(sizeof(Closure) + sizeof(VAL), 1);
639 SETTY(cl, CT_STROFFSET);
631 SETTY(cl, CT_STROFFSET);
640− cl->info.str_offset = off->info.str_offset;
632+ cl->extrasz = sizeof(VAL);
641− cl->sz = off->sz;
633+ cl->extra.basestr[0] = basestr;
643 return cl;
634 return cl;
@@ -647,22 +638,20 @@ VAL idris_strShift(VM* vm, VAL str, int num) {
647 // If there's no room, just copy the string, or we'll have a problem after
638 // If there's no room, just copy the string, or we'll have a problem after
648 // gc moves str
639 // gc moves str
649 if (space(vm, sizeof(Closure))) {
640 if (space(vm, sizeof(Closure))) {
650− Closure* cl = allocate(sizeof(Closure), 0);
651− SETTY(cl, CT_STROFFSET);
652− cl->info.str_offset = cl->info.str_offset;
654 int offset = 0;
641 int offset = 0;
655 VAL root = str;
642 VAL root = str;
643+ Closure* cl = allocate(sizeof(Closure) + sizeof(VAL), 0);
644+ SETTY(cl, CT_STROFFSET);
645+ cl->extrasz = sizeof(VAL);
657 while(root!=NULL && !ISSTR(root)) { // find the root, carry on.
647 while(root!=NULL && !ISSTR(root)) { // find the root, carry on.
658 // In theory, at most one step here!
648 // In theory, at most one step here!
659− offset += root->sz;
649+ offset += root->info.soffset;
660− root = root->info.str_offset;
650+ root = root->extra.basestr[0];
663− cl->info.str_offset = root;
653+ cl->extra.basestr[0] = root;
664− cl->sz = offset+idris_utf8_findOffset(GETSTR(str), num);
654+ cl->info.soffset = offset+idris_utf8_findOffset(GETSTR(str), num);
666 return cl;
655 return cl;
668 char* nstr = GETSTR(str);
657 char* nstr = GETSTR(str);
@@ -681,16 +670,16 @@ VAL idris_strCons(VM* vm, VAL x, VAL xs) {
682 if (xval < 0x80) { // ASCII char
671 if (xval < 0x80) { // ASCII char
683 Closure* cl = allocStr(xlen + 1, 0);
672 Closure* cl = allocStr(xlen + 1, 0);
684− cl->info.str[0] = (char)(GETINT(x));
673+ cl->extra.str[0] = (char)(GETINT(x));
685− memcpy(cl->info.str+1, xstr, xlen);
674+ memcpy(cl->extra.str+1, xstr, xlen);
686 return cl;
675 return cl;
688 char *init = idris_utf8_fromChar(xval);
677 char *init = idris_utf8_fromChar(xval);
689 size_t ilen = strlen(init);
678 size_t ilen = strlen(init);
690 int newlen = ilen + xlen;
679 int newlen = ilen + xlen;
691 Closure* cl = allocStr(newlen, 0);
680 Closure* cl = allocStr(newlen, 0);
692− memcpy(cl->info.str, init, ilen);
681+ memcpy(cl->extra.str, init, ilen);
693− memcpy(cl->info.str + ilen, xstr, xlen);
682+ memcpy(cl->extra.str + ilen, xstr, xlen);
694 free(init);
683 free(init);
695 return cl;
684 return cl;
@@ -715,8 +704,8 @@ VAL idris_substr(VM* vm, VAL offset, VAL length, VAL str) {
715 char *end = idris_utf8_advance(start, length_val);
704 char *end = idris_utf8_advance(start, length_val);
716 size_t sz = end - start;
705 size_t sz = end - start;
717 Closure* newstr = allocStr(sz, 0);
706 Closure* newstr = allocStr(sz, 0);
718− memcpy(newstr->info.str, start, sz);
707+ memcpy(newstr->extra.str, start, sz);
719− newstr->info.str[sz] = '\0';
708+ newstr->extra.str[sz] = '\0';
720 return newstr;
709 return newstr;
@@ -726,7 +715,7 @@ VAL idris_strRev(VM* vm, VAL str) {
726 size_t xlen = GETSTRLEN(str);
715 size_t xlen = GETSTRLEN(str);
728 Closure* cl = allocStr(xlen, 0);
717 Closure* cl = allocStr(xlen, 0);
729− idris_utf8_rev(xstr, cl->info.str);
718+ idris_utf8_rev(xstr, cl->extra.str);
730 return cl;
719 return cl;
@@ -755,17 +744,17 @@ VAL idris_newArray(VM* vm, int size, VAL def) {
756 allocArray(cl, vm, size, 0);
745 allocArray(cl, vm, size, 0);
757 for(i=0; i<size; ++i) {
746 for(i=0; i<size; ++i) {
758− cl->info.array[i] = def;
747+ cl->extra.array[i] = def;
760 return cl;
749 return cl;
763void idris_arraySet(VAL arr, int index, VAL newval) {
752void idris_arraySet(VAL arr, int index, VAL newval) {
764− arr->info.array[index] = newval;
753+ arr->extra.array[index] = newval;
767VAL idris_arrayGet(VAL arr, int index) {
756VAL idris_arrayGet(VAL arr, int index) {
768− return arr->info.array[index];
757+ return arr->extra.array[index];
771VAL idris_systemInfo(VM* vm, VAL index) {
760VAL idris_systemInfo(VM* vm, VAL index) {
@@ -846,11 +835,19 @@ void* idris_stopThread(VM* vm) {
846 return NULL;
835 return NULL;
838+static VAL doCopyTo(VM* vm, VAL x);
840+static void copyArray(VM* vm, VAL * dst, VAL * src, size_t len) {
842+ for(i = 0; i < len; ++i)
843+ dst[i] = doCopyTo(vm, src[i]);
849// VM is assumed to be a different vm from the one x lives on
847// VM is assumed to be a different vm from the one x lives on
851−VAL doCopyTo(VM* vm, VAL x) {
849+static VAL doCopyTo(VM* vm, VAL x) {
852− int i, ar, len;
850+ int ar, len;
854 Closure* cl;
851 Closure* cl;
855 if (x==NULL || ISINT(x)) {
852 if (x==NULL || ISINT(x)) {
856 return x;
853 return x;
@@ -862,41 +859,31 @@ VAL doCopyTo(VM* vm, VAL x) {
864 allocCon(cl, vm, CTAG(x), ar, 1);
861 allocCon(cl, vm, CTAG(x), ar, 1);
865−
862+ copyArray(vm, cl->extra.cargs, x->extra.cargs, ar);
866− argptr = cl->info.cargs;
867− for(i = 0; i < ar; ++i) {
868− *argptr = doCopyTo(vm, x->info.cargs[i]); // recursive version
873 case CT_ARRAY:
865 case CT_ARRAY:
874− len = x->sz;
866+ len = CELEM(x);
875 allocArray(cl, vm, len, 1);
867 allocArray(cl, vm, len, 1);
876−
868+ copyArray(vm, cl->extra.array, x->extra.array, len);
877− argptr = cl->info.array;
878− for(i = 0; i < len; ++i) {
879− *argptr = doCopyTo(vm, x->info.array[i]); // recursive version
883 case CT_FLOAT:
870 case CT_FLOAT:
884− cl = MKFLOATc(vm, x->info.f);
871+ cl = MKFLOATc(vm, GETFLOAT(x));
886 case CT_STRING:
873 case CT_STRING:
887− cl = MKSTRc(vm, x->info.str);
874+ cl = MKSTRclen(vm, x->extra.str, getstrlen(x));
889 case CT_BIGINT:
876 case CT_BIGINT:
890− cl = MKBIGMc(vm, x->info.ptr);
877+ cl = MKBIGMc(vm, GETPTR(x));
892 case CT_PTR:
879 case CT_PTR:
893− cl = MKPTRc(vm, x->info.ptr);
880+ cl = MKPTRc(vm, GETPTR(x));
895 case CT_MANAGEDPTR:
882 case CT_MANAGEDPTR:
896− cl = MKMPTRc(vm, x->info.mptr, x->sz);
883+ cl = MKMPTRc(vm, x->extra.mptr, x->extrasz);
898 case CT_CDATA:
885 case CT_CDATA:
899− cl = MKCDATAc(vm, x->info.c_heap_item);
886+ cl = MKCDATAc(vm, GETCDATA(x));
901 case CT_BITS8:
888 case CT_BITS8:
902 cl = idris_b8CopyForGC(vm, x);
889 cl = idris_b8CopyForGC(vm, x);
@@ -912,7 +899,7 @@ VAL doCopyTo(VM* vm, VAL x) {
913 case CT_RAWDATA:
900 case CT_RAWDATA:
915− size_t size = x->sz + sizeof(Closure);
902+ size_t size = sizeof(Closure) + x->extrasz;
916 cl = allocate(size, 0);
903 cl = allocate(size, 0);
917 memcpy(cl, x, size);
904 memcpy(cl, x, size);
@@ -1148,9 +1135,9 @@ void init_nullaries(void) {
1149 nullary_cons = malloc(256 * sizeof(VAL));
1136 nullary_cons = malloc(256 * sizeof(VAL));
1150 for(i = 0; i < 256; ++i) {
1137 for(i = 0; i < 256; ++i) {
1151− cl = malloc(sizeof(Closure));
1138+ cl = calloc(1, sizeof(Closure));
1152 SETTY(cl, CT_CON);
1139 SETTY(cl, CT_CON);
1153− cl->sz = i << 8;
1140+ cl->info.tag = i;
1154 nullary_cons[i] = cl;
1141 nullary_cons[i] = cl;