diff options
Diffstat (limited to 'JavaScriptCore/runtime/RegExp.cpp')
-rw-r--r-- | JavaScriptCore/runtime/RegExp.cpp | 99 |
1 files changed, 84 insertions, 15 deletions
diff --git a/JavaScriptCore/runtime/RegExp.cpp b/JavaScriptCore/runtime/RegExp.cpp index 5ad9f3f..d4545cb 100644 --- a/JavaScriptCore/runtime/RegExp.cpp +++ b/JavaScriptCore/runtime/RegExp.cpp @@ -46,11 +46,33 @@ namespace JSC { +struct RegExpRepresentation { +#if ENABLE(YARR_JIT) + Yarr::RegexCodeBlock m_regExpJITCode; +#elif ENABLE(YARR) + OwnPtr<Yarr::BytecodePattern> m_regExpBytecode; +#else + JSRegExp* m_regExp; +#endif + +#if !ENABLE(YARR) + ~RegExpRepresentation() + { + jsRegExpFree(m_regExp); + } +#endif +}; + inline RegExp::RegExp(JSGlobalData* globalData, const UString& pattern, const UString& flags) : m_pattern(pattern) , m_flagBits(0) , m_constructionError(0) , m_numSubpatterns(0) +#if ENABLE(REGEXP_TRACING) + , m_rtMatchCallCount(0) + , m_rtMatchFoundCount(0) +#endif + , m_representation(adoptPtr(new RegExpRepresentation)) { // NOTE: The global flag is handled on a case-by-case basis by functions like // String::match and RegExpObject::match. @@ -65,16 +87,17 @@ inline RegExp::RegExp(JSGlobalData* globalData, const UString& pattern, const US compile(globalData); } -#if !ENABLE(YARR) RegExp::~RegExp() { - jsRegExpFree(m_regExp); } -#endif PassRefPtr<RegExp> RegExp::create(JSGlobalData* globalData, const UString& pattern, const UString& flags) { - return adoptRef(new RegExp(globalData, pattern, flags)); + RefPtr<RegExp> res = adoptRef(new RegExp(globalData, pattern, flags)); +#if ENABLE(REGEXP_TRACING) + globalData->addRegExpToTrace(res); +#endif + return res.release(); } #if ENABLE(YARR) @@ -82,9 +105,9 @@ PassRefPtr<RegExp> RegExp::create(JSGlobalData* globalData, const UString& patte void RegExp::compile(JSGlobalData* globalData) { #if ENABLE(YARR_JIT) - Yarr::jitCompileRegex(globalData, m_regExpJITCode, m_pattern, m_numSubpatterns, m_constructionError, ignoreCase(), multiline()); + Yarr::jitCompileRegex(globalData, m_representation->m_regExpJITCode, m_pattern, m_numSubpatterns, m_constructionError, ignoreCase(), multiline()); #else - m_regExpBytecode = Yarr::byteCompileRegex(m_pattern, m_numSubpatterns, m_constructionError, &globalData->m_regexAllocator, ignoreCase(), multiline()); + m_representation->m_regExpBytecode = Yarr::byteCompileRegex(m_pattern, m_numSubpatterns, m_constructionError, &globalData->m_regexAllocator, ignoreCase(), multiline()); #endif } @@ -94,14 +117,18 @@ int RegExp::match(const UString& s, int startOffset, Vector<int, 32>* ovector) startOffset = 0; if (ovector) ovector->resize(0); + +#if ENABLE(REGEXP_TRACING) + m_rtMatchCallCount++; +#endif if (static_cast<unsigned>(startOffset) > s.length() || s.isNull()) return -1; #if ENABLE(YARR_JIT) - if (!!m_regExpJITCode) { + if (!!m_representation->m_regExpJITCode) { #else - if (m_regExpBytecode) { + if (m_representation->m_regExpBytecode) { #endif int offsetVectorSize = (m_numSubpatterns + 1) * 3; // FIXME: should be 2 - but adding temporary fallback to pcre. int* offsetVector; @@ -119,9 +146,9 @@ int RegExp::match(const UString& s, int startOffset, Vector<int, 32>* ovector) offsetVector[j] = -1; #if ENABLE(YARR_JIT) - int result = Yarr::executeRegex(m_regExpJITCode, s.characters(), startOffset, s.length(), offsetVector, offsetVectorSize); + int result = Yarr::executeRegex(m_representation->m_regExpJITCode, s.characters(), startOffset, s.length(), offsetVector, offsetVectorSize); #else - int result = Yarr::interpretRegex(m_regExpBytecode.get(), s.characters(), startOffset, s.length(), offsetVector); + int result = Yarr::interpretRegex(m_representation->m_regExpBytecode.get(), s.characters(), startOffset, s.length(), offsetVector); #endif if (result < 0) { @@ -134,6 +161,11 @@ int RegExp::match(const UString& s, int startOffset, Vector<int, 32>* ovector) ovector->clear(); } +#if ENABLE(REGEXP_TRACING) + if (result != -1) + m_rtMatchFoundCount++; +#endif + return result; } @@ -144,14 +176,18 @@ int RegExp::match(const UString& s, int startOffset, Vector<int, 32>* ovector) void RegExp::compile(JSGlobalData*) { - m_regExp = 0; + m_representation->m_regExp = 0; JSRegExpIgnoreCaseOption ignoreCaseOption = ignoreCase() ? JSRegExpIgnoreCase : JSRegExpDoNotIgnoreCase; JSRegExpMultilineOption multilineOption = multiline() ? JSRegExpMultiline : JSRegExpSingleLine; - m_regExp = jsRegExpCompile(reinterpret_cast<const UChar*>(m_pattern.characters()), m_pattern.length(), ignoreCaseOption, multilineOption, &m_numSubpatterns, &m_constructionError); + m_representation->m_regExp = jsRegExpCompile(reinterpret_cast<const UChar*>(m_pattern.characters()), m_pattern.length(), ignoreCaseOption, multilineOption, &m_numSubpatterns, &m_constructionError); } int RegExp::match(const UString& s, int startOffset, Vector<int, 32>* ovector) { +#if ENABLE(REGEXP_TRACING) + m_rtMatchCallCount++; +#endif + if (startOffset < 0) startOffset = 0; if (ovector) @@ -160,7 +196,7 @@ int RegExp::match(const UString& s, int startOffset, Vector<int, 32>* ovector) if (static_cast<unsigned>(startOffset) > s.length() || s.isNull()) return -1; - if (m_regExp) { + if (m_representation->m_regExp) { // Set up the offset vector for the result. // First 2/3 used for result, the last third used by PCRE. int* offsetVector; @@ -175,7 +211,7 @@ int RegExp::match(const UString& s, int startOffset, Vector<int, 32>* ovector) offsetVector = ovector->data(); } - int numMatches = jsRegExpExecute(m_regExp, reinterpret_cast<const UChar*>(s.characters()), s.length(), startOffset, offsetVector, offsetVectorSize); + int numMatches = jsRegExpExecute(m_representation->m_regExp, reinterpret_cast<const UChar*>(s.characters()), s.length(), startOffset, offsetVector, offsetVectorSize); if (numMatches < 0) { #ifndef NDEBUG @@ -187,12 +223,45 @@ int RegExp::match(const UString& s, int startOffset, Vector<int, 32>* ovector) return -1; } +#if ENABLE(REGEXP_TRACING) + m_rtMatchFoundCount++; +#endif + return offsetVector[0]; } return -1; } - + #endif +#if ENABLE(REGEXP_TRACING) + void RegExp::printTraceData() + { + char formattedPattern[41]; + char rawPattern[41]; + + strncpy(rawPattern, m_pattern.utf8().data(), 40); + rawPattern[40]= '\0'; + + int pattLen = strlen(rawPattern); + + snprintf(formattedPattern, 41, (pattLen <= 38) ? "/%.38s/" : "/%.36s...", rawPattern); + +#if ENABLE(YARR_JIT) + Yarr::RegexCodeBlock& codeBlock = m_representation->m_regExpJITCode; + + char jitAddr[20]; + if (codeBlock.getFallback()) + sprintf(jitAddr, "fallback"); + else + sprintf(jitAddr, "0x%014lx", (uintptr_t)codeBlock.getAddr()); +#else + const char* jitAddr = "JIT Off"; +#endif + + printf("%-40.40s %16.16s %10d %10d\n", formattedPattern, jitAddr, m_rtMatchCallCount, m_rtMatchFoundCount); + } +#endif + } // namespace JSC |