Module: wine Branch: master Commit: 9e523c61304213792812ece5a47fa1ad680be749 URL: http://source.winehq.org/git/wine.git/?a=commit;h=9e523c61304213792812ece5a4...
Author: Jacek Caban jacek@codeweavers.com Date: Wed Sep 23 16:09:22 2009 +0200
jscript: Added RegExp function call implementation.
---
dlls/jscript/error.c | 24 +++++++++++++++++++----- dlls/jscript/jscript.h | 2 ++ dlls/jscript/jscript_En.rc | 1 + dlls/jscript/regexp.c | 33 +++++++++++++++++++++++++++++++-- dlls/jscript/resource.h | 1 + dlls/jscript/tests/api.js | 1 + dlls/jscript/tests/regexp.js | 12 ++++++++++++ 7 files changed, 67 insertions(+), 7 deletions(-)
diff --git a/dlls/jscript/error.c b/dlls/jscript/error.c index 2aa5436..bced477 100644 --- a/dlls/jscript/error.c +++ b/dlls/jscript/error.c @@ -310,6 +310,14 @@ static HRESULT ReferenceErrorConstr_value(DispatchEx *dispex, LCID lcid, WORD fl dispex->ctx->reference_error_constr); }
+static HRESULT RegExpErrorConstr_value(DispatchEx *dispex, LCID lcid, WORD flags, + DISPPARAMS *dp, VARIANT *retv, jsexcept_t *ei, IServiceProvider *sp) +{ + TRACE("\n"); + return error_constr(dispex, flags, dp, retv, ei, + dispex->ctx->regexp_error_constr); +} + static HRESULT SyntaxErrorConstr_value(DispatchEx *dispex, LCID lcid, WORD flags, DISPPARAMS *dp, VARIANT *retv, jsexcept_t *ei, IServiceProvider *sp) { @@ -341,25 +349,26 @@ HRESULT init_error_constr(script_ctx_t *ctx, DispatchEx *object_prototype) static const WCHAR EvalErrorW[] = {'E','v','a','l','E','r','r','o','r',0}; static const WCHAR RangeErrorW[] = {'R','a','n','g','e','E','r','r','o','r',0}; static const WCHAR ReferenceErrorW[] = {'R','e','f','e','r','e','n','c','e','E','r','r','o','r',0}; + static const WCHAR RegExpErrorW[] = {'R','e','g','E','x','p','E','r','r','o','r',0}; static const WCHAR SyntaxErrorW[] = {'S','y','n','t','a','x','E','r','r','o','r',0}; static const WCHAR TypeErrorW[] = {'T','y','p','e','E','r','r','o','r',0}; static const WCHAR URIErrorW[] = {'U','R','I','E','r','r','o','r',0}; static const WCHAR *names[] = {ErrorW, EvalErrorW, RangeErrorW, - ReferenceErrorW, SyntaxErrorW, TypeErrorW, URIErrorW}; + ReferenceErrorW, RegExpErrorW, SyntaxErrorW, TypeErrorW, URIErrorW}; DispatchEx **constr_addr[] = {&ctx->error_constr, &ctx->eval_error_constr, - &ctx->range_error_constr, &ctx->reference_error_constr, + &ctx->range_error_constr, &ctx->reference_error_constr, &ctx->regexp_error_constr, &ctx->syntax_error_constr, &ctx->type_error_constr, &ctx->uri_error_constr}; static builtin_invoke_t constr_val[] = {ErrorConstr_value, EvalErrorConstr_value, - RangeErrorConstr_value, ReferenceErrorConstr_value, SyntaxErrorConstr_value, - TypeErrorConstr_value, URIErrorConstr_value}; + RangeErrorConstr_value, ReferenceErrorConstr_value, RegExpErrorConstr_value, + SyntaxErrorConstr_value, TypeErrorConstr_value, URIErrorConstr_value};
ErrorInstance *err; INT i; VARIANT v; HRESULT hres;
- for(i=0; i<7; i++) { + for(i=0; i < sizeof(names)/sizeof(names[0]); i++) { hres = alloc_error(ctx, i==0 ? object_prototype : NULL, NULL, &err); if(FAILED(hres)) return hres; @@ -433,6 +442,11 @@ HRESULT throw_reference_error(script_ctx_t *ctx, jsexcept_t *ei, UINT id, const return throw_error(ctx, ei, id, str, ctx->reference_error_constr); }
+HRESULT throw_regexp_error(script_ctx_t *ctx, jsexcept_t *ei, UINT id, const WCHAR *str) +{ + return throw_error(ctx, ei, id, str, ctx->regexp_error_constr); +} + HRESULT throw_syntax_error(script_ctx_t *ctx, jsexcept_t *ei, UINT id, const WCHAR *str) { return throw_error(ctx, ei, id, str, ctx->syntax_error_constr); diff --git a/dlls/jscript/jscript.h b/dlls/jscript/jscript.h index f09e257..6f861b8 100644 --- a/dlls/jscript/jscript.h +++ b/dlls/jscript/jscript.h @@ -151,6 +151,7 @@ HRESULT Function_value(DispatchEx*,LCID,WORD,DISPPARAMS*,VARIANT*,jsexcept_t*,IS HRESULT throw_eval_error(script_ctx_t*,jsexcept_t*,UINT,const WCHAR*); HRESULT throw_range_error(script_ctx_t*,jsexcept_t*,UINT,const WCHAR*); HRESULT throw_reference_error(script_ctx_t*,jsexcept_t*,UINT,const WCHAR*); +HRESULT throw_regexp_error(script_ctx_t*,jsexcept_t*,UINT,const WCHAR*); HRESULT throw_syntax_error(script_ctx_t*,jsexcept_t*,UINT,const WCHAR*); HRESULT throw_type_error(script_ctx_t*,jsexcept_t*,UINT,const WCHAR*); HRESULT throw_uri_error(script_ctx_t*,jsexcept_t*,UINT,const WCHAR*); @@ -208,6 +209,7 @@ struct _script_ctx_t { DispatchEx *eval_error_constr; DispatchEx *range_error_constr; DispatchEx *reference_error_constr; + DispatchEx *regexp_error_constr; DispatchEx *syntax_error_constr; DispatchEx *type_error_constr; DispatchEx *uri_error_constr; diff --git a/dlls/jscript/jscript_En.rc b/dlls/jscript/jscript_En.rc index eca9bc8..b7f8744 100644 --- a/dlls/jscript/jscript_En.rc +++ b/dlls/jscript/jscript_En.rc @@ -38,5 +38,6 @@ STRINGTABLE DISCARDABLE IDS_ILLEGAL_ASSIGN "Illegal assignment" IDS_UNDEFINED "'|' is undefined" IDS_NOT_BOOL "Boolean object expected" + IDS_REGEXP_SYNTAX_ERROR "Syntax error in regular expression" IDS_INVALID_LENGTH "Array length must be a finite positive integer" } diff --git a/dlls/jscript/regexp.c b/dlls/jscript/regexp.c index 1c017b0..28154da 100644 --- a/dlls/jscript/regexp.c +++ b/dlls/jscript/regexp.c @@ -3819,8 +3819,12 @@ static HRESULT regexp_constructor(script_ctx_t *ctx, DISPPARAMS *dp, VARIANT *re if(FAILED(hres)) return hres;
- V_VT(retv) = VT_DISPATCH; - V_DISPATCH(retv) = (IDispatch*)_IDispatchEx_(ret); + if(retv) { + V_VT(retv) = VT_DISPATCH; + V_DISPATCH(retv) = (IDispatch*)_IDispatchEx_(ret); + }else { + jsdisp_release(ret); + } return S_OK; }
@@ -3830,6 +3834,31 @@ static HRESULT RegExpConstr_value(DispatchEx *dispex, LCID lcid, WORD flags, DIS TRACE("\n");
switch(flags) { + case DISPATCH_METHOD: + if(arg_cnt(dp)) { + VARIANT *arg = get_arg(dp,0); + if(V_VT(arg) == VT_DISPATCH) { + DispatchEx *jsdisp = iface_to_jsdisp((IUnknown*)V_DISPATCH(arg)); + if(jsdisp) { + if(is_class(jsdisp, JSCLASS_REGEXP)) { + if(arg_cnt(dp) > 1 && V_VT(get_arg(dp,1)) != VT_EMPTY) { + jsdisp_release(jsdisp); + return throw_regexp_error(dispex->ctx, ei, IDS_REGEXP_SYNTAX_ERROR, NULL); + } + + if(retv) { + V_VT(retv) = VT_DISPATCH; + V_DISPATCH(retv) = (IDispatch*)_IDispatchEx_(jsdisp); + }else { + jsdisp_release(jsdisp); + } + return S_OK; + } + jsdisp_release(jsdisp); + } + } + } + /* fall through */ case DISPATCH_CONSTRUCT: return regexp_constructor(dispex->ctx, dp, retv); default: diff --git a/dlls/jscript/resource.h b/dlls/jscript/resource.h index 2749bd6..9e33ebc 100644 --- a/dlls/jscript/resource.h +++ b/dlls/jscript/resource.h @@ -34,4 +34,5 @@ #define IDS_ILLEGAL_ASSIGN 0x1390 #define IDS_UNDEFINED 0x1391 #define IDS_NOT_BOOL 0x1392 +#define IDS_REGEXP_SYNTAX_ERROR 0x1399 #define IDS_INVALID_LENGTH 0x13A5 diff --git a/dlls/jscript/tests/api.js b/dlls/jscript/tests/api.js index 7a39d0f..7b22212 100644 --- a/dlls/jscript/tests/api.js +++ b/dlls/jscript/tests/api.js @@ -1617,6 +1617,7 @@ exception_test(function() {eval("while(")}, "SyntaxError", -2146827286); exception_test(function() {eval("if(")}, "SyntaxError", -2146827286); exception_test(function() {eval("'unterminated")}, "SyntaxError", -2146827273); exception_test(function() {eval("nonexistingfunc()")}, "TypeError", -2146823281); +exception_test(function() {RegExp(/a/, "g");}, "RegExpError", -2146823271);
function testObjectInherit(obj, constr, ts, tls, vo) { ok(obj instanceof Object, "obj is not instance of Object"); diff --git a/dlls/jscript/tests/regexp.js b/dlls/jscript/tests/regexp.js index a839adb..ff98b48 100644 --- a/dlls/jscript/tests/regexp.js +++ b/dlls/jscript/tests/regexp.js @@ -286,4 +286,16 @@ ok(re.source === "abc[^d]", "re.source = '" + re.source + "', expected 'abc[^d]' re = /a\bc[^d]/g; ok(re.source === "a\bc[^d]", "re.source = '" + re.source + "', expected 'a\bc[^d]'");
+re = /abc/; +ok(re === RegExp(re), "re !== RegExp(re)"); + +re = RegExp("abc[^d]", "g"); +ok(re.source === "abc[^d]", "re.source = '" + re.source + "', expected 'abc[^d]'"); + +re = /abc/; +ok(re === RegExp(re, undefined), "re !== RegExp(re, undefined)"); + +re = /abc/; +ok(re === RegExp(re, undefined, 1), "re !== RegExp(re, undefined, 1)"); + reportSuccess();