diff --git a/jsarray.c b/jsarray.c index db4917e..9e81da2 100644 --- a/jsarray.c +++ b/jsarray.c @@ -119,7 +119,7 @@ static void Ap_join(js_State *J, unsigned int argc) } if (js_try(J)) { - free(out); + js_free(J, out); js_throw(J); } @@ -133,7 +133,7 @@ static void Ap_join(js_State *J, unsigned int argc) n += strlen(r); if (k == 0) { - out = malloc(n); + out = js_malloc(J, n); strcpy(out, r); } else { n += seplen; @@ -147,7 +147,7 @@ static void Ap_join(js_State *J, unsigned int argc) js_pushstring(J, out); js_endtry(J); - free(out); + js_free(J, out); } static void Ap_pop(js_State *J, unsigned int argc) diff --git a/jsbuiltin.c b/jsbuiltin.c index 1b99b51..4c34a3b 100644 --- a/jsbuiltin.c +++ b/jsbuiltin.c @@ -103,22 +103,22 @@ static void Encode(js_State *J, const char *str, const char *unescaped) while (*str) { int c = (unsigned char) *str++; if (strchr(unescaped, c)) - sb_putc(&sb, c); + js_putc(J, &sb, c); else { - sb_putc(&sb, '%'); - sb_putc(&sb, HEX[(c >> 4) & 0xf]); - sb_putc(&sb, HEX[c & 0xf]); + js_putc(J, &sb, '%'); + js_putc(J, &sb, HEX[(c >> 4) & 0xf]); + js_putc(J, &sb, HEX[c & 0xf]); } } - sb_putc(&sb, 0); + js_putc(J, &sb, 0); if (js_try(J)) { - free(sb); + js_free(J, sb); js_throw(J); } js_pushstring(J, sb ? sb->s : ""); js_endtry(J); - free(sb); + js_free(J, sb); } static void Decode(js_State *J, const char *str, const char *reserved) @@ -129,7 +129,7 @@ static void Decode(js_State *J, const char *str, const char *reserved) while (*str) { int c = (unsigned char) *str++; if (c != '%') - sb_putc(&sb, c); + js_putc(J, &sb, c); else { if (!str[0] || !str[1]) js_urierror(J, "truncated escape sequence"); @@ -139,23 +139,23 @@ static void Decode(js_State *J, const char *str, const char *reserved) js_urierror(J, "invalid escape sequence"); c = jsY_tohex(a) << 4 | jsY_tohex(b); if (!strchr(reserved, c)) - sb_putc(&sb, c); + js_putc(J, &sb, c); else { - sb_putc(&sb, '%'); - sb_putc(&sb, a); - sb_putc(&sb, b); + js_putc(J, &sb, '%'); + js_putc(J, &sb, a); + js_putc(J, &sb, b); } } } - sb_putc(&sb, 0); + js_putc(J, &sb, 0); if (js_try(J)) { - free(sb); + js_free(J, sb); js_throw(J); } js_pushstring(J, sb ? sb->s : ""); js_endtry(J); - free(sb); + js_free(J, sb); } #define URIRESERVED ";/?:@&=+$," diff --git a/jsbuiltin.h b/jsbuiltin.h index c5854b7..7b71d28 100644 --- a/jsbuiltin.h +++ b/jsbuiltin.h @@ -20,31 +20,31 @@ void jsB_props(js_State *J, const char *name, const char *string); typedef struct js_Buffer { unsigned int n, m; char s[64]; } js_Buffer; -static void sb_putc(js_Buffer **sbp, int c) +static void js_putc(js_State *J, js_Buffer **sbp, int c) { js_Buffer *sb = *sbp; if (!sb) { - sb = malloc(sizeof *sb); + sb = js_malloc(J, sizeof *sb); sb->n = 0; sb->m = sizeof sb->s; *sbp = sb; } else if (sb->n == sb->m) { - sb = realloc(sb, (sb->m *= 2) + offsetof(js_Buffer, s)); + sb = js_realloc(J, sb, (sb->m *= 2) + offsetof(js_Buffer, s)); *sbp = sb; } sb->s[sb->n++] = c; } -static inline void sb_puts(js_Buffer **sb, const char *s) +static inline void js_puts(js_State *J, js_Buffer **sb, const char *s) { while (*s) - sb_putc(sb, *s++); + js_putc(J, sb, *s++); } -static inline void sb_putm(js_Buffer **sb, const char *s, const char *e) +static inline void js_putm(js_State *J, js_Buffer **sb, const char *s, const char *e) { while (s < e) - sb_putc(sb, *s++); + js_putc(J, sb, *s++); } #endif diff --git a/jscompile.c b/jscompile.c index 76cff64..389a8e9 100644 --- a/jscompile.c +++ b/jscompile.c @@ -32,7 +32,7 @@ void jsC_error(js_State *J, js_Ast *node, const char *fmt, ...) static js_Function *newfun(js_State *J, js_Ast *name, js_Ast *params, js_Ast *body, int script) { - js_Function *F = malloc(sizeof *F); + js_Function *F = js_malloc(J, sizeof *F); memset(F, 0, sizeof *F); F->gcmark = 0; F->gcnext = J->gcfun; @@ -619,7 +619,7 @@ static void cexp(JF, js_Ast *exp) static void addjump(JF, enum js_AstType type, js_Ast *target, int inst) { - js_JumpList *jump = malloc(sizeof *jump); + js_JumpList *jump = js_malloc(J, sizeof *jump); jump->type = type; jump->inst = inst; jump->next = target->jumps; diff --git a/jsfunction.c b/jsfunction.c index d2f9fcc..06770dd 100644 --- a/jsfunction.c +++ b/jsfunction.c @@ -19,15 +19,15 @@ static void jsB_Function(js_State *J, unsigned int argc) sb = NULL; if (argc > 1) { for (i = 1; i < argc; ++i) { - if (i > 1) sb_putc(&sb, ','); - sb_puts(&sb, js_tostring(J, i)); + if (i > 1) js_putc(J, &sb, ','); + js_puts(J, &sb, js_tostring(J, i)); } - sb_putc(&sb, ')'); + js_putc(J, &sb, ')'); } } if (js_try(J)) { - free(sb); + js_free(J, sb); jsP_freeparse(J); js_throw(J); } @@ -36,7 +36,7 @@ static void jsB_Function(js_State *J, unsigned int argc) fun = jsC_compilefunction(J, parse); js_endtry(J); - free(sb); + js_free(J, sb); jsP_freeparse(J); js_newfunction(J, fun, J->GE); @@ -62,7 +62,7 @@ static void Fp_toString(js_State *J, unsigned int argc) n += strlen(F->name); for (i = 0; i < F->numparams; ++i) n += strlen(F->vartab[i]) + 1; - s = malloc(n); + s = js_malloc(J, n); strcpy(s, "function "); strcat(s, F->name); strcat(s, "("); @@ -71,8 +71,12 @@ static void Fp_toString(js_State *J, unsigned int argc) strcat(s, F->vartab[i]); } strcat(s, ") { ... }"); + if (js_try(J)) { + js_free(J, s); + js_throw(J); + } js_pushstring(J, s); - free(s); + js_free(J, s); } else { js_pushliteral(J, "function () { ... }"); } diff --git a/jsgc.c b/jsgc.c index c4dae4c..08d8766 100644 --- a/jsgc.c +++ b/jsgc.c @@ -9,24 +9,24 @@ static void jsG_markobject(js_State *J, int mark, js_Object *obj); static void jsG_freeenvironment(js_State *J, js_Environment *env) { - free(env); + js_free(J, env); } static void jsG_freefunction(js_State *J, js_Function *fun) { - free(fun->funtab); - free(fun->numtab); - free(fun->strtab); - free(fun->vartab); - free(fun->code); - free(fun); + js_free(J, fun->funtab); + js_free(J, fun->numtab); + js_free(J, fun->strtab); + js_free(J, fun->vartab); + js_free(J, fun->code); + js_free(J, fun); } static void jsG_freeproperty(js_State *J, js_Property *node) { while (node) { js_Property *next = node->next; - free(node); + js_free(J, node); node = next; } } @@ -35,7 +35,7 @@ static void jsG_freeiterator(js_State *J, js_Iterator *node) { while (node) { js_Iterator *next = node->next; - free(node); + js_free(J, node); node = next; } } @@ -48,7 +48,7 @@ static void jsG_freeobject(js_State *J, js_Object *obj) js_regfree(obj->u.r.prog); if (obj->type == JS_CITERATOR) jsG_freeiterator(J, obj->u.iter.head); - free(obj); + js_free(J, obj); } static void jsG_markfunction(js_State *J, int mark, js_Function *fun) @@ -203,7 +203,7 @@ void js_freestate(js_State *J) jsS_freestrings(J); - free(J->lexbuf.text); + js_free(J, J->lexbuf.text); free(J->stack); free(J); } diff --git a/jsi.h b/jsi.h index 9f69396..3d525fd 100644 --- a/jsi.h +++ b/jsi.h @@ -29,6 +29,10 @@ #define nelem(a) (sizeof (a) / sizeof (a)[0]) +void *js_malloc(js_State *J, size_t size); +void *js_realloc(js_State *J, void *ptr, size_t size); +void js_free(js_State *J, void *ptr); + typedef struct js_Regexp js_Regexp; typedef struct js_Value js_Value; typedef struct js_Object js_Object; diff --git a/jsintern.c b/jsintern.c index 590cc50..426a493 100644 --- a/jsintern.c +++ b/jsintern.c @@ -11,10 +11,10 @@ struct js_StringNode static js_StringNode jsS_sentinel = { &jsS_sentinel, &jsS_sentinel, 0, ""}; -static js_StringNode *jsS_newstringnode(const char *string, const char **result) +static js_StringNode *jsS_newstringnode(js_State *J, const char *string, const char **result) { int n = strlen(string); - js_StringNode *node = malloc(offsetof(js_StringNode, string) + n + 1); + js_StringNode *node = js_malloc(J, offsetof(js_StringNode, string) + n + 1); node->left = node->right = &jsS_sentinel; node->level = 1; strcpy(node->string, string); @@ -44,21 +44,21 @@ static js_StringNode *jsS_split(js_StringNode *node) return node; } -static js_StringNode *jsS_insert(js_StringNode *node, const char *string, const char **result) +static js_StringNode *jsS_insert(js_State *J, js_StringNode *node, const char *string, const char **result) { if (node != &jsS_sentinel) { int c = strcmp(string, node->string); if (c < 0) - node->left = jsS_insert(node->left, string, result); + node->left = jsS_insert(J, node->left, string, result); else if (c > 0) - node->right = jsS_insert(node->right, string, result); + node->right = jsS_insert(J, node->right, string, result); else return *result = node->string, node; node = jsS_skew(node); node = jsS_split(node); return node; } - return jsS_newstringnode(string, result); + return jsS_newstringnode(J, string, result); } static void dumpstringnode(js_StringNode *node, int level) @@ -87,7 +87,7 @@ static void jsS_freestringnode(js_State *J, js_StringNode *node) { if (node->left != &jsS_sentinel) jsS_freestringnode(J, node->left); if (node->right != &jsS_sentinel) jsS_freestringnode(J, node->right); - free(node); + js_free(J, node); } void jsS_freestrings(js_State *J) @@ -101,6 +101,6 @@ const char *js_intern(js_State *J, const char *s) const char *result; if (!J->strings) J->strings = &jsS_sentinel; - J->strings = jsS_insert(J->strings, s, &result); + J->strings = jsS_insert(J, J->strings, s, &result); return result; } diff --git a/jslex.c b/jslex.c index 79378be..693cd82 100644 --- a/jslex.c +++ b/jslex.c @@ -185,7 +185,7 @@ static void textinit(js_State *J) { if (!J->lexbuf.text) { J->lexbuf.cap = 4096; - J->lexbuf.text = malloc(J->lexbuf.cap); + J->lexbuf.text = js_malloc(J, J->lexbuf.cap); } J->lexbuf.len = 0; } @@ -195,7 +195,7 @@ static void textpush(js_State *J, Rune c) int n = runelen(c); if (J->lexbuf.len + n > J->lexbuf.cap) { J->lexbuf.cap = J->lexbuf.cap * 2; - J->lexbuf.text = realloc(J->lexbuf.text, J->lexbuf.cap); + J->lexbuf.text = js_realloc(J, J->lexbuf.text, J->lexbuf.cap); } J->lexbuf.len += runetochar(J->lexbuf.text + J->lexbuf.len, &c); } diff --git a/json.c b/json.c index ef565d3..1408f23 100644 --- a/json.c +++ b/json.c @@ -101,46 +101,46 @@ static void JSON_parse(js_State *J, unsigned int argc) // TODO: reviver Walk() } -static void fmtnum(js_Buffer **sb, double n) +static void fmtnum(js_State *J, js_Buffer **sb, double n) { - if (isnan(n)) sb_puts(sb, "NaN"); - else if (isinf(n)) sb_puts(sb, n < 0 ? "-Infinity" : "Infinity"); - else if (n == 0) sb_puts(sb, "0"); + if (isnan(n)) js_puts(J, sb, "NaN"); + else if (isinf(n)) js_puts(J, sb, n < 0 ? "-Infinity" : "Infinity"); + else if (n == 0) js_puts(J, sb, "0"); else { char buf[40]; sprintf(buf, "%.17g", n); - sb_puts(sb, buf); + js_puts(J, sb, buf); } } -static void fmtstr(js_Buffer **sb, const char *s) +static void fmtstr(js_State *J, js_Buffer **sb, const char *s) { static const char *HEX = "0123456789ABCDEF"; Rune c; - sb_putc(sb, '"'); + js_putc(J, sb, '"'); while (*s) { s += chartorune(&c, s); switch (c) { - case '"': sb_puts(sb, "\\\""); break; - case '\\': sb_puts(sb, "\\\\"); break; - case '\b': sb_puts(sb, "\\b"); break; - case '\f': sb_puts(sb, "\\f"); break; - case '\n': sb_puts(sb, "\\n"); break; - case '\r': sb_puts(sb, "\\r"); break; - case '\t': sb_puts(sb, "\\t"); break; + case '"': js_puts(J, sb, "\\\""); break; + case '\\': js_puts(J, sb, "\\\\"); break; + case '\b': js_puts(J, sb, "\\b"); break; + case '\f': js_puts(J, sb, "\\f"); break; + case '\n': js_puts(J, sb, "\\n"); break; + case '\r': js_puts(J, sb, "\\r"); break; + case '\t': js_puts(J, sb, "\\t"); break; default: if (c < ' ') { - sb_puts(sb, "\\u"); - sb_putc(sb, HEX[(c>>12)&15]); - sb_putc(sb, HEX[(c>>8)&15]); - sb_putc(sb, HEX[(c>>4)&15]); - sb_putc(sb, HEX[c&15]); + js_puts(J, sb, "\\u"); + js_putc(J, sb, HEX[(c>>12)&15]); + js_putc(J, sb, HEX[(c>>8)&15]); + js_putc(J, sb, HEX[(c>>4)&15]); + js_putc(J, sb, HEX[c&15]); } else { - sb_putc(sb, c); break; + js_putc(J, sb, c); break; } } } - sb_putc(sb, '"'); + js_putc(J, sb, '"'); } static int fmtvalue(js_State *J, js_Buffer **sb, const char *key); @@ -151,14 +151,14 @@ static void fmtobject(js_State *J, js_Buffer **sb, js_Object *obj) int save; int n = 0; - sb_putc(sb, '{'); + js_putc(J, sb, '{'); for (ref = obj->head; ref; ref = ref->next) { if (ref->atts & JS_DONTENUM) continue; save = (*sb)->n; - if (n) sb_putc(sb, ','); - fmtstr(sb, ref->name); - sb_putc(sb, ':'); + if (n) js_putc(J, sb, ','); + fmtstr(J, sb, ref->name); + js_putc(J, sb, ':'); js_pushvalue(J, ref->value); if (!fmtvalue(J, sb, ref->name)) (*sb)->n = save; @@ -166,7 +166,7 @@ static void fmtobject(js_State *J, js_Buffer **sb, js_Object *obj) ++n; js_pop(J, 1); } - sb_putc(sb, '}'); + js_putc(J, sb, '}'); } static void fmtarray(js_State *J, js_Buffer **sb) @@ -178,22 +178,22 @@ static void fmtarray(js_State *J, js_Buffer **sb) len = js_touint32(J, -1); js_pop(J, 1); - sb_putc(sb, '['); + js_putc(J, sb, '['); for (k = 0; k < len; ++k) { - if (k) sb_putc(sb, ','); + if (k) js_putc(J, sb, ','); sprintf(buf, "%u", k); js_getproperty(J, -1, buf); if (!fmtvalue(J, sb, buf)) - sb_puts(sb, "null"); + js_puts(J, sb, "null"); js_pop(J, 1); } - sb_putc(sb, ']'); + js_putc(J, sb, ']'); } static int fmtvalue(js_State *J, js_Buffer **sb, const char *key) { if (js_try(J)) { - free(*sb); + js_free(J, *sb); js_throw(J); } if (js_isobject(J, -1)) { @@ -215,21 +215,21 @@ static int fmtvalue(js_State *J, js_Buffer **sb, const char *key) if (js_isobject(J, -1) && !js_iscallable(J, -1)) { js_Object *obj = js_toobject(J, -1); switch (obj->type) { - case JS_CNUMBER: fmtnum(sb, obj->u.number); break; - case JS_CSTRING: fmtstr(sb, obj->u.s.string); break; - case JS_CBOOLEAN: sb_puts(sb, obj->u.boolean ? "true" : "false"); break; + case JS_CNUMBER: fmtnum(J, sb, obj->u.number); break; + case JS_CSTRING: fmtstr(J, sb, obj->u.s.string); break; + case JS_CBOOLEAN: js_puts(J, sb, obj->u.boolean ? "true" : "false"); break; case JS_CARRAY: fmtarray(J, sb); break; default: fmtobject(J, sb, obj); break; } } else if (js_isboolean(J, -1)) - sb_puts(sb, js_toboolean(J, -1) ? "true" : "false"); + js_puts(J, sb, js_toboolean(J, -1) ? "true" : "false"); else if (js_isnumber(J, -1)) - fmtnum(sb, js_tonumber(J, -1)); + fmtnum(J, sb, js_tonumber(J, -1)); else if (js_isstring(J, -1)) - fmtstr(sb, js_tostring(J, -1)); + fmtstr(J, sb, js_tostring(J, -1)); else if (js_isnull(J, -1)) - sb_puts(sb, "null"); + js_puts(J, sb, "null"); else return 0; @@ -242,14 +242,14 @@ static void JSON_stringify(js_State *J, unsigned int argc) if (argc > 0) { js_copy(J, 1); if (fmtvalue(J, &sb, "")) { - sb_putc(&sb, 0); + js_putc(J, &sb, 0); if (js_try(J)) { - free(sb); + js_free(J, sb); js_throw(J); } js_pushstring(J, sb ? sb->s : ""); js_endtry(J); - free(sb); + js_free(J, sb); } } else { js_pushundefined(J); diff --git a/jsparse.c b/jsparse.c index 541d55c..4006219 100644 --- a/jsparse.c +++ b/jsparse.c @@ -54,7 +54,7 @@ static void jsP_warning(js_State *J, const char *fmt, ...) static js_Ast *jsP_newnode(js_State *J, int type, js_Ast *a, js_Ast *b, js_Ast *c, js_Ast *d) { - js_Ast *node = malloc(sizeof(js_Ast)); + js_Ast *node = js_malloc(J, sizeof *node); node->type = type; node->line = J->lexline; @@ -109,7 +109,7 @@ static void jsP_freejumps(js_State *J, js_JumpList *node) { while (node) { js_JumpList *next = node->next; - free(node); + js_free(J, node); node = next; } } @@ -120,7 +120,7 @@ void jsP_freeparse(js_State *J) while (node) { js_Ast *next = node->gcnext; jsP_freejumps(J, node->jumps); - free(node); + js_free(J, node); node = next; } J->gcast = NULL; diff --git a/jsproperty.c b/jsproperty.c index 26b2cac..c031646 100644 --- a/jsproperty.c +++ b/jsproperty.c @@ -29,7 +29,7 @@ static js_Property sentinel = { static js_Property *newproperty(js_State *J, const char *name) { - js_Property *node = malloc(sizeof(js_Property)); + js_Property *node = js_malloc(J, sizeof *node); node->name = js_intern(J, name); node->left = node->right = &sentinel; node->prevp = NULL; @@ -97,12 +97,12 @@ static js_Property *insert(js_State *J, js_Property *node, const char *name, js_ return *result = newproperty(J, name); } -static void freenode(js_State *J, js_Property *node) +static void freeproperty(js_State *J, js_Property *node) { if (node->next) node->next->prevp = node->prevp; *node->prevp = node->next; - free(node); + js_free(J, node); } static js_Property *delete(js_State *J, js_Property *node, const char *name) @@ -119,11 +119,11 @@ static js_Property *delete(js_State *J, js_Property *node, const char *name) if (node->left == &sentinel) { temp = node; node = node->right; - freenode(J, temp); + freeproperty(J, temp); } else if (node->right == &sentinel) { temp = node; node = node->left; - freenode(J, temp); + freeproperty(J, temp); } else { succ = node->right; while (succ->left != &sentinel) @@ -153,7 +153,8 @@ static js_Property *delete(js_State *J, js_Property *node, const char *name) js_Object *jsV_newobject(js_State *J, enum js_Class type, js_Object *prototype) { - js_Object *obj = calloc(sizeof(js_Object), 1); + js_Object *obj = js_malloc(J, sizeof *obj); + memset(obj, 0, sizeof *obj); obj->gcmark = 0; obj->gcnext = J->gcobj; J->gcobj = obj; @@ -246,7 +247,7 @@ static void itwalk(js_State *J, js_Object *io, js_Object *top, int own) unsigned int k; #define ITADD(x) \ - js_Iterator *node = malloc(sizeof *node); \ + js_Iterator *node = js_malloc(J, sizeof *node); \ node->name = x; \ node->next = NULL; \ if (!tail) { \ @@ -297,7 +298,7 @@ const char *jsV_nextiterator(js_State *J, js_Object *io) while (io->u.iter.head) { js_Iterator *next = io->u.iter.head->next; const char *name = io->u.iter.head->name; - free(io->u.iter.head); + js_free(J, io->u.iter.head); io->u.iter.head = next; if (jsV_getproperty(J, io->u.iter.target, name)) return name; diff --git a/jsregexp.c b/jsregexp.c index 164ab61..84f2625 100644 --- a/jsregexp.c +++ b/jsregexp.c @@ -154,7 +154,7 @@ static void Rp_toString(js_State *J, unsigned int argc) re = js_toregexp(J, 0); - out = malloc(strlen(re->source) + 6); /* extra space for //gim */ + out = js_malloc(J, strlen(re->source) + 6); /* extra space for //gim */ strcpy(out, "/"); strcat(out, re->source); strcat(out, "/"); @@ -163,13 +163,13 @@ static void Rp_toString(js_State *J, unsigned int argc) if (re->flags & JS_REGEXP_M) strcat(out, "m"); if (js_try(J)) { - free(out); + js_free(J, out); js_throw(J); } js_pop(J, 0); js_pushstring(J, out); js_endtry(J); - free(out); + js_free(J, out); } static void Rp_exec(js_State *J, unsigned int argc) diff --git a/jsrun.c b/jsrun.c index b20a187..e0d9aa7 100644 --- a/jsrun.c +++ b/jsrun.c @@ -21,6 +21,35 @@ static void js_stackoverflow(js_State *J) js_throw(J); } +static void js_outofmemory(js_State *J) +{ + STACK[TOP].type = JS_TSTRING; + STACK[TOP].u.string = "out of memory"; + ++TOP; + js_throw(J); +} + +void *js_malloc(js_State *J, size_t size) +{ + void *ptr = malloc(size); + if (!ptr) + js_outofmemory(J); + return ptr; +} + +void *js_realloc(js_State *J, void *ptr, size_t size) +{ + ptr = realloc(ptr, size); + if (!ptr) + js_outofmemory(J); + return ptr; +} + +void js_free(js_State *J, void *ptr) +{ + free(ptr); +} + #define CHECKSTACK(n) if (TOP + n >= JS_STACKSIZE) js_stackoverflow(J) void js_pushvalue(js_State *J, js_Value v) @@ -76,16 +105,16 @@ void js_pushlstring(js_State *J, const char *v, unsigned int n) buf[n] = 0; js_pushstring(J, buf); } else { - char *s = malloc(n + 1); + char *s = js_malloc(J, n + 1); memcpy(s, v, n); s[n] = 0; if (js_try(J)) { - free(s); + js_free(J, s); js_throw(J); } js_pushstring(J, s); js_endtry(J); - free(s); + js_free(J, s); } } @@ -680,7 +709,7 @@ int js_hasproperty(js_State *J, int idx, const char *name) js_Environment *jsR_newenvironment(js_State *J, js_Object *vars, js_Environment *outer) { - js_Environment *E = malloc(sizeof *E); + js_Environment *E = js_malloc(J, sizeof *E); E->gcmark = 0; E->gcnext = J->gcenv; J->gcenv = E; diff --git a/jsstate.c b/jsstate.c index b5bbc78..a1afc86 100644 --- a/jsstate.c +++ b/jsstate.c @@ -41,7 +41,7 @@ void js_loadfile(js_State *J, const char *filename) n = ftell(f); fseek(f, 0, SEEK_SET); - s = malloc(n + 1); /* add space for string terminator */ + s = js_malloc(J, n + 1); /* add space for string terminator */ if (!s) { fclose(f); js_error(J, "cannot allocate storage for file contents: '%s'", filename); @@ -49,7 +49,7 @@ void js_loadfile(js_State *J, const char *filename) t = fread(s, 1, n, f); if (t != n) { - free(s); + js_free(J, s); fclose(f); js_error(J, "cannot read data from file: '%s'", filename); } @@ -57,14 +57,14 @@ void js_loadfile(js_State *J, const char *filename) s[n] = 0; /* zero-terminate string containing file data */ if (js_try(J)) { - free(s); + js_free(J, s); fclose(f); js_throw(J); } js_loadstring(J, filename, s); - free(s); + js_free(J, s); fclose(f); js_endtry(J); } @@ -104,9 +104,15 @@ int js_dofile(js_State *J, const char *filename) js_State *js_newstate(void) { js_State *J = malloc(sizeof *J); + if (!J) + return NULL; memset(J, 0, sizeof(*J)); J->stack = malloc(JS_STACKSIZE * sizeof *J->stack); + if (!J->stack) { + free(J); + return NULL; + } J->gcmark = 1; J->nextref = 0; diff --git a/jsstring.c b/jsstring.c index 2c63b0c..36fad0b 100644 --- a/jsstring.c +++ b/jsstring.c @@ -108,11 +108,11 @@ static void Sp_concat(js_State *J, unsigned int argc) s = js_tostring(J, 0); n = strlen(s); - out = malloc(n + 1); + out = js_malloc(J, n + 1); strcpy(out, s); if (js_try(J)) { - free(out); + js_free(J, out); js_throw(J); } @@ -125,7 +125,7 @@ static void Sp_concat(js_State *J, unsigned int argc) js_pushstring(J, out); js_endtry(J); - free(out); + js_free(J, out); } static void Sp_indexOf(js_State *J, unsigned int argc) @@ -221,7 +221,7 @@ static void Sp_substring(js_State *J, unsigned int argc) static void Sp_toLowerCase(js_State *J, unsigned int argc) { const char *src = js_tostring(J, 0); - char *dst = malloc(UTFmax * strlen(src) + 1); + char *dst = js_malloc(J, UTFmax * strlen(src) + 1); const char *s = src; char *d = dst; Rune rune; @@ -232,18 +232,18 @@ static void Sp_toLowerCase(js_State *J, unsigned int argc) } *d = 0; if (js_try(J)) { - free(dst); + js_free(J, dst); js_throw(J); } js_pushstring(J, dst); js_endtry(J); - free(dst); + js_free(J, dst); } static void Sp_toUpperCase(js_State *J, unsigned int argc) { const char *src = js_tostring(J, 0); - char *dst = malloc(UTFmax * strlen(src) + 1); + char *dst = js_malloc(J, UTFmax * strlen(src) + 1); const char *s = src; char *d = dst; Rune rune; @@ -254,12 +254,12 @@ static void Sp_toUpperCase(js_State *J, unsigned int argc) } *d = 0; if (js_try(J)) { - free(dst); + js_free(J, dst); js_throw(J); } js_pushstring(J, dst); js_endtry(J); - free(dst); + js_free(J, dst); } static int istrim(int c) @@ -286,10 +286,10 @@ static void S_fromCharCode(js_State *J, unsigned int argc) Rune c; char *s, *p; - s = p = malloc(argc * UTFmax + 1); + s = p = js_malloc(J, argc * UTFmax + 1); if (js_try(J)) { - free(s); + js_free(J, s); js_throw(J); } @@ -301,7 +301,7 @@ static void S_fromCharCode(js_State *J, unsigned int argc) js_pushstring(J, s); js_endtry(J); - free(s); + js_free(J, s); } static void Sp_match(js_State *J, unsigned int argc) @@ -404,20 +404,20 @@ loop: js_copy(J, 0); /* arg x+3: search string */ js_call(J, 2 + x); r = js_tostring(J, -1); - sb_putm(&sb, source, s); - sb_puts(&sb, r); + js_putm(J, &sb, source, s); + js_puts(J, &sb, r); js_pop(J, 1); } else { r = js_tostring(J, 2); - sb_putm(&sb, source, s); + js_putm(J, &sb, source, s); while (*r) { if (*r == '$') { switch (*(++r)) { - case '$': sb_putc(&sb, '$'); break; - case '`': sb_putm(&sb, source, s); break; - case '\'': sb_puts(&sb, s + n); break; + case '$': js_putc(J, &sb, '$'); break; + case '`': js_putm(J, &sb, source, s); break; + case '\'': js_puts(J, &sb, s + n); break; case '&': - sb_putm(&sb, s, s + n); + js_putm(J, &sb, s, s + n); break; case '0': case '1': case '2': case '3': case '4': case '5': case '6': case '7': case '8': case '9': @@ -426,25 +426,25 @@ loop: x = x * 10 + *(++r) - '0'; // TODO: use prog->nsub somehow if (x > 0 && x < m.nsub) { - sb_putm(&sb, m.sub[x].sp, m.sub[x].ep); + js_putm(J, &sb, m.sub[x].sp, m.sub[x].ep); } else { - sb_putc(&sb, '$'); + js_putc(J, &sb, '$'); if (x > 10) { - sb_putc(&sb, '0' + x / 10); - sb_putc(&sb, '0' + x % 10); + js_putc(J, &sb, '0' + x / 10); + js_putc(J, &sb, '0' + x % 10); } else { - sb_putc(&sb, '0' + x); + js_putc(J, &sb, '0' + x); } } break; default: - sb_putc(&sb, '$'); - sb_putc(&sb, *r); + js_putc(J, &sb, '$'); + js_putc(J, &sb, *r); break; } ++r; } else { - sb_putc(&sb, *r++); + js_putc(J, &sb, *r++); } } } @@ -453,7 +453,7 @@ loop: source = m.sub[0].ep; if (n == 0) { if (*source) - sb_putc(&sb, *source++); + js_putc(J, &sb, *source++); else goto end; } @@ -462,16 +462,16 @@ loop: } end: - sb_puts(&sb, s + n); - sb_putc(&sb, 0); + js_puts(J, &sb, s + n); + js_putc(J, &sb, 0); if (js_try(J)) { - free(sb); + js_free(J, sb); js_throw(J); } js_pushstring(J, sb ? sb->s : ""); js_endtry(J); - free(sb); + js_free(J, sb); } static void Sp_replace_string(js_State *J, unsigned int argc) @@ -498,39 +498,39 @@ static void Sp_replace_string(js_State *J, unsigned int argc) js_copy(J, 0); /* arg 3: search string */ js_call(J, 3); r = js_tostring(J, -1); - sb_putm(&sb, source, s); - sb_puts(&sb, r); - sb_puts(&sb, s + n); - sb_putc(&sb, 0); + js_putm(J, &sb, source, s); + js_puts(J, &sb, r); + js_puts(J, &sb, s + n); + js_putc(J, &sb, 0); js_pop(J, 1); } else { r = js_tostring(J, 2); - sb_putm(&sb, source, s); + js_putm(J, &sb, source, s); while (*r) { if (*r == '$') { switch (*(++r)) { - case '$': sb_putc(&sb, '$'); break; - case '&': sb_putm(&sb, s, s + n); break; - case '`': sb_putm(&sb, source, s); break; - case '\'': sb_puts(&sb, s + n); break; - default: sb_putc(&sb, '$'); sb_putc(&sb, *r); break; + case '$': js_putc(J, &sb, '$'); break; + case '&': js_putm(J, &sb, s, s + n); break; + case '`': js_putm(J, &sb, source, s); break; + case '\'': js_puts(J, &sb, s + n); break; + default: js_putc(J, &sb, '$'); js_putc(J, &sb, *r); break; } ++r; } else { - sb_putc(&sb, *r++); + js_putc(J, &sb, *r++); } } - sb_puts(&sb, s + n); - sb_putc(&sb, 0); + js_puts(J, &sb, s + n); + js_putc(J, &sb, 0); } if (js_try(J)) { - free(sb); + js_free(J, sb); js_throw(J); } js_pushstring(J, sb ? sb->s : ""); js_endtry(J); - free(sb); + js_free(J, sb); } static void Sp_replace(js_State *J, unsigned int argc) diff --git a/jsvalue.c b/jsvalue.c index 06de3b8..345622a 100644 --- a/jsvalue.c +++ b/jsvalue.c @@ -378,17 +378,17 @@ void js_concat(js_State *J) if (va.type == JS_TSTRING || vb.type == JS_TSTRING) { const char *sa = jsV_tostring(J, &va); const char *sb = jsV_tostring(J, &vb); - char *sab = malloc(strlen(sa) + strlen(sb) + 1); + char *sab = js_malloc(J, strlen(sa) + strlen(sb) + 1); strcpy(sab, sa); strcat(sab, sb); if (js_try(J)) { - free(sab); + js_free(J, sab); js_throw(J); } js_pop(J, 2); js_pushstring(J, sab); js_endtry(J); - free(sab); + js_free(J, sab); } else { double x = jsV_tonumber(J, &va); double y = jsV_tonumber(J, &vb);