diff --git a/dlls/jscript/compile.c b/dlls/jscript/compile.c index 981ae963ca8..2e18c509c0f 100644 --- a/dlls/jscript/compile.c +++ b/dlls/jscript/compile.c @@ -75,7 +75,7 @@ static void dump_instr_arg(instr_arg_type_t type, instr_arg_t *arg) { switch(type) { case ARG_STR: - TRACE_(jscript_disas)("\t%s", debugstr_w(arg->str)); + TRACE_(jscript_disas)("\t%s", debugstr_jsstr(arg->str)); break; case ARG_BSTR: TRACE_(jscript_disas)("\t%s", debugstr_wn(arg->bstr, SysStringLen(arg->bstr))); @@ -119,16 +119,37 @@ static inline void *compiler_alloc(bytecode_t *code, size_t size) return jsheap_alloc(&code->heap, size); } -static WCHAR *compiler_alloc_string(bytecode_t *code, const WCHAR *str) +static jsstr_t *compiler_alloc_string_len(compiler_ctx_t *ctx, const WCHAR *str, unsigned len) { - size_t size; - WCHAR *ret; + jsstr_t *new_str; - size = (strlenW(str)+1)*sizeof(WCHAR); - ret = compiler_alloc(code, size); - if(ret) - memcpy(ret, str, size); - return ret; + if(!ctx->code->str_pool_size) { + ctx->code->str_pool = heap_alloc(8 * sizeof(jsstr_t*)); + if(!ctx->code->str_pool) + return NULL; + ctx->code->str_pool_size = 8; + }else if(ctx->code->str_pool_size == ctx->code->str_cnt) { + jsstr_t **new_pool; + + new_pool = heap_realloc(ctx->code->str_pool, ctx->code->str_pool_size*2*sizeof(jsstr_t*)); + if(!new_pool) + return NULL; + + ctx->code->str_pool = new_pool; + ctx->code->str_pool_size *= 2; + } + + new_str = jsstr_alloc_len(str, len); + if(!new_str) + return NULL; + + ctx->code->str_pool[ctx->code->str_cnt++] = new_str; + return new_str; +} + +static jsstr_t *compiler_alloc_string(compiler_ctx_t *ctx, const WCHAR *str) +{ + return compiler_alloc_string_len(ctx, str, strlenW(str)); } static BOOL ensure_bstr_slot(compiler_ctx_t *ctx) @@ -216,9 +237,9 @@ static HRESULT push_instr_int(compiler_ctx_t *ctx, jsop_t op, LONG arg) static HRESULT push_instr_str(compiler_ctx_t *ctx, jsop_t op, const WCHAR *arg) { unsigned instr; - WCHAR *str; + jsstr_t *str; - str = compiler_alloc_string(ctx->code, arg); + str = compiler_alloc_string(ctx, arg); if(!str) return E_OUTOFMEMORY; @@ -268,9 +289,9 @@ static HRESULT push_instr_bstr_uint(compiler_ctx_t *ctx, jsop_t op, const WCHAR static HRESULT push_instr_uint_str(compiler_ctx_t *ctx, jsop_t op, unsigned arg1, const WCHAR *arg2) { unsigned instr; - WCHAR *str; + jsstr_t *str; - str = compiler_alloc_string(ctx->code, arg2); + str = compiler_alloc_string(ctx, arg2); if(!str) return E_OUTOFMEMORY; @@ -711,7 +732,7 @@ static HRESULT compile_typeof_expression(compiler_ctx_t *ctx, unary_expression_t if(is_memberid_expr(expr->expression->type)) { if(expr->expression->type == EXPR_IDENT) - return push_instr_str(ctx, OP_typeofident, ((identifier_expression_t*)expr->expression)->identifier); + return push_instr_bstr(ctx, OP_typeofident, ((identifier_expression_t*)expr->expression)->identifier); op = OP_typeofid; hres = compile_memberid_expression(ctx, expr->expression, 0); @@ -738,13 +759,11 @@ static HRESULT compile_literal(compiler_ctx_t *ctx, literal_t *literal) return push_instr_str(ctx, OP_str, literal->u.wstr); case LT_REGEXP: { unsigned instr; - WCHAR *str; + jsstr_t *str; - str = compiler_alloc(ctx->code, (literal->u.regexp.str_len+1)*sizeof(WCHAR)); + str = compiler_alloc_string_len(ctx, literal->u.regexp.str, literal->u.regexp.str_len); if(!str) return E_OUTOFMEMORY; - memcpy(str, literal->u.regexp.str, literal->u.regexp.str_len*sizeof(WCHAR)); - str[literal->u.regexp.str_len] = 0; instr = push_instr(ctx, OP_regexp); if(!instr) @@ -1796,10 +1815,13 @@ void release_bytecode(bytecode_t *code) for(i=0; i < code->bstr_cnt; i++) SysFreeString(code->bstr_pool[i]); + for(i=0; i < code->str_cnt; i++) + jsstr_release(code->str_pool[i]); heap_free(code->source); jsheap_free(&code->heap); heap_free(code->bstr_pool); + heap_free(code->str_pool); heap_free(code->instrs); heap_free(code); } diff --git a/dlls/jscript/engine.c b/dlls/jscript/engine.c index 66e2b92dd4c..44c8333844e 100644 --- a/dlls/jscript/engine.c +++ b/dlls/jscript/engine.c @@ -549,7 +549,7 @@ static inline unsigned get_op_int(exec_ctx_t *ctx, int i){ return ctx->code->instrs[ctx->ip].u.arg[i].lng; } -static inline const WCHAR *get_op_str(exec_ctx_t *ctx, int i){ +static inline jsstr_t *get_op_str(exec_ctx_t *ctx, int i){ return ctx->code->instrs[ctx->ip].u.arg[i].str; } @@ -718,11 +718,11 @@ static HRESULT interp_throw_ref(exec_ctx_t *ctx) static HRESULT interp_throw_type(exec_ctx_t *ctx) { const HRESULT hres = get_op_uint(ctx, 0); - const WCHAR *str = get_op_str(ctx, 1); + jsstr_t *str = get_op_str(ctx, 1); - TRACE("%08x %s\n", hres, debugstr_w(str)); + TRACE("%08x %s\n", hres, debugstr_jsstr(str)); - return throw_type_error(ctx->script, hres, str); + return throw_type_error(ctx->script, hres, str->str); } /* ECMA-262 3rd Edition 12.14 */ @@ -1134,35 +1134,24 @@ static HRESULT interp_double(exec_ctx_t *ctx) /* ECMA-262 3rd Edition 7.8.4 */ static HRESULT interp_str(exec_ctx_t *ctx) { - const WCHAR *arg = get_op_str(ctx, 0); - jsstr_t *str; + jsstr_t *str = get_op_str(ctx, 0); - TRACE("%s\n", debugstr_w(arg)); + TRACE("%s\n", debugstr_jsstr(str)); - str = jsstr_alloc(arg); - if(!str) - return E_OUTOFMEMORY; - - return stack_push(ctx, jsval_string(str)); + return stack_push(ctx, jsval_string(jsstr_addref(str))); } /* ECMA-262 3rd Edition 7.8 */ static HRESULT interp_regexp(exec_ctx_t *ctx) { - const WCHAR *source = get_op_str(ctx, 0); + jsstr_t *source = get_op_str(ctx, 0); const unsigned flags = get_op_uint(ctx, 1); jsdisp_t *regexp; - jsstr_t *src; HRESULT hres; - TRACE("%s %x\n", debugstr_w(source), flags); + TRACE("%s %x\n", debugstr_jsstr(source), flags); - src = jsstr_alloc(source); - if(!src) - return E_OUTOFMEMORY; - - hres = create_regexp(ctx->script, src, flags, ®exp); - jsstr_release(src); + hres = create_regexp(ctx->script, source, flags, ®exp); if(FAILED(hres)) return hres; diff --git a/dlls/jscript/engine.h b/dlls/jscript/engine.h index 49232eed75a..9123a2bb8dc 100644 --- a/dlls/jscript/engine.h +++ b/dlls/jscript/engine.h @@ -121,7 +121,7 @@ OP_LIST typedef union { BSTR bstr; LONG lng; - WCHAR *str; + jsstr_t *str; unsigned uint; } instr_arg_t; @@ -175,6 +175,10 @@ typedef struct _bytecode_t { unsigned bstr_pool_size; unsigned bstr_cnt; + jsstr_t **str_pool; + unsigned str_pool_size; + unsigned str_cnt; + struct _bytecode_t *next; } bytecode_t;