From 13d8e7b85329ab99d87bfa690ea2bfa5337f7149 Mon Sep 17 00:00:00 2001 From: Jacek Caban Date: Mon, 19 Sep 2011 14:09:21 +0200 Subject: [PATCH] vbscript: Added error object stub implementation. --- dlls/vbscript/Makefile.in | 1 + dlls/vbscript/error.c | 37 +++++++++++++++++++++++++++++++++++++ dlls/vbscript/global.c | 2 +- dlls/vbscript/interp.c | 27 ++++++++++++++++++++++++++- dlls/vbscript/tests/api.vbs | 2 ++ dlls/vbscript/vbscript.c | 2 ++ dlls/vbscript/vbscript.h | 4 ++++ 7 files changed, 73 insertions(+), 2 deletions(-) create mode 100644 dlls/vbscript/error.c diff --git a/dlls/vbscript/Makefile.in b/dlls/vbscript/Makefile.in index e1a83820596..2da0c33a6e5 100644 --- a/dlls/vbscript/Makefile.in +++ b/dlls/vbscript/Makefile.in @@ -3,6 +3,7 @@ IMPORTS = oleaut32 C_SRCS = \ compile.c \ + error.c \ global.c \ interp.c \ lex.c \ diff --git a/dlls/vbscript/error.c b/dlls/vbscript/error.c new file mode 100644 index 00000000000..5d7efd0a3d5 --- /dev/null +++ b/dlls/vbscript/error.c @@ -0,0 +1,37 @@ +/* + * Copyright 2011 Jacek Caban for CodeWeavers + * + * This library is free software; you can redistribute it and/or + * modify it under the terms of the GNU Lesser General Public + * License as published by the Free Software Foundation; either + * version 2.1 of the License, or (at your option) any later version. + * + * This library is distributed in the hope that it will be useful, + * but WITHOUT ANY WARRANTY; without even the implied warranty of + * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the GNU + * Lesser General Public License for more details. + * + * You should have received a copy of the GNU Lesser General Public + * License along with this library; if not, write to the Free Software + * Foundation, Inc., 51 Franklin St, Fifth Floor, Boston, MA 02110-1301, USA + */ + +#include "vbscript.h" +#include "vbscript_defs.h" + +#include "wine/debug.h" + +WINE_DEFAULT_DEBUG_CHANNEL(vbscript); + +HRESULT init_err(script_ctx_t *ctx) +{ + HRESULT hres; + + ctx->err_desc.ctx = ctx; + + hres = get_typeinfo(ErrObj_tid, &ctx->err_desc.typeinfo); + if(FAILED(hres)) + return hres; + + return create_vbdisp(&ctx->err_desc, &ctx->err_obj); +} diff --git a/dlls/vbscript/global.c b/dlls/vbscript/global.c index 987620826c7..3d58ea7f9cc 100644 --- a/dlls/vbscript/global.c +++ b/dlls/vbscript/global.c @@ -1399,5 +1399,5 @@ HRESULT init_global(script_ctx_t *ctx) if(FAILED(hres)) return hres; - return S_OK; + return init_err(ctx); } diff --git a/dlls/vbscript/interp.c b/dlls/vbscript/interp.c index 7c3df7db48b..306c2a21c76 100644 --- a/dlls/vbscript/interp.c +++ b/dlls/vbscript/interp.c @@ -48,6 +48,7 @@ typedef enum { REF_NONE, REF_DISP, REF_VAR, + REF_OBJ, REF_FUNC } ref_type_t; @@ -60,6 +61,7 @@ typedef struct { } d; VARIANT *v; function_t *f; + IDispatch *obj; } u; } ref_t; @@ -92,6 +94,8 @@ static HRESULT lookup_identifier(exec_ctx_t *ctx, BSTR name, vbdisp_invoke_type_ DISPID id; HRESULT hres; + static const WCHAR errW[] = {'e','r','r',0}; + if(invoke_type == VBDISP_LET && (ctx->func->type == FUNC_FUNCTION || ctx->func->type == FUNC_PROPGET || ctx->func->type == FUNC_DEFGET) && !strcmpiW(name, ctx->func->name)) { @@ -147,6 +151,12 @@ static HRESULT lookup_identifier(exec_ctx_t *ctx, BSTR name, vbdisp_invoke_type_ } } + if(!strcmpiW(name, errW)) { + ref->type = REF_OBJ; + ref->u.obj = (IDispatch*)&ctx->script->err_obj->IDispatchEx_iface; + return S_OK; + } + hres = vbdisp_get_id(ctx->script->global_obj, name, invoke_type, TRUE, &id); if(SUCCEEDED(hres)) { ref->type = REF_DISP; @@ -291,8 +301,8 @@ static HRESULT do_icall(exec_ctx_t *ctx, VARIANT *res) { BSTR identifier = ctx->instr->arg1.bstr; const unsigned arg_cnt = ctx->instr->arg2.uint; - ref_t ref = {0}; DISPPARAMS dp; + ref_t ref; HRESULT hres; hres = lookup_identifier(ctx, identifier, VBDISP_CALLGET, &ref); @@ -326,6 +336,18 @@ static HRESULT do_icall(exec_ctx_t *ctx, VARIANT *res) if(FAILED(hres)) return hres; break; + case REF_OBJ: + if(arg_cnt) { + FIXME("arguments on object\n"); + return E_NOTIMPL; + } + + if(res) { + IDispatch_AddRef(ref.u.obj); + V_VT(res) = VT_DISPATCH; + V_DISPATCH(res) = ref.u.obj; + } + break; case REF_NONE: FIXME("%s not found\n", debugstr_w(identifier)); return DISP_E_UNKNOWNNAME; @@ -440,6 +462,9 @@ static HRESULT assign_ident(exec_ctx_t *ctx, BSTR name, VARIANT *val, BOOL own_v case REF_FUNC: FIXME("functions not implemented\n"); return E_NOTIMPL; + case REF_OBJ: + FIXME("REF_OBJ\n"); + return E_NOTIMPL; case REF_NONE: FIXME("%s not found\n", debugstr_w(name)); if(own_val) diff --git a/dlls/vbscript/tests/api.vbs b/dlls/vbscript/tests/api.vbs index 2b2cf6407f6..3b928037c6a 100644 --- a/dlls/vbscript/tests/api.vbs +++ b/dlls/vbscript/tests/api.vbs @@ -32,4 +32,6 @@ Call ok(not isObject(4), "isObject(4) is true?") Call ok(not isObject("x"), "isObject(""x"") is true?") Call ok(not isObject(Null), "isObject(Null) is true?") +Call ok(getVT(err) = "VT_DISPATCH", "getVT(err) = " & getVT(err)) + Call reportSuccess() diff --git a/dlls/vbscript/vbscript.c b/dlls/vbscript/vbscript.c index 9b61b936ac2..c9fa3d00f40 100644 --- a/dlls/vbscript/vbscript.c +++ b/dlls/vbscript/vbscript.c @@ -131,6 +131,8 @@ static void destroy_script(script_ctx_t *ctx) IDispatch_Release(ctx->host_global); if(ctx->site) IActiveScriptSite_Release(ctx->site); + if(ctx->err_obj) + IDispatchEx_Release(&ctx->err_obj->IDispatchEx_iface); if(ctx->global_obj) IDispatchEx_Release(&ctx->global_obj->IDispatchEx_iface); if(ctx->script_obj) diff --git a/dlls/vbscript/vbscript.h b/dlls/vbscript/vbscript.h index 5bd7ff9f26a..dc842cf19d3 100644 --- a/dlls/vbscript/vbscript.h +++ b/dlls/vbscript/vbscript.h @@ -150,6 +150,9 @@ struct _script_ctx_t { class_desc_t global_desc; vbdisp_t *global_obj; + class_desc_t err_desc; + vbdisp_t *err_obj; + dynamic_var_t *global_vars; function_t *global_funcs; class_desc_t *classes; @@ -160,6 +163,7 @@ struct _script_ctx_t { }; HRESULT init_global(script_ctx_t*); +HRESULT init_err(script_ctx_t*); typedef enum { ARG_NONE = 0,