Chromium Code Reviews
chromiumcodereview-hr@appspot.gserviceaccount.com (chromiumcodereview-hr) | Please choose your nickname with Settings | Help | Chromium Project | Gerrit Changes | Sign out
(52)

Side by Side Diff: src/jsregexp.cc

Issue 18753: Reduce work done in EatsAtLeast to a sane level. (Closed) Base URL: http://v8.googlecode.com/svn/branches/bleeding_edge/
Patch Set: Created 11 years, 11 months ago
Use n/p to move between diff chunks; N/P to move between comments. Draft comments are only viewable by you.
Jump to:
View unified diff | Download patch | Annotate | Revision Log
« no previous file with comments | « src/jsregexp.h ('k') | no next file » | no next file with comments »
Toggle Intra-line Diffs ('i') | Expand Comments ('e') | Collapse Comments ('c') | Show Comments Hide Comments ('s')
OLDNEW
1 // Copyright 2006-2008 the V8 project authors. All rights reserved. 1 // Copyright 2006-2008 the V8 project authors. All rights reserved.
2 // Redistribution and use in source and binary forms, with or without 2 // Redistribution and use in source and binary forms, with or without
3 // modification, are permitted provided that the following conditions are 3 // modification, are permitted provided that the following conditions are
4 // met: 4 // met:
5 // 5 //
6 // * Redistributions of source code must retain the above copyright 6 // * Redistributions of source code must retain the above copyright
7 // notice, this list of conditions and the following disclaimer. 7 // notice, this list of conditions and the following disclaimer.
8 // * Redistributions in binary form must reproduce the above 8 // * Redistributions in binary form must reproduce the above
9 // copyright notice, this list of conditions and the following 9 // copyright notice, this list of conditions and the following
10 // disclaimer in the documentation and/or other materials provided 10 // disclaimer in the documentation and/or other materials provided
(...skipping 1945 matching lines...) Expand 10 before | Expand all | Expand 10 after
1956 } 1956 }
1957 1957
1958 // If we get here code has been generated for this node too many times or 1958 // If we get here code has been generated for this node too many times or
1959 // recursion is too deep. Time to switch to a generic version. The code for 1959 // recursion is too deep. Time to switch to a generic version. The code for
1960 // generic versions above can handle deep recursion properly. 1960 // generic versions above can handle deep recursion properly.
1961 bool ok = trace->Flush(compiler, this); 1961 bool ok = trace->Flush(compiler, this);
1962 return ok ? DONE : FAIL; 1962 return ok ? DONE : FAIL;
1963 } 1963 }
1964 1964
1965 1965
1966 int ActionNode::EatsAtLeast(int recursion_depth) { 1966 int ActionNode::EatsAtLeast(int still_to_find, int recursion_depth) {
1967 if (recursion_depth > RegExpCompiler::kMaxRecursion) return 0; 1967 if (recursion_depth > RegExpCompiler::kMaxRecursion) return 0;
1968 if (type_ == POSITIVE_SUBMATCH_SUCCESS) return 0; // Rewinds input! 1968 if (type_ == POSITIVE_SUBMATCH_SUCCESS) return 0; // Rewinds input!
1969 return on_success()->EatsAtLeast(recursion_depth + 1); 1969 return on_success()->EatsAtLeast(still_to_find, recursion_depth + 1);
1970 } 1970 }
1971 1971
1972 1972
1973 int AssertionNode::EatsAtLeast(int recursion_depth) { 1973 int AssertionNode::EatsAtLeast(int still_to_find, int recursion_depth) {
1974 if (recursion_depth > RegExpCompiler::kMaxRecursion) return 0; 1974 if (recursion_depth > RegExpCompiler::kMaxRecursion) return 0;
1975 return on_success()->EatsAtLeast(recursion_depth + 1); 1975 return on_success()->EatsAtLeast(still_to_find, recursion_depth + 1);
1976 } 1976 }
1977 1977
1978 1978
1979 int BackReferenceNode::EatsAtLeast(int recursion_depth) { 1979 int BackReferenceNode::EatsAtLeast(int still_to_find, int recursion_depth) {
1980 if (recursion_depth > RegExpCompiler::kMaxRecursion) return 0; 1980 if (recursion_depth > RegExpCompiler::kMaxRecursion) return 0;
1981 return on_success()->EatsAtLeast(recursion_depth + 1); 1981 return on_success()->EatsAtLeast(still_to_find, recursion_depth + 1);
1982 } 1982 }
1983 1983
1984 1984
1985 int TextNode::EatsAtLeast(int recursion_depth) { 1985 int TextNode::EatsAtLeast(int still_to_find, int recursion_depth) {
1986 int answer = Length(); 1986 int answer = Length();
1987 if (answer >= 4) return answer; 1987 if (answer >= still_to_find) return answer;
1988 if (recursion_depth > RegExpCompiler::kMaxRecursion) return answer; 1988 if (recursion_depth > RegExpCompiler::kMaxRecursion) return answer;
1989 return answer + on_success()->EatsAtLeast(recursion_depth + 1); 1989 return answer + on_success()->EatsAtLeast(still_to_find - answer,
1990 recursion_depth + 1);
1990 } 1991 }
1991 1992
1992 1993
1993 int NegativeLookaheadChoiceNode:: EatsAtLeast(int recursion_depth) { 1994 int NegativeLookaheadChoiceNode:: EatsAtLeast(int still_to_find, int recursion_d epth) {
1994 if (recursion_depth > RegExpCompiler::kMaxRecursion) return 0; 1995 if (recursion_depth > RegExpCompiler::kMaxRecursion) return 0;
1995 // Alternative 0 is the negative lookahead, alternative 1 is what comes 1996 // Alternative 0 is the negative lookahead, alternative 1 is what comes
1996 // afterwards. 1997 // afterwards.
1997 RegExpNode* node = alternatives_->at(1).node(); 1998 RegExpNode* node = alternatives_->at(1).node();
1998 return node->EatsAtLeast(recursion_depth + 1); 1999 return node->EatsAtLeast(still_to_find, recursion_depth + 1);
1999 } 2000 }
2000 2001
2001 2002
2002 void NegativeLookaheadChoiceNode::GetQuickCheckDetails( 2003 void NegativeLookaheadChoiceNode::GetQuickCheckDetails(
2003 QuickCheckDetails* details, 2004 QuickCheckDetails* details,
2004 RegExpCompiler* compiler, 2005 RegExpCompiler* compiler,
2005 int filled_in) { 2006 int filled_in) {
2006 // Alternative 0 is the negative lookahead, alternative 1 is what comes 2007 // Alternative 0 is the negative lookahead, alternative 1 is what comes
2007 // afterwards. 2008 // afterwards.
2008 RegExpNode* node = alternatives_->at(1).node(); 2009 RegExpNode* node = alternatives_->at(1).node();
2009 return node->GetQuickCheckDetails(details, compiler, filled_in); 2010 return node->GetQuickCheckDetails(details, compiler, filled_in);
2010 } 2011 }
2011 2012
2012 2013
2013 int ChoiceNode::EatsAtLeastHelper(int recursion_depth, 2014 int ChoiceNode::EatsAtLeastHelper(int still_to_find,
2015 int recursion_depth,
2014 RegExpNode* ignore_this_node) { 2016 RegExpNode* ignore_this_node) {
2015 if (recursion_depth > RegExpCompiler::kMaxRecursion) return 0; 2017 if (recursion_depth > RegExpCompiler::kMaxRecursion) return 0;
2016 int min = 100; 2018 int min = 100;
2017 int choice_count = alternatives_->length(); 2019 int choice_count = alternatives_->length();
2018 for (int i = 0; i < choice_count; i++) { 2020 for (int i = 0; i < choice_count; i++) {
2019 RegExpNode* node = alternatives_->at(i).node(); 2021 RegExpNode* node = alternatives_->at(i).node();
2020 if (node == ignore_this_node) continue; 2022 if (node == ignore_this_node) continue;
2021 int node_eats_at_least = node->EatsAtLeast(recursion_depth + 1); 2023 int node_eats_at_least = node->EatsAtLeast(still_to_find, recursion_depth + 1);
2022 if (node_eats_at_least < min) min = node_eats_at_least; 2024 if (node_eats_at_least < min) min = node_eats_at_least;
2023 } 2025 }
2024 return min; 2026 return min;
2025 } 2027 }
2026 2028
2027 2029
2028 int LoopChoiceNode::EatsAtLeast(int recursion_depth) { 2030 int LoopChoiceNode::EatsAtLeast(int still_to_find, int recursion_depth) {
2029 return EatsAtLeastHelper(recursion_depth, loop_node_); 2031 return EatsAtLeastHelper(still_to_find, recursion_depth, loop_node_);
2030 } 2032 }
2031 2033
2032 2034
2033 int ChoiceNode::EatsAtLeast(int recursion_depth) { 2035 int ChoiceNode::EatsAtLeast(int still_to_find, int recursion_depth) {
2034 return EatsAtLeastHelper(recursion_depth, NULL); 2036 return EatsAtLeastHelper(still_to_find, recursion_depth, NULL);
2035 } 2037 }
2036 2038
2037 2039
2038 // Takes the left-most 1-bit and smears it out, setting all bits to its right. 2040 // Takes the left-most 1-bit and smears it out, setting all bits to its right.
2039 static inline uint32_t SmearBitsRight(uint32_t v) { 2041 static inline uint32_t SmearBitsRight(uint32_t v) {
2040 v |= v >> 1; 2042 v |= v >> 1;
2041 v |= v >> 2; 2043 v |= v >> 2;
2042 v |= v >> 4; 2044 v |= v >> 4;
2043 v |= v >> 8; 2045 v |= v >> 8;
2044 v |= v >> 16; 2046 v |= v >> 16;
(...skipping 759 matching lines...) Expand 10 before | Expand all | Expand 10 after
2804 } 2806 }
2805 ASSERT(trace->stop_node() == NULL); 2807 ASSERT(trace->stop_node() == NULL);
2806 if (!trace->is_trivial()) { 2808 if (!trace->is_trivial()) {
2807 return trace->Flush(compiler, this); 2809 return trace->Flush(compiler, this);
2808 } 2810 }
2809 return ChoiceNode::Emit(compiler, trace); 2811 return ChoiceNode::Emit(compiler, trace);
2810 } 2812 }
2811 2813
2812 2814
2813 int ChoiceNode::CalculatePreloadCharacters(RegExpCompiler* compiler) { 2815 int ChoiceNode::CalculatePreloadCharacters(RegExpCompiler* compiler) {
2814 int preload_characters = EatsAtLeast(0); 2816 int preload_characters = EatsAtLeast(4, 0);
2815 #ifdef CAN_READ_UNALIGNED 2817 #ifdef CAN_READ_UNALIGNED
2816 bool ascii = compiler->ascii(); 2818 bool ascii = compiler->ascii();
2817 if (ascii) { 2819 if (ascii) {
2818 if (preload_characters > 4) preload_characters = 4; 2820 if (preload_characters > 4) preload_characters = 4;
2819 // We can't preload 3 characters because there is no machine instruction 2821 // We can't preload 3 characters because there is no machine instruction
2820 // to do that. We can't just load 4 because we could be reading 2822 // to do that. We can't just load 4 because we could be reading
2821 // beyond the end of the string, which could cause a memory fault. 2823 // beyond the end of the string, which could cause a memory fault.
2822 if (preload_characters == 3) preload_characters = 2; 2824 if (preload_characters == 3) preload_characters = 2;
2823 } else { 2825 } else {
2824 if (preload_characters > 2) preload_characters = 2; 2826 if (preload_characters > 2) preload_characters = 2;
(...skipping 1858 matching lines...) Expand 10 before | Expand all | Expand 10 after
4683 EmbeddedVector<byte, 1024> codes; 4685 EmbeddedVector<byte, 1024> codes;
4684 RegExpMacroAssemblerIrregexp macro_assembler(codes); 4686 RegExpMacroAssemblerIrregexp macro_assembler(codes);
4685 return compiler.Assemble(&macro_assembler, 4687 return compiler.Assemble(&macro_assembler,
4686 node, 4688 node,
4687 data->capture_count, 4689 data->capture_count,
4688 pattern); 4690 pattern);
4689 } 4691 }
4690 4692
4691 4693
4692 }} // namespace v8::internal 4694 }} // namespace v8::internal
OLDNEW
« no previous file with comments | « src/jsregexp.h ('k') | no next file » | no next file with comments »

Powered by Google App Engine
This is Rietveld 408576698