Unbreak interpreted regexp.
BUG= TEST= Review URL: https://chromiumcodereview.appspot.com/10535164 git-svn-id: http://v8.googlecode.com/svn/branches/bleeding_edge@11825 ce2b1a6d-e550-0410-aec6-3dcde31c8c00
This commit is contained in:
parent
dee723df12
commit
a075583479
@ -35,14 +35,7 @@ namespace v8 {
|
||||
namespace internal {
|
||||
|
||||
|
||||
#ifdef V8_INTERPRETED_REGEXP
|
||||
class RegExpMacroAssemblerARM: public RegExpMacroAssembler {
|
||||
public:
|
||||
RegExpMacroAssemblerARM();
|
||||
virtual ~RegExpMacroAssemblerARM();
|
||||
};
|
||||
|
||||
#else // V8_INTERPRETED_REGEXP
|
||||
#ifndef V8_INTERPRETED_REGEXP
|
||||
class RegExpMacroAssemblerARM: public NativeRegExpMacroAssembler {
|
||||
public:
|
||||
RegExpMacroAssemblerARM(Mode mode, int registers_to_save, Zone* zone);
|
||||
|
@ -34,14 +34,7 @@
|
||||
namespace v8 {
|
||||
namespace internal {
|
||||
|
||||
#ifdef V8_INTERPRETED_REGEXP
|
||||
class RegExpMacroAssemblerIA32: public RegExpMacroAssembler {
|
||||
public:
|
||||
RegExpMacroAssemblerIA32() { }
|
||||
virtual ~RegExpMacroAssemblerIA32() { }
|
||||
};
|
||||
|
||||
#else // V8_INTERPRETED_REGEXP
|
||||
#ifndef V8_INTERPRETED_REGEXP
|
||||
class RegExpMacroAssemblerIA32: public NativeRegExpMacroAssembler {
|
||||
public:
|
||||
RegExpMacroAssemblerIA32(Mode mode, int registers_to_save, Zone* zone);
|
||||
|
@ -231,14 +231,13 @@ Handle<Object> RegExpImpl::Compile(Handle<JSRegExp> re,
|
||||
Handle<Object> RegExpImpl::Exec(Handle<JSRegExp> regexp,
|
||||
Handle<String> subject,
|
||||
int index,
|
||||
Handle<JSArray> last_match_info,
|
||||
Zone* zone) {
|
||||
Handle<JSArray> last_match_info) {
|
||||
switch (regexp->TypeTag()) {
|
||||
case JSRegExp::ATOM:
|
||||
return AtomExec(regexp, subject, index, last_match_info);
|
||||
case JSRegExp::IRREGEXP: {
|
||||
Handle<Object> result =
|
||||
IrregexpExec(regexp, subject, index, last_match_info, zone);
|
||||
IrregexpExec(regexp, subject, index, last_match_info);
|
||||
ASSERT(!result.is_null() ||
|
||||
regexp->GetIsolate()->has_pending_exception());
|
||||
return result;
|
||||
@ -345,8 +344,7 @@ Handle<Object> RegExpImpl::AtomExec(Handle<JSRegExp> re,
|
||||
// If compilation fails, an exception is thrown and this function
|
||||
// returns false.
|
||||
bool RegExpImpl::EnsureCompiledIrregexp(
|
||||
Handle<JSRegExp> re, Handle<String> sample_subject, bool is_ascii,
|
||||
Zone* zone) {
|
||||
Handle<JSRegExp> re, Handle<String> sample_subject, bool is_ascii) {
|
||||
Object* compiled_code = re->DataAt(JSRegExp::code_index(is_ascii));
|
||||
#ifdef V8_INTERPRETED_REGEXP
|
||||
if (compiled_code->IsByteArray()) return true;
|
||||
@ -362,7 +360,7 @@ bool RegExpImpl::EnsureCompiledIrregexp(
|
||||
ASSERT(compiled_code->IsSmi());
|
||||
return true;
|
||||
}
|
||||
return CompileIrregexp(re, sample_subject, is_ascii, zone);
|
||||
return CompileIrregexp(re, sample_subject, is_ascii);
|
||||
}
|
||||
|
||||
|
||||
@ -384,8 +382,7 @@ static bool CreateRegExpErrorObjectAndThrow(Handle<JSRegExp> re,
|
||||
|
||||
bool RegExpImpl::CompileIrregexp(Handle<JSRegExp> re,
|
||||
Handle<String> sample_subject,
|
||||
bool is_ascii,
|
||||
Zone* zone) {
|
||||
bool is_ascii) {
|
||||
// Compile the RegExp.
|
||||
Isolate* isolate = re->GetIsolate();
|
||||
ZoneScope zone_scope(isolate, DELETE_ON_EXIT);
|
||||
@ -437,7 +434,7 @@ bool RegExpImpl::CompileIrregexp(Handle<JSRegExp> re,
|
||||
pattern,
|
||||
sample_subject,
|
||||
is_ascii,
|
||||
zone);
|
||||
isolate->zone());
|
||||
if (result.error_message != NULL) {
|
||||
// Unable to compile regexp.
|
||||
Handle<String> error_message =
|
||||
@ -502,13 +499,12 @@ void RegExpImpl::IrregexpInitialize(Handle<JSRegExp> re,
|
||||
|
||||
|
||||
int RegExpImpl::IrregexpPrepare(Handle<JSRegExp> regexp,
|
||||
Handle<String> subject,
|
||||
Zone* zone) {
|
||||
Handle<String> subject) {
|
||||
if (!subject->IsFlat()) FlattenString(subject);
|
||||
|
||||
// Check the asciiness of the underlying storage.
|
||||
bool is_ascii = subject->IsAsciiRepresentationUnderneath();
|
||||
if (!EnsureCompiledIrregexp(regexp, subject, is_ascii, zone)) return -1;
|
||||
if (!EnsureCompiledIrregexp(regexp, subject, is_ascii)) return -1;
|
||||
|
||||
#ifdef V8_INTERPRETED_REGEXP
|
||||
// Byte-code regexp needs space allocated for all its registers.
|
||||
@ -541,8 +537,7 @@ int RegExpImpl::IrregexpExecRaw(
|
||||
Handle<JSRegExp> regexp,
|
||||
Handle<String> subject,
|
||||
int index,
|
||||
Vector<int> output,
|
||||
Zone* zone) {
|
||||
Vector<int> output) {
|
||||
Isolate* isolate = regexp->GetIsolate();
|
||||
|
||||
Handle<FixedArray> irregexp(FixedArray::cast(regexp->data()), isolate);
|
||||
@ -556,7 +551,7 @@ int RegExpImpl::IrregexpExecRaw(
|
||||
#ifndef V8_INTERPRETED_REGEXP
|
||||
ASSERT(output.length() >= (IrregexpNumberOfCaptures(*irregexp) + 1) * 2);
|
||||
do {
|
||||
EnsureCompiledIrregexp(regexp, subject, is_ascii, zone);
|
||||
EnsureCompiledIrregexp(regexp, subject, is_ascii);
|
||||
Handle<Code> code(IrregexpNativeCode(*irregexp, is_ascii), isolate);
|
||||
NativeRegExpMacroAssembler::Result res =
|
||||
NativeRegExpMacroAssembler::Match(code,
|
||||
@ -582,7 +577,7 @@ int RegExpImpl::IrregexpExecRaw(
|
||||
// the, potentially, different subject (the string can switch between
|
||||
// being internal and external, and even between being ASCII and UC16,
|
||||
// but the characters are always the same).
|
||||
IrregexpPrepare(regexp, subject, zone);
|
||||
IrregexpPrepare(regexp, subject);
|
||||
is_ascii = subject->IsAsciiRepresentationUnderneath();
|
||||
} while (true);
|
||||
UNREACHABLE();
|
||||
@ -617,8 +612,7 @@ int RegExpImpl::IrregexpExecRaw(
|
||||
Handle<Object> RegExpImpl::IrregexpExec(Handle<JSRegExp> jsregexp,
|
||||
Handle<String> subject,
|
||||
int previous_index,
|
||||
Handle<JSArray> last_match_info,
|
||||
Zone* zone) {
|
||||
Handle<JSArray> last_match_info) {
|
||||
Isolate* isolate = jsregexp->GetIsolate();
|
||||
ASSERT_EQ(jsregexp->TypeTag(), JSRegExp::IRREGEXP);
|
||||
|
||||
@ -632,7 +626,7 @@ Handle<Object> RegExpImpl::IrregexpExec(Handle<JSRegExp> jsregexp,
|
||||
}
|
||||
#endif
|
||||
#endif
|
||||
int required_registers = RegExpImpl::IrregexpPrepare(jsregexp, subject, zone);
|
||||
int required_registers = RegExpImpl::IrregexpPrepare(jsregexp, subject);
|
||||
if (required_registers < 0) {
|
||||
// Compiling failed with an exception.
|
||||
ASSERT(isolate->has_pending_exception());
|
||||
@ -643,8 +637,7 @@ Handle<Object> RegExpImpl::IrregexpExec(Handle<JSRegExp> jsregexp,
|
||||
|
||||
int res = RegExpImpl::IrregexpExecRaw(jsregexp, subject, previous_index,
|
||||
Vector<int>(registers.vector(),
|
||||
registers.length()),
|
||||
zone);
|
||||
registers.length()));
|
||||
if (res == RE_SUCCESS) {
|
||||
int capture_register_count =
|
||||
(IrregexpNumberOfCaptures(FixedArray::cast(jsregexp->data())) + 1) * 2;
|
||||
@ -5987,7 +5980,7 @@ RegExpEngine::CompilationResult RegExpEngine::Compile(
|
||||
#else // V8_INTERPRETED_REGEXP
|
||||
// Interpreted regexp implementation.
|
||||
EmbeddedVector<byte, 1024> codes;
|
||||
RegExpMacroAssemblerIrregexp macro_assembler(codes);
|
||||
RegExpMacroAssemblerIrregexp macro_assembler(codes, zone);
|
||||
#endif // V8_INTERPRETED_REGEXP
|
||||
|
||||
// Inserted here, instead of in Assembler, because it depends on information
|
||||
|
@ -78,8 +78,7 @@ class RegExpImpl {
|
||||
static Handle<Object> Exec(Handle<JSRegExp> regexp,
|
||||
Handle<String> subject,
|
||||
int index,
|
||||
Handle<JSArray> lastMatchInfo,
|
||||
Zone* zone);
|
||||
Handle<JSArray> lastMatchInfo);
|
||||
|
||||
// Prepares a JSRegExp object with Irregexp-specific data.
|
||||
static void IrregexpInitialize(Handle<JSRegExp> re,
|
||||
@ -108,8 +107,7 @@ class RegExpImpl {
|
||||
// as its "registers" argument. If the regexp cannot be compiled,
|
||||
// an exception is set as pending, and this function returns negative.
|
||||
static int IrregexpPrepare(Handle<JSRegExp> regexp,
|
||||
Handle<String> subject,
|
||||
Zone* zone);
|
||||
Handle<String> subject);
|
||||
|
||||
// Calculate the size of offsets vector for the case of global regexp
|
||||
// and the number of matches this vector is able to store.
|
||||
@ -126,8 +124,7 @@ class RegExpImpl {
|
||||
static int IrregexpExecRaw(Handle<JSRegExp> regexp,
|
||||
Handle<String> subject,
|
||||
int index,
|
||||
Vector<int> registers,
|
||||
Zone* zone);
|
||||
Vector<int> registers);
|
||||
|
||||
// Execute an Irregexp bytecode pattern.
|
||||
// On a successful match, the result is a JSArray containing
|
||||
@ -136,8 +133,7 @@ class RegExpImpl {
|
||||
static Handle<Object> IrregexpExec(Handle<JSRegExp> regexp,
|
||||
Handle<String> subject,
|
||||
int index,
|
||||
Handle<JSArray> lastMatchInfo,
|
||||
Zone* zone);
|
||||
Handle<JSArray> lastMatchInfo);
|
||||
|
||||
// Array index in the lastMatchInfo array.
|
||||
static const int kLastCaptureCount = 0;
|
||||
@ -202,11 +198,9 @@ class RegExpImpl {
|
||||
static String* two_byte_cached_string_;
|
||||
|
||||
static bool CompileIrregexp(
|
||||
Handle<JSRegExp> re, Handle<String> sample_subject, bool is_ascii,
|
||||
Zone* zone);
|
||||
Handle<JSRegExp> re, Handle<String> sample_subject, bool is_ascii);
|
||||
static inline bool EnsureCompiledIrregexp(
|
||||
Handle<JSRegExp> re, Handle<String> sample_subject, bool is_ascii,
|
||||
Zone* zone);
|
||||
Handle<JSRegExp> re, Handle<String> sample_subject, bool is_ascii);
|
||||
|
||||
|
||||
// Set the subject cache. The previous string buffer is not deleted, so the
|
||||
|
@ -38,13 +38,7 @@
|
||||
namespace v8 {
|
||||
namespace internal {
|
||||
|
||||
#ifdef V8_INTERPRETED_REGEXP
|
||||
class RegExpMacroAssemblerMIPS: public RegExpMacroAssembler {
|
||||
public:
|
||||
RegExpMacroAssemblerMIPS();
|
||||
virtual ~RegExpMacroAssemblerMIPS();
|
||||
};
|
||||
#else // V8_INTERPRETED_REGEXP
|
||||
#ifndef V8_INTERPRETED_REGEXP
|
||||
class RegExpMacroAssemblerMIPS: public NativeRegExpMacroAssembler {
|
||||
public:
|
||||
RegExpMacroAssemblerMIPS(Mode mode, int registers_to_save, Zone* zone);
|
||||
|
@ -38,8 +38,10 @@ namespace internal {
|
||||
|
||||
#ifdef V8_INTERPRETED_REGEXP
|
||||
|
||||
RegExpMacroAssemblerIrregexp::RegExpMacroAssemblerIrregexp(Vector<byte> buffer)
|
||||
: buffer_(buffer),
|
||||
RegExpMacroAssemblerIrregexp::RegExpMacroAssemblerIrregexp(Vector<byte> buffer,
|
||||
Zone* zone)
|
||||
: RegExpMacroAssembler(zone),
|
||||
buffer_(buffer),
|
||||
pc_(0),
|
||||
own_buffer_(false),
|
||||
advance_current_end_(kInvalidPC) {
|
||||
|
@ -48,7 +48,7 @@ class RegExpMacroAssemblerIrregexp: public RegExpMacroAssembler {
|
||||
// for code generation and assumes its size to be buffer_size. If the buffer
|
||||
// is too small, a fatal error occurs. No deallocation of the buffer is done
|
||||
// upon destruction of the assembler.
|
||||
explicit RegExpMacroAssemblerIrregexp(Vector<byte>);
|
||||
RegExpMacroAssemblerIrregexp(Vector<byte>, Zone* zone);
|
||||
virtual ~RegExpMacroAssemblerIrregexp();
|
||||
// The byte-code interpreter checks on each push anyway.
|
||||
virtual int stack_limit_slack() { return 1; }
|
||||
|
@ -1754,8 +1754,7 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_RegExpExec) {
|
||||
Handle<Object> result = RegExpImpl::Exec(regexp,
|
||||
subject,
|
||||
index,
|
||||
last_match_info,
|
||||
isolate->zone());
|
||||
last_match_info);
|
||||
if (result.is_null()) return Failure::Exception();
|
||||
return *result;
|
||||
}
|
||||
@ -3089,8 +3088,7 @@ MUST_USE_RESULT static MaybeObject* StringReplaceRegExpWithString(
|
||||
Handle<Object> match = RegExpImpl::Exec(regexp_handle,
|
||||
subject_handle,
|
||||
0,
|
||||
last_match_info_handle,
|
||||
isolate->zone());
|
||||
last_match_info_handle);
|
||||
if (match.is_null()) {
|
||||
return Failure::Exception();
|
||||
}
|
||||
@ -3191,8 +3189,7 @@ MUST_USE_RESULT static MaybeObject* StringReplaceRegExpWithString(
|
||||
match = RegExpImpl::Exec(regexp_handle,
|
||||
subject_handle,
|
||||
next,
|
||||
last_match_info_handle,
|
||||
isolate->zone());
|
||||
last_match_info_handle);
|
||||
if (match.is_null()) {
|
||||
return Failure::Exception();
|
||||
}
|
||||
@ -3248,8 +3245,7 @@ MUST_USE_RESULT static MaybeObject* StringReplaceRegExpWithEmptyString(
|
||||
Handle<Object> match = RegExpImpl::Exec(regexp_handle,
|
||||
subject_handle,
|
||||
0,
|
||||
last_match_info_handle,
|
||||
isolate->zone());
|
||||
last_match_info_handle);
|
||||
if (match.is_null()) return Failure::Exception();
|
||||
if (match->IsNull()) return *subject_handle;
|
||||
|
||||
@ -3323,8 +3319,7 @@ MUST_USE_RESULT static MaybeObject* StringReplaceRegExpWithEmptyString(
|
||||
match = RegExpImpl::Exec(regexp_handle,
|
||||
subject_handle,
|
||||
next,
|
||||
last_match_info_handle,
|
||||
isolate->zone());
|
||||
last_match_info_handle);
|
||||
if (match.is_null()) return Failure::Exception();
|
||||
if (match->IsNull()) break;
|
||||
|
||||
@ -3739,8 +3734,7 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_StringMatch) {
|
||||
CONVERT_ARG_HANDLE_CHECKED(JSArray, regexp_info, 2);
|
||||
HandleScope handles;
|
||||
|
||||
Handle<Object> match = RegExpImpl::Exec(regexp, subject, 0, regexp_info,
|
||||
isolate->zone());
|
||||
Handle<Object> match = RegExpImpl::Exec(regexp, subject, 0, regexp_info);
|
||||
|
||||
if (match.is_null()) {
|
||||
return Failure::Exception();
|
||||
@ -3765,8 +3759,7 @@ RUNTIME_FUNCTION(MaybeObject*, Runtime_StringMatch) {
|
||||
offsets.Add(start, zone);
|
||||
offsets.Add(end, zone);
|
||||
if (start == end) if (++end > length) break;
|
||||
match = RegExpImpl::Exec(regexp, subject, end, regexp_info,
|
||||
isolate->zone());
|
||||
match = RegExpImpl::Exec(regexp, subject, end, regexp_info);
|
||||
if (match.is_null()) {
|
||||
return Failure::Exception();
|
||||
}
|
||||
@ -3864,8 +3857,7 @@ static int SearchRegExpNoCaptureMultiple(
|
||||
int match_start = -1;
|
||||
int match_end = 0;
|
||||
int pos = 0;
|
||||
int registers_per_match = RegExpImpl::IrregexpPrepare(regexp, subject,
|
||||
isolate->zone());
|
||||
int registers_per_match = RegExpImpl::IrregexpPrepare(regexp, subject);
|
||||
if (registers_per_match < 0) return RegExpImpl::RE_EXCEPTION;
|
||||
|
||||
int max_matches;
|
||||
@ -3880,8 +3872,7 @@ static int SearchRegExpNoCaptureMultiple(
|
||||
int num_matches = RegExpImpl::IrregexpExecRaw(regexp,
|
||||
subject,
|
||||
pos,
|
||||
register_vector,
|
||||
isolate->zone());
|
||||
register_vector);
|
||||
if (num_matches > 0) {
|
||||
for (int match_index = 0; match_index < num_matches; match_index++) {
|
||||
int32_t* current_match = ®ister_vector[match_index * 2];
|
||||
@ -3951,8 +3942,7 @@ static int SearchRegExpMultiple(
|
||||
FixedArrayBuilder* builder) {
|
||||
|
||||
ASSERT(subject->IsFlat());
|
||||
int registers_per_match = RegExpImpl::IrregexpPrepare(regexp, subject,
|
||||
isolate->zone());
|
||||
int registers_per_match = RegExpImpl::IrregexpPrepare(regexp, subject);
|
||||
if (registers_per_match < 0) return RegExpImpl::RE_EXCEPTION;
|
||||
|
||||
int max_matches;
|
||||
@ -3965,8 +3955,7 @@ static int SearchRegExpMultiple(
|
||||
int num_matches = RegExpImpl::IrregexpExecRaw(regexp,
|
||||
subject,
|
||||
0,
|
||||
register_vector,
|
||||
isolate->zone());
|
||||
register_vector);
|
||||
|
||||
int capture_count = regexp->CaptureCount();
|
||||
int subject_length = subject->length();
|
||||
@ -4052,8 +4041,7 @@ static int SearchRegExpMultiple(
|
||||
num_matches = RegExpImpl::IrregexpExecRaw(regexp,
|
||||
subject,
|
||||
pos,
|
||||
register_vector,
|
||||
isolate->zone());
|
||||
register_vector);
|
||||
} while (num_matches > 0);
|
||||
|
||||
if (num_matches != RegExpImpl::RE_EXCEPTION) {
|
||||
|
@ -1341,7 +1341,8 @@ TEST(MacroAssemblerNativeLotsOfRegisters) {
|
||||
TEST(MacroAssembler) {
|
||||
V8::Initialize(NULL);
|
||||
byte codes[1024];
|
||||
RegExpMacroAssemblerIrregexp m(Vector<byte>(codes, 1024));
|
||||
RegExpMacroAssemblerIrregexp m(Vector<byte>(codes, 1024),
|
||||
Isolate::Current()->zone());
|
||||
// ^f(o)o.
|
||||
Label fail, fail2, start;
|
||||
uc16 foo_chars[3];
|
||||
|
Loading…
Reference in New Issue
Block a user