vbscript: Fix handling missing description in EXCEPINFO.

Based on patch by Kevin Puetz.
This commit is contained in:
Jacek Caban 2022-09-21 23:17:02 +02:00 committed by Alexandre Julliard
parent b3ec117b1d
commit d8a03ae630
2 changed files with 135 additions and 4 deletions

View file

@ -2490,14 +2490,19 @@ HRESULT exec_script(script_ctx_t *ctx, BOOL extern_caller, function_t *func, vbd
if(FAILED(hres)) {
if(hres != SCRIPT_E_RECORDED) {
clear_ei(&ctx->ei);
ctx->ei.scode = hres = map_hres(hres);
ctx->ei.bstrSource = get_vbscript_string(VBS_RUNTIME_ERROR);
ctx->ei.bstrDescription = get_vbscript_error_string(hres);
hres = map_hres(hres);
}else if(!ctx->ei.bstrDescription) {
hres = map_hres(ctx->ei.scode);
}else {
hres = ctx->ei.scode;
}
ctx->ei.scode = hres;
if(!ctx->ei.bstrSource)
ctx->ei.bstrSource = get_vbscript_string(VBS_RUNTIME_ERROR);
if(!ctx->ei.bstrDescription)
ctx->ei.bstrDescription = get_vbscript_error_string(hres);
if(exec.resume_next) {
unsigned stack_off;

View file

@ -145,6 +145,7 @@ DEFINE_EXPECT(OnLeaveScript);
#define DISPID_GLOBAL_THROWWITHDESC 1024
#define DISPID_GLOBAL_PROPARGSET 1025
#define DISPID_GLOBAL_UNKOBJ 1026
#define DISPID_GLOBAL_THROWEXCEPTION 1027
#define DISPID_TESTOBJ_PROPGET 2000
#define DISPID_TESTOBJ_PROPPUT 2001
@ -1157,6 +1158,7 @@ static HRESULT WINAPI Global_GetDispID(IDispatchEx *iface, BSTR bstrName, DWORD
{ L"counter", DISPID_GLOBAL_COUNTER },
{ L"doubleAsString", DISPID_GLOBAL_DOUBLEASSTRING },
{ L"testArray", DISPID_GLOBAL_TESTARRAY },
{ L"throwException", DISPID_GLOBAL_THROWEXCEPTION },
{ L"throwInt", DISPID_GLOBAL_THROWINT },
{ L"testOptionalArg", DISPID_GLOBAL_TESTOPTIONALARG },
{ L"testErrorObject", DISPID_GLOBAL_TESTERROROBJECT },
@ -1540,6 +1542,54 @@ static HRESULT WINAPI Global_InvokeEx(IDispatchEx *iface, DISPID id, LCID lcid,
return hres;
case DISPID_GLOBAL_THROWEXCEPTION: {
VARIANT *v = pdp->rgvarg + pdp->cArgs - 1;
ok((wFlags & ~INVOKE_PROPERTYGET) == INVOKE_FUNC, "wFlags = %x\n", wFlags);
ok(pdp != NULL, "pdp == NULL\n");
ok(pdp->rgvarg != NULL, "rgvarg == NULL\n");
ok(!pdp->rgdispidNamedArgs, "rgdispidNamedArgs != NULL\n");
ok(pdp->cArgs >= 1, "cArgs = %d\n", pdp->cArgs);
ok(!pdp->cNamedArgs, "cNamedArgs = %d\n", pdp->cNamedArgs);
ok(pei != NULL, "pei == NULL\n");
if(pvarRes) {
ok(V_VT(pvarRes) == VT_EMPTY, "V_VT(pvarRes) = %d\n", V_VT(pvarRes));
V_VT(pvarRes) = VT_BOOL;
V_BOOL(pvarRes) = VARIANT_FALSE;
}
if(V_VT(v) == (VT_VARIANT|VT_BYREF))
v = V_VARIANTREF(v);
memset(pei, 0, sizeof(*pei));
switch(V_VT(v)) {
case VT_I2:
pei->scode = V_I2(v);
break;
case VT_I4:
pei->scode = V_I4(v);
break;
default:
ok(0, "unexpected vt %d\n", V_VT(v));
return E_INVALIDARG;
}
if(pdp->cArgs >= 2) {
v = pdp->rgvarg + pdp->cArgs - 2;
ok(V_VT(v) == VT_BSTR, "v = %s\n", debugstr_variant(v));
pei->bstrSource = SysAllocString(V_BSTR(v));
}
if(pdp->cArgs >= 3) {
v = pdp->rgvarg + pdp->cArgs - 3;
ok(V_VT(v) == VT_BSTR, "v = %s\n", debugstr_variant(v));
pei->bstrDescription = SysAllocString(V_BSTR(v));
}
return DISP_E_EXCEPTION;
}
case DISPID_GLOBAL_THROWWITHDESC:
pei->scode = 0xdeadbeef;
pei->bstrDescription = SysAllocString(L"test");
@ -2351,6 +2401,82 @@ static void test_callbacks(void)
IActiveScriptParse_Release(parser);
close_script(script);
strict_enter_script = FALSE;
store_script_error = &error1;
SET_EXPECT(OnScriptError);
hres = parse_script_ar("throwException &h80004002&");
ok(hres == MAKE_VBSERROR(430), "got error: %08lx\n", hres);
CHECK_CALLED(OnScriptError);
memset(&ei, 0xcc, sizeof(ei));
hres = IActiveScriptError_GetExceptionInfo(error1, &ei);
ok(hres == S_OK, "GetExceptionInfo returned %08lx\n", hres);
ok(!ei.wCode, "wCode = %x\n", ei.wCode);
ok(!ei.wReserved, "wReserved = %x\n", ei.wReserved);
if(is_english) {
ok(!wcscmp(ei.bstrSource, L"Microsoft VBScript runtime error"),
"bstrSource = %s\n", wine_dbgstr_w(ei.bstrSource));
ok(!wcscmp(ei.bstrDescription, L"Class doesn't support Automation"),
"bstrDescription = %s\n", wine_dbgstr_w(ei.bstrDescription));
}
ok(!ei.bstrHelpFile, "bstrHelpFile = %s\n", wine_dbgstr_w(ei.bstrHelpFile));
ok(!ei.dwHelpContext, "dwHelpContext = %lx\n", ei.dwHelpContext);
ok(!ei.pvReserved, "pvReserved = %p\n", ei.pvReserved);
ok(!ei.pfnDeferredFillIn, "pfnDeferredFillIn = %p\n", ei.pfnDeferredFillIn);
ok(ei.scode == MAKE_VBSERROR(430), "scode = %lx\n", ei.scode);
free_ei(&ei);
IActiveScriptError_Release(error1);
store_script_error = &error1;
SET_EXPECT(OnScriptError);
hres = parse_script_ar("throwException &h80004002&, \"test src\"");
ok(hres == MAKE_VBSERROR(430), "got error: %08lx\n", hres);
CHECK_CALLED(OnScriptError);
memset(&ei, 0xcc, sizeof(ei));
hres = IActiveScriptError_GetExceptionInfo(error1, &ei);
ok(hres == S_OK, "GetExceptionInfo returned %08lx\n", hres);
ok(!ei.wCode, "wCode = %x\n", ei.wCode);
ok(!ei.wReserved, "wReserved = %x\n", ei.wReserved);
if(is_english) {
ok(!wcscmp(ei.bstrSource, L"test src"), "bstrSource = %s\n", wine_dbgstr_w(ei.bstrSource));
ok(!wcscmp(ei.bstrDescription, L"Class doesn't support Automation"),
"bstrDescription = %s\n", wine_dbgstr_w(ei.bstrDescription));
}
ok(!ei.bstrHelpFile, "bstrHelpFile = %s\n", wine_dbgstr_w(ei.bstrHelpFile));
ok(!ei.dwHelpContext, "dwHelpContext = %lx\n", ei.dwHelpContext);
ok(!ei.pvReserved, "pvReserved = %p\n", ei.pvReserved);
ok(!ei.pfnDeferredFillIn, "pfnDeferredFillIn = %p\n", ei.pfnDeferredFillIn);
ok(ei.scode == MAKE_VBSERROR(430), "scode = %lx\n", ei.scode);
free_ei(&ei);
IActiveScriptError_Release(error1);
store_script_error = &error1;
SET_EXPECT(OnScriptError);
hres = parse_script_ar("throwException &h80004002&, \"test src\", \"test desc\"");
ok(hres == E_NOINTERFACE, "got error: %08lx\n", hres);
CHECK_CALLED(OnScriptError);
memset(&ei, 0xcc, sizeof(ei));
hres = IActiveScriptError_GetExceptionInfo(error1, &ei);
ok(hres == S_OK, "GetExceptionInfo returned %08lx\n", hres);
ok(!ei.wCode, "wCode = %x\n", ei.wCode);
ok(!ei.wReserved, "wReserved = %x\n", ei.wReserved);
if(is_english) {
ok(!wcscmp(ei.bstrSource, L"test src"), "bstrSource = %s\n", wine_dbgstr_w(ei.bstrSource));
ok(!wcscmp(ei.bstrDescription, L"test desc"),
"bstrDescription = %s\n", wine_dbgstr_w(ei.bstrDescription));
}
ok(!ei.bstrHelpFile, "bstrHelpFile = %s\n", wine_dbgstr_w(ei.bstrHelpFile));
ok(!ei.dwHelpContext, "dwHelpContext = %lx\n", ei.dwHelpContext);
ok(!ei.pvReserved, "pvReserved = %p\n", ei.pvReserved);
ok(!ei.pfnDeferredFillIn, "pfnDeferredFillIn = %p\n", ei.pfnDeferredFillIn);
ok(ei.scode == E_NOINTERFACE, "scode = %lx\n", ei.scode);
free_ei(&ei);
IActiveScriptError_Release(error1);
}
static void test_gc(void)