Reviewed by Darin and Adam.
<rdar://problem/5368990> REGRESSION: newsgator.com sign-on 6x slower than Safari 3 beta due to GC changes (14808)
* kjs/string_object.cpp:
(KJS::replace): if the string didn't change (very common in some cases) reuse the original string value.
(KJS::StringProtoFunc::callAsFunction): Pass in the StringImp* when replacing, not just the UString.
* kjs/string_object.h:
(KJS::StringInstance::internalValue): covariant override to return StringImp for convenience
git-svn-id: http://svn.webkit.org/repository/webkit/trunk@24873 268f45cc-cd09-0410-ab3c-d52691b4dbfc
diff --git a/JavaScriptCore/kjs/string_object.cpp b/JavaScriptCore/kjs/string_object.cpp
index 5affa19..bfa723e 100644
--- a/JavaScriptCore/kjs/string_object.cpp
+++ b/JavaScriptCore/kjs/string_object.cpp
@@ -313,8 +313,9 @@
#endif
}
-static JSValue *replace(ExecState *exec, const UString &source, JSValue *pattern, JSValue *replacement)
+static JSValue *replace(ExecState *exec, StringImp* sourceVal, JSValue *pattern, JSValue *replacement)
{
+ UString source = sourceVal->value();
JSObject *replacementFunction = 0;
UString replacementString;
@@ -365,7 +366,7 @@
}
args.append(jsNumber(completeMatchStart));
- args.append(jsString(source));
+ args.append(sourceVal);
substitutedReplacement = replacementFunction->call(exec, exec->dynamicInterpreter()->globalObject(),
args)->toString(exec);
@@ -389,12 +390,16 @@
pushSourceRange(sourceRanges, sourceRangeCount, sourceRangeCapacity, UString::Range(lastIndex, source.size() - lastIndex));
UString result;
+
if (sourceRanges)
result = source.spliceSubstringsWithSeparators(sourceRanges, sourceRangeCount, replacements, replacementCount);
delete [] sourceRanges;
delete [] replacements;
+ if (result == source)
+ return sourceVal;
+
return jsString(result);
}
@@ -404,14 +409,14 @@
int matchLen = patternString.size();
// Do the replacement
if (matchPos == -1)
- return jsString(source);
+ return sourceVal;
if (replacementFunction) {
List args;
args.append(jsString(source.substr(matchPos, matchLen)));
args.append(jsNumber(matchPos));
- args.append(jsString(source));
+ args.append(sourceVal);
replacementString = replacementFunction->call(exec, exec->dynamicInterpreter()->globalObject(),
args)->toString(exec);
@@ -562,7 +567,11 @@
break;
}
case Replace:
- result = replace(exec, s, a0, a1);
+ StringImp* sVal = thisObj->inherits(&StringInstance::info) ?
+ static_cast<StringInstance*>(thisObj)->internalValue() :
+ static_cast<StringImp*>(jsString(s));
+
+ result = replace(exec, sVal, a0, a1);
break;
case Slice:
{