diff options
author | wolfbeast <mcwerewolf@wolfbeast.com> | 2019-11-26 13:37:09 +0100 |
---|---|---|
committer | wolfbeast <mcwerewolf@wolfbeast.com> | 2019-11-26 13:37:09 +0100 |
commit | 185a9a750878ed1d9705fbd162dbfe9bf2e4ea0c (patch) | |
tree | 9b83879173624e3dcb5ba6d1404fb89f2c47cb66 /js/src/vm | |
parent | e8c40b0bc2aa25b9f85ddbe3949c296311cc0f3f (diff) | |
download | uxp-185a9a750878ed1d9705fbd162dbfe9bf2e4ea0c.tar.gz |
Issue #1302 - Add self-hosted implementation for string regex .matchAll
This resolves #1302.
Diffstat (limited to 'js/src/vm')
-rw-r--r-- | js/src/vm/CommonPropertyNames.h | 1 | ||||
-rw-r--r-- | js/src/vm/GlobalObject.cpp | 79 | ||||
-rw-r--r-- | js/src/vm/GlobalObject.h | 8 | ||||
-rw-r--r-- | js/src/vm/SelfHosting.cpp | 23 |
4 files changed, 55 insertions, 56 deletions
diff --git a/js/src/vm/CommonPropertyNames.h b/js/src/vm/CommonPropertyNames.h index 4ae49d5771..99cb02e586 100644 --- a/js/src/vm/CommonPropertyNames.h +++ b/js/src/vm/CommonPropertyNames.h @@ -282,6 +282,7 @@ macro(RegExpFlagsGetter, RegExpFlagsGetter, "RegExpFlagsGetter") \ macro(RegExpMatcher, RegExpMatcher, "RegExpMatcher") \ macro(RegExpSearcher, RegExpSearcher, "RegExpSearcher") \ + macro(RegExpStringIterator, RegExpStringIterator, "RegExp String Iterator") \ macro(RegExpTester, RegExpTester, "RegExpTester") \ macro(RegExp_prototype_Exec, RegExp_prototype_Exec, "RegExp_prototype_Exec") \ macro(Reify, Reify, "Reify") \ diff --git a/js/src/vm/GlobalObject.cpp b/js/src/vm/GlobalObject.cpp index 85707e1c60..013208f666 100644 --- a/js/src/vm/GlobalObject.cpp +++ b/js/src/vm/GlobalObject.cpp @@ -468,62 +468,29 @@ GlobalObject::initSelfHostingBuiltins(JSContext* cx, Handle<GlobalObject*> globa return false; } - RootedValue std_isConcatSpreadable(cx); - std_isConcatSpreadable.setSymbol(cx->wellKnownSymbols().get(JS::SymbolCode::isConcatSpreadable)); - if (!JS_DefineProperty(cx, global, "std_isConcatSpreadable", std_isConcatSpreadable, - JSPROP_PERMANENT | JSPROP_READONLY)) - { - return false; - } - - // Define a top-level property 'std_iterator' with the name of the method - // used by for-of loops to create an iterator. - RootedValue std_iterator(cx); - std_iterator.setSymbol(cx->wellKnownSymbols().get(JS::SymbolCode::iterator)); - if (!JS_DefineProperty(cx, global, "std_iterator", std_iterator, - JSPROP_PERMANENT | JSPROP_READONLY)) - { - return false; - } - - RootedValue std_match(cx); - std_match.setSymbol(cx->wellKnownSymbols().get(JS::SymbolCode::match)); - if (!JS_DefineProperty(cx, global, "std_match", std_match, - JSPROP_PERMANENT | JSPROP_READONLY)) - { - return false; - } - - RootedValue std_replace(cx); - std_replace.setSymbol(cx->wellKnownSymbols().get(JS::SymbolCode::replace)); - if (!JS_DefineProperty(cx, global, "std_replace", std_replace, - JSPROP_PERMANENT | JSPROP_READONLY)) - { - return false; - } - - RootedValue std_search(cx); - std_search.setSymbol(cx->wellKnownSymbols().get(JS::SymbolCode::search)); - if (!JS_DefineProperty(cx, global, "std_search", std_search, - JSPROP_PERMANENT | JSPROP_READONLY)) - { - return false; - } - - RootedValue std_species(cx); - std_species.setSymbol(cx->wellKnownSymbols().get(JS::SymbolCode::species)); - if (!JS_DefineProperty(cx, global, "std_species", std_species, - JSPROP_PERMANENT | JSPROP_READONLY)) - { - return false; - } - - RootedValue std_split(cx); - std_split.setSymbol(cx->wellKnownSymbols().get(JS::SymbolCode::split)); - if (!JS_DefineProperty(cx, global, "std_split", std_split, - JSPROP_PERMANENT | JSPROP_READONLY)) - { - return false; + struct SymbolAndName { + JS::SymbolCode code; + const char* name; + }; + + SymbolAndName wellKnownSymbols[] = { + {JS::SymbolCode::isConcatSpreadable, "std_isConcatSpreadable"}, + {JS::SymbolCode::iterator, "std_iterator"}, + {JS::SymbolCode::match, "std_match"}, + {JS::SymbolCode::matchAll, "std_matchAll"}, + {JS::SymbolCode::replace, "std_replace"}, + {JS::SymbolCode::search, "std_search"}, + {JS::SymbolCode::species, "std_species"}, + {JS::SymbolCode::split, "std_split"}, + }; + + RootedValue symVal(cx); + for (const auto& sym : wellKnownSymbols) { + symVal.setSymbol(cx->wellKnownSymbols().get(sym.code)); + if (!JS_DefineProperty(cx, global, sym.name, symVal, + JSPROP_PERMANENT | JSPROP_READONLY)) { + return false; + } } return InitBareBuiltinCtor(cx, global, JSProto_Array) && diff --git a/js/src/vm/GlobalObject.h b/js/src/vm/GlobalObject.h index 5aacfc5dcd..9179abbb7d 100644 --- a/js/src/vm/GlobalObject.h +++ b/js/src/vm/GlobalObject.h @@ -93,6 +93,7 @@ class GlobalObject : public NativeObject ITERATOR_PROTO, ARRAY_ITERATOR_PROTO, STRING_ITERATOR_PROTO, + REGEXP_STRING_ITERATOR_PROTO, LEGACY_GENERATOR_OBJECT_PROTO, STAR_GENERATOR_OBJECT_PROTO, STAR_GENERATOR_FUNCTION_PROTO, @@ -583,6 +584,12 @@ class GlobalObject : public NativeObject } static NativeObject* + getOrCreateRegExpStringIteratorPrototype(JSContext* cx, Handle<GlobalObject*> global) { + return MaybeNativeObject(getOrCreateObject(cx, global, REGEXP_STRING_ITERATOR_PROTO, + initRegExpStringIteratorProto)); + } + + static NativeObject* getOrCreateLegacyGeneratorObjectPrototype(JSContext* cx, Handle<GlobalObject*> global) { return MaybeNativeObject(getOrCreateObject(cx, global, LEGACY_GENERATOR_OBJECT_PROTO, initLegacyGeneratorProto)); @@ -767,6 +774,7 @@ class GlobalObject : public NativeObject static bool initIteratorProto(JSContext* cx, Handle<GlobalObject*> global); static bool initArrayIteratorProto(JSContext* cx, Handle<GlobalObject*> global); static bool initStringIteratorProto(JSContext* cx, Handle<GlobalObject*> global); + static bool initRegExpStringIteratorProto(JSContext* cx, Handle<GlobalObject*> global); // Implemented in vm/GeneratorObject.cpp. static bool initLegacyGeneratorProto(JSContext* cx, Handle<GlobalObject*> global); diff --git a/js/src/vm/SelfHosting.cpp b/js/src/vm/SelfHosting.cpp index 8334104652..ffd707b147 100644 --- a/js/src/vm/SelfHosting.cpp +++ b/js/src/vm/SelfHosting.cpp @@ -857,6 +857,24 @@ intrinsic_NewStringIterator(JSContext* cx, unsigned argc, Value* vp) } static bool +intrinsic_NewRegExpStringIterator(JSContext* cx, unsigned argc, Value* vp) +{ + CallArgs args = CallArgsFromVp(argc, vp); + MOZ_ASSERT(args.length() == 0); + + RootedObject proto(cx, GlobalObject::getOrCreateRegExpStringIteratorPrototype(cx, cx->global())); + if (!proto) + return false; + + JSObject* obj = NewObjectWithGivenProto(cx, &RegExpStringIteratorObject::class_, proto); + if (!obj) + return false; + + args.rval().setObject(*obj); + return true; +} + +static bool intrinsic_SetCanonicalName(JSContext* cx, unsigned argc, Value* vp) { CallArgs args = CallArgsFromVp(argc, vp); @@ -2288,6 +2306,8 @@ static const JSFunctionSpec intrinsic_functions[] = { JS_INLINABLE_FN("GuardToStringIterator", intrinsic_GuardToBuiltin<StringIteratorObject>, 1,0, IntrinsicGuardToStringIterator), + JS_FN("GuardToRegExpStringIterator", + intrinsic_GuardToBuiltin<RegExpStringIteratorObject>, 1,0), JS_FN("_CreateMapIterationResultPair", intrinsic_CreateMapIterationResultPair, 0, 0), JS_INLINABLE_FN("_GetNextMapEntryForIterator", intrinsic_GetNextMapEntryForIterator, 2,0, @@ -2305,6 +2325,9 @@ static const JSFunctionSpec intrinsic_functions[] = { JS_FN("NewStringIterator", intrinsic_NewStringIterator, 0,0), JS_FN("CallStringIteratorMethodIfWrapped", CallNonGenericSelfhostedMethod<Is<StringIteratorObject>>, 2,0), + JS_FN("NewRegExpStringIterator", intrinsic_NewRegExpStringIterator, 0,0), + JS_FN("CallRegExpStringIteratorMethodIfWrapped", + CallNonGenericSelfhostedMethod<Is<RegExpStringIteratorObject>>, 2,0), JS_FN("IsStarGeneratorObject", intrinsic_IsInstanceOfBuiltin<StarGeneratorObject>, 1,0), |