vbscript: Use a dedicated opcode for identifier expressions.

Signed-off-by: Jacek Caban <jacek@codeweavers.com>
Signed-off-by: Alexandre Julliard <julliard@winehq.org>
This commit is contained in:
Jacek Caban 2021-10-08 19:13:59 +02:00 committed by Alexandre Julliard
parent 1699847dad
commit 2613f8bfe6
3 changed files with 43 additions and 8 deletions

View File

@ -446,7 +446,8 @@ static HRESULT compile_args(compile_ctx_t *ctx, expression_t *args, unsigned *re
return S_OK; return S_OK;
} }
static HRESULT compile_member_expression(compile_ctx_t *ctx, member_expression_t *expr, unsigned arg_cnt, BOOL ret_val) static HRESULT compile_member_call_expression(compile_ctx_t *ctx, member_expression_t *expr,
unsigned arg_cnt, BOOL ret_val)
{ {
HRESULT hres; HRESULT hres;
@ -471,6 +472,20 @@ static HRESULT compile_member_expression(compile_ctx_t *ctx, member_expression_t
return hres; return hres;
} }
static HRESULT compile_member_expression(compile_ctx_t *ctx, member_expression_t *expr)
{
expression_t *const_expr;
if (expr->obj_expr) /* FIXME: we should probably have a dedicated opcode as well */
return compile_member_call_expression(ctx, expr, 0, TRUE);
const_expr = lookup_const_decls(ctx, expr->identifier, TRUE);
if(const_expr)
return compile_expression(ctx, const_expr);
return push_instr_bstr(ctx, OP_ident, expr->identifier);
}
static HRESULT compile_call_expression(compile_ctx_t *ctx, call_expression_t *expr, BOOL ret_val) static HRESULT compile_call_expression(compile_ctx_t *ctx, call_expression_t *expr, BOOL ret_val)
{ {
unsigned arg_cnt = 0; unsigned arg_cnt = 0;
@ -484,7 +499,7 @@ static HRESULT compile_call_expression(compile_ctx_t *ctx, call_expression_t *ex
for(call = expr->call_expr; call->type == EXPR_BRACKETS; call = ((unary_expression_t*)call)->subexpr); for(call = expr->call_expr; call->type == EXPR_BRACKETS; call = ((unary_expression_t*)call)->subexpr);
if(call->type == EXPR_MEMBER) if(call->type == EXPR_MEMBER)
return compile_member_expression(ctx, (member_expression_t*)call, arg_cnt, ret_val); return compile_member_call_expression(ctx, (member_expression_t*)call, arg_cnt, ret_val);
hres = compile_expression(ctx, call); hres = compile_expression(ctx, call);
if(FAILED(hres)) if(FAILED(hres))
@ -582,7 +597,7 @@ static HRESULT compile_expression(compile_ctx_t *ctx, expression_t *expr)
case EXPR_ME: case EXPR_ME:
return push_instr(ctx, OP_me) ? S_OK : E_OUTOFMEMORY; return push_instr(ctx, OP_me) ? S_OK : E_OUTOFMEMORY;
case EXPR_MEMBER: case EXPR_MEMBER:
return compile_member_expression(ctx, (member_expression_t*)expr, 0, TRUE); return compile_member_expression(ctx, (member_expression_t*)expr);
case EXPR_MOD: case EXPR_MOD:
return compile_binary_expression(ctx, (binary_expression_t*)expr, OP_mod); return compile_binary_expression(ctx, (binary_expression_t*)expr, OP_mod);
case EXPR_MUL: case EXPR_MUL:

View File

@ -615,10 +615,8 @@ static HRESULT variant_call(exec_ctx_t *ctx, VARIANT *v, unsigned arg_cnt, VARIA
return S_OK; return S_OK;
} }
static HRESULT do_icall(exec_ctx_t *ctx, VARIANT *res) static HRESULT do_icall(exec_ctx_t *ctx, VARIANT *res, BSTR identifier, unsigned arg_cnt)
{ {
BSTR identifier = ctx->instr->arg1.bstr;
const unsigned arg_cnt = ctx->instr->arg2.uint;
DISPPARAMS dp; DISPPARAMS dp;
ref_t ref; ref_t ref;
HRESULT hres; HRESULT hres;
@ -687,12 +685,14 @@ static HRESULT do_icall(exec_ctx_t *ctx, VARIANT *res)
static HRESULT interp_icall(exec_ctx_t *ctx) static HRESULT interp_icall(exec_ctx_t *ctx)
{ {
BSTR identifier = ctx->instr->arg1.bstr;
const unsigned arg_cnt = ctx->instr->arg2.uint;
VARIANT v; VARIANT v;
HRESULT hres; HRESULT hres;
TRACE("\n"); TRACE("\n");
hres = do_icall(ctx, &v); hres = do_icall(ctx, &v, identifier, arg_cnt);
if(FAILED(hres)) if(FAILED(hres))
return hres; return hres;
@ -701,8 +701,12 @@ static HRESULT interp_icall(exec_ctx_t *ctx)
static HRESULT interp_icallv(exec_ctx_t *ctx) static HRESULT interp_icallv(exec_ctx_t *ctx)
{ {
BSTR identifier = ctx->instr->arg1.bstr;
const unsigned arg_cnt = ctx->instr->arg2.uint;
TRACE("\n"); TRACE("\n");
return do_icall(ctx, NULL);
return do_icall(ctx, NULL, identifier, arg_cnt);
} }
static HRESULT interp_vcall(exec_ctx_t *ctx) static HRESULT interp_vcall(exec_ctx_t *ctx)
@ -788,6 +792,21 @@ static HRESULT interp_mcallv(exec_ctx_t *ctx)
return do_mcall(ctx, NULL); return do_mcall(ctx, NULL);
} }
static HRESULT interp_ident(exec_ctx_t *ctx)
{
BSTR identifier = ctx->instr->arg1.bstr;
VARIANT v;
HRESULT hres;
TRACE("%s\n", debugstr_w(identifier));
hres = do_icall(ctx, &v, identifier, 0);
if(FAILED(hres))
return hres;
return stack_push(ctx, &v);
}
static HRESULT assign_value(exec_ctx_t *ctx, VARIANT *dst, VARIANT *src, WORD flags) static HRESULT assign_value(exec_ctx_t *ctx, VARIANT *dst, VARIANT *src, WORD flags)
{ {
VARIANT value; VARIANT value;

View File

@ -242,6 +242,7 @@ typedef enum {
X(gteq, 1, 0, 0) \ X(gteq, 1, 0, 0) \
X(icall, 1, ARG_BSTR, ARG_UINT) \ X(icall, 1, ARG_BSTR, ARG_UINT) \
X(icallv, 1, ARG_BSTR, ARG_UINT) \ X(icallv, 1, ARG_BSTR, ARG_UINT) \
X(ident, 1, ARG_BSTR, 0) \
X(idiv, 1, 0, 0) \ X(idiv, 1, 0, 0) \
X(imp, 1, 0, 0) \ X(imp, 1, 0, 0) \
X(incc, 1, ARG_BSTR, 0) \ X(incc, 1, ARG_BSTR, 0) \