153e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles)/* 253e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) * Copyright (C) 2004, 2008, 2009 Apple Inc. All rights reserved. 353e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) * Copyright (C) 2008 Collabora Ltd. 453e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) * Copyright (C) 2011 Peter Varga (pvarga@webkit.org), University of Szeged 553e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) * Copyright (C) 2013 Google Inc. All rights reserved. 653e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) * 753e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) * Redistribution and use in source and binary forms, with or without 853e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) * modification, are permitted provided that the following conditions 953e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) * are met: 1053e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) * 1. Redistributions of source code must retain the above copyright 1153e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) * notice, this list of conditions and the following disclaimer. 1253e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) * 2. Redistributions in binary form must reproduce the above copyright 1353e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) * notice, this list of conditions and the following disclaimer in the 1453e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) * documentation and/or other materials provided with the distribution. 1553e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) * 1653e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) * THIS SOFTWARE IS PROVIDED BY APPLE COMPUTER, INC. ``AS IS'' AND ANY 1753e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE 1853e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR 1953e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL APPLE COMPUTER, INC. OR 2053e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, 2153e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, 2253e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR 2353e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY 2453e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT 2553e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE 2602772c6a72f1ee0b226341a4f4439970c29fc861Ben Murdoch * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. 2753e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) */ 2853e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) 2953e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles)#include "config.h" 30a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)#include "bindings/v8/ScriptRegexp.h" 3153e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) 3253e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles)#include "bindings/v8/V8Binding.h" 3353e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles)#include "bindings/v8/V8PerIsolateData.h" 34d5428f32f5d1719f774f62e19147104ca245a3abTorne (Richard Coles)#include "bindings/v8/V8ScriptRunner.h" 35f91f5fa1608c2cdd9af1842fb5dadbe78275be2aBo Liu#include "core/dom/ScriptForbiddenScope.h" 3653e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) 3753e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles)namespace WebCore { 3853e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) 39a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)ScriptRegexp::ScriptRegexp(const String& pattern, TextCaseSensitivity caseSensitivity, MultilineMode multilineMode) 4053e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles){ 4193ac45cfc74041c8ae536ce58a9534d46db2024eTorne (Richard Coles) v8::Isolate* isolate = v8::Isolate::GetCurrent(); 4293ac45cfc74041c8ae536ce58a9534d46db2024eTorne (Richard Coles) v8::HandleScope handleScope(isolate); 43f6b7aed3f7ce69aca0d7a032d144cbd088b04393Torne (Richard Coles) v8::Context::Scope contextScope(V8PerIsolateData::from(isolate)->ensureScriptRegexpContext()); 44d5428f32f5d1719f774f62e19147104ca245a3abTorne (Richard Coles) v8::TryCatch tryCatch; 4553e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) 4653e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) unsigned flags = v8::RegExp::kNone; 4753e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) if (caseSensitivity == TextCaseInsensitive) 4853e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) flags |= v8::RegExp::kIgnoreCase; 4953e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) if (multilineMode == MultilineEnabled) 5053e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) flags |= v8::RegExp::kMultiline; 5153e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) 52d5428f32f5d1719f774f62e19147104ca245a3abTorne (Richard Coles) v8::Local<v8::RegExp> regex = v8::RegExp::New(v8String(isolate, pattern), static_cast<v8::RegExp::Flags>(flags)); 5353e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) 5453e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) // If the regex failed to compile we'll get an empty handle. 5553e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) if (!regex.IsEmpty()) 5693ac45cfc74041c8ae536ce58a9534d46db2024eTorne (Richard Coles) m_regex.set(isolate, regex); 5753e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles)} 5853e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) 59a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles)int ScriptRegexp::match(const String& string, int startFrom, int* matchLength) const 6053e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles){ 6153e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) if (matchLength) 6253e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) *matchLength = 0; 6353e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) 6453e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) if (m_regex.isEmpty() || string.isNull()) 65a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles) return -1; 6653e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) 6753e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) // v8 strings are limited to int. 6853e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) if (string.length() > INT_MAX) 69a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles) return -1; 7053e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) 71f91f5fa1608c2cdd9af1842fb5dadbe78275be2aBo Liu ScriptForbiddenScope::AllowUserAgentScript allowScript; 72f91f5fa1608c2cdd9af1842fb5dadbe78275be2aBo Liu 7393ac45cfc74041c8ae536ce58a9534d46db2024eTorne (Richard Coles) v8::Isolate* isolate = v8::Isolate::GetCurrent(); 7493ac45cfc74041c8ae536ce58a9534d46db2024eTorne (Richard Coles) v8::HandleScope handleScope(isolate); 75f6b7aed3f7ce69aca0d7a032d144cbd088b04393Torne (Richard Coles) v8::Context::Scope contextScope(V8PerIsolateData::from(isolate)->ensureScriptRegexpContext()); 7653e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) v8::TryCatch tryCatch; 7753e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) 78521d96ec04ace82590870fb04353ec4f82bb150fTorne (Richard Coles) v8::Local<v8::RegExp> regex = m_regex.newLocal(isolate); 79a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles) v8::Local<v8::Function> exec = regex->Get(v8AtomicString(isolate, "exec")).As<v8::Function>(); 80d5428f32f5d1719f774f62e19147104ca245a3abTorne (Richard Coles) v8::Handle<v8::Value> argv[] = { v8String(isolate, string.substring(startFrom)) }; 81d5428f32f5d1719f774f62e19147104ca245a3abTorne (Richard Coles) v8::Local<v8::Value> returnValue = V8ScriptRunner::callInternalFunction(exec, regex, WTF_ARRAY_LENGTH(argv), argv, isolate); 8253e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) 83d6cdb82654e8f3343a693ca752d5c4cee0324e17Torne (Richard Coles) if (tryCatch.HasCaught()) 84d6cdb82654e8f3343a693ca752d5c4cee0324e17Torne (Richard Coles) return -1; 85d6cdb82654e8f3343a693ca752d5c4cee0324e17Torne (Richard Coles) 8653e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) // RegExp#exec returns null if there's no match, otherwise it returns an 8753e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) // Array of strings with the first being the whole match string and others 8853e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) // being subgroups. The Array also has some random properties tacked on like 8953e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) // "index" which is the offset of the match. 9053e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) // 9153e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) // https://developer.mozilla.org/en-US/docs/JavaScript/Reference/Global_Objects/RegExp/exec 9253e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) 93d6cdb82654e8f3343a693ca752d5c4cee0324e17Torne (Richard Coles) ASSERT(!returnValue.IsEmpty()); 9453e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) if (!returnValue->IsArray()) 95a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles) return -1; 9653e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) 9753e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) v8::Local<v8::Array> result = returnValue.As<v8::Array>(); 98a854de003a23bf3c7f95ec0f8154ada64092ff5cTorne (Richard Coles) int matchOffset = result->Get(v8AtomicString(isolate, "index"))->ToInt32()->Value(); 9953e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) if (matchLength) { 10053e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) v8::Local<v8::String> match = result->Get(0).As<v8::String>(); 10153e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) *matchLength = match->Length(); 10253e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) } 10353e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) 10453e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) return matchOffset + startFrom; 10553e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles)} 10653e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles) 10753e740f4a82e17f3ae59772501622dc354e42336Torne (Richard Coles)} // namespace WebCore 108