| Index: src/string.js
|
| diff --git a/src/string.js b/src/string.js
|
| index ac5cb7f99ef006378056828d1c97341ea1372d9d..5b739615e023a1b385fa31818a7fe146065ae65d 100644
|
| --- a/src/string.js
|
| +++ b/src/string.js
|
| @@ -2,11 +2,19 @@
|
| // Use of this source code is governed by a BSD-style license that can be
|
| // found in the LICENSE file.
|
|
|
| -// This file relies on the fact that the following declaration has been made
|
| -// in runtime.js:
|
| -// var $String = global.String;
|
| +var $stringCharAt;
|
| +var $stringIndexOf;
|
| +var $stringSubstring;
|
|
|
| -// -------------------------------------------------------------------
|
| +(function() {
|
| +
|
| +%CheckIsBootstrapping();
|
| +
|
| +var GlobalArray = global.Array;
|
| +var GlobalRegExp = global.RegExp;
|
| +var GlobalString = global.String;
|
| +
|
| +//-------------------------------------------------------------------
|
|
|
| function StringConstructor(x) {
|
| if (%_ArgumentsLength() == 0) x = '';
|
| @@ -147,16 +155,15 @@ function StringMatchJS(regexp) {
|
| // value is discarded.
|
| var lastIndex = regexp.lastIndex;
|
| TO_INTEGER_FOR_SIDE_EFFECT(lastIndex);
|
| - if (!regexp.global) return RegExpExecNoTests(regexp, subject, 0);
|
| - // lastMatchInfo is defined in regexp.js.
|
| - var result = %StringMatch(subject, regexp, lastMatchInfo);
|
| - if (result !== null) lastMatchInfoOverride = null;
|
| + if (!regexp.global) return $regexpExecNoTests(regexp, subject, 0);
|
| + var result = %StringMatch(subject, regexp, $regexpLastMatchInfo);
|
| + if (result !== null) $regexpLastMatchInfoOverride = null;
|
| regexp.lastIndex = 0;
|
| return result;
|
| }
|
| // Non-regexp argument.
|
| - regexp = new $RegExp(regexp);
|
| - return RegExpExecNoTests(regexp, subject, 0);
|
| + regexp = new GlobalRegExp(regexp);
|
| + return $regexpExecNoTests(regexp, subject, 0);
|
| }
|
|
|
|
|
| @@ -182,9 +189,9 @@ function StringNormalizeJS(form) {
|
| }
|
|
|
|
|
| -// This has the same size as the lastMatchInfo array, and can be used for
|
| -// functions that expect that structure to be returned. It is used when the
|
| -// needle is a string rather than a regexp. In this case we can't update
|
| +// This has the same size as the $regexpLastMatchInfo array, and can be used
|
| +// for functions that expect that structure to be returned. It is used when
|
| +// the needle is a string rather than a regexp. In this case we can't update
|
| // lastMatchArray without erroneously affecting the properties on the global
|
| // RegExp object.
|
| var reusableMatchInfo = [2, "", "", -1, -1];
|
| @@ -224,7 +231,7 @@ function StringReplace(search, replace) {
|
|
|
| if (!search.global) {
|
| // Non-global regexp search, string replace.
|
| - var match = DoRegExpExec(search, subject, 0);
|
| + var match = $regexpExec(search, subject, 0);
|
| if (match == null) {
|
| search.lastIndex = 0
|
| return subject;
|
| @@ -233,28 +240,28 @@ function StringReplace(search, replace) {
|
| return %_SubString(subject, 0, match[CAPTURE0]) +
|
| %_SubString(subject, match[CAPTURE1], subject.length)
|
| }
|
| - return ExpandReplacement(replace, subject, lastMatchInfo,
|
| + return ExpandReplacement(replace, subject, $regexpLastMatchInfo,
|
| %_SubString(subject, 0, match[CAPTURE0])) +
|
| %_SubString(subject, match[CAPTURE1], subject.length);
|
| }
|
|
|
| // Global regexp search, string replace.
|
| search.lastIndex = 0;
|
| - if (lastMatchInfoOverride == null) {
|
| + if ($regexpLastMatchInfoOverride == null) {
|
| return %StringReplaceGlobalRegExpWithString(
|
| - subject, search, replace, lastMatchInfo);
|
| + subject, search, replace, $regexpLastMatchInfo);
|
| } else {
|
| // We use this hack to detect whether StringReplaceRegExpWithString
|
| // found at least one hit. In that case we need to remove any
|
| // override.
|
| - var saved_subject = lastMatchInfo[LAST_SUBJECT_INDEX];
|
| - lastMatchInfo[LAST_SUBJECT_INDEX] = 0;
|
| + var saved_subject = $regexpLastMatchInfo[LAST_SUBJECT_INDEX];
|
| + $regexpLastMatchInfo[LAST_SUBJECT_INDEX] = 0;
|
| var answer = %StringReplaceGlobalRegExpWithString(
|
| - subject, search, replace, lastMatchInfo);
|
| - if (%_IsSmi(lastMatchInfo[LAST_SUBJECT_INDEX])) {
|
| - lastMatchInfo[LAST_SUBJECT_INDEX] = saved_subject;
|
| + subject, search, replace, $regexpLastMatchInfo);
|
| + if (%_IsSmi($regexpLastMatchInfo[LAST_SUBJECT_INDEX])) {
|
| + $regexpLastMatchInfo[LAST_SUBJECT_INDEX] = saved_subject;
|
| } else {
|
| - lastMatchInfoOverride = null;
|
| + $regexpLastMatchInfoOverride = null;
|
| }
|
| return answer;
|
| }
|
| @@ -418,7 +425,7 @@ function StringReplaceGlobalRegExpWithFunction(subject, regexp, replace) {
|
| }
|
| var res = %RegExpExecMultiple(regexp,
|
| subject,
|
| - lastMatchInfo,
|
| + $regexpLastMatchInfo,
|
| resultArray);
|
| regexp.lastIndex = 0;
|
| if (IS_NULL(res)) {
|
| @@ -427,7 +434,7 @@ function StringReplaceGlobalRegExpWithFunction(subject, regexp, replace) {
|
| return subject;
|
| }
|
| var len = res.length;
|
| - if (NUMBER_OF_CAPTURES(lastMatchInfo) == 2) {
|
| + if (NUMBER_OF_CAPTURES($regexpLastMatchInfo) == 2) {
|
| // If the number of captures is two then there are no explicit captures in
|
| // the regexp, just the implicit capture that captures the whole match. In
|
| // this case we can simplify quite a bit and end up with something faster.
|
| @@ -451,7 +458,7 @@ function StringReplaceGlobalRegExpWithFunction(subject, regexp, replace) {
|
| } else {
|
| override[0] = elem;
|
| override[1] = match_start;
|
| - lastMatchInfoOverride = override;
|
| + $regexpLastMatchInfoOverride = override;
|
| var func_result =
|
| %_CallFunction(receiver, elem, match_start, subject, replace);
|
| // Overwrite the i'th element in the results with the string we got
|
| @@ -467,7 +474,7 @@ function StringReplaceGlobalRegExpWithFunction(subject, regexp, replace) {
|
| if (!%_IsSmi(elem)) {
|
| // elem must be an Array.
|
| // Use the apply argument as backing for global RegExp properties.
|
| - lastMatchInfoOverride = elem;
|
| + $regexpLastMatchInfoOverride = elem;
|
| var func_result = %Apply(replace, receiver, elem, 0, elem.length);
|
| // Overwrite the i'th element in the results with the string we got
|
| // back from the callback function.
|
| @@ -483,7 +490,7 @@ function StringReplaceGlobalRegExpWithFunction(subject, regexp, replace) {
|
|
|
|
|
| function StringReplaceNonGlobalRegExpWithFunction(subject, regexp, replace) {
|
| - var matchInfo = DoRegExpExec(regexp, subject, 0);
|
| + var matchInfo = $regexpExec(regexp, subject, 0);
|
| if (IS_NULL(matchInfo)) {
|
| regexp.lastIndex = 0;
|
| return subject;
|
| @@ -530,9 +537,9 @@ function StringSearch(re) {
|
| } else if (IS_REGEXP(re)) {
|
| regexp = re;
|
| } else {
|
| - regexp = new $RegExp(re);
|
| + regexp = new GlobalRegExp(re);
|
| }
|
| - var match = DoRegExpExec(regexp, TO_STRING_INLINE(this), 0);
|
| + var match = $regexpExec(regexp, TO_STRING_INLINE(this), 0);
|
| if (match) {
|
| return match[CAPTURE0];
|
| }
|
| @@ -618,7 +625,7 @@ function StringSplitJS(separator, limit) {
|
|
|
| function StringSplitOnRegExp(subject, separator, limit, length) {
|
| if (length === 0) {
|
| - if (DoRegExpExec(separator, subject, 0, 0) != null) {
|
| + if ($regexpExec(separator, subject, 0, 0) != null) {
|
| return [];
|
| }
|
| return [subject];
|
| @@ -637,7 +644,7 @@ function StringSplitOnRegExp(subject, separator, limit, length) {
|
| break;
|
| }
|
|
|
| - var matchInfo = DoRegExpExec(separator, subject, startIndex);
|
| + var matchInfo = $regexpExec(separator, subject, startIndex);
|
| if (matchInfo == null || length === (startMatch = matchInfo[CAPTURE0])) {
|
| result[result.length] = %_SubString(subject, currentIndex, length);
|
| break;
|
| @@ -926,60 +933,61 @@ function StringSup() {
|
|
|
| // -------------------------------------------------------------------
|
|
|
| -function SetUpString() {
|
| - %CheckIsBootstrapping();
|
| -
|
| - // Set the String function and constructor.
|
| - %SetCode($String, StringConstructor);
|
| - %FunctionSetPrototype($String, new $String());
|
| -
|
| - // Set up the constructor property on the String prototype object.
|
| - %AddNamedProperty($String.prototype, "constructor", $String, DONT_ENUM);
|
| -
|
| - // Set up the non-enumerable functions on the String object.
|
| - InstallFunctions($String, DONT_ENUM, $Array(
|
| - "fromCharCode", StringFromCharCode
|
| - ));
|
| -
|
| - // Set up the non-enumerable functions on the String prototype object.
|
| - InstallFunctions($String.prototype, DONT_ENUM, $Array(
|
| - "valueOf", StringValueOf,
|
| - "toString", StringToString,
|
| - "charAt", StringCharAt,
|
| - "charCodeAt", StringCharCodeAt,
|
| - "concat", StringConcat,
|
| - "indexOf", StringIndexOfJS,
|
| - "lastIndexOf", StringLastIndexOfJS,
|
| - "localeCompare", StringLocaleCompareJS,
|
| - "match", StringMatchJS,
|
| - "normalize", StringNormalizeJS,
|
| - "replace", StringReplace,
|
| - "search", StringSearch,
|
| - "slice", StringSlice,
|
| - "split", StringSplitJS,
|
| - "substring", StringSubstring,
|
| - "substr", StringSubstr,
|
| - "toLowerCase", StringToLowerCaseJS,
|
| - "toLocaleLowerCase", StringToLocaleLowerCase,
|
| - "toUpperCase", StringToUpperCaseJS,
|
| - "toLocaleUpperCase", StringToLocaleUpperCase,
|
| - "trim", StringTrimJS,
|
| - "trimLeft", StringTrimLeft,
|
| - "trimRight", StringTrimRight,
|
| - "link", StringLink,
|
| - "anchor", StringAnchor,
|
| - "fontcolor", StringFontcolor,
|
| - "fontsize", StringFontsize,
|
| - "big", StringBig,
|
| - "blink", StringBlink,
|
| - "bold", StringBold,
|
| - "fixed", StringFixed,
|
| - "italics", StringItalics,
|
| - "small", StringSmall,
|
| - "strike", StringStrike,
|
| - "sub", StringSub,
|
| - "sup", StringSup
|
| - ));
|
| -}
|
| -
|
| -SetUpString();
|
| +// Set the String function and constructor.
|
| +%SetCode(GlobalString, StringConstructor);
|
| +%FunctionSetPrototype(GlobalString, new GlobalString());
|
| +
|
| +// Set up the constructor property on the String prototype object.
|
| +%AddNamedProperty(
|
| + GlobalString.prototype, "constructor", GlobalString, DONT_ENUM);
|
| +
|
| +// Set up the non-enumerable functions on the String object.
|
| +InstallFunctions(GlobalString, DONT_ENUM, GlobalArray(
|
| + "fromCharCode", StringFromCharCode
|
| +));
|
| +
|
| +// Set up the non-enumerable functions on the String prototype object.
|
| +InstallFunctions(GlobalString.prototype, DONT_ENUM, GlobalArray(
|
| + "valueOf", StringValueOf,
|
| + "toString", StringToString,
|
| + "charAt", StringCharAt,
|
| + "charCodeAt", StringCharCodeAt,
|
| + "concat", StringConcat,
|
| + "indexOf", StringIndexOfJS,
|
| + "lastIndexOf", StringLastIndexOfJS,
|
| + "localeCompare", StringLocaleCompareJS,
|
| + "match", StringMatchJS,
|
| + "normalize", StringNormalizeJS,
|
| + "replace", StringReplace,
|
| + "search", StringSearch,
|
| + "slice", StringSlice,
|
| + "split", StringSplitJS,
|
| + "substring", StringSubstring,
|
| + "substr", StringSubstr,
|
| + "toLowerCase", StringToLowerCaseJS,
|
| + "toLocaleLowerCase", StringToLocaleLowerCase,
|
| + "toUpperCase", StringToUpperCaseJS,
|
| + "toLocaleUpperCase", StringToLocaleUpperCase,
|
| + "trim", StringTrimJS,
|
| + "trimLeft", StringTrimLeft,
|
| + "trimRight", StringTrimRight,
|
| + "link", StringLink,
|
| + "anchor", StringAnchor,
|
| + "fontcolor", StringFontcolor,
|
| + "fontsize", StringFontsize,
|
| + "big", StringBig,
|
| + "blink", StringBlink,
|
| + "bold", StringBold,
|
| + "fixed", StringFixed,
|
| + "italics", StringItalics,
|
| + "small", StringSmall,
|
| + "strike", StringStrike,
|
| + "sub", StringSub,
|
| + "sup", StringSup
|
| +));
|
| +
|
| +$stringCharAt = StringCharAt;
|
| +$stringIndexOf = StringIndexOfJS;
|
| +$stringSubstring = StringSubstring;
|
| +
|
| +})();
|
|
|