From: Gabriel Ivăncescu gabrielopcode@gmail.com
Signed-off-by: Gabriel Ivăncescu gabrielopcode@gmail.com --- dlls/jscript/array.c | 18 +++-- dlls/jscript/dispex.c | 23 ++++--- dlls/jscript/engine.c | 10 +-- dlls/jscript/function.c | 2 +- dlls/jscript/jscript.h | 2 +- dlls/jscript/json.c | 4 +- dlls/jscript/set.c | 3 +- dlls/jscript/tests/run.c | 143 +++++++++++++++++++++++++++++++++++++++ 8 files changed, 178 insertions(+), 27 deletions(-)
diff --git a/dlls/jscript/array.c b/dlls/jscript/array.c index 341505a335c..198fc3c16c1 100644 --- a/dlls/jscript/array.c +++ b/dlls/jscript/array.c @@ -1061,7 +1061,8 @@ static HRESULT Array_every(script_ctx_t *ctx, jsval_t vthis, WORD flags, unsigne args[0] = value; args[1] = jsval_number(i); args[2] = jsval_obj(jsthis); - hres = disp_call_value(ctx, callback, context_this, DISPATCH_METHOD, ARRAY_SIZE(args), args, &res); + hres = disp_call_value(ctx, callback, context_this, DISPATCH_METHOD, ARRAY_SIZE(args), args, &res, + &ctx->jscaller->IServiceProvider_iface); jsval_release(value); if(FAILED(hres)) goto done; @@ -1128,7 +1129,8 @@ static HRESULT Array_filter(script_ctx_t *ctx, jsval_t vthis, WORD flags, unsign args[0] = value; args[1] = jsval_number(i); args[2] = jsval_obj(jsthis); - hres = disp_call_value(ctx, callback, context_this, DISPATCH_METHOD, ARRAY_SIZE(args), args, &res); + hres = disp_call_value(ctx, callback, context_this, DISPATCH_METHOD, ARRAY_SIZE(args), args, &res, + &ctx->jscaller->IServiceProvider_iface); if(SUCCEEDED(hres)) { hres = to_boolean(res, &boolval); jsval_release(res); @@ -1190,7 +1192,8 @@ static HRESULT Array_forEach(script_ctx_t *ctx, jsval_t vthis, WORD flags, unsig args[0] = value; args[1] = jsval_number(i); args[2] = jsval_obj(jsthis); - hres = disp_call_value(ctx, callback, context_this, DISPATCH_METHOD, ARRAY_SIZE(args), args, &res); + hres = disp_call_value(ctx, callback, context_this, DISPATCH_METHOD, ARRAY_SIZE(args), args, &res, + &ctx->jscaller->IServiceProvider_iface); jsval_release(value); if(FAILED(hres)) goto done; @@ -1365,7 +1368,8 @@ static HRESULT Array_map(script_ctx_t *ctx, jsval_t vthis, WORD flags, unsigned
callback_args[1] = jsval_number(k); callback_args[2] = jsval_obj(jsthis); - hres = disp_call_value(ctx, callback, context_this, DISPATCH_METHOD, 3, callback_args, &mapped_value); + hres = disp_call_value(ctx, callback, context_this, DISPATCH_METHOD, 3, callback_args, &mapped_value, + &ctx->jscaller->IServiceProvider_iface); jsval_release(callback_args[0]); if(FAILED(hres)) break; @@ -1432,7 +1436,8 @@ static HRESULT Array_reduce(script_ctx_t *ctx, jsval_t vthis, WORD flags, unsign callback_args[0] = acc; callback_args[2] = jsval_number(k); callback_args[3] = jsval_obj(jsthis); - hres = disp_call_value(ctx, callback, jsval_undefined(), DISPATCH_METHOD, ARRAY_SIZE(callback_args), callback_args, &new_acc); + hres = disp_call_value(ctx, callback, jsval_undefined(), DISPATCH_METHOD, ARRAY_SIZE(callback_args), + callback_args, &new_acc, &ctx->jscaller->IServiceProvider_iface); jsval_release(callback_args[1]); if(FAILED(hres)) break; @@ -1493,7 +1498,8 @@ static HRESULT Array_some(script_ctx_t *ctx, jsval_t vthis, WORD flags, unsigned args[0] = value; args[1] = jsval_number(i); args[2] = jsval_obj(jsthis); - hres = disp_call_value(ctx, callback, context_this, DISPATCH_METHOD, ARRAY_SIZE(args), args, &res); + hres = disp_call_value(ctx, callback, context_this, DISPATCH_METHOD, ARRAY_SIZE(args), args, &res, + &ctx->jscaller->IServiceProvider_iface); jsval_release(value); if(FAILED(hres)) goto done; diff --git a/dlls/jscript/dispex.c b/dlls/jscript/dispex.c index 4b56ec9fc70..73a4a5bbecd 100644 --- a/dlls/jscript/dispex.c +++ b/dlls/jscript/dispex.c @@ -574,7 +574,7 @@ static HRESULT invoke_prop_func(jsdisp_t *This, IDispatch *jsthis, dispex_prop_t
return disp_call_value(This->ctx, get_object(prop->u.val), jsval_disp(jsthis ? jsthis : (IDispatch*)&This->IDispatchEx_iface), - flags, argc, argv, r); + flags, argc, argv, r, caller); } case PROP_ACCESSOR: case PROP_IDX: { @@ -587,7 +587,7 @@ static HRESULT invoke_prop_func(jsdisp_t *This, IDispatch *jsthis, dispex_prop_t if(is_object_instance(val)) { hres = disp_call_value(This->ctx, get_object(val), jsval_disp(jsthis ? jsthis : (IDispatch*)&This->IDispatchEx_iface), - flags, argc, argv, r); + flags, argc, argv, r, caller); }else { FIXME("invoke %s\n", debugstr_jsval(val)); hres = E_NOTIMPL; @@ -2364,7 +2364,7 @@ HRESULT jsdisp_call(jsdisp_t *disp, DISPID id, WORD flags, unsigned argc, jsval_ if(!prop) return DISP_E_MEMBERNOTFOUND;
- return invoke_prop_func(disp, to_disp(disp), prop, flags, argc, argv, r, NULL); + return invoke_prop_func(disp, to_disp(disp), prop, flags, argc, argv, r, &disp->ctx->jscaller->IServiceProvider_iface); }
HRESULT jsdisp_call_name(jsdisp_t *disp, const WCHAR *name, WORD flags, unsigned argc, jsval_t *argv, jsval_t *r) @@ -2379,10 +2379,11 @@ HRESULT jsdisp_call_name(jsdisp_t *disp, const WCHAR *name, WORD flags, unsigned if(!prop || prop->type == PROP_DELETED) return JS_E_INVALID_PROPERTY;
- return invoke_prop_func(disp, to_disp(disp), prop, flags, argc, argv, r, NULL); + return invoke_prop_func(disp, to_disp(disp), prop, flags, argc, argv, r, &disp->ctx->jscaller->IServiceProvider_iface); }
-static HRESULT disp_invoke(script_ctx_t *ctx, IDispatch *disp, DISPID id, WORD flags, DISPPARAMS *params, VARIANT *r) +static HRESULT disp_invoke(script_ctx_t *ctx, IDispatch *disp, DISPID id, WORD flags, DISPPARAMS *params, VARIANT *r, + IServiceProvider *caller) { IDispatchEx *dispex; EXCEPINFO ei; @@ -2391,7 +2392,7 @@ static HRESULT disp_invoke(script_ctx_t *ctx, IDispatch *disp, DISPID id, WORD f memset(&ei, 0, sizeof(ei)); hres = IDispatch_QueryInterface(disp, &IID_IDispatchEx, (void**)&dispex); if(SUCCEEDED(hres)) { - hres = IDispatchEx_InvokeEx(dispex, id, ctx->lcid, flags, params, r, &ei, &ctx->jscaller->IServiceProvider_iface); + hres = IDispatchEx_InvokeEx(dispex, id, ctx->lcid, flags, params, r, &ei, caller); IDispatchEx_Release(dispex); }else { UINT err = 0; @@ -2489,7 +2490,7 @@ HRESULT disp_call(script_ctx_t *ctx, IDispatch *disp, DISPID id, WORD flags, uns }
V_VT(&retv) = VT_EMPTY; - hres = disp_invoke(ctx, disp, id, flags, &dp, ret ? &retv : NULL); + hres = disp_invoke(ctx, disp, id, flags, &dp, ret ? &retv : NULL, &ctx->jscaller->IServiceProvider_iface);
for(i=0; i<argc; i++) VariantClear(dp.rgvarg+argc-i-1); @@ -2530,7 +2531,7 @@ HRESULT disp_call_name(script_ctx_t *ctx, IDispatch *disp, const WCHAR *name, WO }
HRESULT disp_call_value(script_ctx_t *ctx, IDispatch *disp, jsval_t vthis, WORD flags, unsigned argc, jsval_t *argv, - jsval_t *r) + jsval_t *r, IServiceProvider *caller) { VARIANT buf[6], retv, *args = buf; IDispatch *jsthis; @@ -2586,7 +2587,7 @@ HRESULT disp_call_value(script_ctx_t *ctx, IDispatch *disp, jsval_t vthis, WORD
if(SUCCEEDED(hres)) { V_VT(&retv) = VT_EMPTY; - hres = disp_invoke(ctx, disp, DISPID_VALUE, flags, &dp, r ? &retv : NULL); + hres = disp_invoke(ctx, disp, DISPID_VALUE, flags, &dp, r ? &retv : NULL, caller); }
for(i = 0; i < argc; i++) @@ -2665,7 +2666,7 @@ HRESULT disp_propput(script_ctx_t *ctx, IDispatch *disp, DISPID id, jsval_t val) if(V_VT(&var) == VT_DISPATCH) flags |= DISPATCH_PROPERTYPUTREF;
- hres = disp_invoke(ctx, disp, id, flags, &dp, NULL); + hres = disp_invoke(ctx, disp, id, flags, &dp, NULL, &ctx->jscaller->IServiceProvider_iface); VariantClear(&var); }
@@ -2773,7 +2774,7 @@ HRESULT disp_propget(script_ctx_t *ctx, IDispatch *disp, DISPID id, jsval_t *val jsdisp_release(jsdisp);
V_VT(&var) = VT_EMPTY; - hres = disp_invoke(ctx, disp, id, INVOKE_PROPERTYGET, &dp, &var); + hres = disp_invoke(ctx, disp, id, INVOKE_PROPERTYGET, &dp, &var, &ctx->jscaller->IServiceProvider_iface); if(SUCCEEDED(hres)) { hres = variant_to_jsval(ctx, &var, val); VariantClear(&var); diff --git a/dlls/jscript/engine.c b/dlls/jscript/engine.c index b0557065e69..459d1e833df 100644 --- a/dlls/jscript/engine.c +++ b/dlls/jscript/engine.c @@ -327,7 +327,7 @@ static HRESULT exprval_call(script_ctx_t *ctx, exprval_t *ref, WORD flags, unsig return E_FAIL; }
- return disp_call_value(ctx, get_object(v), jsval_undefined(), flags, argc, argv, r); + return disp_call_value(ctx, get_object(v), jsval_undefined(), flags, argc, argv, r, &ctx->jscaller->IServiceProvider_iface); } case EXPRVAL_IDREF: /* ECMA-262 3rd Edition 11.2.3.7 / ECMA-262 5.1 Edition 11.2.3.6 * @@ -340,7 +340,7 @@ static HRESULT exprval_call(script_ctx_t *ctx, exprval_t *ref, WORD flags, unsig FIXME("invoke %s\n", debugstr_jsval(v)); hres = E_FAIL; }else { - hres = disp_call_value(ctx, get_object(v), jsval_undefined(), flags, argc, argv, r); + hres = disp_call_value(ctx, get_object(v), jsval_undefined(), flags, argc, argv, r, &ctx->jscaller->IServiceProvider_iface); } jsval_release(v); return hres; @@ -351,7 +351,7 @@ static HRESULT exprval_call(script_ctx_t *ctx, exprval_t *ref, WORD flags, unsig
hres = to_object(ctx, ref->u.val, &obj); if(SUCCEEDED(hres)) { - hres = disp_call_value(ctx, obj, jsval_undefined(), flags, argc, argv, r); + hres = disp_call_value(ctx, obj, jsval_undefined(), flags, argc, argv, r, &ctx->jscaller->IServiceProvider_iface); IDispatch_Release(obj); } return hres; @@ -1421,7 +1421,7 @@ static HRESULT interp_new(script_ctx_t *ctx)
clear_acc(ctx); return disp_call_value(ctx, get_object(constr), jsval_undefined(), DISPATCH_CONSTRUCT | DISPATCH_JSCRIPT_CALLEREXECSSOURCE, - argc, stack_args(ctx, argc), &ctx->acc); + argc, stack_args(ctx, argc), &ctx->acc, &ctx->jscaller->IServiceProvider_iface); }
/* ECMA-262 3rd Edition 11.2.3 */ @@ -1439,7 +1439,7 @@ static HRESULT interp_call(script_ctx_t *ctx)
clear_acc(ctx); return disp_call_value(ctx, get_object(obj), jsval_undefined(), DISPATCH_METHOD | DISPATCH_JSCRIPT_CALLEREXECSSOURCE, - argn, stack_args(ctx, argn), do_ret ? &ctx->acc : NULL); + argn, stack_args(ctx, argn), do_ret ? &ctx->acc : NULL, &ctx->jscaller->IServiceProvider_iface); }
/* ECMA-262 3rd Edition 11.2.3 */ diff --git a/dlls/jscript/function.c b/dlls/jscript/function.c index 5f210a04050..c3b22eb843c 100644 --- a/dlls/jscript/function.c +++ b/dlls/jscript/function.c @@ -411,7 +411,7 @@ static HRESULT Function_apply(script_ctx_t *ctx, jsval_t vthis, WORD flags, unsi hres = function->vtbl->call(ctx, function, this_val, flags, cnt, args, r); }else { jsval_t res; - hres = disp_call_value(ctx, get_object(vthis), this_val, DISPATCH_METHOD, cnt, args, &res); + hres = disp_call_value(ctx, get_object(vthis), this_val, DISPATCH_METHOD, cnt, args, &res, &ctx->jscaller->IServiceProvider_iface); if(SUCCEEDED(hres)) { if(r) *r = res; diff --git a/dlls/jscript/jscript.h b/dlls/jscript/jscript.h index 36a6d23c917..04b3a6cc8c9 100644 --- a/dlls/jscript/jscript.h +++ b/dlls/jscript/jscript.h @@ -240,7 +240,7 @@ HRESULT init_dispex_from_constr(jsdisp_t*,script_ctx_t*,const builtin_info_t*,js
HRESULT disp_call(script_ctx_t*,IDispatch*,DISPID,WORD,unsigned,jsval_t*,jsval_t*) DECLSPEC_HIDDEN; HRESULT disp_call_name(script_ctx_t*,IDispatch*,const WCHAR*,WORD,unsigned,jsval_t*,jsval_t*) DECLSPEC_HIDDEN; -HRESULT disp_call_value(script_ctx_t*,IDispatch*,jsval_t,WORD,unsigned,jsval_t*,jsval_t*) DECLSPEC_HIDDEN; +HRESULT disp_call_value(script_ctx_t*,IDispatch*,jsval_t,WORD,unsigned,jsval_t*,jsval_t*,IServiceProvider*) DECLSPEC_HIDDEN; HRESULT jsdisp_call_value(jsdisp_t*,jsval_t,WORD,unsigned,jsval_t*,jsval_t*) DECLSPEC_HIDDEN; HRESULT jsdisp_call(jsdisp_t*,DISPID,WORD,unsigned,jsval_t*,jsval_t*) DECLSPEC_HIDDEN; HRESULT jsdisp_call_name(jsdisp_t*,const WCHAR*,WORD,unsigned,jsval_t*,jsval_t*) DECLSPEC_HIDDEN; diff --git a/dlls/jscript/json.c b/dlls/jscript/json.c index e36c4973ef2..d2be768ffea 100644 --- a/dlls/jscript/json.c +++ b/dlls/jscript/json.c @@ -350,8 +350,8 @@ static jsval_t transform_json_object(struct transform_json_object_ctx *proc_ctx, }
args[0] = jsval_string(name); - proc_ctx->hres = disp_call_value(proc_ctx->ctx, proc_ctx->reviver, jsval_obj(holder), - DISPATCH_METHOD, ARRAY_SIZE(args), args, &res); + proc_ctx->hres = disp_call_value(proc_ctx->ctx, proc_ctx->reviver, jsval_obj(holder), DISPATCH_METHOD, + ARRAY_SIZE(args), args, &res, &proc_ctx->ctx->jscaller->IServiceProvider_iface); return FAILED(proc_ctx->hres) ? jsval_undefined() : res; }
diff --git a/dlls/jscript/set.c b/dlls/jscript/set.c index eca26a890f7..cd2ef4bd269 100644 --- a/dlls/jscript/set.c +++ b/dlls/jscript/set.c @@ -208,7 +208,8 @@ static HRESULT iterate_map(MapInstance *map, script_ctx_t *ctx, unsigned argc, j args[1] = entry->key; args[2] = jsval_obj(&map->dispex); grab_map_entry(entry); - hres = disp_call_value(ctx, get_object(argv[0]), context_this, DISPATCH_METHOD, ARRAY_SIZE(args), args, &v); + hres = disp_call_value(ctx, get_object(argv[0]), context_this, DISPATCH_METHOD, ARRAY_SIZE(args), + args, &v, &ctx->jscaller->IServiceProvider_iface); iter = list_next(&map->entries, iter); release_map_entry(entry); if(FAILED(hres)) diff --git a/dlls/jscript/tests/run.c b/dlls/jscript/tests/run.c index 21f09474fee..c5d9c47e63c 100644 --- a/dlls/jscript/tests/run.c +++ b/dlls/jscript/tests/run.c @@ -114,6 +114,9 @@ DEFINE_EXPECT(testobj_newenum); DEFINE_EXPECT(testobj_getidfail_d); DEFINE_EXPECT(testobj_tolocalestr_d); DEFINE_EXPECT(testobj_tolocalestr_i); +DEFINE_EXPECT(test_caller_get); +DEFINE_EXPECT(test_caller_null); +DEFINE_EXPECT(test_caller_obj); DEFINE_EXPECT(testdestrobj); DEFINE_EXPECT(enumvariant_next_0); DEFINE_EXPECT(enumvariant_next_1); @@ -333,6 +336,44 @@ static IEnumVARIANTVtbl testEnumVARIANTVtbl = {
static IEnumVARIANT testEnumVARIANT = { &testEnumVARIANTVtbl };
+static HRESULT WINAPI sp_QueryInterface(IServiceProvider *iface, REFIID riid, void **ppv) +{ + if(IsEqualGUID(&IID_IUnknown, riid) || IsEqualGUID(&IID_IServiceProvider, riid)) { + *ppv = iface; + return S_OK; + } + + ok(0, "unexpected call %s\n", wine_dbgstr_guid(riid)); + *ppv = NULL; + return E_NOTIMPL; +} + +static ULONG WINAPI sp_AddRef(IServiceProvider *iface) +{ + return 2; +} + +static ULONG WINAPI sp_Release(IServiceProvider *iface) +{ + return 1; +} + +static HRESULT WINAPI sp_QueryService(IServiceProvider *iface, REFGUID guidService, REFIID riid, void **ppv) +{ + ok(0, "unexpected call %s\n", wine_dbgstr_guid(guidService)); + *ppv = NULL; + return E_NOTIMPL; +} + +static const IServiceProviderVtbl sp_vtbl = { + sp_QueryInterface, + sp_AddRef, + sp_Release, + sp_QueryService +}; + +static IServiceProvider sp_obj = { &sp_vtbl }; + static HRESULT WINAPI DispatchEx_QueryInterface(IDispatchEx *iface, REFIID riid, void **ppv) { *ppv = NULL; @@ -629,6 +670,61 @@ static IDispatchExVtbl testObjVtbl = {
static IDispatchEx testObj = { &testObjVtbl };
+static HRESULT WINAPI testcallerobj_InvokeEx(IDispatchEx *iface, DISPID id, LCID lcid, WORD wFlags, DISPPARAMS *pdp, + VARIANT *pvarRes, EXCEPINFO *pei, IServiceProvider *pspCaller) +{ + ok(id == DISPID_VALUE, "id = %ld\n", id); + ok(pdp != NULL, "pdp == NULL\n"); + ok(pvarRes != NULL, "pvarRes == NULL\n"); + ok(V_VT(pvarRes) == VT_EMPTY, "V_VT(pvarRes) = %d\n", V_VT(pvarRes)); + if(wFlags == DISPATCH_PROPERTYGET) { + CHECK_EXPECT(test_caller_get); + ok(!pdp->rgdispidNamedArgs, "rgdispidNamedArgs != NULL\n"); + ok(!pdp->cNamedArgs, "cNamedArgs = %d\n", pdp->cNamedArgs); + ok(pei != NULL, "pei == NULL\n"); + ok(pspCaller != NULL, "pspCaller == NULL\n"); + ok(pspCaller != &sp_obj, "pspCaller == sp_obj\n"); + V_VT(pvarRes) = VT_DISPATCH; + V_DISPATCH(pvarRes) = (IDispatch*)iface; + }else if(pspCaller) { + CHECK_EXPECT(test_caller_obj); + ok(wFlags == DISPATCH_METHOD, "wFlags = %04x\n", wFlags); + ok(pdp->rgdispidNamedArgs != NULL, "rgdispidNamedArgs == NULL\n"); + ok(pdp->cNamedArgs == 1, "cNamedArgs = %d\n", pdp->cNamedArgs); + ok(pspCaller == &sp_obj, "pspCaller != sp_obj\n"); + V_VT(pvarRes) = VT_I4; + V_I4(pvarRes) = 137; + }else { + CHECK_EXPECT(test_caller_null); + ok(wFlags == DISPATCH_METHOD, "wFlags = %04x\n", wFlags); + ok(pdp->rgdispidNamedArgs != NULL, "rgdispidNamedArgs == NULL\n"); + ok(pdp->cNamedArgs == 1, "cNamedArgs = %d\n", pdp->cNamedArgs); + V_VT(pvarRes) = VT_I4; + V_I4(pvarRes) = 42; + } + return S_OK; +} + +static IDispatchExVtbl testcallerobj_vtbl = { + DispatchEx_QueryInterface, + DispatchEx_AddRef, + DispatchEx_Release, + DispatchEx_GetTypeInfoCount, + DispatchEx_GetTypeInfo, + DispatchEx_GetIDsOfNames, + DispatchEx_Invoke, + DispatchEx_GetDispID, + testcallerobj_InvokeEx, + DispatchEx_DeleteMemberByName, + DispatchEx_DeleteMemberByDispID, + DispatchEx_GetMemberProperties, + DispatchEx_GetMemberName, + DispatchEx_GetNextDispID, + DispatchEx_GetNameSpaceParent +}; + +static IDispatchEx testcallerobj = { &testcallerobj_vtbl }; + static LONG test_destr_ref;
static ULONG WINAPI testDestrObj_AddRef(IDispatchEx *iface) @@ -3214,6 +3310,7 @@ static void test_script_exprs(void)
static void test_invokeex(void) { + static DISPID propput_dispid = DISPID_PROPERTYPUT; DISPPARAMS dp = {NULL}, dp_max = {NULL}; DISPID func_id, max_id, prop_id; IActiveScript *script; @@ -3442,6 +3539,52 @@ static void test_invokeex(void)
IDispatchEx_Release(dispex); IActiveScript_Release(script); + + /* test InvokeEx with host prop and custom caller */ + hres = parse_script_expr(L"var o = {}; o", &v, &script); + ok(hres == S_OK, "parse_script_expr failed: %08lx\n", hres); + ok(V_VT(&v) == VT_DISPATCH, "V_VT(v) = %d\n", V_VT(&v)); + + hres = IDispatch_QueryInterface(V_DISPATCH(&v), &IID_IDispatchEx, (void**)&dispex); + ok(hres == S_OK, "Could not get IDispatchEx iface: %08lx\n", hres); + VariantClear(&v); + + str = SysAllocString(L"caller"); + hres = IDispatchEx_GetDispID(dispex, str, fdexNameEnsure, &func_id); + SysFreeString(str); + ok(hres == S_OK, "GetDispID failed: %08lx\n", hres); + + SET_EXPECT(test_caller_get); + dp.cArgs = dp.cNamedArgs = 1; + dp.rgvarg = &arg; + dp.rgdispidNamedArgs = &propput_dispid; + V_VT(&arg) = VT_DISPATCH; + V_DISPATCH(&arg) = (IDispatch*)&testcallerobj; + hres = IDispatchEx_InvokeEx(dispex, func_id, 0, DISPATCH_PROPERTYPUT, &dp, NULL, NULL, NULL); + ok(hres == S_OK, "InvokeEx failed: %08lx\n", hres); + todo_wine + CHECK_CALLED(test_caller_get); + + SET_EXPECT(test_caller_null); + dp.cArgs = dp.cNamedArgs = 0; + dp.rgvarg = NULL; + dp.rgdispidNamedArgs = NULL; + hres = IDispatchEx_InvokeEx(dispex, func_id, 0, DISPATCH_METHOD, &dp, &v, NULL, NULL); + ok(hres == S_OK, "InvokeEx failed: %08lx\n", hres); + ok(V_VT(&v) == VT_I4, "V_VT(v) = %d\n", V_VT(&v)); + ok(V_I4(&v) == 42, "V_I4(v) = %s\n", wine_dbgstr_variant(&v)); + CHECK_CALLED(test_caller_null); + V_VT(&v) = VT_EMPTY; + + SET_EXPECT(test_caller_obj); + hres = IDispatchEx_InvokeEx(dispex, func_id, 0, DISPATCH_METHOD, &dp, &v, NULL, &sp_obj); + ok(hres == S_OK, "InvokeEx failed: %08lx\n", hres); + ok(V_VT(&v) == VT_I4, "V_VT(v) = %d\n", V_VT(&v)); + ok(V_I4(&v) == 137, "V_I4(v) = %s\n", wine_dbgstr_variant(&v)); + CHECK_CALLED(test_caller_obj); + + IDispatchEx_Release(dispex); + IActiveScript_Release(script); }
static void test_destructors(void)