Jacek Caban : jscript: Store match result in script context.
Alexandre Julliard
julliard at winehq.org
Thu May 27 10:46:39 CDT 2010
Module: wine
Branch: master
Commit: 32c61c5092e76c9f50655b92880c4033fc78b3d6
URL: http://source.winehq.org/git/wine.git/?a=commit;h=32c61c5092e76c9f50655b92880c4033fc78b3d6
Author: Jacek Caban <jacek at codeweavers.com>
Date: Wed May 26 19:18:18 2010 +0200
jscript: Store match result in script context.
---
dlls/jscript/jscript.c | 1 +
dlls/jscript/jscript.h | 4 ++++
dlls/jscript/regexp.c | 23 +++++++++++++++++++++--
dlls/jscript/string.c | 27 +++++++++++++++++++++------
4 files changed, 47 insertions(+), 8 deletions(-)
diff --git a/dlls/jscript/jscript.c b/dlls/jscript/jscript.c
index 9a516aa..c7c77e3 100644
--- a/dlls/jscript/jscript.c
+++ b/dlls/jscript/jscript.c
@@ -71,6 +71,7 @@ void script_release(script_ctx_t *ctx)
return;
jsheap_free(&ctx->tmp_heap);
+ SysFreeString(ctx->last_match);
heap_free(ctx);
}
diff --git a/dlls/jscript/jscript.h b/dlls/jscript/jscript.h
index c58c05d..901f25d 100644
--- a/dlls/jscript/jscript.h
+++ b/dlls/jscript/jscript.h
@@ -272,6 +272,10 @@ struct _script_ctx_t {
IDispatch *host_global;
+ BSTR last_match;
+ DWORD last_match_index;
+ DWORD last_match_length;
+
DispatchEx *global;
DispatchEx *function_constr;
DispatchEx *activex_constr;
diff --git a/dlls/jscript/regexp.c b/dlls/jscript/regexp.c
index da23f5c..c4c7225 100644
--- a/dlls/jscript/regexp.c
+++ b/dlls/jscript/regexp.c
@@ -3348,8 +3348,6 @@ static HRESULT do_regexp_match_next(script_ctx_t *ctx, RegExpInstance *regexp, D
}
if(parens) {
- DWORD i;
-
if(regexp->jsregexp->parenCount > *parens_size) {
match_result_t *new_parens;
@@ -3362,6 +3360,22 @@ static HRESULT do_regexp_match_next(script_ctx_t *ctx, RegExpInstance *regexp, D
*parens = new_parens;
}
+ }
+
+ /* FIXME: We often already have a copy of input string that we could use to store last match */
+ if(!(rem_flags & REM_NO_CTX_UPDATE) &&
+ (!ctx->last_match || len != SysStringLen(ctx->last_match) || strncmpW(ctx->last_match, str, len))) {
+ BSTR last_match;
+
+ last_match = SysAllocStringLen(str, len);
+ if(!last_match)
+ return E_OUTOFMEMORY;
+ SysFreeString(ctx->last_match);
+ ctx->last_match = last_match;
+ }
+
+ if(parens) {
+ DWORD i;
*parens_cnt = regexp->jsregexp->parenCount;
@@ -3382,6 +3396,11 @@ static HRESULT do_regexp_match_next(script_ctx_t *ctx, RegExpInstance *regexp, D
ret->len = matchlen;
set_last_index(regexp, result->cp-str);
+ if(!(rem_flags & REM_NO_CTX_UPDATE)) {
+ ctx->last_match_index = ret->str-str;
+ ctx->last_match_length = matchlen;
+ }
+
return S_OK;
}
diff --git a/dlls/jscript/string.c b/dlls/jscript/string.c
index 510dcc2..05b9eba 100644
--- a/dlls/jscript/string.c
+++ b/dlls/jscript/string.c
@@ -779,9 +779,9 @@ static HRESULT String_replace(script_ctx_t *ctx, vdisp_t *jsthis, WORD flags, DI
DWORD parens_cnt = 0, parens_size=0, rep_len=0, length;
BSTR rep_str = NULL, match_str = NULL, ret_str, val_str;
DispatchEx *rep_func = NULL, *regexp = NULL;
- match_result_t *parens = NULL, match, **parens_ptr = &parens;
+ match_result_t *parens = NULL, match = {NULL,0}, **parens_ptr = &parens;
strbuf_t ret = {NULL,0,0};
- DWORD re_flags = 0;
+ DWORD re_flags = REM_NO_CTX_UPDATE;
VARIANT *arg_var;
HRESULT hres = S_OK;
@@ -860,7 +860,7 @@ static HRESULT String_replace(script_ctx_t *ctx, vdisp_t *jsthis, WORD flags, DI
if(regexp) {
hres = regexp_match_next(ctx, regexp, re_flags, str, length, &cp, parens_ptr,
&parens_size, &parens_cnt, &match);
- re_flags = REM_CHECK_GLOBAL;
+ re_flags |= REM_CHECK_GLOBAL;
if(hres == S_FALSE) {
hres = S_OK;
@@ -969,13 +969,28 @@ static HRESULT String_replace(script_ctx_t *ctx, vdisp_t *jsthis, WORD flags, DI
if(rep_func)
jsdisp_release(rep_func);
- if(regexp)
- jsdisp_release(regexp);
- SysFreeString(val_str);
SysFreeString(rep_str);
SysFreeString(match_str);
heap_free(parens);
+ if(SUCCEEDED(hres) && match.str && regexp) {
+ if(!val_str)
+ val_str = SysAllocStringLen(str, length);
+ if(val_str) {
+ SysFreeString(ctx->last_match);
+ ctx->last_match = val_str;
+ val_str = NULL;
+ ctx->last_match_index = match.str-str;
+ ctx->last_match_length = match.len;
+ }else {
+ hres = E_OUTOFMEMORY;
+ }
+ }
+
+ if(regexp)
+ jsdisp_release(regexp);
+ SysFreeString(val_str);
+
if(SUCCEEDED(hres) && retv) {
ret_str = SysAllocStringLen(ret.buf, ret.len);
if(!ret_str)
More information about the wine-cvs
mailing list