13#define MAKE_ACCEPT(Name) \
14 void* RegExp##Name::Accept(RegExpVisitor* visitor, void* data) { \
15 return visitor->Visit##Name(this, data); \
20#define MAKE_TYPE_CASE(Name) \
21 RegExp##Name* RegExpTree::As##Name() { return nullptr; } \
22 bool RegExpTree::Is##Name() { return false; }
26#define MAKE_TYPE_CASE(Name) \
27 RegExp##Name* RegExp##Name::As##Name() { return this; } \
28 bool RegExp##Name::Is##Name() { return true; }
34Interval ListCaptureRegisters(ZoneList<RegExpTree*>*
children) {
44 return ListCaptureRegisters(
nodes());
81 for (
int i = 0;
i < nodes->
length();
i++) {
83 if (node->IsAnchoredAtStart()) {
86 if (node->max_match() > 0) {
96 for (
int i = nodes->
length() - 1;
i >= 0;
i--) {
98 if (node->IsAnchoredAtEnd()) {
101 if (node->max_match() > 0) {
111 for (
int i = 0;
i < alternatives->
length();
i++) {
120 for (
int i = 0;
i < alternatives->
length();
i++) {
146 RegExpUnparser(std::ostream& os,
Zone* zone) :
os_(os),
zone_(zone) {}
147 void VisitCharacterRange(CharacterRange that);
148#define MAKE_CASE(Name) void* Visit##Name(RegExp##Name*, void* data) override;
158void* RegExpUnparser::VisitDisjunction(RegExpDisjunction* that,
void* data) {
160 for (
int i = 0;
i < that->alternatives()->
length();
i++) {
162 that->alternatives()->at(
i)->Accept(
this, data);
169void* RegExpUnparser::VisitAlternative(RegExpAlternative* that,
void* data) {
173 that->nodes()->at(
i)->Accept(
this, data);
180void RegExpUnparser::VisitCharacterRange(CharacterRange that) {
181 os_ << AsUC32(that.from());
182 if (!that.IsSingleton()) {
183 os_ <<
"-" << AsUC32(that.to());
187void* RegExpUnparser::VisitClassRanges(RegExpClassRanges* that,
void* data) {
188 if (that->is_negated())
os_ <<
"^";
191 if (
i > 0)
os_ <<
" ";
192 VisitCharacterRange(that->ranges(
zone_)->at(
i));
198void* RegExpUnparser::VisitClassSetOperand(RegExpClassSetOperand* that,
202 if (
i > 0)
os_ <<
" ";
203 VisitCharacterRange(that->ranges()->at(
i));
205 if (that->has_strings()) {
206 for (
auto iter : *that->strings()) {
208 os_ << std::string(iter.first.begin(), iter.first.end());
216void* RegExpUnparser::VisitClassSetExpression(RegExpClassSetExpression* that,
218 switch (that->operation()) {
219 case RegExpClassSetExpression::OperationType::kUnion:
222 case RegExpClassSetExpression::OperationType::kIntersection:
225 case RegExpClassSetExpression::OperationType::kSubtraction:
229 if (that->is_negated())
os_ <<
"^";
231 for (
int i = 0;
i < that->operands()->
length();
i++) {
232 if (
i > 0)
os_ <<
" ";
233 that->operands()->at(
i)->Accept(
this, data);
239void* RegExpUnparser::VisitAssertion(RegExpAssertion* that,
void* data) {
240 switch (that->assertion_type()) {
241 case RegExpAssertion::Type::START_OF_INPUT:
244 case RegExpAssertion::Type::END_OF_INPUT:
247 case RegExpAssertion::Type::START_OF_LINE:
250 case RegExpAssertion::Type::END_OF_LINE:
253 case RegExpAssertion::Type::BOUNDARY:
256 case RegExpAssertion::Type::NON_BOUNDARY:
264void* RegExpUnparser::VisitAtom(RegExpAtom* that,
void* data) {
266 base::Vector<const base::uc16> chardata = that->data();
267 for (
int i = 0;
i < chardata.
length();
i++) {
268 os_ << AsUC16(chardata[
i]);
275void* RegExpUnparser::VisitText(RegExpText* that,
void* data) {
276 if (that->elements()->length() == 1) {
277 that->elements()->at(0).tree()->Accept(
this, data);
280 for (
int i = 0;
i < that->elements()->
length();
i++) {
282 that->elements()->at(
i).tree()->Accept(
this, data);
290void* RegExpUnparser::VisitQuantifier(RegExpQuantifier* that,
void* data) {
291 os_ <<
"(# " << that->min() <<
" ";
292 if (that->max() == RegExpTree::kInfinity) {
295 os_ << that->max() <<
" ";
297 os_ << (that->is_greedy() ?
"g " : that->is_possessive() ?
"p " :
"n ");
298 that->body()->Accept(
this, data);
304void* RegExpUnparser::VisitCapture(RegExpCapture* that,
void* data) {
306 that->body()->Accept(
this, data);
311void* RegExpUnparser::VisitGroup(RegExpGroup* that,
void* data) {
312 os_ <<
"(?" << that->flags() <<
": ";
313 that->body()->Accept(
this, data);
318void* RegExpUnparser::VisitLookaround(RegExpLookaround* that,
void* data) {
320 os_ << (that->type() == RegExpLookaround::LOOKAHEAD ?
"->" :
"<-");
321 os_ << (that->is_positive() ?
" + " :
" - ");
322 that->body()->Accept(
this, data);
328void* RegExpUnparser::VisitBackReference(RegExpBackReference* that,
330 os_ <<
"(<- " << that->captures()->first()->index();
331 for (
int i = 1;
i < that->captures()->
length(); ++
i) {
332 os_ <<
"," << that->captures()->at(
i)->index();
339void* RegExpUnparser::VisitEmpty(RegExpEmpty* that,
void* data) {
345 RegExpUnparser unparser(os, zone);
346 Accept(&unparser,
nullptr);
365int IncreaseBy(
int previous,
int increase) {
380 for (
int i = 0;
i < nodes->
length();
i++) {
384 int node_max_match = node->max_match();
391 : ranges_(ranges), strings_(strings) {
395 if (!ranges->is_empty()) {
400 for (
auto string : *strings) {
411 is_negated_(is_negated),
412 may_contain_strings_(may_contain_strings),
413 operands_(operands) {
433 zone->template New<ZoneList<CharacterRange>>(0, zone);
435 zone->template New<RegExpClassSetOperand>(ranges,
nullptr);
437 zone->template New<ZoneList<RegExpTree*>>(1, zone);
439 return zone->template New<RegExpClassSetExpression>(
Interval Union(Interval that)
bool IsAnchoredAtStart() override
Interval CaptureRegisters() override
bool IsAnchoredAtEnd() override
RegExpAlternative(ZoneList< RegExpTree * > *nodes)
ZoneList< RegExpTree * > * nodes() const
bool IsAnchoredAtEnd() override
bool IsAnchoredAtStart() override
Type assertion_type() const
static int StartRegister(int index)
static int EndRegister(int index)
bool IsAnchoredAtStart() override
Interval CaptureRegisters() override
bool IsAnchoredAtEnd() override
const bool may_contain_strings_
const ZoneList< RegExpTree * > * operands() const
static RegExpClassSetExpression * Empty(Zone *zone, bool is_negated)
RegExpClassSetExpression(OperationType op, bool is_negated, bool may_contain_strings, ZoneList< RegExpTree * > *operands)
RegExpClassSetOperand(ZoneList< CharacterRange > *ranges, CharacterClassStrings *strings)
bool IsAnchoredAtStart() override
RegExpDisjunction(ZoneList< RegExpTree * > *alternatives)
ZoneList< RegExpTree * > * alternatives() const
Interval CaptureRegisters() override
bool IsAnchoredAtEnd() override
bool IsAnchoredAtStart() override
RegExpTree * body() const
Interval CaptureRegisters() override
Interval CaptureRegisters() override
RegExpTree * body() const
virtual bool IsAnchoredAtStart()
virtual bool IsAnchoredAtEnd()
virtual int min_match()=0
static const int kInfinity
virtual Interval CaptureRegisters()
virtual int max_match()=0
V8_EXPORT_PRIVATE std::ostream & Print(std::ostream &os, Zone *zone)
V8_INLINE int length() const
ZoneLinkedList< BFEntry > nodes_
std::vector< std::unique_ptr< InstanceTypeTree > > children
ZoneVector< RpoNumber > & result
#define MAKE_CASE(TYPE, Name, name)
#define MAKE_ACCEPT(Name)
#define MAKE_TYPE_CASE(Name)
#define FOR_EACH_REG_EXP_TREE_TYPE(VISIT)
SmallRegExpTreeVector alternatives_
#define DCHECK_NOT_NULL(val)
#define DCHECK(condition)
#define DCHECK_LT(v1, v2)