jscript: Added call expression implementation.
This commit is contained in:
parent
652a0121a9
commit
a16f205382
|
@ -464,16 +464,100 @@ HRESULT member_expression_eval(exec_ctx_t *ctx, expression_t *expr, DWORD flags,
|
||||||
return E_NOTIMPL;
|
return E_NOTIMPL;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
static void free_dp(DISPPARAMS *dp)
|
||||||
|
{
|
||||||
|
DWORD i;
|
||||||
|
|
||||||
|
for(i=0; i < dp->cArgs; i++)
|
||||||
|
VariantClear(dp->rgvarg+i);
|
||||||
|
heap_free(dp->rgvarg);
|
||||||
|
}
|
||||||
|
|
||||||
|
static HRESULT args_to_param(exec_ctx_t *ctx, argument_t *args, jsexcept_t *ei, DISPPARAMS *dp)
|
||||||
|
{
|
||||||
|
VARIANTARG *vargs;
|
||||||
|
exprval_t exprval;
|
||||||
|
argument_t *iter;
|
||||||
|
DWORD cnt = 0, i;
|
||||||
|
HRESULT hres = S_OK;
|
||||||
|
|
||||||
|
memset(dp, 0, sizeof(*dp));
|
||||||
|
|
||||||
|
for(iter = args; iter; iter = iter->next)
|
||||||
|
cnt++;
|
||||||
|
if(!cnt)
|
||||||
|
return S_OK;
|
||||||
|
|
||||||
|
vargs = heap_alloc_zero(cnt * sizeof(*vargs));
|
||||||
|
if(!vargs)
|
||||||
|
return E_OUTOFMEMORY;
|
||||||
|
|
||||||
|
for(i = cnt, iter = args; iter; iter = iter->next) {
|
||||||
|
hres = expr_eval(ctx, iter->expr, 0, ei, &exprval);
|
||||||
|
if(FAILED(hres))
|
||||||
|
break;
|
||||||
|
|
||||||
|
hres = exprval_to_value(ctx->parser->script, &exprval, ei, vargs + (--i));
|
||||||
|
exprval_release(&exprval);
|
||||||
|
if(FAILED(hres))
|
||||||
|
break;
|
||||||
|
}
|
||||||
|
|
||||||
|
if(FAILED(hres)) {
|
||||||
|
free_dp(dp);
|
||||||
|
return hres;
|
||||||
|
}
|
||||||
|
|
||||||
|
dp->rgvarg = vargs;
|
||||||
|
dp->cArgs = cnt;
|
||||||
|
return S_OK;
|
||||||
|
}
|
||||||
|
|
||||||
HRESULT member_new_expression_eval(exec_ctx_t *ctx, expression_t *expr, DWORD flags, jsexcept_t *ei, exprval_t *ret)
|
HRESULT member_new_expression_eval(exec_ctx_t *ctx, expression_t *expr, DWORD flags, jsexcept_t *ei, exprval_t *ret)
|
||||||
{
|
{
|
||||||
FIXME("\n");
|
FIXME("\n");
|
||||||
return E_NOTIMPL;
|
return E_NOTIMPL;
|
||||||
}
|
}
|
||||||
|
|
||||||
HRESULT call_expression_eval(exec_ctx_t *ctx, expression_t *expr, DWORD flags, jsexcept_t *ei, exprval_t *ret)
|
HRESULT call_expression_eval(exec_ctx_t *ctx, expression_t *_expr, DWORD flags, jsexcept_t *ei, exprval_t *ret)
|
||||||
{
|
{
|
||||||
FIXME("\n");
|
call_expression_t *expr = (call_expression_t*)_expr;
|
||||||
return E_NOTIMPL;
|
VARIANT func, var;
|
||||||
|
exprval_t exprval;
|
||||||
|
DISPPARAMS dp;
|
||||||
|
HRESULT hres;
|
||||||
|
|
||||||
|
TRACE("\n");
|
||||||
|
|
||||||
|
hres = expr_eval(ctx, expr->expression, 0, ei, &exprval);
|
||||||
|
if(FAILED(hres))
|
||||||
|
return hres;
|
||||||
|
|
||||||
|
hres = args_to_param(ctx, expr->argument_list, ei, &dp);
|
||||||
|
if(SUCCEEDED(hres)) {
|
||||||
|
switch(exprval.type) {
|
||||||
|
case EXPRVAL_IDREF:
|
||||||
|
hres = disp_call(exprval.u.idref.disp, exprval.u.idref.id, ctx->parser->script->lcid, DISPATCH_METHOD,
|
||||||
|
&dp, flags & EXPR_NOVAL ? NULL : &var, ei, NULL/*FIXME*/);
|
||||||
|
if(flags & EXPR_NOVAL)
|
||||||
|
V_VT(&var) = VT_EMPTY;
|
||||||
|
break;
|
||||||
|
default:
|
||||||
|
FIXME("unimplemented type %d\n", V_VT(&func));
|
||||||
|
hres = E_NOTIMPL;
|
||||||
|
}
|
||||||
|
|
||||||
|
free_dp(&dp);
|
||||||
|
}
|
||||||
|
|
||||||
|
exprval_release(&exprval);
|
||||||
|
if(FAILED(hres))
|
||||||
|
return hres;
|
||||||
|
|
||||||
|
TRACE("= %s\n", debugstr_variant(&var));
|
||||||
|
ret->type = EXPRVAL_VARIANT;
|
||||||
|
ret->u.var = var;
|
||||||
|
return S_OK;
|
||||||
}
|
}
|
||||||
|
|
||||||
HRESULT this_expression_eval(exec_ctx_t *ctx, expression_t *expr, DWORD flags, jsexcept_t *ei, exprval_t *ret)
|
HRESULT this_expression_eval(exec_ctx_t *ctx, expression_t *expr, DWORD flags, jsexcept_t *ei, exprval_t *ret)
|
||||||
|
|
|
@ -61,9 +61,12 @@ DEFINE_EXPECT(global_propget_d);
|
||||||
DEFINE_EXPECT(global_propget_i);
|
DEFINE_EXPECT(global_propget_i);
|
||||||
DEFINE_EXPECT(global_propput_d);
|
DEFINE_EXPECT(global_propput_d);
|
||||||
DEFINE_EXPECT(global_propput_i);
|
DEFINE_EXPECT(global_propput_i);
|
||||||
|
DEFINE_EXPECT(global_success_d);
|
||||||
|
DEFINE_EXPECT(global_success_i);
|
||||||
|
|
||||||
#define DISPID_GLOBAL_TESTPROPGET 0x1000
|
#define DISPID_GLOBAL_TESTPROPGET 0x1000
|
||||||
#define DISPID_GLOBAL_TESTPROPPUT 0x1001
|
#define DISPID_GLOBAL_TESTPROPPUT 0x1001
|
||||||
|
#define DISPID_GLOBAL_REPORTSUCCESS 0x1002
|
||||||
|
|
||||||
static const WCHAR testW[] = {'t','e','s','t',0};
|
static const WCHAR testW[] = {'t','e','s','t',0};
|
||||||
|
|
||||||
|
@ -188,6 +191,12 @@ static HRESULT WINAPI DispatchEx_GetNameSpaceParent(IDispatchEx *iface, IUnknown
|
||||||
|
|
||||||
static HRESULT WINAPI Global_GetDispID(IDispatchEx *iface, BSTR bstrName, DWORD grfdex, DISPID *pid)
|
static HRESULT WINAPI Global_GetDispID(IDispatchEx *iface, BSTR bstrName, DWORD grfdex, DISPID *pid)
|
||||||
{
|
{
|
||||||
|
if(!strcmp_wa(bstrName, "reportSuccess")) {
|
||||||
|
CHECK_EXPECT(global_success_d);
|
||||||
|
ok(grfdex == fdexNameCaseSensitive, "grfdex = %x\n", grfdex);
|
||||||
|
*pid = DISPID_GLOBAL_REPORTSUCCESS;
|
||||||
|
return S_OK;
|
||||||
|
}
|
||||||
if(!strcmp_wa(bstrName, "testPropGet")) {
|
if(!strcmp_wa(bstrName, "testPropGet")) {
|
||||||
CHECK_EXPECT(global_propget_d);
|
CHECK_EXPECT(global_propget_d);
|
||||||
ok(grfdex == fdexNameCaseSensitive, "grfdex = %x\n", grfdex);
|
ok(grfdex == fdexNameCaseSensitive, "grfdex = %x\n", grfdex);
|
||||||
|
@ -209,6 +218,19 @@ static HRESULT WINAPI Global_InvokeEx(IDispatchEx *iface, DISPID id, LCID lcid,
|
||||||
VARIANT *pvarRes, EXCEPINFO *pei, IServiceProvider *pspCaller)
|
VARIANT *pvarRes, EXCEPINFO *pei, IServiceProvider *pspCaller)
|
||||||
{
|
{
|
||||||
switch(id) {
|
switch(id) {
|
||||||
|
case DISPID_GLOBAL_REPORTSUCCESS:
|
||||||
|
CHECK_EXPECT(global_success_i);
|
||||||
|
|
||||||
|
ok(wFlags == INVOKE_FUNC, "wFlags = %x\n", wFlags);
|
||||||
|
ok(pdp != NULL, "pdp == NULL\n");
|
||||||
|
ok(!pdp->rgdispidNamedArgs, "rgdispidNamedArgs != NULL\n");
|
||||||
|
ok(pdp->cArgs == 0, "cArgs = %d\n", pdp->cArgs);
|
||||||
|
ok(!pdp->cNamedArgs, "cNamedArgs = %d\n", pdp->cNamedArgs);
|
||||||
|
ok(!pvarRes, "pvarRes != NULL\n");
|
||||||
|
ok(pei != NULL, "pei == NULL\n");
|
||||||
|
|
||||||
|
return S_OK;
|
||||||
|
|
||||||
case DISPID_GLOBAL_TESTPROPGET:
|
case DISPID_GLOBAL_TESTPROPGET:
|
||||||
CHECK_EXPECT(global_propget_i);
|
CHECK_EXPECT(global_propget_i);
|
||||||
|
|
||||||
|
@ -427,6 +449,12 @@ static void run_tests(void)
|
||||||
parse_script_a("testPropPut = 1;");
|
parse_script_a("testPropPut = 1;");
|
||||||
CHECK_CALLED(global_propput_d);
|
CHECK_CALLED(global_propput_d);
|
||||||
CHECK_CALLED(global_propput_i);
|
CHECK_CALLED(global_propput_i);
|
||||||
|
|
||||||
|
SET_EXPECT(global_success_d);
|
||||||
|
SET_EXPECT(global_success_i);
|
||||||
|
parse_script_a("reportSuccess();");
|
||||||
|
CHECK_CALLED(global_success_d);
|
||||||
|
CHECK_CALLED(global_success_i);
|
||||||
}
|
}
|
||||||
|
|
||||||
START_TEST(run)
|
START_TEST(run)
|
||||||
|
|
Loading…
Reference in New Issue