summaryrefslogtreecommitdiffstats
path: root/chromium/third_party/WebKit/Source/bindings/v8
diff options
context:
space:
mode:
authorJocelyn Turcotte <jocelyn.turcotte@digia.com>2014-08-08 14:30:41 +0200
committerJocelyn Turcotte <jocelyn.turcotte@digia.com>2014-08-12 13:49:54 +0200
commitab0a50979b9eb4dfa3320eff7e187e41efedf7a9 (patch)
tree498dfb8a97ff3361a9f7486863a52bb4e26bb898 /chromium/third_party/WebKit/Source/bindings/v8
parent4ce69f7403811819800e7c5ae1318b2647e778d1 (diff)
Update Chromium to beta version 37.0.2062.68
Change-Id: I188e3b5aff1bec75566014291b654eb19f5bc8ca Reviewed-by: Andras Becsi <andras.becsi@digia.com>
Diffstat (limited to 'chromium/third_party/WebKit/Source/bindings/v8')
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ArrayValue.cpp2
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/BindingSecurity.cpp44
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/BindingSecurity.h12
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/CallbackPromiseAdapter.h32
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/CustomElementBinding.cpp2
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/CustomElementBinding.h6
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/CustomElementConstructorBuilder.cpp102
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/CustomElementConstructorBuilder.h3
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/CustomElementWrapper.cpp20
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/CustomElementWrapper.h3
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/DOMDataStore.cpp27
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/DOMDataStore.h108
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/DOMRequestState.h85
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/DOMWrapperMap.h134
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/DOMWrapperWorld.cpp144
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/DOMWrapperWorld.h83
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/DebuggerScript.js179
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/Dictionary.cpp191
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/Dictionary.h131
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ExceptionMessages.cpp83
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ExceptionMessages.h115
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ExceptionState.cpp53
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ExceptionState.h57
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ExceptionStatePlaceholder.cpp4
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ExceptionStatePlaceholder.h29
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/IDBBindingUtilities.cpp181
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/IDBBindingUtilities.h24
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/IDBBindingUtilitiesTest.cpp131
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/NPV8Object.cpp126
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/NPV8Object.h6
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/Nullable.h51
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/PageScriptDebugServer.cpp114
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/PageScriptDebugServer.h36
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/RetainedDOMInfo.h17
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ScheduledAction.cpp53
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ScheduledAction.h17
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ScopedPersistent.h7
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ScriptCallStackFactory.cpp26
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ScriptCallStackFactory.h8
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ScriptController.cpp334
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ScriptController.h38
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ScriptDebugServer.cpp268
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ScriptDebugServer.h49
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ScriptEventListener.cpp78
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ScriptEventListener.h9
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ScriptFunction.cpp32
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ScriptFunction.h (renamed from chromium/third_party/WebKit/Source/bindings/v8/custom/V8MIDIOutputCustom.cpp)32
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ScriptFunctionCall.cpp113
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ScriptFunctionCall.h26
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ScriptGCEvent.cpp2
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ScriptGCEvent.h3
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ScriptHeapSnapshot.cpp18
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ScriptHeapSnapshot.h9
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ScriptObject.h66
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ScriptPreprocessor.cpp46
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ScriptPreprocessor.h7
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ScriptProfiler.cpp85
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ScriptProfiler.h10
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ScriptPromise.cpp104
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ScriptPromise.h45
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ScriptPromiseResolver.cpp74
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ScriptPromiseResolver.h139
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ScriptPromiseResolverTest.cpp184
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ScriptPromiseResolverWithContext.cpp101
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ScriptPromiseResolverWithContext.h145
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ScriptPromiseTest.cpp260
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ScriptRegexp.cpp25
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ScriptScope.cpp58
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ScriptScope.h55
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ScriptSourceCode.h2
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ScriptState.cpp148
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ScriptState.h179
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ScriptString.cpp45
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ScriptString.h27
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ScriptValue.cpp96
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ScriptValue.h89
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/ScriptWrappable.h169
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/SerializedScriptValue.cpp1139
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/SerializedScriptValue.h37
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/UnsafePersistent.h129
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8AbstractEventListener.cpp89
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8AbstractEventListener.h30
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8Binding.cpp670
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8Binding.h1340
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8BindingMacros.h115
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8Callback.cpp8
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8Callback.h14
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8CustomElementLifecycleCallbacks.cpp97
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8CustomElementLifecycleCallbacks.h12
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8DOMActivityLogger.cpp72
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8DOMActivityLogger.h26
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8DOMConfiguration.cpp49
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8DOMConfiguration.h23
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8DOMWrapper.cpp68
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8DOMWrapper.h96
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8ErrorHandler.cpp42
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8ErrorHandler.h16
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8EventListener.cpp24
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8EventListener.h11
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8EventListenerList.cpp17
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8EventListenerList.h37
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8GCController.cpp207
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8GCController.h3
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8GCForContextDispose.cpp5
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8GCForContextDispose.h1
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8GarbageCollected.h (renamed from chromium/third_party/WebKit/Source/bindings/v8/ScriptObject.cpp)87
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8HiddenPropertyName.cpp79
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8HiddenPropertyName.h83
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8HiddenValue.cpp46
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8HiddenValue.h61
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8Initializer.cpp101
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8LazyEventListener.cpp113
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8LazyEventListener.h16
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8MutationCallback.cpp37
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8MutationCallback.h17
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8NPObject.cpp156
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8NPObject.h3
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8NPUtils.cpp6
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8NodeFilterCondition.cpp42
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8NodeFilterCondition.h15
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8ObjectConstructor.cpp28
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8ObjectConstructor.h23
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8PerContextData.cpp79
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8PerContextData.h119
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8PerIsolateData.cpp157
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8PerIsolateData.h102
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8PersistentValueMap.h128
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8PersistentValueVector.h (renamed from chromium/third_party/WebKit/Source/bindings/v8/custom/V8NodeListCustom.cpp)59
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8RecursionScope.cpp7
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8RecursionScope.h41
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8ScriptRunner.cpp142
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8ScriptRunner.h16
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8StringResource.cpp85
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8StringResource.h59
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8ThrowException.cpp4
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8ThrowException.h4
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8Utilities.cpp181
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8Utilities.h72
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8ValueCache.cpp55
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8ValueCache.h42
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8WindowShell.cpp248
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8WindowShell.h40
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8WorkerGlobalScopeEventListener.cpp66
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/V8WorkerGlobalScopeEventListener.h14
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/WorkerScriptController.cpp157
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/WorkerScriptController.h36
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/WorkerScriptDebugServer.cpp21
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/WorkerScriptDebugServer.h18
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/WrapperTypeInfo.h85
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8AlgorithmCustom.cpp78
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8ArrayBufferCustom.cpp28
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8ArrayBufferCustom.h17
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8ArrayBufferViewCustom.cpp4
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8ArrayBufferViewCustom.h7
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8ArrayBufferViewCustomScript.js36
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8AudioNodeCustom.cpp36
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8BiquadFilterNodeCustom.cpp60
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8BlobCustom.cpp13
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8BlobCustomHelpers.cpp47
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8BlobCustomHelpers.h10
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8CSSRuleCustom.cpp29
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8CSSStyleDeclarationCustom.cpp132
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8CSSValueCustom.cpp20
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8CanvasRenderingContext2DCustom.cpp45
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8CanvasRenderingContextCustom.cpp51
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8ClientCustom.cpp39
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8CryptoCustom.cpp11
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8CustomEventCustom.cpp25
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8CustomSQLStatementErrorCallback.cpp23
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8CustomXPathNSResolver.cpp28
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8CustomXPathNSResolver.h6
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8DataViewCustom.cpp2
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8DataViewCustom.h4
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8DedicatedWorkerGlobalScopeCustom.cpp17
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8DeviceMotionEventCustom.cpp40
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8DeviceOrientationEventCustom.cpp10
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8DocumentCustom.cpp40
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8ElementCustom.cpp236
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8EntryCustom.cpp8
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8EntrySyncCustom.cpp8
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8ErrorEventCustom.cpp12
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8EventCustom.cpp12
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8EventTargetCustom.cpp9
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8FileCustom.cpp15
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8FileReaderCustom.cpp10
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8Float32ArrayCustom.h4
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8Float64ArrayCustom.h4
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8FormDataCustom.cpp71
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8GeolocationCustom.cpp80
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8HTMLAllCollectionCustom.cpp46
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8HTMLCanvasElementCustom.cpp55
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8HTMLCollectionCustom.cpp16
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8HTMLDocumentCustom.cpp27
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8HTMLElementCustom.cpp4
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8HTMLFormControlsCollectionCustom.cpp71
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8HTMLFrameElementCustom.cpp59
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8HTMLOptionsCollectionCustom.cpp56
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8HTMLPlugInElementCustom.cpp34
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8HistoryCustom.cpp40
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8ImageDataCustom.cpp2
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8InjectedScriptHostCustom.cpp151
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8InjectedScriptManager.cpp45
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8InspectorFrontendHostCustom.cpp13
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8Int16ArrayCustom.h4
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8Int32ArrayCustom.h4
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8Int8ArrayCustom.h4
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8JavaScriptCallFrameCustom.cpp2
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8LocationCustom.cpp2
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8MIDIInputCustom.cpp52
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8MessageChannelCustom.cpp15
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8MessageEventCustom.cpp92
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8MessagePortCustom.cpp16
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8MutationObserverCustom.cpp19
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8NodeCustom.cpp67
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8OscillatorNodeCustom.cpp60
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8PannerNodeCustom.cpp84
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8PerformanceEntryCustom.cpp8
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8PopStateEventCustom.cpp16
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8PromiseCustom.cpp794
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8PromiseCustom.h136
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8SQLResultSetRowListCustom.cpp17
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8SQLTransactionCustom.cpp42
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8SQLTransactionSyncCustom.cpp26
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8SVGElementCustom.cpp4
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8SVGLengthCustom.cpp102
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8SVGPathSegCustom.cpp42
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8ServiceWorkerCustom.cpp38
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8StyleSheetCustom.cpp6
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8SubtleCryptoCustom.cpp125
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8TextCustom.cpp4
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8TextTrackCueCustom.cpp31
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8TrackEventCustom.cpp14
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8TypedArrayCustom.h17
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8Uint16ArrayCustom.h4
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8Uint32ArrayCustom.h4
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8Uint8ArrayCustom.h4
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8Uint8ClampedArrayCustom.h4
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8WebGLRenderingContextCustom.cpp449
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8WebKitPointCustom.cpp4
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8WindowCustom.cpp242
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8WorkerCryptoCustom.cpp43
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8WorkerCustom.cpp16
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8WorkerGlobalScopeCustom.cpp22
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8XMLHttpRequestCustom.cpp60
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/V8XSLTProcessorCustom.cpp34
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/custom/custom.gypi92
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/npruntime.cpp4
-rw-r--r--chromium/third_party/WebKit/Source/bindings/v8/v8.gypi165
248 files changed, 9206 insertions, 8673 deletions
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ArrayValue.cpp b/chromium/third_party/WebKit/Source/bindings/v8/ArrayValue.cpp
index 1280548b9f6..065fd2f8815 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/ArrayValue.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ArrayValue.cpp
@@ -62,7 +62,7 @@ bool ArrayValue::get(size_t index, Dictionary& value) const
ASSERT(m_isolate);
ASSERT(m_isolate == v8::Isolate::GetCurrent());
- v8::Local<v8::Value> indexedValue = m_array->Get(v8::Integer::NewFromUnsigned(index, m_isolate));
+ v8::Local<v8::Value> indexedValue = m_array->Get(v8::Integer::NewFromUnsigned(m_isolate, index));
if (indexedValue.IsEmpty() || !indexedValue->IsObject())
return false;
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/BindingSecurity.cpp b/chromium/third_party/WebKit/Source/bindings/v8/BindingSecurity.cpp
index 7f9db62257d..126b2ba6519 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/BindingSecurity.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/BindingSecurity.cpp
@@ -34,65 +34,69 @@
#include "bindings/v8/V8Binding.h"
#include "core/dom/Document.h"
#include "core/html/HTMLFrameElementBase.h"
-#include "core/frame/DOMWindow.h"
-#include "core/frame/Frame.h"
+#include "core/frame/LocalDOMWindow.h"
+#include "core/frame/LocalFrame.h"
#include "core/frame/Settings.h"
#include "platform/weborigin/SecurityOrigin.h"
namespace WebCore {
-static bool isDocumentAccessibleFromDOMWindow(Document* targetDocument, DOMWindow* activeWindow)
+static bool isDocumentAccessibleFromDOMWindow(Document* targetDocument, LocalDOMWindow* callingWindow)
{
if (!targetDocument)
return false;
- if (!activeWindow)
+ if (!callingWindow)
return false;
- if (activeWindow->document()->securityOrigin()->canAccess(targetDocument->securityOrigin()))
+ if (callingWindow->document()->securityOrigin()->canAccess(targetDocument->securityOrigin()))
return true;
return false;
}
-static bool canAccessDocument(Document* targetDocument, ExceptionState& exceptionState)
+static bool canAccessDocument(v8::Isolate* isolate, Document* targetDocument, ExceptionState& exceptionState)
{
- DOMWindow* activeWindow = activeDOMWindow();
- if (isDocumentAccessibleFromDOMWindow(targetDocument, activeWindow))
+ LocalDOMWindow* callingWindow = callingDOMWindow(isolate);
+ if (isDocumentAccessibleFromDOMWindow(targetDocument, callingWindow))
return true;
if (targetDocument->domWindow())
- exceptionState.throwSecurityError(targetDocument->domWindow()->sanitizedCrossDomainAccessErrorMessage(activeWindow), targetDocument->domWindow()->crossDomainAccessErrorMessage(activeWindow));
+ exceptionState.throwSecurityError(targetDocument->domWindow()->sanitizedCrossDomainAccessErrorMessage(callingWindow), targetDocument->domWindow()->crossDomainAccessErrorMessage(callingWindow));
return false;
}
-static bool canAccessDocument(Document* targetDocument, SecurityReportingOption reportingOption = ReportSecurityError)
+static bool canAccessDocument(v8::Isolate* isolate, Document* targetDocument, SecurityReportingOption reportingOption = ReportSecurityError)
{
- DOMWindow* activeWindow = activeDOMWindow();
- if (isDocumentAccessibleFromDOMWindow(targetDocument, activeWindow))
+ LocalDOMWindow* callingWindow = callingDOMWindow(isolate);
+ if (isDocumentAccessibleFromDOMWindow(targetDocument, callingWindow))
return true;
if (reportingOption == ReportSecurityError && targetDocument->domWindow()) {
- if (Frame* frame = targetDocument->frame())
- frame->domWindow()->printErrorMessage(targetDocument->domWindow()->crossDomainAccessErrorMessage(activeWindow));
+ if (LocalFrame* frame = targetDocument->frame())
+ frame->domWindow()->printErrorMessage(targetDocument->domWindow()->crossDomainAccessErrorMessage(callingWindow));
}
return false;
}
-bool BindingSecurity::shouldAllowAccessToFrame(Frame* target, SecurityReportingOption reportingOption)
+bool BindingSecurity::shouldAllowAccessToFrame(v8::Isolate* isolate, Frame* target, SecurityReportingOption reportingOption)
{
- return target && canAccessDocument(target->document(), reportingOption);
+ if (!target || !target->isLocalFrame())
+ return false;
+ return canAccessDocument(isolate, toLocalFrame(target)->document(), reportingOption);
}
-bool BindingSecurity::shouldAllowAccessToFrame(Frame* target, ExceptionState& exceptionState)
+bool BindingSecurity::shouldAllowAccessToFrame(v8::Isolate* isolate, Frame* target, ExceptionState& exceptionState)
{
- return target && canAccessDocument(target->document(), exceptionState);
+ if (!target || !target->isLocalFrame())
+ return false;
+ return canAccessDocument(isolate, toLocalFrame(target)->document(), exceptionState);
}
-bool BindingSecurity::shouldAllowAccessToNode(Node* target, ExceptionState& exceptionState)
+bool BindingSecurity::shouldAllowAccessToNode(v8::Isolate* isolate, Node* target, ExceptionState& exceptionState)
{
- return target && canAccessDocument(&target->document(), exceptionState);
+ return target && canAccessDocument(isolate, &target->document(), exceptionState);
}
}
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/BindingSecurity.h b/chromium/third_party/WebKit/Source/bindings/v8/BindingSecurity.h
index 253a7f25781..b6e5bba893d 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/BindingSecurity.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/BindingSecurity.h
@@ -31,13 +31,15 @@
#ifndef BindingSecurity_h
#define BindingSecurity_h
+// FIXME: The LocalFrame include should not be necessary, clients should be including it where they use it.
+#include "core/frame/LocalFrame.h"
#include "wtf/text/WTFString.h"
+#include <v8.h>
namespace WebCore {
-class DOMWindow;
+class LocalDOMWindow;
class ExceptionState;
-class Frame;
class Node;
enum SecurityReportingOption {
@@ -47,9 +49,9 @@ enum SecurityReportingOption {
class BindingSecurity {
public:
- static bool shouldAllowAccessToNode(Node*, ExceptionState&);
- static bool shouldAllowAccessToFrame(Frame*, SecurityReportingOption = ReportSecurityError);
- static bool shouldAllowAccessToFrame(Frame*, ExceptionState&);
+ static bool shouldAllowAccessToNode(v8::Isolate*, Node*, ExceptionState&);
+ static bool shouldAllowAccessToFrame(v8::Isolate*, Frame*, SecurityReportingOption = ReportSecurityError);
+ static bool shouldAllowAccessToFrame(v8::Isolate*, Frame*, ExceptionState&);
};
}
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/CallbackPromiseAdapter.h b/chromium/third_party/WebKit/Source/bindings/v8/CallbackPromiseAdapter.h
index 19b5a543918..21719792209 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/CallbackPromiseAdapter.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/CallbackPromiseAdapter.h
@@ -31,8 +31,7 @@
#ifndef CallbackPromiseAdapter_h
#define CallbackPromiseAdapter_h
-#include "bindings/v8/DOMRequestState.h"
-#include "bindings/v8/ScriptPromiseResolver.h"
+#include "bindings/v8/ScriptPromiseResolverWithContext.h"
#include "public/platform/WebCallbacks.h"
namespace WebCore {
@@ -40,16 +39,25 @@ namespace WebCore {
// This class provides an easy way to convert from a Script-exposed
// class (i.e. a class that has a toV8() overload) that uses Promises
// to a WebKit API class that uses WebCallbacks. You can define
-// seperate Success and Error classes, but this example just uses one
+// separate Success and Error classes, but this example just uses one
// object for both.
//
// To use:
//
// class MyClass ... {
// typedef blink::WebMyClass WebType;
-// static PassRefPtr<MyClass> from(blink::WebMyClass* webInstance) {
+// static PassRefPtr<MyClass> from(ScriptPromiseResolverWithContext* resolver,
+// blink::WebMyClass* webInstance) {
// // convert/create as appropriate, but often it's just:
// return MyClass::create(adoptPtr(webInstance));
+//
+// // Since promise resolving is done as an async task, it's not
+// // guaranteed that the script context has seen the promise resolve
+// // immediately after calling onSuccess/onError. You can use the
+// // ScriptPromise from the resolver to schedule a task that executes
+// // after resolving:
+// ScriptState::Scope scope(resolver->scriptState());
+// resolver->promise().then(...);
// }
//
// Now when calling into a WebKit API that requires a WebCallbacks<blink::WebMyClass, blink::WebMyClass>*:
@@ -61,28 +69,24 @@ namespace WebCore {
// example that ownership of the WebCallbacks instance is being passed
// in and it is up to the callee to free the WebCallbacks instace.
template<typename S, typename T>
-class CallbackPromiseAdapter : public blink::WebCallbacks<typename S::WebType, typename T::WebType> {
+class CallbackPromiseAdapter FINAL : public blink::WebCallbacks<typename S::WebType, typename T::WebType> {
public:
- explicit CallbackPromiseAdapter(PassRefPtr<ScriptPromiseResolver> resolver, ExecutionContext* context)
+ CallbackPromiseAdapter(PassRefPtr<ScriptPromiseResolverWithContext> resolver)
: m_resolver(resolver)
- , m_requestState(context)
{
}
virtual ~CallbackPromiseAdapter() { }
virtual void onSuccess(typename S::WebType* result) OVERRIDE
{
- DOMRequestState::Scope scope(m_requestState);
- m_resolver->resolve(S::from(result));
+ m_resolver->resolve(S::from(m_resolver.get(), result));
}
- void onError(typename T::WebType* error) OVERRIDE
+ virtual void onError(typename T::WebType* error) OVERRIDE
{
- DOMRequestState::Scope scope(m_requestState);
- m_resolver->reject(T::from(error));
+ m_resolver->reject(T::from(m_resolver.get(), error));
}
private:
- RefPtr<ScriptPromiseResolver> m_resolver;
- DOMRequestState m_requestState;
+ RefPtr<ScriptPromiseResolverWithContext> m_resolver;
WTF_MAKE_NONCOPYABLE(CallbackPromiseAdapter);
};
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/CustomElementBinding.cpp b/chromium/third_party/WebKit/Source/bindings/v8/CustomElementBinding.cpp
index 25ba61792f3..7a692394496 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/CustomElementBinding.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/CustomElementBinding.cpp
@@ -43,7 +43,7 @@ CustomElementBinding::CustomElementBinding(v8::Isolate* isolate, v8::Handle<v8::
, m_prototype(isolate, prototype)
, m_wrapperType(wrapperType)
{
- ASSERT(m_prototype.value());
+ ASSERT(!m_prototype.isEmpty());
ASSERT(m_wrapperType);
}
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/CustomElementBinding.h b/chromium/third_party/WebKit/Source/bindings/v8/CustomElementBinding.h
index 3fa394a0b09..b989e361823 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/CustomElementBinding.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/CustomElementBinding.h
@@ -31,7 +31,7 @@
#ifndef CustomElementBinding_h
#define CustomElementBinding_h
-#include "bindings/v8/UnsafePersistent.h"
+#include "bindings/v8/ScopedPersistent.h"
#include "wtf/PassOwnPtr.h"
#include <v8.h>
@@ -43,7 +43,7 @@ class CustomElementBinding {
public:
static PassOwnPtr<CustomElementBinding> create(v8::Isolate*, v8::Handle<v8::Object> prototype, const WrapperTypeInfo*);
- ~CustomElementBinding() { m_prototype.dispose(); }
+ ~CustomElementBinding() { }
v8::Handle<v8::Object> prototype() { return m_prototype.newLocal(m_isolate); }
const WrapperTypeInfo* wrapperType() { return m_wrapperType; }
@@ -52,7 +52,7 @@ private:
CustomElementBinding(v8::Isolate*, v8::Handle<v8::Object> prototype, const WrapperTypeInfo*);
v8::Isolate* m_isolate;
- UnsafePersistent<v8::Object> m_prototype;
+ ScopedPersistent<v8::Object> m_prototype;
const WrapperTypeInfo* m_wrapperType;
};
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/CustomElementConstructorBuilder.cpp b/chromium/third_party/WebKit/Source/bindings/v8/CustomElementConstructorBuilder.cpp
index b13466635ae..a8e43a1012e 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/CustomElementConstructorBuilder.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/CustomElementConstructorBuilder.cpp
@@ -31,20 +31,18 @@
#include "config.h"
#include "bindings/v8/CustomElementConstructorBuilder.h"
-#include "HTMLNames.h"
-#include "SVGNames.h"
-#include "V8Document.h"
-#include "V8HTMLElementWrapperFactory.h"
-#include "V8SVGElementWrapperFactory.h"
+#include "bindings/core/v8/V8Document.h"
#include "bindings/v8/CustomElementBinding.h"
#include "bindings/v8/DOMWrapperWorld.h"
#include "bindings/v8/Dictionary.h"
#include "bindings/v8/ExceptionState.h"
-#include "bindings/v8/ScriptState.h"
-#include "bindings/v8/UnsafePersistent.h"
#include "bindings/v8/V8Binding.h"
-#include "bindings/v8/V8HiddenPropertyName.h"
+#include "bindings/v8/V8HiddenValue.h"
#include "bindings/v8/V8PerContextData.h"
+#include "core/HTMLNames.h"
+#include "core/SVGNames.h"
+#include "core/V8HTMLElementWrapperFactory.h" // FIXME: should be bindings/core/v8
+#include "core/V8SVGElementWrapperFactory.h" // FIXME: should be bindings/core/v8
#include "core/dom/Document.h"
#include "core/dom/custom/CustomElementCallbackDispatcher.h"
#include "core/dom/custom/CustomElementDefinition.h"
@@ -56,44 +54,58 @@ namespace WebCore {
static void constructCustomElement(const v8::FunctionCallbackInfo<v8::Value>&);
-CustomElementConstructorBuilder::CustomElementConstructorBuilder(ScriptState* state, const Dictionary* options)
- : m_context(state->context())
+CustomElementConstructorBuilder::CustomElementConstructorBuilder(ScriptState* scriptState, const Dictionary* options)
+ : m_scriptState(scriptState)
, m_options(options)
, m_wrapperType(0)
{
- ASSERT(m_context == v8::Isolate::GetCurrent()->GetCurrentContext());
+ ASSERT(m_scriptState->context() == m_scriptState->isolate()->GetCurrentContext());
}
bool CustomElementConstructorBuilder::isFeatureAllowed() const
{
- // Check that we are in the main world
- return !DOMWrapperWorld::isolatedWorld(m_context);
+ return m_scriptState->world().isMainWorld();
}
bool CustomElementConstructorBuilder::validateOptions(const AtomicString& type, QualifiedName& tagName, ExceptionState& exceptionState)
{
ASSERT(m_prototype.IsEmpty());
+ v8::TryCatch tryCatch;
+
ScriptValue prototypeScriptValue;
if (m_options->get("prototype", prototypeScriptValue) && !prototypeScriptValue.isNull()) {
+ ASSERT(!tryCatch.HasCaught());
if (!prototypeScriptValue.isObject()) {
CustomElementException::throwException(CustomElementException::PrototypeNotAnObject, type, exceptionState);
+ tryCatch.ReThrow();
return false;
}
m_prototype = prototypeScriptValue.v8Value().As<v8::Object>();
- } else {
- m_prototype = v8::Object::New();
- v8::Local<v8::Object> basePrototype = V8PerContextData::from(m_context)->prototypeForType(&V8HTMLElement::wrapperTypeInfo);
+ } else if (!tryCatch.HasCaught()) {
+ m_prototype = v8::Object::New(m_scriptState->isolate());
+ v8::Local<v8::Object> basePrototype = m_scriptState->perContextData()->prototypeForType(&V8HTMLElement::wrapperTypeInfo);
if (!basePrototype.IsEmpty())
m_prototype->SetPrototype(basePrototype);
}
- String extends;
+ if (tryCatch.HasCaught()) {
+ tryCatch.ReThrow();
+ return false;
+ }
+
+ AtomicString extends;
bool extendsProvidedAndNonNull = m_options->get("extends", extends);
- if (!V8PerContextData::from(m_context)) {
+ if (tryCatch.HasCaught()) {
+ tryCatch.ReThrow();
+ return false;
+ }
+
+ if (!m_scriptState->perContextData()) {
// FIXME: This should generate an InvalidContext exception at a later point.
CustomElementException::throwException(CustomElementException::ContextDestroyedCheckingPrototype, type, exceptionState);
+ tryCatch.ReThrow();
return false;
}
@@ -101,6 +113,8 @@ bool CustomElementConstructorBuilder::validateOptions(const AtomicString& type,
if (hasValidPrototypeChainFor(&V8SVGElement::wrapperTypeInfo))
namespaceURI = SVGNames::svgNamespaceURI;
+ ASSERT(!tryCatch.HasCaught());
+
AtomicString localName;
if (extendsProvidedAndNonNull) {
@@ -108,15 +122,18 @@ bool CustomElementConstructorBuilder::validateOptions(const AtomicString& type,
if (!Document::isValidName(localName)) {
CustomElementException::throwException(CustomElementException::ExtendsIsInvalidName, type, exceptionState);
+ tryCatch.ReThrow();
return false;
}
if (CustomElement::isValidName(localName)) {
CustomElementException::throwException(CustomElementException::ExtendsIsCustomElementName, type, exceptionState);
+ tryCatch.ReThrow();
return false;
}
} else {
if (namespaceURI == SVGNames::svgNamespaceURI) {
CustomElementException::throwException(CustomElementException::ExtendsIsInvalidName, type, exceptionState);
+ tryCatch.ReThrow();
return false;
}
localName = type;
@@ -129,6 +146,7 @@ bool CustomElementConstructorBuilder::validateOptions(const AtomicString& type,
else
m_wrapperType = findWrapperTypeForSVGTagName(localName);
+ ASSERT(!tryCatch.HasCaught());
ASSERT(m_wrapperType);
tagName = QualifiedName(nullAtom, localName, namespaceURI);
return m_wrapperType;
@@ -138,18 +156,16 @@ PassRefPtr<CustomElementLifecycleCallbacks> CustomElementConstructorBuilder::cre
{
ASSERT(!m_prototype.IsEmpty());
- RefPtr<ExecutionContext> executionContext(toExecutionContext(m_context));
-
v8::TryCatch exceptionCatcher;
exceptionCatcher.SetVerbose(true);
- v8::Isolate* isolate = v8::Isolate::GetCurrent();
+ v8::Isolate* isolate = m_scriptState->isolate();
v8::Handle<v8::Function> created = retrieveCallback(isolate, "createdCallback");
v8::Handle<v8::Function> attached = retrieveCallback(isolate, "attachedCallback");
v8::Handle<v8::Function> detached = retrieveCallback(isolate, "detachedCallback");
v8::Handle<v8::Function> attributeChanged = retrieveCallback(isolate, "attributeChangedCallback");
- m_callbacks = V8CustomElementLifecycleCallbacks::create(executionContext.get(), m_prototype, created, attached, detached, attributeChanged);
+ m_callbacks = V8CustomElementLifecycleCallbacks::create(m_scriptState.get(), m_prototype, created, attached, detached, attributeChanged);
return m_callbacks.get();
}
@@ -167,7 +183,7 @@ bool CustomElementConstructorBuilder::createConstructor(Document* document, Cust
ASSERT(m_constructor.IsEmpty());
ASSERT(document);
- v8::Isolate* isolate = m_context->GetIsolate();
+ v8::Isolate* isolate = m_scriptState->isolate();
if (!prototypeIsValid(definition->descriptor().type(), exceptionState))
return false;
@@ -191,10 +207,10 @@ bool CustomElementConstructorBuilder::createConstructor(Document* document, Cust
m_constructor->SetName(v8Type->IsNull() ? v8TagName : v8Type.As<v8::String>());
- V8HiddenPropertyName::setNamedHiddenReference(m_constructor, "customElementDocument", toV8(document, m_context->Global(), isolate));
- V8HiddenPropertyName::setNamedHiddenReference(m_constructor, "customElementNamespaceURI", v8String(isolate, descriptor.namespaceURI()));
- V8HiddenPropertyName::setNamedHiddenReference(m_constructor, "customElementTagName", v8TagName);
- V8HiddenPropertyName::setNamedHiddenReference(m_constructor, "customElementType", v8Type);
+ V8HiddenValue::setHiddenValue(isolate, m_constructor, V8HiddenValue::customElementDocument(isolate), toV8(document, m_scriptState->context()->Global(), isolate));
+ V8HiddenValue::setHiddenValue(isolate, m_constructor, V8HiddenValue::customElementNamespaceURI(isolate), v8String(isolate, descriptor.namespaceURI()));
+ V8HiddenValue::setHiddenValue(isolate, m_constructor, V8HiddenValue::customElementTagName(isolate), v8TagName);
+ V8HiddenValue::setHiddenValue(isolate, m_constructor, V8HiddenValue::customElementType(isolate), v8Type);
v8::Handle<v8::String> prototypeKey = v8String(isolate, "prototype");
ASSERT(m_constructor->HasOwnProperty(prototypeKey));
@@ -207,7 +223,7 @@ bool CustomElementConstructorBuilder::createConstructor(Document* document, Cust
// property.
m_constructor->ForceSet(prototypeKey, m_prototype, v8::PropertyAttribute(v8::ReadOnly | v8::DontEnum | v8::DontDelete));
- V8HiddenPropertyName::setNamedHiddenReference(m_prototype, "customElementIsInterfacePrototypeObject", v8::True(isolate));
+ V8HiddenValue::setHiddenValue(isolate, m_prototype, V8HiddenValue::customElementIsInterfacePrototypeObject(isolate), v8::True(isolate));
m_prototype->ForceSet(v8String(isolate, "constructor"), m_constructor, v8::DontEnum);
return true;
@@ -215,12 +231,12 @@ bool CustomElementConstructorBuilder::createConstructor(Document* document, Cust
bool CustomElementConstructorBuilder::prototypeIsValid(const AtomicString& type, ExceptionState& exceptionState) const
{
- if (m_prototype->InternalFieldCount() || !m_prototype->GetHiddenValue(V8HiddenPropertyName::customElementIsInterfacePrototypeObject(m_context->GetIsolate())).IsEmpty()) {
+ if (m_prototype->InternalFieldCount() || !V8HiddenValue::getHiddenValue(m_scriptState->isolate(), m_prototype, V8HiddenValue::customElementIsInterfacePrototypeObject(m_scriptState->isolate())).IsEmpty()) {
CustomElementException::throwException(CustomElementException::PrototypeInUse, type, exceptionState);
return false;
}
- if (m_prototype->GetPropertyAttributes(v8String(m_context->GetIsolate(), "constructor")) & v8::DontDelete) {
+ if (m_prototype->GetPropertyAttributes(v8String(m_scriptState->isolate(), "constructor")) & v8::DontDelete) {
CustomElementException::throwException(CustomElementException::ConstructorPropertyNotConfigurable, type, exceptionState);
return false;
}
@@ -232,17 +248,17 @@ bool CustomElementConstructorBuilder::didRegisterDefinition(CustomElementDefinit
{
ASSERT(!m_constructor.IsEmpty());
- return m_callbacks->setBinding(definition, CustomElementBinding::create(m_context->GetIsolate(), m_prototype, m_wrapperType));
+ return m_callbacks->setBinding(definition, CustomElementBinding::create(m_scriptState->isolate(), m_prototype, m_wrapperType));
}
ScriptValue CustomElementConstructorBuilder::bindingsReturnValue() const
{
- return ScriptValue(m_constructor, m_context->GetIsolate());
+ return ScriptValue(m_scriptState.get(), m_constructor);
}
bool CustomElementConstructorBuilder::hasValidPrototypeChainFor(const WrapperTypeInfo* type) const
{
- v8::Handle<v8::Object> elementPrototype = V8PerContextData::from(m_context)->prototypeForType(type);
+ v8::Handle<v8::Object> elementPrototype = m_scriptState->perContextData()->prototypeForType(type);
if (elementPrototype.IsEmpty())
return false;
@@ -266,22 +282,28 @@ static void constructCustomElement(const v8::FunctionCallbackInfo<v8::Value>& in
}
if (info.Length() > 0) {
- throwUninformativeAndGenericTypeError(isolate);
+ throwTypeError("This constructor should be called without arguments.", isolate);
return;
}
- Document* document = V8Document::toNative(info.Callee()->GetHiddenValue(V8HiddenPropertyName::customElementDocument(isolate)).As<v8::Object>());
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<>, namespaceURI, info.Callee()->GetHiddenValue(V8HiddenPropertyName::customElementNamespaceURI(isolate)));
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<>, tagName, info.Callee()->GetHiddenValue(V8HiddenPropertyName::customElementTagName(isolate)));
- v8::Handle<v8::Value> maybeType = info.Callee()->GetHiddenValue(V8HiddenPropertyName::customElementType(isolate));
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<>, type, maybeType);
+ Document* document = V8Document::toNative(V8HiddenValue::getHiddenValue(info.GetIsolate(), info.Callee(), V8HiddenValue::customElementDocument(isolate)).As<v8::Object>());
+ TOSTRING_VOID(V8StringResource<>, namespaceURI, V8HiddenValue::getHiddenValue(isolate, info.Callee(), V8HiddenValue::customElementNamespaceURI(isolate)));
+ TOSTRING_VOID(V8StringResource<>, tagName, V8HiddenValue::getHiddenValue(isolate, info.Callee(), V8HiddenValue::customElementTagName(isolate)));
+ v8::Handle<v8::Value> maybeType = V8HiddenValue::getHiddenValue(info.GetIsolate(), info.Callee(), V8HiddenValue::customElementType(isolate));
+ TOSTRING_VOID(V8StringResource<>, type, maybeType);
ExceptionState exceptionState(ExceptionState::ConstructionContext, "CustomElement", info.Holder(), info.GetIsolate());
CustomElementCallbackDispatcher::CallbackDeliveryScope deliveryScope;
- RefPtr<Element> element = document->createElementNS(namespaceURI, tagName, maybeType->IsNull() ? nullAtom : type, exceptionState);
+ RefPtrWillBeRawPtr<Element> element = document->createElementNS(namespaceURI, tagName, maybeType->IsNull() ? nullAtom : type, exceptionState);
if (exceptionState.throwIfNeeded())
return;
+#if ENABLE(OILPAN)
+ // FIXME: Oilpan: We don't have RawPtr<Eement> version of
+ // v8SetReturnValueFast until Node.idl has WillBeGarbageCollected.
+ v8SetReturnValueFast(info, element.get(), document);
+#else
v8SetReturnValueFast(info, element.release(), document);
+#endif
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/CustomElementConstructorBuilder.h b/chromium/third_party/WebKit/Source/bindings/v8/CustomElementConstructorBuilder.h
index 21f81e8c787..623244d2a70 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/CustomElementConstructorBuilder.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/CustomElementConstructorBuilder.h
@@ -49,7 +49,6 @@ class Document;
class Element;
class ExceptionState;
class QualifiedName;
-class ScriptState;
class V8PerContextData;
struct WrapperTypeInfo;
@@ -82,7 +81,7 @@ private:
bool prototypeIsValid(const AtomicString& type, ExceptionState&) const;
v8::Handle<v8::Function> retrieveCallback(v8::Isolate*, const char* name);
- v8::Handle<v8::Context> m_context;
+ RefPtr<ScriptState> m_scriptState;
const Dictionary* m_options;
v8::Handle<v8::Object> m_prototype;
const WrapperTypeInfo* m_wrapperType;
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/CustomElementWrapper.cpp b/chromium/third_party/WebKit/Source/bindings/v8/CustomElementWrapper.cpp
index 128c1e417e2..abd8830ea8b 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/CustomElementWrapper.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/CustomElementWrapper.cpp
@@ -31,13 +31,13 @@
#include "config.h"
#include "bindings/v8/CustomElementWrapper.h"
-#include "V8HTMLElement.h"
-#include "V8HTMLElementWrapperFactory.h"
-#include "V8SVGElement.h"
-#include "V8SVGElementWrapperFactory.h"
+#include "bindings/core/v8/V8HTMLElement.h"
+#include "bindings/core/v8/V8SVGElement.h"
#include "bindings/v8/DOMDataStore.h"
#include "bindings/v8/DOMWrapperWorld.h"
#include "bindings/v8/V8PerContextData.h"
+#include "core/V8HTMLElementWrapperFactory.h" // FIXME: should be bindings/core/v8
+#include "core/V8SVGElementWrapperFactory.h" // FIXME: should be bindings/core/v8
#include "core/dom/custom/CustomElement.h"
#include "core/html/HTMLElement.h"
#include "core/html/HTMLUnknownElement.h"
@@ -86,23 +86,21 @@ v8::Handle<v8::Object> createUpgradeCandidateWrapper(ElementType* element, v8::H
}
template<typename ElementType, typename WrapperType>
-v8::Handle<v8::Object> CustomElementWrapper<ElementType, WrapperType>::wrap(PassRefPtr<ElementType> element, v8::Handle<v8::Object> creationContext, v8::Isolate* isolate, v8::Handle<v8::Object> (*createSpecificWrapper)(ElementType* element, v8::Handle<v8::Object> creationContext, v8::Isolate*))
+v8::Handle<v8::Object> CustomElementWrapper<ElementType, WrapperType>::wrap(PassRefPtrWillBeRawPtr<ElementType> element, v8::Handle<v8::Object> creationContext, v8::Isolate* isolate, v8::Handle<v8::Object> (*createSpecificWrapper)(ElementType* element, v8::Handle<v8::Object> creationContext, v8::Isolate*))
{
ASSERT(DOMDataStore::getWrapper<V8Element>(element.get(), isolate).IsEmpty());
- // FIXME: creationContext.IsEmpty() should never happen. Remove
- // this when callers (like InspectorController::inspect) are fixed
- // to never pass an empty creation context.
- v8::Handle<v8::Context> context = creationContext.IsEmpty() ? isolate->GetCurrentContext() : creationContext->CreationContext();
+ ASSERT(!creationContext.IsEmpty());
+ v8::Handle<v8::Context> context = creationContext->CreationContext();
- if (!element->isUpgradedCustomElement() || DOMWrapperWorld::isolatedWorld(context))
+ if (!element->isUpgradedCustomElement() || DOMWrapperWorld::world(context).isIsolatedWorld())
return createUpgradeCandidateWrapper(element.get(), creationContext, isolate, createSpecificWrapper);
V8PerContextData* perContextData = V8PerContextData::from(context);
if (!perContextData)
return v8::Handle<v8::Object>();
- CustomElementBinding* binding = perContextData->customElementBinding(CustomElement::definitionFor(element.get()));
+ CustomElementBinding* binding = perContextData->customElementBinding(element->customElementDefinition());
v8::Handle<v8::Object> wrapper = V8DOMWrapper::createWrapper(creationContext, binding->wrapperType(), element.get(), isolate);
if (wrapper.IsEmpty())
return v8::Handle<v8::Object>();
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/CustomElementWrapper.h b/chromium/third_party/WebKit/Source/bindings/v8/CustomElementWrapper.h
index c3cbbe8e58d..bf3ba6e8dce 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/CustomElementWrapper.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/CustomElementWrapper.h
@@ -31,6 +31,7 @@
#ifndef CustomElementWrapper_h
#define CustomElementWrapper_h
+#include "platform/heap/Handle.h"
#include "wtf/PassRefPtr.h"
#include <v8.h>
@@ -47,7 +48,7 @@ private:
friend v8::Handle<v8::Object> createV8HTMLWrapper(HTMLElement*, v8::Handle<v8::Object>, v8::Isolate*);
friend v8::Handle<v8::Object> createV8SVGWrapper(SVGElement*, v8::Handle<v8::Object>, v8::Isolate*);
- static v8::Handle<v8::Object> wrap(PassRefPtr<ElementType>, v8::Handle<v8::Object> creationContext, v8::Isolate*, v8::Handle<v8::Object> (*createSpecificWrapper)(ElementType* element, v8::Handle<v8::Object> creationContext, v8::Isolate*));
+ static v8::Handle<v8::Object> wrap(PassRefPtrWillBeRawPtr<ElementType>, v8::Handle<v8::Object> creationContext, v8::Isolate*, v8::Handle<v8::Object> (*createSpecificWrapper)(ElementType* element, v8::Handle<v8::Object> creationContext, v8::Isolate*));
};
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/DOMDataStore.cpp b/chromium/third_party/WebKit/Source/bindings/v8/DOMDataStore.cpp
index fcfb12f00e7..c9ef7c4195c 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/DOMDataStore.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/DOMDataStore.cpp
@@ -37,40 +37,21 @@
namespace WebCore {
-DOMDataStore::DOMDataStore(WrapperWorldType type)
- : m_type(type)
+DOMDataStore::DOMDataStore(bool isMainWorld)
+ : m_isMainWorld(isMainWorld)
, m_wrapperMap(v8::Isolate::GetCurrent()) // FIXME Don't call GetCurrent twice.
{
- V8PerIsolateData::current()->registerDOMDataStore(this);
}
DOMDataStore::~DOMDataStore()
{
- ASSERT(m_type != MainWorld); // We never actually destruct the main world's DOMDataStore.
- V8PerIsolateData::current()->unregisterDOMDataStore(this);
+ ASSERT(!m_isMainWorld); // We never actually destruct the main world's DOMDataStore.
m_wrapperMap.clear();
}
-DOMDataStore& DOMDataStore::mainWorldStore()
-{
- DEFINE_STATIC_LOCAL(DOMDataStore, mainWorldDOMDataStore, (MainWorld));
- ASSERT(isMainThread());
- return mainWorldDOMDataStore;
-}
-
DOMDataStore& DOMDataStore::current(v8::Isolate* isolate)
{
- V8PerIsolateData* data = isolate ? V8PerIsolateData::from(isolate) : V8PerIsolateData::current();
- if (UNLIKELY(!!data->workerDOMDataStore()))
- return *data->workerDOMDataStore();
-
- if (DOMWrapperWorld::isolatedWorldsExist()) {
- DOMWrapperWorld* isolatedWorld = DOMWrapperWorld::isolatedWorld(isolate->GetEnteredContext());
- if (UNLIKELY(!!isolatedWorld))
- return isolatedWorld->isolatedWorldDOMDataStore();
- }
-
- return mainWorldStore();
+ return DOMWrapperWorld::current(isolate).domDataStore();
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/DOMDataStore.h b/chromium/third_party/WebKit/Source/bindings/v8/DOMDataStore.h
index a75d38f02d5..852e8110a32 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/DOMDataStore.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/DOMDataStore.h
@@ -46,24 +46,39 @@ class Node;
class DOMDataStore {
WTF_MAKE_NONCOPYABLE(DOMDataStore);
public:
- explicit DOMDataStore(WrapperWorldType);
+ explicit DOMDataStore(bool isMainWorld);
~DOMDataStore();
static DOMDataStore& current(v8::Isolate*);
+ // We can use a wrapper stored in a ScriptWrappable when we're in the main world.
+ // This method does the fast check if we're in the main world. If this method returns true,
+ // it is guaranteed that we're in the main world. On the other hand, if this method returns
+ // false, nothing is guaranteed (we might be in the main world).
+ template<typename T>
+ static bool canUseScriptWrappable(T* object)
+ {
+ return !DOMWrapperWorld::isolatedWorldsExist()
+ && !canExistInWorker(object)
+ && ScriptWrappable::wrapperCanBeStoredInObject(object);
+ }
+
template<typename V8T, typename T, typename Wrappable>
static bool setReturnValueFromWrapperFast(v8::ReturnValue<v8::Value> returnValue, T* object, v8::Local<v8::Object> holder, Wrappable* wrappable)
{
- // What we'd really like to check here is whether we're in the
- // main world or in an isolated world. The fastest way to do that
- // is to check that there is no isolated world and the 'object'
- // is an object that can exist in the main world. The second fastest
- // way is to check whether the wrappable's wrapper is the same as
- // the holder.
- if ((!DOMWrapperWorld::isolatedWorldsExist() && !canExistInWorker(object)) || holderContainsWrapper(holder, wrappable)) {
- if (ScriptWrappable::wrapperCanBeStoredInObject(object))
- return ScriptWrappable::setReturnValueWithSecurityCheck<V8T>(returnValue, object);
- return mainWorldStore().m_wrapperMap.setReturnValueFrom(returnValue, V8T::toInternalPointer(object));
+ if (canUseScriptWrappable(object)) {
+ ScriptWrappable::assertWrapperSanity<V8T, T>(object, object);
+ return ScriptWrappable::fromObject(object)->setReturnValue(returnValue);
+ }
+ // The second fastest way to check if we're in the main world is to check if
+ // the wrappable's wrapper is the same as the holder.
+ // FIXME: Investigate if it's worth having this check for performance.
+ if (holderContainsWrapper(holder, wrappable)) {
+ if (ScriptWrappable::wrapperCanBeStoredInObject(object)) {
+ ScriptWrappable::assertWrapperSanity<V8T, T>(object, object);
+ return ScriptWrappable::fromObject(object)->setReturnValue(returnValue);
+ }
+ return DOMWrapperWorld::mainWorld().domDataStore().m_wrapperMap.setReturnValueFrom(returnValue, V8T::toInternalPointer(object));
}
return current(returnValue.GetIsolate()).template setReturnValueFrom<V8T>(returnValue, object);
}
@@ -71,9 +86,9 @@ public:
template<typename V8T, typename T>
static bool setReturnValueFromWrapper(v8::ReturnValue<v8::Value> returnValue, T* object)
{
- if (ScriptWrappable::wrapperCanBeStoredInObject(object) && !canExistInWorker(object)) {
- if (LIKELY(!DOMWrapperWorld::isolatedWorldsExist()))
- return ScriptWrappable::setReturnValueWithSecurityCheck<V8T>(returnValue, object);
+ if (canUseScriptWrappable(object)) {
+ ScriptWrappable::assertWrapperSanity<V8T, T>(object, object);
+ return ScriptWrappable::fromObject(object)->setReturnValue(returnValue);
}
return current(returnValue.GetIsolate()).template setReturnValueFrom<V8T>(returnValue, object);
}
@@ -82,20 +97,18 @@ public:
static bool setReturnValueFromWrapperForMainWorld(v8::ReturnValue<v8::Value> returnValue, T* object)
{
if (ScriptWrappable::wrapperCanBeStoredInObject(object))
- return ScriptWrappable::setReturnValue(returnValue, object);
- return mainWorldStore().m_wrapperMap.setReturnValueFrom(returnValue, V8T::toInternalPointer(object));
+ return ScriptWrappable::fromObject(object)->setReturnValue(returnValue);
+ return DOMWrapperWorld::mainWorld().domDataStore().m_wrapperMap.setReturnValueFrom(returnValue, V8T::toInternalPointer(object));
}
template<typename V8T, typename T>
static v8::Handle<v8::Object> getWrapper(T* object, v8::Isolate* isolate)
{
- if (ScriptWrappable::wrapperCanBeStoredInObject(object) && !canExistInWorker(object)) {
- if (LIKELY(!DOMWrapperWorld::isolatedWorldsExist())) {
- v8::Handle<v8::Object> result = ScriptWrappable::getUnsafeWrapperFromObject(object).newLocal(isolate);
- // Security: always guard against malicious tampering.
- RELEASE_ASSERT_WITH_SECURITY_IMPLICATION(result.IsEmpty() || result->GetAlignedPointerFromInternalField(v8DOMWrapperObjectIndex) == V8T::toInternalPointer(object));
- return result;
- }
+ if (canUseScriptWrappable(object)) {
+ v8::Handle<v8::Object> result = ScriptWrappable::fromObject(object)->newLocalWrapper(isolate);
+ // Security: always guard against malicious tampering.
+ ScriptWrappable::assertWrapperSanity<V8T, T>(result, object);
+ return result;
}
return current(isolate).template get<V8T>(object, isolate);
}
@@ -103,13 +116,10 @@ public:
template<typename V8T, typename T>
static void setWrapperReference(const v8::Persistent<v8::Object>& parent, T* child, v8::Isolate* isolate)
{
- if (ScriptWrappable::wrapperCanBeStoredInObject(child) && !canExistInWorker(child)) {
- if (LIKELY(!DOMWrapperWorld::isolatedWorldsExist())) {
- UnsafePersistent<v8::Object> unsafePersistent = ScriptWrappable::getUnsafeWrapperFromObject(child);
- // Security: always guard against malicious tampering.
- RELEASE_ASSERT_WITH_SECURITY_IMPLICATION(unsafePersistent.isEmpty() || unsafePersistent.value()->GetAlignedPointerFromInternalField(v8DOMWrapperObjectIndex) == V8T::toInternalPointer(child));
- unsafePersistent.setReferenceFrom(parent, isolate);
- }
+ if (canUseScriptWrappable(child)) {
+ ScriptWrappable::assertWrapperSanity<V8T, T>(child, child);
+ ScriptWrappable::fromObject(child)->setReference(parent, isolate);
+ return;
}
current(isolate).template setReference<V8T>(parent, child, isolate);
}
@@ -117,11 +127,9 @@ public:
template<typename V8T, typename T>
static void setWrapper(T* object, v8::Handle<v8::Object> wrapper, v8::Isolate* isolate, const WrapperConfiguration& configuration)
{
- if (ScriptWrappable::wrapperCanBeStoredInObject(object) && !canExistInWorker(object)) {
- if (LIKELY(!DOMWrapperWorld::isolatedWorldsExist())) {
- ScriptWrappable::setWrapperInObject(object, wrapper, isolate, configuration);
- return;
- }
+ if (canUseScriptWrappable(object)) {
+ ScriptWrappable::fromObject(object)->setWrapper(wrapper, isolate, configuration);
+ return;
}
return current(isolate).template set<V8T>(object, wrapper, isolate, configuration);
}
@@ -135,16 +143,16 @@ public:
template<typename V8T, typename T>
inline v8::Handle<v8::Object> get(T* object, v8::Isolate* isolate)
{
- if (ScriptWrappable::wrapperCanBeStoredInObject(object) && m_type == MainWorld)
- return ScriptWrappable::getUnsafeWrapperFromObject(object).newLocal(isolate);
+ if (ScriptWrappable::wrapperCanBeStoredInObject(object) && m_isMainWorld)
+ return ScriptWrappable::fromObject(object)->newLocalWrapper(isolate);
return m_wrapperMap.newLocal(V8T::toInternalPointer(object), isolate);
}
template<typename V8T, typename T>
inline void setReference(const v8::Persistent<v8::Object>& parent, T* child, v8::Isolate* isolate)
{
- if (ScriptWrappable::wrapperCanBeStoredInObject(child) && m_type == MainWorld) {
- ScriptWrappable::getUnsafeWrapperFromObject(child).setReferenceFrom(parent, isolate);
+ if (ScriptWrappable::wrapperCanBeStoredInObject(child) && m_isMainWorld) {
+ ScriptWrappable::fromObject(child)->setReference(parent, isolate);
return;
}
m_wrapperMap.setReference(parent, V8T::toInternalPointer(child), isolate);
@@ -153,16 +161,16 @@ public:
template<typename V8T, typename T>
inline bool setReturnValueFrom(v8::ReturnValue<v8::Value> returnValue, T* object)
{
- if (ScriptWrappable::wrapperCanBeStoredInObject(object) && m_type == MainWorld)
- return ScriptWrappable::setReturnValue(returnValue, object);
+ if (ScriptWrappable::wrapperCanBeStoredInObject(object) && m_isMainWorld)
+ return ScriptWrappable::fromObject(object)->setReturnValue(returnValue);
return m_wrapperMap.setReturnValueFrom(returnValue, V8T::toInternalPointer(object));
}
template<typename V8T, typename T>
inline bool containsWrapper(T* object)
{
- if (ScriptWrappable::wrapperCanBeStoredInObject(object) && m_type == MainWorld)
- return !ScriptWrappable::getUnsafeWrapperFromObject(object).isEmpty();
+ if (ScriptWrappable::wrapperCanBeStoredInObject(object) && m_isMainWorld)
+ return ScriptWrappable::fromObject(object)->containsWrapper();
return m_wrapperMap.containsKey(V8T::toInternalPointer(object));
}
@@ -172,15 +180,13 @@ private:
{
ASSERT(!!object);
ASSERT(!wrapper.IsEmpty());
- if (ScriptWrappable::wrapperCanBeStoredInObject(object) && m_type == MainWorld) {
- ScriptWrappable::setWrapperInObject(object, wrapper, isolate, configuration);
+ if (ScriptWrappable::wrapperCanBeStoredInObject(object) && m_isMainWorld) {
+ ScriptWrappable::fromObject(object)->setWrapper(wrapper, isolate, configuration);
return;
}
m_wrapperMap.set(V8T::toInternalPointer(object), wrapper, configuration);
}
- static DOMDataStore& mainWorldStore();
-
static bool canExistInWorker(void*) { return true; }
static bool canExistInWorker(Node*) { return false; }
@@ -192,12 +198,12 @@ private:
static bool holderContainsWrapper(v8::Local<v8::Object> holder, ScriptWrappable* wrappable)
{
// Verify our assumptions about the main world.
- UnsafePersistent<v8::Object> unsafePersistent = wrappable->unsafePersistent();
- ASSERT(unsafePersistent.isEmpty() || !(holder == *unsafePersistent.persistent()) || current(v8::Isolate::GetCurrent()).m_type == MainWorld);
- return holder == *unsafePersistent.persistent();
+ ASSERT(wrappable);
+ ASSERT(!wrappable->containsWrapper() || !wrappable->isEqualTo(holder) || current(v8::Isolate::GetCurrent()).m_isMainWorld);
+ return wrappable->isEqualTo(holder);
}
- WrapperWorldType m_type;
+ bool m_isMainWorld;
DOMWrapperMap<void> m_wrapperMap;
};
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/DOMRequestState.h b/chromium/third_party/WebKit/Source/bindings/v8/DOMRequestState.h
deleted file mode 100644
index 710f3d371b0..00000000000
--- a/chromium/third_party/WebKit/Source/bindings/v8/DOMRequestState.h
+++ /dev/null
@@ -1,85 +0,0 @@
-/*
- * Copyright (C) 2012 Google Inc. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- *
- * 1. Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * 2. Redistributions in binary form must reproduce the above copyright
- * notice, this list of conditions and the following disclaimer in the
- * documentation and/or other materials provided with the distribution.
- *
- * THIS SOFTWARE IS PROVIDED BY APPLE AND ITS CONTRIBUTORS "AS IS" AND ANY
- * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
- * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
- * DISCLAIMED. IN NO EVENT SHALL APPLE OR ITS CONTRIBUTORS BE LIABLE FOR ANY
- * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
- * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
- * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND
- * ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF
- * THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-#ifndef DOMRequestState_h
-#define DOMRequestState_h
-
-#include "bindings/v8/DOMWrapperWorld.h"
-#include "bindings/v8/V8Binding.h"
-#include "core/dom/ExecutionContext.h"
-#include "v8.h"
-#include "wtf/RefPtr.h"
-
-namespace WebCore {
-
-class DOMRequestState {
-public:
- explicit DOMRequestState(ExecutionContext* executionContext)
- : m_executionContext(executionContext)
- , m_world(DOMWrapperWorld::current())
- , m_isolate(toIsolate(executionContext))
- {
- ASSERT(m_executionContext);
- }
-
- void clear()
- {
- m_executionContext = 0;
- m_world.clear();
- }
-
- class Scope {
- public:
- explicit Scope(DOMRequestState& state)
- : m_handleScope(state.isolate())
- , m_contextScope(state.context())
- {
- }
- private:
- v8::HandleScope m_handleScope;
- v8::Context::Scope m_contextScope;
- };
-
- v8::Local<v8::Context> context()
- {
- ASSERT(m_executionContext);
- return toV8Context(m_executionContext, m_world.get());
- }
-
- v8::Isolate* isolate() const
- {
- return m_isolate;
- }
-
- bool isValid() const { return m_executionContext; }
-
-private:
- ExecutionContext* m_executionContext;
- RefPtr<DOMWrapperWorld> m_world;
- v8::Isolate* m_isolate;
-};
-
-}
-#endif
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/DOMWrapperMap.h b/chromium/third_party/WebKit/Source/bindings/v8/DOMWrapperMap.h
index 5987f57ace8..1ebbc53fb7c 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/DOMWrapperMap.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/DOMWrapperMap.h
@@ -31,9 +31,8 @@
#ifndef DOMWrapperMap_h
#define DOMWrapperMap_h
-#include "bindings/v8/UnsafePersistent.h"
-#include "bindings/v8/V8Utilities.h"
#include "bindings/v8/WrapperTypeInfo.h"
+#include <v8-util.h>
#include <v8.h>
#include "wtf/HashMap.h"
@@ -42,96 +41,127 @@ namespace WebCore {
template<class KeyType>
class DOMWrapperMap {
public:
- typedef HashMap<KeyType*, UnsafePersistent<v8::Object> > MapType;
-
explicit DOMWrapperMap(v8::Isolate* isolate)
: m_isolate(isolate)
+ , m_map(isolate)
{
}
v8::Handle<v8::Object> newLocal(KeyType* key, v8::Isolate* isolate)
{
- return m_map.get(key).newLocal(isolate);
+ return m_map.Get(key);
}
bool setReturnValueFrom(v8::ReturnValue<v8::Value> returnValue, KeyType* key)
{
- typename MapType::iterator it = m_map.find(key);
- if (it == m_map.end())
- return false;
- returnValue.Set(*(it->value.persistent()));
- return true;
+ return m_map.SetReturnValue(key, returnValue);
}
void setReference(const v8::Persistent<v8::Object>& parent, KeyType* key, v8::Isolate* isolate)
{
- m_map.get(key).setReferenceFrom(parent, isolate);
+ m_map.SetReference(key, parent);
}
bool containsKey(KeyType* key)
{
- return m_map.find(key) != m_map.end();
- }
-
- bool containsKeyAndValue(KeyType* key, v8::Handle<v8::Object> value)
- {
- typename MapType::iterator it = m_map.find(key);
- if (it == m_map.end())
- return false;
- return *(it->value.persistent()) == value;
+ return m_map.Contains(key);
}
void set(KeyType* key, v8::Handle<v8::Object> wrapper, const WrapperConfiguration& configuration)
{
ASSERT(static_cast<KeyType*>(toNative(wrapper)) == key);
- v8::Persistent<v8::Object> persistent(m_isolate, wrapper);
- configuration.configureWrapper(&persistent);
- persistent.SetWeak(this, &setWeakCallback);
- typename MapType::AddResult result = m_map.add(key, UnsafePersistent<v8::Object>());
- ASSERT(result.isNewEntry);
- // FIXME: Stop handling this case once duplicate wrappers are guaranteed not to be created.
- if (!result.isNewEntry)
- result.iterator->value.dispose();
- result.iterator->value = UnsafePersistent<v8::Object>(persistent);
+ RELEASE_ASSERT(!containsKey(key)); // See crbug.com/368095
+ v8::UniquePersistent<v8::Object> unique(m_isolate, wrapper);
+ configuration.configureWrapper(&unique);
+ m_map.Set(key, unique.Pass());
}
void clear()
{
- while (!m_map.isEmpty()) {
- // Swap out m_map on each iteration to ensure any wrappers added due to side effects of the loop are cleared.
- MapType map;
- map.swap(m_map);
- for (typename MapType::iterator it = map.begin(); it != map.end(); ++it) {
- toWrapperTypeInfo(*(it->value.persistent()))->derefObject(it->key);
- it->value.dispose();
- }
- }
+ m_map.Clear();
}
void removeAndDispose(KeyType* key)
{
- typename MapType::iterator it = m_map.find(key);
- ASSERT_WITH_SECURITY_IMPLICATION(it != m_map.end());
- it->value.dispose();
- m_map.remove(it);
+ ASSERT(containsKey(key));
+ m_map.Remove(key);
}
private:
- static void setWeakCallback(const v8::WeakCallbackData<v8::Object, DOMWrapperMap<KeyType> >&);
+ class PersistentValueMapTraits {
+ public:
+ // Map traits:
+ typedef HashMap<KeyType*, v8::PersistentContainerValue> Impl;
+ typedef typename Impl::iterator Iterator;
+ static size_t Size(const Impl* impl) { return impl->size(); }
+ static bool Empty(Impl* impl) { return impl->isEmpty(); }
+ static void Swap(Impl& impl, Impl& other) { impl.swap(other); }
+ static Iterator Begin(Impl* impl) { return impl->begin(); }
+ static Iterator End(Impl* impl) { return impl->end(); }
+ static v8::PersistentContainerValue Value(Iterator& iter)
+ {
+ return iter->value;
+ }
+ static KeyType* Key(Iterator& iter) { return iter->key; }
+ static v8::PersistentContainerValue Set(
+ Impl* impl, KeyType* key, v8::PersistentContainerValue value)
+ {
+ v8::PersistentContainerValue oldValue = Get(impl, key);
+ impl->set(key, value);
+ return oldValue;
+ }
+ static v8::PersistentContainerValue Get(const Impl* impl, KeyType* key)
+ {
+ return impl->get(key);
+ }
+
+ static v8::PersistentContainerValue Remove(Impl* impl, KeyType* key)
+ {
+ return impl->take(key);
+ }
+
+ // Weak traits:
+ static const v8::PersistentContainerCallbackType kCallbackType = v8::kWeak;
+ typedef v8::PersistentValueMap<KeyType*, v8::Object, PersistentValueMapTraits> MapType;
+ typedef MapType WeakCallbackDataType;
+
+ static WeakCallbackDataType* WeakCallbackParameter(MapType* map, KeyType* key, v8::Local<v8::Object>& value)
+ {
+ return map;
+ }
+
+ static void DisposeCallbackData(WeakCallbackDataType* callbackData) { }
+
+ static MapType* MapFromWeakCallbackData(
+ const v8::WeakCallbackData<v8::Object, WeakCallbackDataType>& data)
+ {
+ return data.GetParameter();
+ }
+
+ static KeyType* KeyFromWeakCallbackData(
+ const v8::WeakCallbackData<v8::Object, WeakCallbackDataType>& data)
+ {
+ return static_cast<KeyType*>(toNative(data.GetValue()));
+ }
+
+ // Dispose traits:
+ // Generally nothing to do, but see below for a specialization for
+ // DomWrapperMap<void>.
+ static void Dispose(v8::Isolate* isolate, v8::UniquePersistent<v8::Object> value, KeyType* key) { }
+ };
v8::Isolate* m_isolate;
- MapType m_map;
+ typename PersistentValueMapTraits::MapType m_map;
};
-template<>
-inline void DOMWrapperMap<void>::setWeakCallback(const v8::WeakCallbackData<v8::Object, DOMWrapperMap<void> >& data)
+template <>
+inline void DOMWrapperMap<void>::PersistentValueMapTraits::Dispose(
+ v8::Isolate* isolate,
+ v8::UniquePersistent<v8::Object> value,
+ void* key)
{
- const WrapperTypeInfo* type = toWrapperTypeInfo(data.GetValue());
- ASSERT(type->derefObjectFunction);
- void* key = static_cast<void*>(toNative(data.GetValue()));
- ASSERT(*(data.GetParameter()->m_map.get(key).persistent()) == data.GetValue());
- data.GetParameter()->removeAndDispose(key);
- type->derefObject(key);
+ RELEASE_ASSERT(!value.IsEmpty()); // See crbug.com/368095.
+ releaseObject(v8::Local<v8::Object>::New(isolate, value));
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/DOMWrapperWorld.cpp b/chromium/third_party/WebKit/Source/bindings/v8/DOMWrapperWorld.cpp
index d014206817f..59cb4505716 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/DOMWrapperWorld.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/DOMWrapperWorld.cpp
@@ -31,7 +31,7 @@
#include "config.h"
#include "bindings/v8/DOMWrapperWorld.h"
-#include "V8Window.h"
+#include "bindings/core/v8/V8Window.h"
#include "bindings/v8/DOMDataStore.h"
#include "bindings/v8/ScriptController.h"
#include "bindings/v8/V8Binding.h"
@@ -41,70 +41,30 @@
#include "bindings/v8/WrapperTypeInfo.h"
#include "core/dom/ExecutionContext.h"
#include "wtf/HashTraits.h"
-#include "wtf/MainThread.h"
#include "wtf/StdLibExtras.h"
namespace WebCore {
unsigned DOMWrapperWorld::isolatedWorldCount = 0;
-static bool initializingWindow = false;
+DOMWrapperWorld* DOMWrapperWorld::worldOfInitializingWindow = 0;
-void DOMWrapperWorld::setInitializingWindow(bool initializing)
+PassRefPtr<DOMWrapperWorld> DOMWrapperWorld::create(int worldId, int extensionGroup)
{
- initializingWindow = initializing;
-}
-
-PassRefPtr<DOMWrapperWorld> DOMWrapperWorld::createMainWorld()
-{
- return adoptRef(new DOMWrapperWorld(MainWorldId, mainWorldExtensionGroup));
+ return adoptRef(new DOMWrapperWorld(worldId, extensionGroup));
}
DOMWrapperWorld::DOMWrapperWorld(int worldId, int extensionGroup)
: m_worldId(worldId)
, m_extensionGroup(extensionGroup)
+ , m_domDataStore(adoptPtr(new DOMDataStore(isMainWorld())))
{
- if (isIsolatedWorld())
- m_domDataStore = adoptPtr(new DOMDataStore(IsolatedWorld));
-}
-
-DOMWrapperWorld* DOMWrapperWorld::current()
-{
- v8::Isolate* isolate = v8::Isolate::GetCurrent();
- ASSERT(isolate->InContext());
- v8::Handle<v8::Context> context = isolate->GetCurrentContext();
- if (!V8DOMWrapper::isWrapperOfType(toInnerGlobalObject(context), &V8Window::wrapperTypeInfo))
- return 0;
- ASSERT(isMainThread());
- if (DOMWrapperWorld* world = isolatedWorld(context))
- return world;
- return mainThreadNormalWorld();
}
-DOMWrapperWorld* mainThreadNormalWorld()
+DOMWrapperWorld& DOMWrapperWorld::mainWorld()
{
ASSERT(isMainThread());
- DEFINE_STATIC_REF(DOMWrapperWorld, cachedNormalWorld, (DOMWrapperWorld::createMainWorld()));
- return cachedNormalWorld;
-}
-
-// FIXME: Remove this function. There is currently an issue with the inspector related to the call to dispatchDidClearWindowObjectInWorld in ScriptController::windowShell.
-DOMWrapperWorld* existingWindowShellWorkaroundWorld()
-{
- DEFINE_STATIC_REF(DOMWrapperWorld, world, (adoptRef(new DOMWrapperWorld(MainWorldId - 1, DOMWrapperWorld::mainWorldExtensionGroup - 1))));
- return world;
-}
-
-bool DOMWrapperWorld::contextHasCorrectPrototype(v8::Handle<v8::Context> context)
-{
- ASSERT(isMainThread());
- if (initializingWindow)
- return true;
- return V8DOMWrapper::isWrapperOfType(toInnerGlobalObject(context), &V8Window::wrapperTypeInfo);
-}
-
-void DOMWrapperWorld::setIsolatedWorldField(v8::Handle<v8::Context> context)
-{
- V8PerContextDataHolder::from(context)->setIsolatedWorld(isMainWorld() ? 0 : this);
+ DEFINE_STATIC_REF(DOMWrapperWorld, cachedMainWorld, (DOMWrapperWorld::create(MainWorldId, mainWorldExtensionGroup)));
+ return *cachedMainWorld;
}
typedef HashMap<int, DOMWrapperWorld*> WorldMap;
@@ -115,9 +75,10 @@ static WorldMap& isolatedWorldMap()
return map;
}
-void DOMWrapperWorld::getAllWorlds(Vector<RefPtr<DOMWrapperWorld> >& worlds)
+void DOMWrapperWorld::allWorldsInMainThread(Vector<RefPtr<DOMWrapperWorld> >& worlds)
{
- worlds.append(mainThreadNormalWorld());
+ ASSERT(isMainThread());
+ worlds.append(&mainWorld());
WorldMap& isolatedWorlds = isolatedWorldMap();
for (WorldMap::iterator it = isolatedWorlds.begin(); it != isolatedWorlds.end(); ++it)
worlds.append(it->value);
@@ -127,48 +88,57 @@ DOMWrapperWorld::~DOMWrapperWorld()
{
ASSERT(!isMainWorld());
+ dispose();
+
if (!isIsolatedWorld())
return;
WorldMap& map = isolatedWorldMap();
- WorldMap::iterator i = map.find(m_worldId);
- if (i == map.end()) {
+ WorldMap::iterator it = map.find(m_worldId);
+ if (it == map.end()) {
ASSERT_NOT_REACHED();
return;
}
- ASSERT(i->value == this);
+ ASSERT(it->value == this);
- map.remove(i);
+ map.remove(it);
isolatedWorldCount--;
ASSERT(map.size() == isolatedWorldCount);
}
+void DOMWrapperWorld::dispose()
+{
+ m_domDataStore.clear();
+}
+
+#ifndef NDEBUG
+static bool isIsolatedWorldId(int worldId)
+{
+ return MainWorldId < worldId && worldId < IsolatedWorldIdLimit;
+}
+#endif
+
PassRefPtr<DOMWrapperWorld> DOMWrapperWorld::ensureIsolatedWorld(int worldId, int extensionGroup)
{
- ASSERT(worldId > MainWorldId);
+ ASSERT(isIsolatedWorldId(worldId));
WorldMap& map = isolatedWorldMap();
WorldMap::AddResult result = map.add(worldId, 0);
- RefPtr<DOMWrapperWorld> world = result.iterator->value;
+ RefPtr<DOMWrapperWorld> world = result.storedValue->value;
if (world) {
ASSERT(world->worldId() == worldId);
ASSERT(world->extensionGroup() == extensionGroup);
return world.release();
}
- world = adoptRef(new DOMWrapperWorld(worldId, extensionGroup));
- result.iterator->value = world.get();
+ world = DOMWrapperWorld::create(worldId, extensionGroup);
+ result.storedValue->value = world.get();
isolatedWorldCount++;
ASSERT(map.size() == isolatedWorldCount);
return world.release();
}
-v8::Handle<v8::Context> DOMWrapperWorld::context(ScriptController& controller)
-{
- return controller.windowShell(this)->context();
-}
-
typedef HashMap<int, RefPtr<SecurityOrigin> > IsolatedWorldSecurityOriginMap;
static IsolatedWorldSecurityOriginMap& isolatedWorldSecurityOrigins()
{
@@ -185,19 +155,13 @@ SecurityOrigin* DOMWrapperWorld::isolatedWorldSecurityOrigin()
return it == origins.end() ? 0 : it->value.get();
}
-void DOMWrapperWorld::setIsolatedWorldSecurityOrigin(int worldID, PassRefPtr<SecurityOrigin> securityOrigin)
+void DOMWrapperWorld::setIsolatedWorldSecurityOrigin(int worldId, PassRefPtr<SecurityOrigin> securityOrigin)
{
- ASSERT(DOMWrapperWorld::isIsolatedWorldId(worldID));
+ ASSERT(isIsolatedWorldId(worldId));
if (securityOrigin)
- isolatedWorldSecurityOrigins().set(worldID, securityOrigin);
+ isolatedWorldSecurityOrigins().set(worldId, securityOrigin);
else
- isolatedWorldSecurityOrigins().remove(worldID);
-}
-
-void DOMWrapperWorld::clearIsolatedWorldSecurityOrigin(int worldID)
-{
- ASSERT(DOMWrapperWorld::isIsolatedWorldId(worldID));
- isolatedWorldSecurityOrigins().remove(worldID);
+ isolatedWorldSecurityOrigins().remove(worldId);
}
typedef HashMap<int, bool> IsolatedWorldContentSecurityPolicyMap;
@@ -216,39 +180,13 @@ bool DOMWrapperWorld::isolatedWorldHasContentSecurityPolicy()
return it == policies.end() ? false : it->value;
}
-void DOMWrapperWorld::setIsolatedWorldContentSecurityPolicy(int worldID, const String& policy)
+void DOMWrapperWorld::setIsolatedWorldContentSecurityPolicy(int worldId, const String& policy)
{
- ASSERT(DOMWrapperWorld::isIsolatedWorldId(worldID));
+ ASSERT(isIsolatedWorldId(worldId));
if (!policy.isEmpty())
- isolatedWorldContentSecurityPolicies().set(worldID, true);
+ isolatedWorldContentSecurityPolicies().set(worldId, true);
else
- isolatedWorldContentSecurityPolicies().remove(worldID);
-}
-
-void DOMWrapperWorld::clearIsolatedWorldContentSecurityPolicy(int worldID)
-{
- ASSERT(DOMWrapperWorld::isIsolatedWorldId(worldID));
- isolatedWorldContentSecurityPolicies().remove(worldID);
-}
-
-typedef HashMap<int, OwnPtr<V8DOMActivityLogger>, WTF::IntHash<int>, WTF::UnsignedWithZeroKeyHashTraits<int> > DOMActivityLoggerMap;
-static DOMActivityLoggerMap& domActivityLoggers()
-{
- ASSERT(isMainThread());
- DEFINE_STATIC_LOCAL(DOMActivityLoggerMap, map, ());
- return map;
-}
-
-void DOMWrapperWorld::setActivityLogger(int worldId, PassOwnPtr<V8DOMActivityLogger> logger)
-{
- domActivityLoggers().set(worldId, logger);
-}
-
-V8DOMActivityLogger* DOMWrapperWorld::activityLogger(int worldId)
-{
- DOMActivityLoggerMap& loggers = domActivityLoggers();
- DOMActivityLoggerMap::iterator it = loggers.find(worldId);
- return it == loggers.end() ? 0 : it->value.get();
+ isolatedWorldContentSecurityPolicies().remove(worldId);
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/DOMWrapperWorld.h b/chromium/third_party/WebKit/Source/bindings/v8/DOMWrapperWorld.h
index 201e019309f..aa294a1fcfb 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/DOMWrapperWorld.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/DOMWrapperWorld.h
@@ -31,54 +31,67 @@
#ifndef DOMWrapperWorld_h
#define DOMWrapperWorld_h
-#include "bindings/v8/V8DOMActivityLogger.h"
-#include "bindings/v8/V8PerContextData.h"
+#include "bindings/v8/ScriptState.h"
#include "platform/weborigin/SecurityOrigin.h"
-#include <v8.h>
+#include "wtf/MainThread.h"
#include "wtf/PassRefPtr.h"
#include "wtf/RefCounted.h"
#include "wtf/RefPtr.h"
#include "wtf/text/WTFString.h"
+#include <v8.h>
namespace WebCore {
class DOMDataStore;
-class ScriptController;
class ExecutionContext;
+class ScriptController;
enum WorldIdConstants {
MainWorldId = 0,
+ // Embedder isolated worlds can use IDs in [1, 1<<29).
EmbedderWorldIdLimit = (1 << 29),
- ScriptPreprocessorIsolatedWorldId
+ ScriptPreprocessorIsolatedWorldId,
+ IsolatedWorldIdLimit,
+ WorkerWorldId,
+ TestingWorldId,
};
// This class represent a collection of DOM wrappers for a specific world.
class DOMWrapperWorld : public RefCounted<DOMWrapperWorld> {
public:
+ static PassRefPtr<DOMWrapperWorld> create(int worldId = -1, int extensionGroup = -1);
+
static const int mainWorldExtensionGroup = 0;
static PassRefPtr<DOMWrapperWorld> ensureIsolatedWorld(int worldId, int extensionGroup);
~DOMWrapperWorld();
+ void dispose();
static bool isolatedWorldsExist() { return isolatedWorldCount; }
- static bool isIsolatedWorldId(int worldId) { return worldId > MainWorldId; }
- static void getAllWorlds(Vector<RefPtr<DOMWrapperWorld> >& worlds);
+ static void allWorldsInMainThread(Vector<RefPtr<DOMWrapperWorld> >& worlds);
- void setIsolatedWorldField(v8::Handle<v8::Context>);
+ static DOMWrapperWorld& world(v8::Handle<v8::Context> context)
+ {
+ return ScriptState::from(context)->world();
+ }
- static DOMWrapperWorld* isolatedWorld(v8::Handle<v8::Context> context)
+ static DOMWrapperWorld& current(v8::Isolate* isolate)
{
- ASSERT(contextHasCorrectPrototype(context));
- return V8PerContextDataHolder::from(context)->isolatedWorld();
+ if (isMainThread() && worldOfInitializingWindow) {
+ // It's possible that current() is being called while window is being initialized.
+ // In order to make current() workable during the initialization phase,
+ // we cache the world of the initializing window on worldOfInitializingWindow.
+ // If there is no initiazing window, worldOfInitializingWindow is 0.
+ return *worldOfInitializingWindow;
+ }
+ return world(isolate->GetCurrentContext());
}
- // Will return null if there is no DOMWrapperWorld for the current v8::Context
- static DOMWrapperWorld* current();
+ static DOMWrapperWorld& mainWorld();
// Associates an isolated world (see above for description) with a security
// origin. XMLHttpRequest instances used in that world will be considered
// to come from that origin, not the frame's.
- static void setIsolatedWorldSecurityOrigin(int worldID, PassRefPtr<SecurityOrigin>);
- static void clearIsolatedWorldSecurityOrigin(int worldID);
+ static void setIsolatedWorldSecurityOrigin(int worldId, PassRefPtr<SecurityOrigin>);
SecurityOrigin* isolatedWorldSecurityOrigin();
// Associated an isolated world with a Content Security Policy. Resources
@@ -89,50 +102,36 @@ public:
// FIXME: Right now, resource injection simply bypasses the main world's
// DOM. More work is necessary to allow the isolated world's policy to be
// applied correctly.
- static void setIsolatedWorldContentSecurityPolicy(int worldID, const String& policy);
- static void clearIsolatedWorldContentSecurityPolicy(int worldID);
+ static void setIsolatedWorldContentSecurityPolicy(int worldId, const String& policy);
bool isolatedWorldHasContentSecurityPolicy();
- // Associate a logger with the world identified by worldId (worlId may be 0
- // identifying the main world).
- static void setActivityLogger(int worldId, PassOwnPtr<V8DOMActivityLogger>);
- static V8DOMActivityLogger* activityLogger(int worldId);
-
bool isMainWorld() const { return m_worldId == MainWorldId; }
- bool isIsolatedWorld() const { return isIsolatedWorldId(m_worldId); }
+ bool isWorkerWorld() const { return m_worldId == WorkerWorldId; }
+ bool isIsolatedWorld() const { return MainWorldId < m_worldId && m_worldId < IsolatedWorldIdLimit; }
int worldId() const { return m_worldId; }
int extensionGroup() const { return m_extensionGroup; }
- DOMDataStore& isolatedWorldDOMDataStore() const
+ DOMDataStore& domDataStore() const { return *m_domDataStore; }
+
+ static void setWorldOfInitializingWindow(DOMWrapperWorld* world)
{
- ASSERT(isIsolatedWorld());
- return *m_domDataStore;
+ ASSERT(isMainThread());
+ worldOfInitializingWindow = world;
}
- v8::Handle<v8::Context> context(ScriptController&);
-
- static void setInitializingWindow(bool);
+ // FIXME: Remove this method once we fix crbug.com/345014.
+ static bool windowIsBeingInitialized() { return !!worldOfInitializingWindow; }
private:
- static unsigned isolatedWorldCount;
- static PassRefPtr<DOMWrapperWorld> createMainWorld();
- static bool contextHasCorrectPrototype(v8::Handle<v8::Context>);
-
DOMWrapperWorld(int worldId, int extensionGroup);
+ static unsigned isolatedWorldCount;
+ static DOMWrapperWorld* worldOfInitializingWindow;
+
const int m_worldId;
const int m_extensionGroup;
OwnPtr<DOMDataStore> m_domDataStore;
-
- friend DOMWrapperWorld* mainThreadNormalWorld();
- friend DOMWrapperWorld* existingWindowShellWorkaroundWorld();
};
-DOMWrapperWorld* mainThreadNormalWorld();
-
-// FIXME: this is a workaround for a problem in ScriptController
-// Do not use this anywhere else!!
-DOMWrapperWorld* existingWindowShellWorkaroundWorld();
-
} // namespace WebCore
#endif // DOMWrapperWorld_h
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/DebuggerScript.js b/chromium/third_party/WebKit/Source/bindings/v8/DebuggerScript.js
index 2f92b48013e..bec40048c12 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/DebuggerScript.js
+++ b/chromium/third_party/WebKit/Source/bindings/v8/DebuggerScript.js
@@ -33,11 +33,17 @@
var DebuggerScript = {};
DebuggerScript.PauseOnExceptionsState = {
- DontPauseOnExceptions : 0,
- PauseOnAllExceptions : 1,
+ DontPauseOnExceptions: 0,
+ PauseOnAllExceptions: 1,
PauseOnUncaughtExceptions: 2
};
+DebuggerScript.ScopeInfoDetails = {
+ AllScopes: 0,
+ FastAsyncScopes: 1,
+ NoScopes: 2
+};
+
DebuggerScript._pauseOnExceptionsState = DebuggerScript.PauseOnExceptionsState.DontPauseOnExceptions;
Debug.clearBreakOnException();
Debug.clearBreakOnUncaughtException();
@@ -70,10 +76,10 @@ DebuggerScript.getFunctionScopes = function(fun)
return null;
var result = [];
for (var i = 0; i < count; i++) {
- var scopeMirror = mirror.scope(i);
+ var scopeDetails = mirror.scope(i).details();
result[i] = {
- type: scopeMirror.scopeType(),
- object: DebuggerScript._buildScopeObject(scopeMirror)
+ type: scopeDetails.type(),
+ object: DebuggerScript._buildScopeObject(scopeDetails.type(), scopeDetails.object())
};
}
return result;
@@ -199,15 +205,23 @@ DebuggerScript.setPauseOnExceptionsState = function(newState)
Debug.clearBreakOnUncaughtException();
}
-DebuggerScript.currentCallFrame = function(execState, maximumLimit)
+DebuggerScript.frameCount = function(execState)
{
+ return execState.frameCount();
+}
+
+DebuggerScript.currentCallFrame = function(execState, data)
+{
+ var maximumLimit = data >> 2;
+ var scopeDetailsLevel = data & 3;
+
var frameCount = execState.frameCount();
- if (maximumLimit >= 0 && maximumLimit < frameCount)
+ if (maximumLimit && maximumLimit < frameCount)
frameCount = maximumLimit;
var topFrame = undefined;
for (var i = frameCount - 1; i >= 0; i--) {
var frameMirror = execState.frame(i);
- topFrame = DebuggerScript._frameMirrorToJSCallFrame(frameMirror, topFrame);
+ topFrame = DebuggerScript._frameMirrorToJSCallFrame(frameMirror, topFrame, scopeDetailsLevel);
}
return topFrame;
}
@@ -219,14 +233,12 @@ DebuggerScript.stepIntoStatement = function(execState)
DebuggerScript.stepOverStatement = function(execState, callFrame)
{
- var frameMirror = callFrame ? callFrame.frameMirror : undefined;
- execState.prepareStep(Debug.StepAction.StepNext, 1, frameMirror);
+ execState.prepareStep(Debug.StepAction.StepNext, 1);
}
DebuggerScript.stepOutOfFunction = function(execState, callFrame)
{
- var frameMirror = callFrame ? callFrame.frameMirror : undefined;
- execState.prepareStep(Debug.StepAction.StepOut, 1, frameMirror);
+ execState.prepareStep(Debug.StepAction.StepOut, 1);
}
// Returns array in form:
@@ -310,43 +322,95 @@ DebuggerScript.isEvalCompilation = function(eventData)
return (script.compilationType() === Debug.ScriptCompilationType.Eval);
}
-DebuggerScript._frameMirrorToJSCallFrame = function(frameMirror, callerFrame)
+// NOTE: This function is performance critical, as it can be run on every
+// statement that generates an async event (like addEventListener) to support
+// asynchronous call stacks. Thus, when possible, initialize the data lazily.
+DebuggerScript._frameMirrorToJSCallFrame = function(frameMirror, callerFrame, scopeDetailsLevel)
{
- // Get function name and display name.
+ // Stuff that can not be initialized lazily (i.e. valid while paused with a valid break_id).
+ // The frameMirror and scopeMirror can be accessed only while paused on the debugger.
+ var frameDetails = frameMirror.details();
+
+ var funcObject = frameDetails.func();
+ var sourcePosition = frameDetails.sourcePosition();
+ var thisObject = frameDetails.receiver();
+
+ var isAtReturn = !!frameDetails.isAtReturn();
+ var returnValue = isAtReturn ? frameDetails.returnValue() : undefined;
+
+ var scopeMirrors = (scopeDetailsLevel === DebuggerScript.ScopeInfoDetails.NoScopes ? [] : frameMirror.allScopes(scopeDetailsLevel === DebuggerScript.ScopeInfoDetails.FastAsyncScopes));
+ var scopeTypes = new Array(scopeMirrors.length);
+ var scopeObjects = new Array(scopeMirrors.length);
+ for (var i = 0; i < scopeMirrors.length; ++i) {
+ var scopeDetails = scopeMirrors[i].details();
+ scopeTypes[i] = scopeDetails.type();
+ scopeObjects[i] = scopeDetails.object();
+ }
+
+ // Calculated lazily.
+ var scopeChain;
var funcMirror;
- var displayName;
- try {
- funcMirror = frameMirror.func();
- if (funcMirror) {
- var valueMirror = funcMirror.property("displayName").value();
- if (valueMirror && valueMirror.isString())
- displayName = valueMirror.value();
+ var location;
+
+ function lazyScopeChain()
+ {
+ if (!scopeChain) {
+ scopeChain = [];
+ for (var i = 0; i < scopeObjects.length; ++i)
+ scopeChain.push(DebuggerScript._buildScopeObject(scopeTypes[i], scopeObjects[i]));
+ scopeObjects = null; // Free for GC.
+ }
+ return scopeChain;
+ }
+
+ function ensureFuncMirror()
+ {
+ if (!funcMirror) {
+ funcMirror = MakeMirror(funcObject);
+ if (!funcMirror.isFunction())
+ funcMirror = new UnresolvedFunctionMirror(funcObject);
}
- } catch(e) {
+ return funcMirror;
}
- var functionName;
- if (funcMirror)
- functionName = displayName || funcMirror.name() || funcMirror.inferredName();
- // Get script ID.
- var script = funcMirror.script();
- var sourceID = script && script.id();
+ function ensureLocation()
+ {
+ if (!location) {
+ var script = ensureFuncMirror().script();
+ if (script)
+ location = script.locationFromPosition(sourcePosition, true);
+ if (!location)
+ location = { line: 0, column: 0 };
+ }
+ return location;
+ }
- // Get location.
- var location = frameMirror.sourceLocation();
+ function line()
+ {
+ return ensureLocation().line;
+ }
- // Get this object.
- var thisObject = frameMirror.details_.receiver();
+ function column()
+ {
+ return ensureLocation().column;
+ }
- var isAtReturn = !!frameMirror.details_.isAtReturn();
- var returnValue = isAtReturn ? frameMirror.details_.returnValue() : undefined;
+ function sourceID()
+ {
+ var script = ensureFuncMirror().script();
+ return script && script.id();
+ }
- var scopeChain = [];
- var scopeType = [];
- for (var i = 0; i < frameMirror.scopeCount(); i++) {
- var scopeMirror = frameMirror.scope(i);
- scopeType.push(scopeMirror.scopeType());
- scopeChain.push(DebuggerScript._buildScopeObject(scopeMirror));
+ function functionName()
+ {
+ var func = ensureFuncMirror();
+ if (!func.resolved())
+ return undefined;
+ var displayName;
+ var valueMirror = func.property("displayName").value();
+ if (valueMirror && valueMirror.isString())
+ displayName = valueMirror.value();
+ return displayName || func.name() || func.inferredName();
}
function evaluate(expression)
@@ -370,7 +434,7 @@ DebuggerScript._frameMirrorToJSCallFrame = function(frameMirror, callerFrame)
var stepInPositionsProtocol;
if (stepInPositionsV8) {
stepInPositionsProtocol = [];
- var script = frameMirror.func().script();
+ var script = ensureFuncMirror().script();
if (script) {
var scriptId = String(script.id());
for (var i = 0; i < stepInPositionsV8.length; i++) {
@@ -388,54 +452,55 @@ DebuggerScript._frameMirrorToJSCallFrame = function(frameMirror, callerFrame)
return {
"sourceID": sourceID,
- "line": location ? location.line : 0,
- "column": location ? location.column : 0,
+ "line": line,
+ "column": column,
"functionName": functionName,
"thisObject": thisObject,
- "scopeChain": scopeChain,
- "scopeType": scopeType,
+ "scopeChain": lazyScopeChain,
+ "scopeType": scopeTypes,
"evaluate": evaluate,
"caller": callerFrame,
"restart": restart,
"setVariableValue": setVariableValue,
"stepInPositions": stepInPositions,
"isAtReturn": isAtReturn,
- "returnValue": returnValue,
- "frameMirror": frameMirror
+ "returnValue": returnValue
};
}
-DebuggerScript._buildScopeObject = function(scopeMirror) {
- var scopeObject;
- switch (scopeMirror.scopeType()) {
+DebuggerScript._buildScopeObject = function(scopeType, scopeObject)
+{
+ var result;
+ switch (scopeType) {
case ScopeType.Local:
case ScopeType.Closure:
case ScopeType.Catch:
// For transient objects we create a "persistent" copy that contains
// the same properties.
- scopeObject = {};
// Reset scope object prototype to null so that the proto properties
// don't appear in the local scope section.
- scopeObject.__proto__ = null;
- var scopeObjectMirror = scopeMirror.scopeObject();
- var properties = scopeObjectMirror.properties();
+ result = { __proto__: null };
+ var properties = MakeMirror(scopeObject, true /* transient */).properties();
for (var j = 0; j < properties.length; j++) {
var name = properties[j].name();
if (name.charAt(0) === ".")
continue; // Skip internal variables like ".arguments"
- scopeObject[name] = properties[j].value_;
+ result[name] = properties[j].value_;
}
break;
case ScopeType.Global:
case ScopeType.With:
- scopeObject = scopeMirror.details_.object();
+ result = scopeObject;
break;
case ScopeType.Block:
// Unsupported yet. Mustn't be reachable.
break;
}
- return scopeObject;
+ return result;
}
+// We never resolve Mirror by its handle so to avoid memory leaks caused by Mirrors in the cache we disable it.
+ToggleMirrorCache(false);
+
return DebuggerScript;
})();
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/Dictionary.cpp b/chromium/third_party/WebKit/Source/bindings/v8/Dictionary.cpp
index 6431d5b1738..156eede687c 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/Dictionary.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/Dictionary.cpp
@@ -26,36 +26,35 @@
#include "config.h"
#include "bindings/v8/Dictionary.h"
-#include "V8DOMError.h"
-#include "V8EventTarget.h"
-#include "V8IDBKeyRange.h"
-#include "V8MIDIPort.h"
-#include "V8MediaKeyError.h"
-#include "V8SpeechRecognitionError.h"
-#include "V8SpeechRecognitionResult.h"
-#include "V8SpeechRecognitionResultList.h"
-#include "V8Storage.h"
-#include "V8VoidCallback.h"
-#include "V8Window.h"
+#include "bindings/core/v8/V8DOMError.h"
+#include "bindings/core/v8/V8EventTarget.h"
+#include "bindings/core/v8/V8MediaKeyError.h"
+#include "bindings/core/v8/V8MessagePort.h"
+#include "bindings/core/v8/V8Storage.h"
+#include "bindings/core/v8/V8TextTrack.h"
+#include "bindings/core/v8/V8VoidCallback.h"
+#include "bindings/core/v8/V8Window.h"
+#include "bindings/modules/v8/V8Gamepad.h"
+#include "bindings/modules/v8/V8HeaderMap.h"
+#include "bindings/modules/v8/V8IDBKeyRange.h"
+#include "bindings/modules/v8/V8MIDIPort.h"
+#include "bindings/modules/v8/V8MediaStream.h"
+#include "bindings/modules/v8/V8SpeechRecognitionResult.h"
+#include "bindings/modules/v8/V8SpeechRecognitionResultList.h"
#include "bindings/v8/ArrayValue.h"
#include "bindings/v8/ExceptionMessages.h"
#include "bindings/v8/ExceptionState.h"
#include "bindings/v8/V8Binding.h"
-#include "bindings/v8/V8Utilities.h"
#include "bindings/v8/custom/V8ArrayBufferViewCustom.h"
#include "bindings/v8/custom/V8Uint8ArrayCustom.h"
+#include "core/html/track/TrackBase.h"
+#include "modules/gamepad/Gamepad.h"
#include "modules/indexeddb/IDBKeyRange.h"
-#include "modules/speech/SpeechRecognitionError.h"
+#include "modules/mediastream/MediaStream.h"
#include "modules/speech/SpeechRecognitionResult.h"
#include "modules/speech/SpeechRecognitionResultList.h"
#include "wtf/MathExtras.h"
-#include "V8TextTrack.h"
-#include "core/html/track/TrackBase.h"
-
-#include "V8MediaStream.h"
-#include "modules/mediastream/MediaStream.h"
-
namespace WebCore {
Dictionary::Dictionary()
@@ -174,7 +173,7 @@ bool Dictionary::get(const String& key, double& value, bool& hasValue) const
}
hasValue = true;
- V8TRYCATCH_RETURN(v8::Local<v8::Number>, v8Number, v8Value->ToNumber(), false);
+ TONATIVE_DEFAULT(v8::Local<v8::Number>, v8Number, v8Value->ToNumber(), false);
if (v8Number.IsEmpty())
return false;
value = v8Number->Value();
@@ -199,17 +198,28 @@ bool Dictionary::convert(ConversionContext& context, const String& key, double&
return true;
}
-bool Dictionary::get(const String& key, String& value) const
+template<typename StringType>
+inline bool Dictionary::getStringType(const String& key, StringType& value) const
{
v8::Local<v8::Value> v8Value;
if (!getKey(key, v8Value))
return false;
- V8TRYCATCH_FOR_V8STRINGRESOURCE_RETURN(V8StringResource<>, stringValue, v8Value, false);
+ TOSTRING_DEFAULT(V8StringResource<>, stringValue, v8Value, false);
value = stringValue;
return true;
}
+bool Dictionary::get(const String& key, String& value) const
+{
+ return getStringType(key, value);
+}
+
+bool Dictionary::get(const String& key, AtomicString& value) const
+{
+ return getStringType(key, value);
+}
+
bool Dictionary::convert(ConversionContext& context, const String& key, String& value) const
{
ConversionContextScope scope(context);
@@ -218,7 +228,7 @@ bool Dictionary::convert(ConversionContext& context, const String& key, String&
if (!getKey(key, v8Value))
return true;
- V8TRYCATCH_FOR_V8STRINGRESOURCE_RETURN(V8StringResource<>, stringValue, v8Value, false);
+ TOSTRING_DEFAULT(V8StringResource<>, stringValue, v8Value, false);
value = stringValue;
return true;
}
@@ -229,7 +239,7 @@ bool Dictionary::get(const String& key, ScriptValue& value) const
if (!getKey(key, v8Value))
return false;
- value = ScriptValue(v8Value, m_isolate);
+ value = ScriptValue(ScriptState::current(m_isolate), v8Value);
return true;
}
@@ -299,7 +309,7 @@ bool Dictionary::get(const String& key, unsigned long long& value) const
if (!getKey(key, v8Value))
return false;
- V8TRYCATCH_RETURN(v8::Local<v8::Number>, v8Number, v8Value->ToNumber(), false);
+ TONATIVE_DEFAULT(v8::Local<v8::Number>, v8Number, v8Value->ToNumber(), false);
if (v8Number.IsEmpty())
return false;
double d = v8Number->Value();
@@ -307,7 +317,7 @@ bool Dictionary::get(const String& key, unsigned long long& value) const
return true;
}
-bool Dictionary::get(const String& key, RefPtr<DOMWindow>& value) const
+bool Dictionary::get(const String& key, RefPtrWillBeMember<LocalDOMWindow>& value) const
{
v8::Local<v8::Value> v8Value;
if (!getKey(key, v8Value))
@@ -315,25 +325,17 @@ bool Dictionary::get(const String& key, RefPtr<DOMWindow>& value) const
// We need to handle a DOMWindow specially, because a DOMWindow wrapper
// exists on a prototype chain of v8Value.
- value = 0;
- if (v8Value->IsObject()) {
- v8::Handle<v8::Object> wrapper = v8::Handle<v8::Object>::Cast(v8Value);
- v8::Handle<v8::Object> window = wrapper->FindInstanceInPrototypeChain(V8Window::domTemplate(m_isolate, worldTypeInMainThread(m_isolate)));
- if (!window.IsEmpty())
- value = V8Window::toNative(window);
- }
+ value = toDOMWindow(v8Value, m_isolate);
return true;
}
-bool Dictionary::get(const String& key, RefPtr<Storage>& value) const
+bool Dictionary::get(const String& key, RefPtrWillBeMember<Storage>& value) const
{
v8::Local<v8::Value> v8Value;
if (!getKey(key, v8Value))
return false;
- value = 0;
- if (V8Storage::hasInstance(v8Value, m_isolate, worldType(m_isolate)))
- value = V8Storage::toNative(v8::Handle<v8::Object>::Cast(v8Value));
+ value = V8Storage::toNativeWithTypeCheck(m_isolate, v8Value);
return true;
}
@@ -345,7 +347,11 @@ bool Dictionary::get(const String& key, MessagePortArray& value) const
ASSERT(m_isolate);
ASSERT(m_isolate == v8::Isolate::GetCurrent());
- return getMessagePortArray(v8Value, key, value, m_isolate);
+ if (WebCore::isUndefinedOrNull(v8Value))
+ return true;
+ bool success = false;
+ value = toRefPtrNativeArray<MessagePort, V8MessagePort>(v8Value, key, m_isolate, &success);
+ return success;
}
bool Dictionary::convert(ConversionContext& context, const String& key, MessagePortArray& value) const
@@ -373,8 +379,8 @@ bool Dictionary::get(const String& key, HashSet<AtomicString>& value) const
ASSERT(m_isolate == v8::Isolate::GetCurrent());
v8::Local<v8::Array> v8Array = v8::Local<v8::Array>::Cast(v8Value);
for (size_t i = 0; i < v8Array->Length(); ++i) {
- v8::Local<v8::Value> indexedValue = v8Array->Get(v8::Integer::New(i, m_isolate));
- V8TRYCATCH_FOR_V8STRINGRESOURCE_RETURN(V8StringResource<>, stringValue, indexedValue, false);
+ v8::Local<v8::Value> indexedValue = v8Array->Get(v8::Integer::New(m_isolate, i));
+ TOSTRING_DEFAULT(V8StringResource<>, stringValue, indexedValue, false);
value.add(stringValue);
}
@@ -406,7 +412,7 @@ bool Dictionary::getWithUndefinedOrNullCheck(const String& key, String& value) c
if (!getKey(key, v8Value) || WebCore::isUndefinedOrNull(v8Value))
return false;
- V8TRYCATCH_FOR_V8STRINGRESOURCE_RETURN(V8StringResource<>, stringValue, v8Value, false);
+ TOSTRING_DEFAULT(V8StringResource<>, stringValue, v8Value, false);
value = stringValue;
return true;
}
@@ -417,9 +423,7 @@ bool Dictionary::get(const String& key, RefPtr<Uint8Array>& value) const
if (!getKey(key, v8Value))
return false;
- value = 0;
- if (V8Uint8Array::hasInstance(v8Value, m_isolate, worldType(m_isolate)))
- value = V8Uint8Array::toNative(v8::Handle<v8::Object>::Cast(v8Value));
+ value = V8Uint8Array::toNativeWithTypeCheck(m_isolate, v8Value);
return true;
}
@@ -429,21 +433,17 @@ bool Dictionary::get(const String& key, RefPtr<ArrayBufferView>& value) const
if (!getKey(key, v8Value))
return false;
- value = 0;
- if (V8ArrayBufferView::hasInstance(v8Value, m_isolate, worldType(m_isolate)))
- value = V8ArrayBufferView::toNative(v8::Handle<v8::Object>::Cast(v8Value));
+ value = V8ArrayBufferView::toNativeWithTypeCheck(m_isolate, v8Value);
return true;
}
-bool Dictionary::get(const String& key, RefPtr<MIDIPort>& value) const
+bool Dictionary::get(const String& key, RefPtrWillBeMember<MIDIPort>& value) const
{
v8::Local<v8::Value> v8Value;
if (!getKey(key, v8Value))
return false;
- value = 0;
- if (V8MIDIPort::hasInstance(v8Value, m_isolate, worldType(m_isolate)))
- value = V8MIDIPort::toNative(v8::Handle<v8::Object>::Cast(v8Value));
+ value = V8MIDIPort::toNativeWithTypeCheck(m_isolate, v8Value);
return true;
}
@@ -453,13 +453,11 @@ bool Dictionary::get(const String& key, RefPtr<MediaKeyError>& value) const
if (!getKey(key, v8Value))
return false;
- value = 0;
- if (V8MediaKeyError::hasInstance(v8Value, m_isolate, worldType(m_isolate)))
- value = V8MediaKeyError::toNative(v8::Handle<v8::Object>::Cast(v8Value));
+ value = V8MediaKeyError::toNativeWithTypeCheck(m_isolate, v8Value);
return true;
}
-bool Dictionary::get(const String& key, RefPtr<TrackBase>& value) const
+bool Dictionary::get(const String& key, RefPtrWillBeMember<TrackBase>& value) const
{
v8::Local<v8::Value> v8Value;
if (!getKey(key, v8Value))
@@ -471,7 +469,7 @@ bool Dictionary::get(const String& key, RefPtr<TrackBase>& value) const
// FIXME: this will need to be changed so it can also return an AudioTrack or a VideoTrack once
// we add them.
- v8::Handle<v8::Object> track = wrapper->FindInstanceInPrototypeChain(V8TextTrack::domTemplate(m_isolate, worldType(m_isolate)));
+ v8::Handle<v8::Object> track = V8TextTrack::findInstanceInPrototypeChain(wrapper, m_isolate);
if (!track.IsEmpty())
source = V8TextTrack::toNative(track);
}
@@ -479,39 +477,33 @@ bool Dictionary::get(const String& key, RefPtr<TrackBase>& value) const
return true;
}
-bool Dictionary::get(const String& key, RefPtr<SpeechRecognitionError>& value) const
+bool Dictionary::get(const String& key, Member<SpeechRecognitionResult>& value) const
{
v8::Local<v8::Value> v8Value;
if (!getKey(key, v8Value))
return false;
- value = 0;
- if (V8SpeechRecognitionError::hasInstance(v8Value, m_isolate, worldType(m_isolate)))
- value = V8SpeechRecognitionError::toNative(v8::Handle<v8::Object>::Cast(v8Value));
+ value = V8SpeechRecognitionResult::toNativeWithTypeCheck(m_isolate, v8Value);
return true;
}
-bool Dictionary::get(const String& key, RefPtr<SpeechRecognitionResult>& value) const
+bool Dictionary::get(const String& key, Member<SpeechRecognitionResultList>& value) const
{
v8::Local<v8::Value> v8Value;
if (!getKey(key, v8Value))
return false;
- value = 0;
- if (V8SpeechRecognitionResult::hasInstance(v8Value, m_isolate, worldType(m_isolate)))
- value = V8SpeechRecognitionResult::toNative(v8::Handle<v8::Object>::Cast(v8Value));
+ value = V8SpeechRecognitionResultList::toNativeWithTypeCheck(m_isolate, v8Value);
return true;
}
-bool Dictionary::get(const String& key, RefPtr<SpeechRecognitionResultList>& value) const
+bool Dictionary::get(const String& key, Member<Gamepad>& value) const
{
v8::Local<v8::Value> v8Value;
if (!getKey(key, v8Value))
return false;
- value = 0;
- if (V8SpeechRecognitionResultList::hasInstance(v8Value, m_isolate, worldType(m_isolate)))
- value = V8SpeechRecognitionResultList::toNative(v8::Handle<v8::Object>::Cast(v8Value));
+ value = V8Gamepad::toNativeWithTypeCheck(m_isolate, v8Value);
return true;
}
@@ -521,24 +513,22 @@ bool Dictionary::get(const String& key, RefPtr<MediaStream>& value) const
if (!getKey(key, v8Value))
return false;
- value = 0;
- if (V8MediaStream::hasInstance(v8Value, m_isolate, worldType(m_isolate)))
- value = V8MediaStream::toNative(v8::Handle<v8::Object>::Cast(v8Value));
+ value = V8MediaStream::toNativeWithTypeCheck(m_isolate, v8Value);
return true;
}
-bool Dictionary::get(const String& key, RefPtr<EventTarget>& value) const
+bool Dictionary::get(const String& key, RefPtrWillBeMember<EventTarget>& value) const
{
v8::Local<v8::Value> v8Value;
if (!getKey(key, v8Value))
return false;
- value = 0;
- // We need to handle a DOMWindow specially, because a DOMWindow wrapper
+ value = nullptr;
+ // We need to handle a LocalDOMWindow specially, because a LocalDOMWindow wrapper
// exists on a prototype chain of v8Value.
if (v8Value->IsObject()) {
v8::Handle<v8::Object> wrapper = v8::Handle<v8::Object>::Cast(v8Value);
- v8::Handle<v8::Object> window = wrapper->FindInstanceInPrototypeChain(V8Window::domTemplate(m_isolate, worldTypeInMainThread(m_isolate)));
+ v8::Handle<v8::Object> window = V8Window::findInstanceInPrototypeChain(wrapper, m_isolate);
if (!window.IsEmpty()) {
value = toWrapperTypeInfo(window)->toEventTarget(window);
return true;
@@ -567,6 +557,16 @@ bool Dictionary::get(const String& key, Dictionary& value) const
return true;
}
+bool Dictionary::get(const String& key, RefPtr<HeaderMap>& value) const
+{
+ v8::Local<v8::Value> v8Value;
+ if (!getKey(key, v8Value))
+ return false;
+
+ value = V8HeaderMap::toNativeWithTypeCheck(m_isolate, v8Value);
+ return true;
+}
+
bool Dictionary::convert(ConversionContext& context, const String& key, Dictionary& value) const
{
ConversionContextScope scope(context);
@@ -596,8 +596,8 @@ bool Dictionary::get(const String& key, Vector<String>& value) const
v8::Local<v8::Array> v8Array = v8::Local<v8::Array>::Cast(v8Value);
for (size_t i = 0; i < v8Array->Length(); ++i) {
- v8::Local<v8::Value> indexedValue = v8Array->Get(v8::Uint32::New(i, m_isolate));
- V8TRYCATCH_FOR_V8STRINGRESOURCE_RETURN(V8StringResource<>, stringValue, indexedValue, false);
+ v8::Local<v8::Value> indexedValue = v8Array->Get(v8::Uint32::New(m_isolate, i));
+ TOSTRING_DEFAULT(V8StringResource<>, stringValue, indexedValue, false);
value.append(stringValue);
}
@@ -657,33 +657,13 @@ bool Dictionary::convert(ConversionContext& context, const String& key, ArrayVal
return get(key, value);
}
-bool Dictionary::get(const String& key, RefPtr<DOMError>& value) const
-{
- v8::Local<v8::Value> v8Value;
- if (!getKey(key, v8Value))
- return false;
-
- DOMError* error = 0;
- if (v8Value->IsObject()) {
- v8::Handle<v8::Object> wrapper = v8::Handle<v8::Object>::Cast(v8Value);
- v8::Handle<v8::Object> domError = wrapper->FindInstanceInPrototypeChain(V8DOMError::domTemplate(m_isolate, worldType(m_isolate)));
- if (!domError.IsEmpty())
- error = V8DOMError::toNative(domError);
- }
- value = error;
- return true;
-}
-
-bool Dictionary::get(const String& key, OwnPtr<VoidCallback>& value) const
+bool Dictionary::get(const String& key, RefPtrWillBeMember<DOMError>& value) const
{
v8::Local<v8::Value> v8Value;
if (!getKey(key, v8Value))
return false;
- if (!v8Value->IsFunction())
- return false;
-
- value = V8VoidCallback::create(v8::Handle<v8::Function>::Cast(v8Value), getExecutionContext());
+ value = V8DOMError::toNativeWithTypeCheck(m_isolate, v8Value);
return true;
}
@@ -705,8 +685,8 @@ bool Dictionary::getOwnPropertiesAsStringHashMap(HashMap<String, String>& hashMa
continue;
v8::Local<v8::Value> value = options->Get(key);
- V8TRYCATCH_FOR_V8STRINGRESOURCE_RETURN(V8StringResource<>, stringKey, key, false);
- V8TRYCATCH_FOR_V8STRINGRESOURCE_RETURN(V8StringResource<>, stringValue, value, false);
+ TOSTRING_DEFAULT(V8StringResource<>, stringKey, key, false);
+ TOSTRING_DEFAULT(V8StringResource<>, stringValue, value, false);
if (!static_cast<const String&>(stringKey).isEmpty())
hashMap.set(stringKey, stringValue);
}
@@ -730,7 +710,7 @@ bool Dictionary::getOwnPropertyNames(Vector<String>& names) const
v8::Local<v8::String> key = properties->Get(i)->ToString();
if (!options->Has(key))
continue;
- V8TRYCATCH_FOR_V8STRINGRESOURCE_RETURN(V8StringResource<>, stringKey, key, false);
+ TOSTRING_DEFAULT(V8StringResource<>, stringKey, key, false);
names.append(stringKey);
}
@@ -758,12 +738,7 @@ Dictionary::ConversionContext& Dictionary::ConversionContext::setConversionType(
void Dictionary::ConversionContext::throwTypeError(const String& detail)
{
- if (forConstructor()) {
- exceptionState().throwTypeError(detail);
- } else {
- ASSERT(!methodName().isEmpty());
- exceptionState().throwTypeError(ExceptionMessages::failedToExecute(interfaceName(), methodName(), detail));
- }
+ exceptionState().throwTypeError(detail);
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/Dictionary.h b/chromium/third_party/WebKit/Source/bindings/v8/Dictionary.h
index 3f29651e876..2268c63bd2f 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/Dictionary.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/Dictionary.h
@@ -28,6 +28,7 @@
#include "bindings/v8/ExceptionMessages.h"
#include "bindings/v8/ExceptionState.h"
+#include "bindings/v8/Nullable.h"
#include "bindings/v8/ScriptValue.h"
#include "bindings/v8/V8Binding.h"
#include "bindings/v8/V8BindingMacros.h"
@@ -44,12 +45,14 @@ namespace WebCore {
class ArrayValue;
class DOMError;
-class DOMWindow;
+class LocalDOMWindow;
+class Gamepad;
+class MediaStream;
+class HeaderMap;
class IDBKeyRange;
class MIDIPort;
class MediaKeyError;
class Notification;
-class SpeechRecognitionError;
class SpeechRecognitionResult;
class SpeechRecognitionResultList;
class Storage;
@@ -57,6 +60,7 @@ class TrackBase;
class VoidCallback;
class Dictionary {
+ ALLOW_ONLY_INLINE_ALLOCATION();
public:
Dictionary();
Dictionary(const v8::Handle<v8::Value>& options, v8::Isolate*);
@@ -72,32 +76,33 @@ public:
bool get(const String&, double&, bool& hasValue) const;
bool get(const String&, double&) const;
bool get(const String&, String&) const;
+ bool get(const String&, AtomicString&) const;
bool get(const String&, ScriptValue&) const;
bool get(const String&, short&) const;
bool get(const String&, unsigned short&) const;
bool get(const String&, unsigned&) const;
bool get(const String&, unsigned long&) const;
bool get(const String&, unsigned long long&) const;
- bool get(const String&, RefPtr<DOMWindow>&) const;
- bool get(const String&, RefPtr<Storage>&) const;
+ bool get(const String&, RefPtrWillBeMember<LocalDOMWindow>&) const;
+ bool get(const String&, RefPtrWillBeMember<Storage>&) const;
bool get(const String&, MessagePortArray&) const;
bool get(const String&, RefPtr<Uint8Array>&) const;
bool get(const String&, RefPtr<ArrayBufferView>&) const;
- bool get(const String&, RefPtr<MIDIPort>&) const;
+ bool get(const String&, RefPtrWillBeMember<MIDIPort>&) const;
bool get(const String&, RefPtr<MediaKeyError>&) const;
- bool get(const String&, RefPtr<TrackBase>&) const;
- bool get(const String&, RefPtr<SpeechRecognitionError>&) const;
- bool get(const String&, RefPtr<SpeechRecognitionResult>&) const;
- bool get(const String&, RefPtr<SpeechRecognitionResultList>&) const;
+ bool get(const String&, RefPtrWillBeMember<TrackBase>&) const;
+ bool get(const String&, Member<SpeechRecognitionResult>&) const;
+ bool get(const String&, Member<SpeechRecognitionResultList>&) const;
+ bool get(const String&, Member<Gamepad>&) const;
bool get(const String&, RefPtr<MediaStream>&) const;
- bool get(const String&, RefPtr<EventTarget>&) const;
+ bool get(const String&, RefPtrWillBeMember<EventTarget>&) const;
bool get(const String&, HashSet<AtomicString>&) const;
bool get(const String&, Dictionary&) const;
bool get(const String&, Vector<String>&) const;
bool get(const String&, ArrayValue&) const;
- bool get(const String&, RefPtr<DOMError>&) const;
- bool get(const String&, OwnPtr<VoidCallback>&) const;
+ bool get(const String&, RefPtrWillBeMember<DOMError>&) const;
bool get(const String&, v8::Local<v8::Value>&) const;
+ bool get(const String&, RefPtr<HeaderMap>&) const;
class ConversionContext {
public:
@@ -152,14 +157,20 @@ public:
bool convert(ConversionContext&, const String&, ScriptValue&) const;
template<typename IntegralType>
- bool convert(ConversionContext &, const String&, IntegralType&) const;
- bool convert(ConversionContext &, const String&, MessagePortArray&) const;
- bool convert(ConversionContext &, const String&, HashSet<AtomicString>&) const;
- bool convert(ConversionContext &, const String&, Dictionary&) const;
- bool convert(ConversionContext &, const String&, Vector<String>&) const;
- bool convert(ConversionContext &, const String&, ArrayValue&) const;
- template<typename T>
- bool convert(ConversionContext &, const String&, RefPtr<T>&) const;
+ bool convert(ConversionContext&, const String&, IntegralType&) const;
+ template<typename IntegralType>
+ bool convert(ConversionContext&, const String&, Nullable<IntegralType>&) const;
+
+ bool convert(ConversionContext&, const String&, MessagePortArray&) const;
+ bool convert(ConversionContext&, const String&, HashSet<AtomicString>&) const;
+ bool convert(ConversionContext&, const String&, Dictionary&) const;
+ bool convert(ConversionContext&, const String&, Vector<String>&) const;
+ bool convert(ConversionContext&, const String&, ArrayValue&) const;
+ template<template <typename> class PointerType, typename T>
+ bool convert(ConversionContext&, const String&, PointerType<T>&) const;
+
+ template<typename StringType>
+ bool getStringType(const String&, StringType&) const;
bool getOwnPropertiesAsStringHashMap(HashMap<String, String>&) const;
bool getOwnPropertyNames(Vector<String>&) const;
@@ -168,13 +179,7 @@ public:
bool hasProperty(const String&) const;
- // Only allow inline allocation.
- void* operator new(size_t, NotNullTag, void* location) { return location; }
-
private:
- // Disallow new allocation.
- void* operator new(size_t);
-
bool getKey(const String& key, v8::Local<v8::Value>&) const;
v8::Handle<v8::Value> m_options;
@@ -195,90 +200,90 @@ struct IntegralTypeTraits {
template <>
struct IntegralTypeTraits<uint8_t> {
- static inline uint8_t toIntegral(v8::Handle<v8::Value> value, IntegerConversionConfiguration configuration, bool& ok)
+ static inline uint8_t toIntegral(v8::Handle<v8::Value> value, IntegerConversionConfiguration configuration, ExceptionState& exceptionState)
{
- return toUInt8(value, configuration, ok);
+ return toUInt8(value, configuration, exceptionState);
}
static const String typeName() { return "UInt8"; }
};
template <>
struct IntegralTypeTraits<int8_t> {
- static inline int8_t toIntegral(v8::Handle<v8::Value> value, IntegerConversionConfiguration configuration, bool& ok)
+ static inline int8_t toIntegral(v8::Handle<v8::Value> value, IntegerConversionConfiguration configuration, ExceptionState& exceptionState)
{
- return toInt8(value, configuration, ok);
+ return toInt8(value, configuration, exceptionState);
}
static const String typeName() { return "Int8"; }
};
template <>
struct IntegralTypeTraits<unsigned short> {
- static inline uint16_t toIntegral(v8::Handle<v8::Value> value, IntegerConversionConfiguration configuration, bool& ok)
+ static inline uint16_t toIntegral(v8::Handle<v8::Value> value, IntegerConversionConfiguration configuration, ExceptionState& exceptionState)
{
- return toUInt16(value, configuration, ok);
+ return toUInt16(value, configuration, exceptionState);
}
static const String typeName() { return "UInt16"; }
};
template <>
struct IntegralTypeTraits<short> {
- static inline int16_t toIntegral(v8::Handle<v8::Value> value, IntegerConversionConfiguration configuration, bool& ok)
+ static inline int16_t toIntegral(v8::Handle<v8::Value> value, IntegerConversionConfiguration configuration, ExceptionState& exceptionState)
{
- return toInt16(value, configuration, ok);
+ return toInt16(value, configuration, exceptionState);
}
static const String typeName() { return "Int16"; }
};
template <>
struct IntegralTypeTraits<unsigned> {
- static inline uint32_t toIntegral(v8::Handle<v8::Value> value, IntegerConversionConfiguration configuration, bool& ok)
+ static inline uint32_t toIntegral(v8::Handle<v8::Value> value, IntegerConversionConfiguration configuration, ExceptionState& exceptionState)
{
- return toUInt32(value, configuration, ok);
+ return toUInt32(value, configuration, exceptionState);
}
static const String typeName() { return "UInt32"; }
};
template <>
struct IntegralTypeTraits<unsigned long> {
- static inline uint32_t toIntegral(v8::Handle<v8::Value> value, IntegerConversionConfiguration configuration, bool& ok)
+ static inline uint32_t toIntegral(v8::Handle<v8::Value> value, IntegerConversionConfiguration configuration, ExceptionState& exceptionState)
{
- return toUInt32(value, configuration, ok);
+ return toUInt32(value, configuration, exceptionState);
}
static const String typeName() { return "UInt32"; }
};
template <>
struct IntegralTypeTraits<int> {
- static inline int32_t toIntegral(v8::Handle<v8::Value> value, IntegerConversionConfiguration configuration, bool& ok)
+ static inline int32_t toIntegral(v8::Handle<v8::Value> value, IntegerConversionConfiguration configuration, ExceptionState& exceptionState)
{
- return toInt32(value, configuration, ok);
+ return toInt32(value, configuration, exceptionState);
}
static const String typeName() { return "Int32"; }
};
template <>
struct IntegralTypeTraits<long> {
- static inline int32_t toIntegral(v8::Handle<v8::Value> value, IntegerConversionConfiguration configuration, bool& ok)
+ static inline int32_t toIntegral(v8::Handle<v8::Value> value, IntegerConversionConfiguration configuration, ExceptionState& exceptionState)
{
- return toInt32(value, configuration, ok);
+ return toInt32(value, configuration, exceptionState);
}
static const String typeName() { return "Int32"; }
};
template <>
struct IntegralTypeTraits<unsigned long long> {
- static inline unsigned long long toIntegral(v8::Handle<v8::Value> value, IntegerConversionConfiguration configuration, bool& ok)
+ static inline unsigned long long toIntegral(v8::Handle<v8::Value> value, IntegerConversionConfiguration configuration, ExceptionState& exceptionState)
{
- return toUInt64(value, configuration, ok);
+ return toUInt64(value, configuration, exceptionState);
}
static const String typeName() { return "UInt64"; }
};
template <>
struct IntegralTypeTraits<long long> {
- static inline long long toIntegral(v8::Handle<v8::Value> value, IntegerConversionConfiguration configuration, bool& ok)
+ static inline long long toIntegral(v8::Handle<v8::Value> value, IntegerConversionConfiguration configuration, ExceptionState& exceptionState)
{
- return toInt64(value, configuration, ok);
+ return toInt64(value, configuration, exceptionState);
}
static const String typeName() { return "Int64"; }
};
@@ -291,18 +296,36 @@ template<typename T> bool Dictionary::convert(ConversionContext& context, const
if (!getKey(key, v8Value))
return true;
- bool ok = false;
- value = IntegralTypeTraits<T>::toIntegral(v8Value, NormalConversion, ok);
- if (ok)
+ value = IntegralTypeTraits<T>::toIntegral(v8Value, NormalConversion, context.exceptionState());
+ if (context.exceptionState().throwIfNeeded())
+ return false;
+
+ return true;
+}
+
+template<typename T> bool Dictionary::convert(ConversionContext& context, const String& key, Nullable<T>& value) const
+{
+ ConversionContextScope scope(context);
+
+ v8::Local<v8::Value> v8Value;
+ if (!getKey(key, v8Value))
return true;
- V8TRYCATCH_RETURN(v8::Local<v8::Number>, v8Number, v8Value->ToNumber(), false);
- ASSERT(v8Number.IsEmpty());
- context.throwTypeError(ExceptionMessages::incorrectPropertyType(key, "does not have type " + IntegralTypeTraits<T>::typeName() + "."));
- return false;
+ if (context.isNullable() && WebCore::isUndefinedOrNull(v8Value)) {
+ value = Nullable<T>();
+ return true;
+ }
+
+ T converted = IntegralTypeTraits<T>::toIntegral(v8Value, NormalConversion, context.exceptionState());
+
+ if (context.exceptionState().throwIfNeeded())
+ return false;
+
+ value = Nullable<T>(converted);
+ return true;
}
-template<typename T> bool Dictionary::convert(ConversionContext& context, const String& key, RefPtr<T>& value) const
+template<template <typename> class PointerType, typename T> bool Dictionary::convert(ConversionContext& context, const String& key, PointerType<T>& value) const
{
ConversionContextScope scope(context);
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ExceptionMessages.cpp b/chromium/third_party/WebKit/Source/bindings/v8/ExceptionMessages.cpp
index beea8bef6d3..c65e04703d4 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/ExceptionMessages.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ExceptionMessages.cpp
@@ -31,33 +31,59 @@
#include "config.h"
#include "bindings/v8/ExceptionMessages.h"
+#include "platform/Decimal.h"
#include "wtf/MathExtras.h"
namespace WebCore {
-String ExceptionMessages::failedToConstruct(const String& type, const String& detail)
+String ExceptionMessages::failedToConstruct(const char* type, const String& detail)
{
- return "Failed to construct '" + type + (!detail.isEmpty() ? String("': " + detail) : String("'"));
+ return "Failed to construct '" + String(type) + (!detail.isEmpty() ? String("': " + detail) : String("'"));
}
-String ExceptionMessages::failedToExecute(const String& method, const String& type, const String& detail)
+String ExceptionMessages::failedToEnumerate(const char* type, const String& detail)
{
- return "Failed to execute '" + method + "' on '" + type + (!detail.isEmpty() ? String("': " + detail) : String("'"));
+ return "Failed to enumerate the properties of '" + String(type) + (!detail.isEmpty() ? String("': " + detail) : String("'"));
}
-String ExceptionMessages::failedToGet(const String& property, const String& type, const String& detail)
+String ExceptionMessages::failedToExecute(const char* method, const char* type, const String& detail)
{
- return "Failed to read the '" + property + "' property from '" + type + "': " + detail;
+ return "Failed to execute '" + String(method) + "' on '" + String(type) + (!detail.isEmpty() ? String("': " + detail) : String("'"));
}
-String ExceptionMessages::failedToSet(const String& property, const String& type, const String& detail)
+String ExceptionMessages::failedToGet(const char* property, const char* type, const String& detail)
{
- return "Failed to set the '" + property + "' property on '" + type + "': " + detail;
+ return "Failed to read the '" + String(property) + "' property from '" + String(type) + "': " + detail;
}
-String ExceptionMessages::failedToDelete(const String& property, const String& type, const String& detail)
+String ExceptionMessages::failedToSet(const char* property, const char* type, const String& detail)
{
- return "Failed to delete the '" + property + "' property from '" + type + "': " + detail;
+ return "Failed to set the '" + String(property) + "' property on '" + String(type) + "': " + detail;
+}
+
+String ExceptionMessages::failedToDelete(const char* property, const char* type, const String& detail)
+{
+ return "Failed to delete the '" + String(property) + "' property from '" + String(type) + "': " + detail;
+}
+
+String ExceptionMessages::failedToGetIndexed(const char* type, const String& detail)
+{
+ return "Failed to read an indexed property from '" + String(type) + "': " + detail;
+}
+
+String ExceptionMessages::failedToSetIndexed(const char* type, const String& detail)
+{
+ return "Failed to set an indexed property on '" + String(type) + "': " + detail;
+}
+
+String ExceptionMessages::failedToDeleteIndexed(const char* type, const String& detail)
+{
+ return "Failed to delete an indexed property from '" + String(type) + "': " + detail;
+}
+
+String ExceptionMessages::constructorNotCallableAsFunction(const char* type)
+{
+ return failedToConstruct(type, "Please use the 'new' operator, this DOM object constructor cannot be called as a function.");
}
String ExceptionMessages::incorrectPropertyType(const String& property, const String& detail)
@@ -65,9 +91,14 @@ String ExceptionMessages::incorrectPropertyType(const String& property, const St
return "The '" + property + "' property " + detail;
}
-String ExceptionMessages::incorrectArgumentType(int argumentIndex, const String& detail)
+String ExceptionMessages::invalidArity(const char* expected, unsigned provided)
{
- return "The " + ordinalNumber(argumentIndex) + " argument " + detail;
+ return "Valid arities are: " + String(expected) + ", but " + String::number(provided) + " arguments provided.";
+}
+
+String ExceptionMessages::argumentNullOrIncorrectType(int argumentIndex, const String& expectedType)
+{
+ return "The " + ordinalNumber(argumentIndex) + " argument provided is either null, or an invalid " + expectedType + " object.";
}
String ExceptionMessages::notAnArrayTypeArgumentOrValue(int argumentIndex)
@@ -90,10 +121,16 @@ String ExceptionMessages::notEnoughArguments(unsigned expected, unsigned provide
return String::number(expected) + " argument" + (expected > 1 ? "s" : "") + " required, but only " + String::number(provided) + " present.";
}
-String ExceptionMessages::notAFiniteNumber(double value)
+String ExceptionMessages::notAFiniteNumber(double value, const char* name)
{
ASSERT(!std::isfinite(value));
- return std::isinf(value) ? "The value provided is infinite." : "The value provided is not a number.";
+ return String::format("The %s is %s.", name, std::isinf(value) ? "infinite" : "not a number");
+}
+
+String ExceptionMessages::notAFiniteNumber(const Decimal& value, const char* name)
+{
+ ASSERT(!value.isFinite());
+ return String::format("The %s is %s.", name, value.isInfinity() ? "infinite" : "not a number");
}
String ExceptionMessages::ordinalNumber(int number)
@@ -116,4 +153,22 @@ String ExceptionMessages::ordinalNumber(int number)
return String::number(number) + suffix;
}
+String ExceptionMessages::readOnly(const char* detail)
+{
+ DEFINE_STATIC_LOCAL(String, readOnly, ("This object is read-only."));
+ return detail ? String::format("This object is read-only, because %s.", detail) : readOnly;
+}
+
+template <>
+String ExceptionMessages::formatNumber<float>(float number)
+{
+ return formatPotentiallyNonFiniteNumber(number);
+}
+
+template <>
+String ExceptionMessages::formatNumber<double>(double number)
+{
+ return formatPotentiallyNonFiniteNumber(number);
+}
+
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ExceptionMessages.h b/chromium/third_party/WebKit/Source/bindings/v8/ExceptionMessages.h
index 92f8a9f5879..a74819b3970 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/ExceptionMessages.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ExceptionMessages.h
@@ -31,33 +31,134 @@
#ifndef ExceptionMessages_h
#define ExceptionMessages_h
+#include "wtf/MathExtras.h"
+#include "wtf/text/StringBuilder.h"
#include "wtf/text/WTFString.h"
namespace WebCore {
+class Decimal;
+
class ExceptionMessages {
public:
- static String failedToConstruct(const String& type, const String& detail = String());
- static String failedToExecute(const String& method, const String& type, const String& detail = String());
- static String failedToGet(const String& property, const String& type, const String& detail);
- static String failedToSet(const String& property, const String& type, const String& detail);
- static String failedToDelete(const String& property, const String& type, const String& detail);
+ enum BoundType {
+ InclusiveBound,
+ ExclusiveBound,
+ };
+
+ static String argumentNullOrIncorrectType(int argumentIndex, const String& expectedType);
+ static String constructorNotCallableAsFunction(const char* type);
+
+ static String failedToConstruct(const char* type, const String& detail);
+ static String failedToEnumerate(const char* type, const String& detail);
+ static String failedToExecute(const char* method, const char* type, const String& detail);
+ static String failedToGet(const char* property, const char* type, const String& detail);
+ static String failedToSet(const char* property, const char* type, const String& detail);
+ static String failedToDelete(const char* property, const char* type, const String& detail);
+ static String failedToGetIndexed(const char* type, const String& detail);
+ static String failedToSetIndexed(const char* type, const String& detail);
+ static String failedToDeleteIndexed(const char* type, const String& detail);
+
+ template <typename NumType>
+ static String formatNumber(NumType number)
+ {
+ return formatFiniteNumber(number);
+ }
- static String incorrectArgumentType(int argumentIndex, const String& detail);
static String incorrectPropertyType(const String& property, const String& detail);
+ template <typename NumberType>
+ static String indexExceedsMaximumBound(const char* name, NumberType given, NumberType bound)
+ {
+ bool eq = given == bound;
+ StringBuilder result;
+ result.append("The ");
+ result.append(name);
+ result.append(" provided (");
+ result.append(formatNumber(given));
+ result.append(") is greater than ");
+ result.append(eq ? "or equal to " : "");
+ result.append("the maximum bound (");
+ result.append(formatNumber(bound));
+ result.append(").");
+ return result.toString();
+ }
+
+ template <typename NumberType>
+ static String indexExceedsMinimumBound(const char* name, NumberType given, NumberType bound)
+ {
+ bool eq = given == bound;
+ StringBuilder result;
+ result.append("The ");
+ result.append(name);
+ result.append(" provided (");
+ result.append(formatNumber(given));
+ result.append(") is less than ");
+ result.append(eq ? "or equal to " : "");
+ result.append("the minimum bound (");
+ result.append(formatNumber(bound));
+ result.append(").");
+ return result.toString();
+ }
+
+ template <typename NumberType>
+ static String indexOutsideRange(const char* name, NumberType given, NumberType lowerBound, BoundType lowerType, NumberType upperBound, BoundType upperType)
+ {
+ StringBuilder result;
+ result.append("The ");
+ result.append(name);
+ result.append(" provided (");
+ result.append(formatNumber(given));
+ result.append(") is outside the range ");
+ result.append(lowerType == ExclusiveBound ? '(' : '[');
+ result.append(formatNumber(lowerBound));
+ result.append(", ");
+ result.append(formatNumber(upperBound));
+ result.append(upperType == ExclusiveBound ? ')' : ']');
+ result.append('.');
+ return result.toString();
+ }
+
+ static String invalidArity(const char* expected, unsigned provided);
+
// If > 0, the argument index that failed type check (1-indexed.)
// If == 0, a (non-argument) value (e.g., a setter) failed the same check.
static String notAnArrayTypeArgumentOrValue(int argumentIndex);
static String notASequenceTypeProperty(const String& propertyName);
- static String notAFiniteNumber(double value);
+ static String notAFiniteNumber(double value, const char* name = "value provided");
+ static String notAFiniteNumber(const Decimal& value, const char* name = "value provided");
static String notEnoughArguments(unsigned expected, unsigned providedleastNumMandatoryParams);
+ static String readOnly(const char* detail = 0);
+
private:
+ template <typename NumType>
+ static String formatFiniteNumber(NumType number)
+ {
+ if (number > 1e20 || number < -1e20)
+ return String::format("%e", 1.0*number);
+ return String::number(number);
+ }
+
+ template <typename NumType>
+ static String formatPotentiallyNonFiniteNumber(NumType number)
+ {
+ if (std::isnan(number))
+ return "NaN";
+ if (std::isinf(number))
+ return number > 0 ? "Infinity" : "-Infinity";
+ if (number > 1e20 || number < -1e20)
+ return String::format("%e", number);
+ return String::number(number);
+ }
+
static String ordinalNumber(int number);
};
+template <> String ExceptionMessages::formatNumber<float>(float number);
+template <> String ExceptionMessages::formatNumber<double>(double number);
+
} // namespace WebCore
#endif // ExceptionMessages_h
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ExceptionState.cpp b/chromium/third_party/WebKit/Source/bindings/v8/ExceptionState.cpp
index 77c9103d7be..d51325cc41d 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/ExceptionState.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ExceptionState.cpp
@@ -47,21 +47,26 @@ void ExceptionState::throwDOMException(const ExceptionCode& ec, const String& me
{
ASSERT(ec);
ASSERT(m_isolate);
+ ASSERT(!m_creationContext.IsEmpty());
// SecurityError is thrown via ::throwSecurityError, and _careful_ consideration must be given to the data exposed to JavaScript via the 'sanitizedMessage'.
ASSERT(ec != SecurityError);
m_code = ec;
String processedMessage = addExceptionContext(message);
+ m_message = processedMessage;
setException(V8ThrowException::createDOMException(ec, processedMessage, m_creationContext, m_isolate));
}
void ExceptionState::throwSecurityError(const String& sanitizedMessage, const String& unsanitizedMessage)
{
ASSERT(m_isolate);
+ ASSERT(!m_creationContext.IsEmpty());
m_code = SecurityError;
String finalSanitized = addExceptionContext(sanitizedMessage);
+ m_message = finalSanitized;
String finalUnsanitized = addExceptionContext(unsanitizedMessage);
+
setException(V8ThrowException::createDOMException(SecurityError, finalSanitized, finalUnsanitized, m_creationContext, m_isolate));
}
@@ -76,26 +81,57 @@ void ExceptionState::setException(v8::Handle<v8::Value> exception)
m_exception.set(m_isolate, exception);
}
+void ExceptionState::throwException()
+{
+ ASSERT(!m_exception.isEmpty());
+ V8ThrowException::throwError(m_exception.newLocal(m_isolate), m_isolate);
+}
+
void ExceptionState::throwTypeError(const String& message)
{
ASSERT(m_isolate);
m_code = TypeError;
+ m_message = message;
setException(V8ThrowException::createTypeError(addExceptionContext(message), m_isolate));
}
+void NonThrowableExceptionState::throwDOMException(const ExceptionCode& ec, const String& message)
+{
+ ASSERT_NOT_REACHED();
+ m_code = ec;
+ m_message = message;
+}
+
+void NonThrowableExceptionState::throwTypeError(const String& message)
+{
+ ASSERT_NOT_REACHED();
+ m_code = TypeError;
+ m_message = message;
+}
+
+void NonThrowableExceptionState::throwSecurityError(const String& sanitizedMessage, const String&)
+{
+ ASSERT_NOT_REACHED();
+ m_code = SecurityError;
+ m_message = sanitizedMessage;
+}
+
void TrackExceptionState::throwDOMException(const ExceptionCode& ec, const String& message)
{
m_code = ec;
+ m_message = message;
}
-void TrackExceptionState::throwTypeError(const String&)
+void TrackExceptionState::throwTypeError(const String& message)
{
m_code = TypeError;
+ m_message = message;
}
-void TrackExceptionState::throwSecurityError(const String&, const String&)
+void TrackExceptionState::throwSecurityError(const String& sanitizedMessage, const String&)
{
m_code = SecurityError;
+ m_message = sanitizedMessage;
}
String ExceptionState::addExceptionContext(const String& message) const
@@ -113,8 +149,17 @@ String ExceptionState::addExceptionContext(const String& message) const
processedMessage = ExceptionMessages::failedToGet(propertyName(), interfaceName(), message);
else if (m_context == SetterContext)
processedMessage = ExceptionMessages::failedToSet(propertyName(), interfaceName(), message);
- } else if (!propertyName() && interfaceName() && m_context == ConstructionContext) {
- processedMessage = ExceptionMessages::failedToConstruct(interfaceName(), message);
+ } else if (!propertyName() && interfaceName()) {
+ if (m_context == ConstructionContext)
+ processedMessage = ExceptionMessages::failedToConstruct(interfaceName(), message);
+ else if (m_context == EnumerationContext)
+ processedMessage = ExceptionMessages::failedToEnumerate(interfaceName(), message);
+ else if (m_context == IndexedDeletionContext)
+ processedMessage = ExceptionMessages::failedToDeleteIndexed(interfaceName(), message);
+ else if (m_context == IndexedGetterContext)
+ processedMessage = ExceptionMessages::failedToGetIndexed(interfaceName(), message);
+ else if (m_context == IndexedSetterContext)
+ processedMessage = ExceptionMessages::failedToSetIndexed(interfaceName(), message);
}
return processedMessage;
}
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ExceptionState.h b/chromium/third_party/WebKit/Source/bindings/v8/ExceptionState.h
index bfe2790e16a..d9c2b05b8ef 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/ExceptionState.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ExceptionState.h
@@ -50,17 +50,14 @@ public:
DeletionContext,
GetterContext,
SetterContext,
+ EnumerationContext,
+ QueryContext,
+ IndexedGetterContext,
+ IndexedSetterContext,
+ IndexedDeletionContext,
UnknownContext, // FIXME: Remove this once we've flipped over to the new API.
};
- explicit ExceptionState(const v8::Handle<v8::Object>& creationContext, v8::Isolate* isolate)
- : m_code(0)
- , m_context(UnknownContext)
- , m_propertyName(0)
- , m_interfaceName(0)
- , m_creationContext(creationContext)
- , m_isolate(isolate) { }
-
ExceptionState(Context context, const char* propertyName, const char* interfaceName, const v8::Handle<v8::Object>& creationContext, v8::Isolate* isolate)
: m_code(0)
, m_context(context)
@@ -75,30 +72,23 @@ public:
, m_propertyName(0)
, m_interfaceName(interfaceName)
, m_creationContext(creationContext)
- , m_isolate(isolate) { ASSERT(m_context == ConstructionContext); }
+ , m_isolate(isolate) { ASSERT(m_context == ConstructionContext || m_context == EnumerationContext || m_context == IndexedSetterContext || m_context == IndexedGetterContext || m_context == IndexedDeletionContext); }
virtual void throwDOMException(const ExceptionCode&, const String& message);
virtual void throwTypeError(const String& message);
virtual void throwSecurityError(const String& sanitizedMessage, const String& unsanitizedMessage = String());
- // Please don't use these methods. Use ::throwDOMException and ::throwTypeError, and pass in a useful exception message.
- virtual void throwUninformativeAndGenericDOMException(const ExceptionCode& ec) { throwDOMException(ec, String()); }
- virtual void throwUninformativeAndGenericTypeError() { throwTypeError(String()); }
-
bool hadException() const { return !m_exception.isEmpty() || m_code; }
void clearException();
ExceptionCode code() const { return m_code; }
+ const String& message() const { return m_message; }
bool throwIfNeeded()
{
- if (m_exception.isEmpty()) {
- if (!m_code)
- return false;
- throwUninformativeAndGenericDOMException(m_code);
- }
-
- V8ThrowException::throwError(m_exception.newLocal(m_isolate), m_isolate);
+ if (!hadException())
+ return false;
+ throwException();
return true;
}
@@ -106,14 +96,21 @@ public:
const char* propertyName() const { return m_propertyName; }
const char* interfaceName() const { return m_interfaceName; }
+ void rethrowV8Exception(v8::Handle<v8::Value> value)
+ {
+ setException(value);
+ }
+
protected:
ExceptionCode m_code;
Context m_context;
+ String m_message;
const char* m_propertyName;
const char* m_interfaceName;
private:
void setException(v8::Handle<v8::Value>);
+ void throwException();
String addExceptionContext(const String&) const;
@@ -122,12 +119,22 @@ private:
v8::Isolate* m_isolate;
};
-class TrackExceptionState : public ExceptionState {
+// Used if exceptions can/should not be directly thrown.
+class NonThrowableExceptionState FINAL : public ExceptionState {
+public:
+ NonThrowableExceptionState(): ExceptionState(ExceptionState::UnknownContext, 0, 0, v8::Handle<v8::Object>(), v8::Isolate::GetCurrent()) { }
+ virtual void throwDOMException(const ExceptionCode&, const String& message) OVERRIDE;
+ virtual void throwTypeError(const String& message = String()) OVERRIDE;
+ virtual void throwSecurityError(const String& sanitizedMessage, const String& unsanitizedMessage = String()) OVERRIDE;
+};
+
+// Used if any exceptions thrown are ignorable.
+class TrackExceptionState FINAL : public ExceptionState {
public:
- TrackExceptionState(): ExceptionState(v8::Handle<v8::Object>(), 0) { }
- virtual void throwDOMException(const ExceptionCode&, const String& message) OVERRIDE FINAL;
- virtual void throwTypeError(const String& message = String()) OVERRIDE FINAL;
- virtual void throwSecurityError(const String& sanitizedMessage, const String& unsanitizedMessage = String()) OVERRIDE FINAL;
+ TrackExceptionState(): ExceptionState(ExceptionState::UnknownContext, 0, 0, v8::Handle<v8::Object>(), v8::Isolate::GetCurrent()) { }
+ virtual void throwDOMException(const ExceptionCode&, const String& message) OVERRIDE;
+ virtual void throwTypeError(const String& message = String()) OVERRIDE;
+ virtual void throwSecurityError(const String& sanitizedMessage, const String& unsanitizedMessage = String()) OVERRIDE;
};
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ExceptionStatePlaceholder.cpp b/chromium/third_party/WebKit/Source/bindings/v8/ExceptionStatePlaceholder.cpp
index 9d33119c814..6cfb6b2452e 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/ExceptionStatePlaceholder.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ExceptionStatePlaceholder.cpp
@@ -33,10 +33,10 @@
namespace WebCore {
-#if !ASSERT_DISABLED
+#if ASSERT_ENABLED
NoExceptionStateAssertionChecker::NoExceptionStateAssertionChecker(const char* file, int line)
- : ExceptionState(v8::Handle<v8::Object>(), 0)
+ : ExceptionState(ExceptionState::UnknownContext, 0, 0, v8::Handle<v8::Object>(), 0)
, m_file(file)
, m_line(line) { }
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ExceptionStatePlaceholder.h b/chromium/third_party/WebKit/Source/bindings/v8/ExceptionStatePlaceholder.h
index 84f6eb0b0f6..6df5b1ab9bb 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/ExceptionStatePlaceholder.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ExceptionStatePlaceholder.h
@@ -34,6 +34,7 @@
#include "bindings/v8/ExceptionState.h"
#include "wtf/Assertions.h"
#include "wtf/text/WTFString.h"
+#include <v8.h>
namespace WebCore {
@@ -41,30 +42,26 @@ class ExceptionState;
typedef int ExceptionCode;
-class IgnorableExceptionState : public ExceptionState {
+class IgnorableExceptionState FINAL : public ExceptionState {
public:
- IgnorableExceptionState(): ExceptionState(v8::Handle<v8::Object>(), 0) { }
+ IgnorableExceptionState(): ExceptionState(ExceptionState::UnknownContext, 0, 0, v8::Handle<v8::Object>(), 0) { }
ExceptionState& returnThis() { return *this; }
- virtual void throwDOMException(const ExceptionCode&, const String& message = String()) OVERRIDE FINAL { };
- virtual void throwTypeError(const String& message = String()) OVERRIDE FINAL { }
- virtual void throwSecurityError(const String& sanitizedMessage, const String& unsanitizedMessage = String()) OVERRIDE FINAL { }
+ virtual void throwDOMException(const ExceptionCode&, const String& message = String()) OVERRIDE { }
+ virtual void throwTypeError(const String& message = String()) OVERRIDE { }
+ virtual void throwSecurityError(const String& sanitizedMessage, const String& unsanitizedMessage = String()) OVERRIDE { }
};
#define IGNORE_EXCEPTION (::WebCore::IgnorableExceptionState().returnThis())
-#if ASSERT_DISABLED
+#if ASSERT_ENABLED
-#define ASSERT_NO_EXCEPTION (::WebCore::IgnorableExceptionState().returnThis())
-
-#else
-
-class NoExceptionStateAssertionChecker : public ExceptionState {
+class NoExceptionStateAssertionChecker FINAL : public ExceptionState {
public:
NoExceptionStateAssertionChecker(const char* file, int line);
ExceptionState& returnThis() { return *this; }
- virtual void throwDOMException(const ExceptionCode&, const String& message = String()) OVERRIDE FINAL;
- virtual void throwTypeError(const String& message = String()) OVERRIDE FINAL;
- virtual void throwSecurityError(const String& sanitizedMessage, const String& unsanitizedMessage = String()) OVERRIDE FINAL;
+ virtual void throwDOMException(const ExceptionCode&, const String& message = String()) OVERRIDE;
+ virtual void throwTypeError(const String& message = String()) OVERRIDE;
+ virtual void throwSecurityError(const String& sanitizedMessage, const String& unsanitizedMessage = String()) OVERRIDE;
private:
const char* m_file;
@@ -73,6 +70,10 @@ private:
#define ASSERT_NO_EXCEPTION (::WebCore::NoExceptionStateAssertionChecker(__FILE__, __LINE__).returnThis())
+#else
+
+#define ASSERT_NO_EXCEPTION (::WebCore::IgnorableExceptionState().returnThis())
+
#endif
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/IDBBindingUtilities.cpp b/chromium/third_party/WebKit/Source/bindings/v8/IDBBindingUtilities.cpp
index 1676649e556..bc50f3c7a8a 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/IDBBindingUtilities.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/IDBBindingUtilities.cpp
@@ -26,23 +26,25 @@
#include "config.h"
#include "bindings/v8/IDBBindingUtilities.h"
-#include "V8DOMStringList.h"
-#include "V8IDBCursor.h"
-#include "V8IDBCursorWithValue.h"
-#include "V8IDBDatabase.h"
-#include "V8IDBIndex.h"
-#include "V8IDBKeyRange.h"
-#include "V8IDBObjectStore.h"
-#include "V8IDBTransaction.h"
-#include "bindings/v8/DOMRequestState.h"
+#include "bindings/core/v8/V8DOMStringList.h"
+#include "bindings/modules/v8/V8IDBCursor.h"
+#include "bindings/modules/v8/V8IDBCursorWithValue.h"
+#include "bindings/modules/v8/V8IDBDatabase.h"
+#include "bindings/modules/v8/V8IDBIndex.h"
+#include "bindings/modules/v8/V8IDBKeyRange.h"
+#include "bindings/modules/v8/V8IDBObjectStore.h"
+#include "bindings/modules/v8/V8IDBRequest.h"
+#include "bindings/modules/v8/V8IDBTransaction.h"
#include "bindings/v8/SerializedScriptValue.h"
#include "bindings/v8/V8Binding.h"
+#include "bindings/v8/V8HiddenValue.h"
#include "bindings/v8/custom/V8ArrayBufferViewCustom.h"
#include "bindings/v8/custom/V8Uint8ArrayCustom.h"
#include "modules/indexeddb/IDBKey.h"
#include "modules/indexeddb/IDBKeyPath.h"
#include "modules/indexeddb/IDBKeyRange.h"
#include "modules/indexeddb/IDBTracing.h"
+#include "platform/RuntimeEnabledFeatures.h"
#include "platform/SharedBuffer.h"
#include "wtf/ArrayBufferView.h"
#include "wtf/MathExtras.h"
@@ -51,7 +53,7 @@
namespace WebCore {
-v8::Handle<v8::Value> deserializeIDBValueBuffer(SharedBuffer*, v8::Isolate*);
+static v8::Handle<v8::Value> deserializeIDBValueBuffer(v8::Isolate*, SharedBuffer*, const Vector<blink::WebBlobInfo>*);
static v8::Handle<v8::Value> toV8(const IDBKeyPath& value, v8::Handle<v8::Object> creationContext, v8::Isolate* isolate)
{
@@ -61,7 +63,7 @@ static v8::Handle<v8::Value> toV8(const IDBKeyPath& value, v8::Handle<v8::Object
case IDBKeyPath::StringType:
return v8String(isolate, value.string());
case IDBKeyPath::ArrayType:
- RefPtr<DOMStringList> keyPaths = DOMStringList::create();
+ RefPtrWillBeRawPtr<DOMStringList> keyPaths = DOMStringList::create();
for (Vector<String>::const_iterator it = value.array().begin(); it != value.array().end(); ++it)
keyPaths->append(*it);
return toV8(keyPaths.release(), creationContext, isolate);
@@ -70,7 +72,7 @@ static v8::Handle<v8::Value> toV8(const IDBKeyPath& value, v8::Handle<v8::Object
return v8::Undefined(isolate);
}
-v8::Handle<v8::Value> toV8(const IDBKey* key, v8::Handle<v8::Object> creationContext, v8::Isolate* isolate)
+static v8::Handle<v8::Value> toV8(const IDBKey* key, v8::Handle<v8::Object> creationContext, v8::Isolate* isolate)
{
if (!key) {
// This should be undefined, not null.
@@ -104,7 +106,7 @@ v8::Handle<v8::Value> toV8(const IDBKey* key, v8::Handle<v8::Object> creationCon
return v8Undefined();
}
-v8::Handle<v8::Value> toV8(const IDBAny* impl, v8::Handle<v8::Object> creationContext, v8::Isolate* isolate)
+static v8::Handle<v8::Value> toV8(const IDBAny* impl, v8::Handle<v8::Object> creationContext, v8::Isolate* isolate)
{
if (!impl)
return v8::Null(isolate);
@@ -116,10 +118,22 @@ v8::Handle<v8::Value> toV8(const IDBAny* impl, v8::Handle<v8::Object> creationCo
return v8::Null(isolate);
case IDBAny::DOMStringListType:
return toV8(impl->domStringList(), creationContext, isolate);
- case IDBAny::IDBCursorType:
- return toV8(impl->idbCursor(), creationContext, isolate);
- case IDBAny::IDBCursorWithValueType:
- return toV8(impl->idbCursorWithValue(), creationContext, isolate);
+ case IDBAny::IDBCursorType: {
+ // Ensure request wrapper is kept alive at least as long as the cursor wrapper,
+ // so that event listeners are retained.
+ v8::Handle<v8::Value> cursor = toV8(impl->idbCursor(), creationContext, isolate);
+ v8::Handle<v8::Value> request = toV8(impl->idbCursor()->request(), creationContext, isolate);
+ V8HiddenValue::setHiddenValue(isolate, cursor->ToObject(), V8HiddenValue::idbCursorRequest(isolate), request);
+ return cursor;
+ }
+ case IDBAny::IDBCursorWithValueType: {
+ // Ensure request wrapper is kept alive at least as long as the cursor wrapper,
+ // so that event listeners are retained.
+ v8::Handle<v8::Value> cursor = toV8(impl->idbCursorWithValue(), creationContext, isolate);
+ v8::Handle<v8::Value> request = toV8(impl->idbCursorWithValue()->request(), creationContext, isolate);
+ V8HiddenValue::setHiddenValue(isolate, cursor->ToObject(), V8HiddenValue::idbCursorRequest(isolate), request);
+ return cursor;
+ }
case IDBAny::IDBDatabaseType:
return toV8(impl->idbDatabase(), creationContext, isolate);
case IDBAny::IDBIndexType:
@@ -129,7 +143,7 @@ v8::Handle<v8::Value> toV8(const IDBAny* impl, v8::Handle<v8::Object> creationCo
case IDBAny::IDBTransactionType:
return toV8(impl->idbTransaction(), creationContext, isolate);
case IDBAny::BufferType:
- return deserializeIDBValueBuffer(impl->buffer(), isolate);
+ return deserializeIDBValueBuffer(isolate, impl->buffer(), impl->blobInfo());
case IDBAny::StringType:
return v8String(isolate, impl->string());
case IDBAny::IntegerType:
@@ -139,9 +153,9 @@ v8::Handle<v8::Value> toV8(const IDBAny* impl, v8::Handle<v8::Object> creationCo
case IDBAny::KeyPathType:
return toV8(impl->keyPath(), creationContext, isolate);
case IDBAny::BufferKeyAndKeyPathType: {
- v8::Handle<v8::Value> value = deserializeIDBValueBuffer(impl->buffer(), isolate);
+ v8::Handle<v8::Value> value = deserializeIDBValueBuffer(isolate, impl->buffer(), impl->blobInfo());
v8::Handle<v8::Value> key = toV8(impl->key(), creationContext, isolate);
- bool injected = injectV8KeyIntoV8Value(key, value, impl->keyPath(), isolate);
+ bool injected = injectV8KeyIntoV8Value(isolate, key, value, impl->keyPath());
ASSERT_UNUSED(injected, injected);
return value;
}
@@ -153,7 +167,7 @@ v8::Handle<v8::Value> toV8(const IDBAny* impl, v8::Handle<v8::Object> creationCo
static const size_t maximumDepth = 2000;
-static PassRefPtr<IDBKey> createIDBKeyFromValue(v8::Handle<v8::Value> value, Vector<v8::Handle<v8::Array> >& stack, v8::Isolate* isolate)
+static IDBKey* createIDBKeyFromValue(v8::Isolate* isolate, v8::Handle<v8::Value> value, Vector<v8::Handle<v8::Array> >& stack, bool allowExperimentalTypes = false)
{
if (value->IsNumber() && !std::isnan(value->NumberValue()))
return IDBKey::createNumber(value->NumberValue());
@@ -161,6 +175,14 @@ static PassRefPtr<IDBKey> createIDBKeyFromValue(v8::Handle<v8::Value> value, Vec
return IDBKey::createString(toCoreString(value.As<v8::String>()));
if (value->IsDate() && !std::isnan(value->NumberValue()))
return IDBKey::createDate(value->NumberValue());
+ if (value->IsUint8Array() && (allowExperimentalTypes || RuntimeEnabledFeatures::indexedDBExperimentalEnabled())) {
+ // Per discussion in https://www.w3.org/Bugs/Public/show_bug.cgi?id=23332 the
+ // input type is constrained to Uint8Array to match the output type.
+ ArrayBufferView* view = WebCore::V8ArrayBufferView::toNative(value->ToObject());
+ const char* start = static_cast<const char*>(view->baseAddress());
+ size_t length = view->byteLength();
+ return IDBKey::createBinary(SharedBuffer::create(start, length));
+ }
if (value->IsArray()) {
v8::Handle<v8::Array> array = v8::Handle<v8::Array>::Cast(value);
@@ -173,8 +195,8 @@ static PassRefPtr<IDBKey> createIDBKeyFromValue(v8::Handle<v8::Value> value, Vec
IDBKey::KeyArray subkeys;
uint32_t length = array->Length();
for (uint32_t i = 0; i < length; ++i) {
- v8::Local<v8::Value> item = array->Get(v8::Int32::New(i, isolate));
- RefPtr<IDBKey> subkey = createIDBKeyFromValue(item, stack, isolate);
+ v8::Local<v8::Value> item = array->Get(v8::Int32::New(isolate, i));
+ IDBKey* subkey = createIDBKeyFromValue(isolate, item, stack, allowExperimentalTypes);
if (!subkey)
subkeys.append(IDBKey::createInvalid());
else
@@ -187,11 +209,10 @@ static PassRefPtr<IDBKey> createIDBKeyFromValue(v8::Handle<v8::Value> value, Vec
return 0;
}
-static PassRefPtr<IDBKey> createIDBKeyFromValue(v8::Handle<v8::Value> value, v8::Isolate* isolate)
+static IDBKey* createIDBKeyFromValue(v8::Isolate* isolate, v8::Handle<v8::Value> value, bool allowExperimentalTypes = false)
{
Vector<v8::Handle<v8::Array> > stack;
- RefPtr<IDBKey> key = createIDBKeyFromValue(value, stack, isolate);
- if (key)
+ if (IDBKey* key = createIDBKeyFromValue(isolate, value, stack, allowExperimentalTypes))
return key;
return IDBKey::createInvalid();
}
@@ -213,7 +234,7 @@ static bool setValue(v8::Handle<v8::Value>& v8Object, T indexOrName, const v8::H
return object->Set(indexOrName, v8Value);
}
-static bool get(v8::Handle<v8::Value>& object, const String& keyPathElement, v8::Handle<v8::Value>& result, v8::Isolate* isolate)
+static bool get(v8::Isolate* isolate, v8::Handle<v8::Value>& object, const String& keyPathElement, v8::Handle<v8::Value>& result)
{
if (object->IsString() && keyPathElement == "length") {
int32_t length = v8::Handle<v8::String>::Cast(object)->Length();
@@ -228,25 +249,25 @@ static bool canSet(v8::Handle<v8::Value>& object, const String& keyPathElement)
return object->IsObject();
}
-static bool set(v8::Handle<v8::Value>& object, const String& keyPathElement, const v8::Handle<v8::Value>& v8Value, v8::Isolate* isolate)
+static bool set(v8::Isolate* isolate, v8::Handle<v8::Value>& object, const String& keyPathElement, const v8::Handle<v8::Value>& v8Value)
{
return canSet(object, keyPathElement) && setValue(object, v8String(isolate, keyPathElement), v8Value);
}
-static v8::Handle<v8::Value> getNthValueOnKeyPath(v8::Handle<v8::Value>& rootValue, const Vector<String>& keyPathElements, size_t index, v8::Isolate* isolate)
+static v8::Handle<v8::Value> getNthValueOnKeyPath(v8::Isolate* isolate, v8::Handle<v8::Value>& rootValue, const Vector<String>& keyPathElements, size_t index)
{
v8::Handle<v8::Value> currentValue(rootValue);
ASSERT(index <= keyPathElements.size());
for (size_t i = 0; i < index; ++i) {
v8::Handle<v8::Value> parentValue(currentValue);
- if (!get(parentValue, keyPathElements[i], currentValue, isolate))
+ if (!get(isolate, parentValue, keyPathElements[i], currentValue))
return v8Undefined();
}
return currentValue;
}
-static bool canInjectNthValueOnKeyPath(v8::Handle<v8::Value>& rootValue, const Vector<String>& keyPathElements, size_t index, v8::Isolate* isolate)
+static bool canInjectNthValueOnKeyPath(v8::Isolate* isolate, v8::Handle<v8::Value>& rootValue, const Vector<String>& keyPathElements, size_t index)
{
if (!rootValue->IsObject())
return false;
@@ -257,14 +278,14 @@ static bool canInjectNthValueOnKeyPath(v8::Handle<v8::Value>& rootValue, const V
for (size_t i = 0; i < index; ++i) {
v8::Handle<v8::Value> parentValue(currentValue);
const String& keyPathElement = keyPathElements[i];
- if (!get(parentValue, keyPathElement, currentValue, isolate))
+ if (!get(isolate, parentValue, keyPathElement, currentValue))
return canSet(parentValue, keyPathElement);
}
return true;
}
-static v8::Handle<v8::Value> ensureNthValueOnKeyPath(v8::Handle<v8::Value>& rootValue, const Vector<String>& keyPathElements, size_t index, v8::Isolate* isolate)
+static v8::Handle<v8::Value> ensureNthValueOnKeyPath(v8::Isolate* isolate, v8::Handle<v8::Value>& rootValue, const Vector<String>& keyPathElements, size_t index)
{
v8::Handle<v8::Value> currentValue(rootValue);
@@ -272,9 +293,9 @@ static v8::Handle<v8::Value> ensureNthValueOnKeyPath(v8::Handle<v8::Value>& root
for (size_t i = 0; i < index; ++i) {
v8::Handle<v8::Value> parentValue(currentValue);
const String& keyPathElement = keyPathElements[i];
- if (!get(parentValue, keyPathElement, currentValue, isolate)) {
- v8::Handle<v8::Object> object = v8::Object::New();
- if (!set(parentValue, keyPathElement, object, isolate))
+ if (!get(isolate, parentValue, keyPathElement, currentValue)) {
+ v8::Handle<v8::Object> object = v8::Object::New(isolate);
+ if (!set(isolate, parentValue, keyPathElement, object))
return v8Undefined();
currentValue = object;
}
@@ -283,7 +304,7 @@ static v8::Handle<v8::Value> ensureNthValueOnKeyPath(v8::Handle<v8::Value>& root
return currentValue;
}
-static PassRefPtr<IDBKey> createIDBKeyFromScriptValueAndKeyPath(const ScriptValue& value, const String& keyPath, v8::Isolate* isolate)
+static IDBKey* createIDBKeyFromScriptValueAndKeyPathInternal(v8::Isolate* isolate, const ScriptValue& value, const String& keyPath, bool allowExperimentalTypes)
{
Vector<String> keyPathElements;
IDBKeyPathParseError error;
@@ -293,24 +314,21 @@ static PassRefPtr<IDBKey> createIDBKeyFromScriptValueAndKeyPath(const ScriptValu
v8::HandleScope handleScope(isolate);
v8::Handle<v8::Value> v8Value(value.v8Value());
- v8::Handle<v8::Value> v8Key(getNthValueOnKeyPath(v8Value, keyPathElements, keyPathElements.size(), isolate));
+ v8::Handle<v8::Value> v8Key(getNthValueOnKeyPath(isolate, v8Value, keyPathElements, keyPathElements.size()));
if (v8Key.IsEmpty())
return 0;
- return createIDBKeyFromValue(v8Key, isolate);
+ return createIDBKeyFromValue(isolate, v8Key, allowExperimentalTypes);
}
-PassRefPtr<IDBKey> createIDBKeyFromScriptValueAndKeyPath(DOMRequestState* state, const ScriptValue& value, const IDBKeyPath& keyPath)
+static IDBKey* createIDBKeyFromScriptValueAndKeyPathInternal(v8::Isolate* isolate, const ScriptValue& value, const IDBKeyPath& keyPath, bool allowExperimentalTypes = false)
{
- IDB_TRACE("createIDBKeyFromScriptValueAndKeyPath");
ASSERT(!keyPath.isNull());
- v8::Isolate* isolate = state ? state->context()->GetIsolate() : v8::Isolate::GetCurrent();
- ASSERT(isolate->InContext());
v8::HandleScope handleScope(isolate);
if (keyPath.type() == IDBKeyPath::ArrayType) {
IDBKey::KeyArray result;
const Vector<String>& array = keyPath.array();
for (size_t i = 0; i < array.size(); ++i) {
- RefPtr<IDBKey> key = createIDBKeyFromScriptValueAndKeyPath(value, array[i], isolate);
+ IDBKey* key = createIDBKeyFromScriptValueAndKeyPathInternal(isolate, value, array[i], allowExperimentalTypes);
if (!key)
return 0;
result.append(key);
@@ -319,10 +337,16 @@ PassRefPtr<IDBKey> createIDBKeyFromScriptValueAndKeyPath(DOMRequestState* state,
}
ASSERT(keyPath.type() == IDBKeyPath::StringType);
- return createIDBKeyFromScriptValueAndKeyPath(value, keyPath.string(), isolate);
+ return createIDBKeyFromScriptValueAndKeyPathInternal(isolate, value, keyPath.string(), allowExperimentalTypes);
+}
+
+IDBKey* createIDBKeyFromScriptValueAndKeyPath(v8::Isolate* isolate, const ScriptValue& value, const IDBKeyPath& keyPath)
+{
+ IDB_TRACE("createIDBKeyFromScriptValueAndKeyPath");
+ return createIDBKeyFromScriptValueAndKeyPathInternal(isolate, value, keyPath);
}
-v8::Handle<v8::Value> deserializeIDBValueBuffer(SharedBuffer* buffer, v8::Isolate* isolate)
+static v8::Handle<v8::Value> deserializeIDBValueBuffer(v8::Isolate* isolate, SharedBuffer* buffer, const Vector<blink::WebBlobInfo>* blobInfo)
{
ASSERT(isolate->InContext());
if (!buffer)
@@ -332,10 +356,10 @@ v8::Handle<v8::Value> deserializeIDBValueBuffer(SharedBuffer* buffer, v8::Isolat
Vector<uint8_t> value;
value.append(buffer->data(), buffer->size());
RefPtr<SerializedScriptValue> serializedValue = SerializedScriptValue::createFromWireBytes(value);
- return serializedValue->deserialize(isolate);
+ return serializedValue->deserialize(isolate, 0, blobInfo);
}
-bool injectV8KeyIntoV8Value(v8::Handle<v8::Value> key, v8::Handle<v8::Value> value, const IDBKeyPath& keyPath, v8::Isolate* isolate)
+bool injectV8KeyIntoV8Value(v8::Isolate* isolate, v8::Handle<v8::Value> key, v8::Handle<v8::Value> value, const IDBKeyPath& keyPath)
{
IDB_TRACE("injectIDBV8KeyIntoV8Value");
ASSERT(isolate->InContext());
@@ -350,17 +374,17 @@ bool injectV8KeyIntoV8Value(v8::Handle<v8::Value> key, v8::Handle<v8::Value> val
return false;
v8::HandleScope handleScope(isolate);
- v8::Handle<v8::Value> parent(ensureNthValueOnKeyPath(value, keyPathElements, keyPathElements.size() - 1, isolate));
+ v8::Handle<v8::Value> parent(ensureNthValueOnKeyPath(isolate, value, keyPathElements, keyPathElements.size() - 1));
if (parent.IsEmpty())
return false;
- if (!set(parent, keyPathElements.last(), key, isolate))
+ if (!set(isolate, parent, keyPathElements.last(), key))
return false;
return true;
}
-bool canInjectIDBKeyIntoScriptValue(DOMRequestState* state, const ScriptValue& scriptValue, const IDBKeyPath& keyPath)
+bool canInjectIDBKeyIntoScriptValue(v8::Isolate* isolate, const ScriptValue& scriptValue, const IDBKeyPath& keyPath)
{
IDB_TRACE("canInjectIDBKeyIntoScriptValue");
ASSERT(keyPath.type() == IDBKeyPath::StringType);
@@ -373,63 +397,54 @@ bool canInjectIDBKeyIntoScriptValue(DOMRequestState* state, const ScriptValue& s
return false;
v8::Handle<v8::Value> v8Value(scriptValue.v8Value());
- return canInjectNthValueOnKeyPath(v8Value, keyPathElements, keyPathElements.size() - 1, state->context()->GetIsolate());
+ return canInjectNthValueOnKeyPath(isolate, v8Value, keyPathElements, keyPathElements.size() - 1);
}
-ScriptValue idbAnyToScriptValue(DOMRequestState* state, PassRefPtr<IDBAny> any)
+ScriptValue idbAnyToScriptValue(ScriptState* scriptState, IDBAny* any)
{
- v8::Isolate* isolate = state ? state->context()->GetIsolate() : v8::Isolate::GetCurrent();
- ASSERT(isolate->InContext());
- v8::Local<v8::Context> context = state ? state->context() : isolate->GetCurrentContext();
+ v8::Isolate* isolate = scriptState->isolate();
v8::HandleScope handleScope(isolate);
- v8::Handle<v8::Value> v8Value(toV8(any.get(), context->Global(), isolate));
- return ScriptValue(v8Value, isolate);
+ v8::Handle<v8::Value> v8Value(toV8(any, scriptState->context()->Global(), isolate));
+ return ScriptValue(scriptState, v8Value);
}
-ScriptValue idbKeyToScriptValue(DOMRequestState* state, PassRefPtr<IDBKey> key)
+ScriptValue idbKeyToScriptValue(ScriptState* scriptState, IDBKey* key)
{
- v8::Isolate* isolate = state ? state->context()->GetIsolate() : v8::Isolate::GetCurrent();
- ASSERT(isolate->InContext());
- v8::Local<v8::Context> context = state ? state->context() : isolate->GetCurrentContext();
+ v8::Isolate* isolate = scriptState->isolate();
v8::HandleScope handleScope(isolate);
- v8::Handle<v8::Value> v8Value(toV8(key.get(), context->Global(), isolate));
- return ScriptValue(v8Value, isolate);
+ v8::Handle<v8::Value> v8Value(toV8(key, scriptState->context()->Global(), isolate));
+ return ScriptValue(scriptState, v8Value);
}
-PassRefPtr<IDBKey> scriptValueToIDBKey(DOMRequestState* state, const ScriptValue& scriptValue)
+IDBKey* scriptValueToIDBKey(v8::Isolate* isolate, const ScriptValue& scriptValue)
{
- v8::Isolate* isolate = state ? state->context()->GetIsolate() : v8::Isolate::GetCurrent();
ASSERT(isolate->InContext());
v8::HandleScope handleScope(isolate);
v8::Handle<v8::Value> v8Value(scriptValue.v8Value());
- return createIDBKeyFromValue(v8Value, isolate);
+ return createIDBKeyFromValue(isolate, v8Value);
}
-PassRefPtr<IDBKeyRange> scriptValueToIDBKeyRange(DOMRequestState* state, const ScriptValue& scriptValue)
+IDBKeyRange* scriptValueToIDBKeyRange(v8::Isolate* isolate, const ScriptValue& scriptValue)
{
- v8::Isolate* isolate = state ? state->context()->GetIsolate() : v8::Isolate::GetCurrent();
v8::HandleScope handleScope(isolate);
v8::Handle<v8::Value> value(scriptValue.v8Value());
- if (V8IDBKeyRange::hasInstance(value, isolate, worldType(isolate)))
- return V8IDBKeyRange::toNative(value.As<v8::Object>());
- return 0;
+ return V8IDBKeyRange::toNativeWithTypeCheck(isolate, value);
}
#ifndef NDEBUG
-void assertPrimaryKeyValidOrInjectable(DOMRequestState* state, PassRefPtr<SharedBuffer> buffer, PassRefPtr<IDBKey> prpKey, const IDBKeyPath& keyPath)
+void assertPrimaryKeyValidOrInjectable(ScriptState* scriptState, PassRefPtr<SharedBuffer> buffer, const Vector<blink::WebBlobInfo>* blobInfo, IDBKey* key, const IDBKeyPath& keyPath)
{
- RefPtr<IDBKey> key(prpKey);
-
- DOMRequestState::Scope scope(*state);
- v8::Isolate* isolate = state ? state->context()->GetIsolate() : v8::Isolate::GetCurrent();
-
- ScriptValue keyValue = idbKeyToScriptValue(state, key);
- ScriptValue scriptValue(deserializeIDBValueBuffer(buffer.get(), isolate), isolate);
+ ScriptState::Scope scope(scriptState);
+ v8::Isolate* isolate = scriptState->isolate();
+ ScriptValue keyValue = idbKeyToScriptValue(scriptState, key);
+ ScriptValue scriptValue(scriptState, deserializeIDBValueBuffer(isolate, buffer.get(), blobInfo));
- RefPtr<IDBKey> expectedKey = createIDBKeyFromScriptValueAndKeyPath(state, scriptValue, keyPath);
- ASSERT(!expectedKey || expectedKey->isEqual(key.get()));
+ // This assertion is about already persisted data, so allow experimental types.
+ const bool allowExperimentalTypes = true;
+ IDBKey* expectedKey = createIDBKeyFromScriptValueAndKeyPathInternal(isolate, scriptValue, keyPath, allowExperimentalTypes);
+ ASSERT(!expectedKey || expectedKey->isEqual(key));
- bool injected = injectV8KeyIntoV8Value(keyValue.v8Value(), scriptValue.v8Value(), keyPath, isolate);
+ bool injected = injectV8KeyIntoV8Value(isolate, keyValue.v8Value(), scriptValue.v8Value(), keyPath);
ASSERT_UNUSED(injected, injected);
}
#endif
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/IDBBindingUtilities.h b/chromium/third_party/WebKit/Source/bindings/v8/IDBBindingUtilities.h
index b36c71cb03d..fba64423937 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/IDBBindingUtilities.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/IDBBindingUtilities.h
@@ -26,13 +26,19 @@
#ifndef IDBBindingUtilities_h
#define IDBBindingUtilities_h
+#include "bindings/v8/ScriptState.h"
#include "bindings/v8/ScriptValue.h"
#include <v8.h>
#include "wtf/Forward.h"
+namespace blink {
+
+class WebBlobInfo;
+
+}
+
namespace WebCore {
-class DOMRequestState;
class IDBAny;
class IDBKey;
class IDBKeyPath;
@@ -41,18 +47,18 @@ class SerializedScriptValue;
class SharedBuffer;
// Exposed for unit testing:
-bool injectV8KeyIntoV8Value(v8::Handle<v8::Value> key, v8::Handle<v8::Value>, const IDBKeyPath&, v8::Isolate*);
+bool injectV8KeyIntoV8Value(v8::Isolate*, v8::Handle<v8::Value> key, v8::Handle<v8::Value>, const IDBKeyPath&);
// For use by Source/modules/indexeddb:
-PassRefPtr<IDBKey> createIDBKeyFromScriptValueAndKeyPath(DOMRequestState*, const ScriptValue&, const IDBKeyPath&);
-bool canInjectIDBKeyIntoScriptValue(DOMRequestState*, const ScriptValue&, const IDBKeyPath&);
-ScriptValue idbAnyToScriptValue(DOMRequestState*, PassRefPtr<IDBAny>);
-ScriptValue idbKeyToScriptValue(DOMRequestState*, PassRefPtr<IDBKey>);
-PassRefPtr<IDBKey> scriptValueToIDBKey(DOMRequestState*, const ScriptValue&);
-PassRefPtr<IDBKeyRange> scriptValueToIDBKeyRange(DOMRequestState*, const ScriptValue&);
+IDBKey* createIDBKeyFromScriptValueAndKeyPath(v8::Isolate*, const ScriptValue&, const IDBKeyPath&);
+bool canInjectIDBKeyIntoScriptValue(v8::Isolate*, const ScriptValue&, const IDBKeyPath&);
+ScriptValue idbAnyToScriptValue(ScriptState*, IDBAny*);
+ScriptValue idbKeyToScriptValue(ScriptState*, IDBKey*);
+IDBKey* scriptValueToIDBKey(v8::Isolate*, const ScriptValue&);
+IDBKeyRange* scriptValueToIDBKeyRange(v8::Isolate*, const ScriptValue&);
#ifndef NDEBUG
-void assertPrimaryKeyValidOrInjectable(DOMRequestState*, PassRefPtr<SharedBuffer>, PassRefPtr<IDBKey>, const IDBKeyPath&);
+void assertPrimaryKeyValidOrInjectable(ScriptState*, PassRefPtr<SharedBuffer>, const Vector<blink::WebBlobInfo>*, IDBKey*, const IDBKeyPath&);
#endif
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/IDBBindingUtilitiesTest.cpp b/chromium/third_party/WebKit/Source/bindings/v8/IDBBindingUtilitiesTest.cpp
index 0f6ff63ee32..b984d04ceeb 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/IDBBindingUtilitiesTest.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/IDBBindingUtilitiesTest.cpp
@@ -28,64 +28,60 @@
#include "bindings/v8/V8Binding.h"
#include "bindings/v8/V8PerIsolateData.h"
-#include "bindings/v8/V8Utilities.h"
#include "modules/indexeddb/IDBKey.h"
#include "modules/indexeddb/IDBKeyPath.h"
-
#include <gtest/gtest.h>
using namespace WebCore;
namespace {
-PassRefPtr<IDBKey> checkKeyFromValueAndKeyPathInternal(const ScriptValue& value, const String& keyPath)
+IDBKey* checkKeyFromValueAndKeyPathInternal(v8::Isolate* isolate, const ScriptValue& value, const String& keyPath)
{
IDBKeyPath idbKeyPath(keyPath);
EXPECT_TRUE(idbKeyPath.isValid());
- return createIDBKeyFromScriptValueAndKeyPath(0, value, idbKeyPath);
+ return createIDBKeyFromScriptValueAndKeyPath(isolate, value, idbKeyPath);
}
-void checkKeyPathNullValue(const ScriptValue& value, const String& keyPath)
+void checkKeyPathNullValue(v8::Isolate* isolate, const ScriptValue& value, const String& keyPath)
{
- RefPtr<IDBKey> idbKey = checkKeyFromValueAndKeyPathInternal(value, keyPath);
- ASSERT_FALSE(idbKey.get());
+ ASSERT_FALSE(checkKeyFromValueAndKeyPathInternal(isolate, value, keyPath));
}
-bool injectKey(PassRefPtr<IDBKey> key, ScriptValue& value, const String& keyPath)
+bool injectKey(ScriptState* scriptState, IDBKey* key, ScriptValue& value, const String& keyPath)
{
IDBKeyPath idbKeyPath(keyPath);
EXPECT_TRUE(idbKeyPath.isValid());
- ScriptValue keyValue = idbKeyToScriptValue(0, key);
- return injectV8KeyIntoV8Value(keyValue.v8Value(), value.v8Value(), idbKeyPath, v8::Isolate::GetCurrent());
+ ScriptValue keyValue = idbKeyToScriptValue(scriptState, key);
+ return injectV8KeyIntoV8Value(scriptState->isolate(), keyValue.v8Value(), value.v8Value(), idbKeyPath);
}
-void checkInjection(PassRefPtr<IDBKey> prpKey, ScriptValue& value, const String& keyPath)
+void checkInjection(ScriptState* scriptState, IDBKey* key, ScriptValue& value, const String& keyPath)
{
- RefPtr<IDBKey> key = prpKey;
- bool result = injectKey(key, value, keyPath);
+ bool result = injectKey(scriptState, key, value, keyPath);
ASSERT_TRUE(result);
- RefPtr<IDBKey> extractedKey = checkKeyFromValueAndKeyPathInternal(value, keyPath);
- EXPECT_TRUE(key->isEqual(extractedKey.get()));
+ IDBKey* extractedKey = checkKeyFromValueAndKeyPathInternal(scriptState->isolate(), value, keyPath);
+ EXPECT_TRUE(key->isEqual(extractedKey));
}
-void checkInjectionFails(PassRefPtr<IDBKey> key, ScriptValue& value, const String& keyPath)
+void checkInjectionFails(ScriptState* scriptState, IDBKey* key, ScriptValue& value, const String& keyPath)
{
- EXPECT_FALSE(injectKey(key, value, keyPath));
+ EXPECT_FALSE(injectKey(scriptState, key, value, keyPath));
}
-void checkKeyPathStringValue(const ScriptValue& value, const String& keyPath, const String& expected)
+void checkKeyPathStringValue(v8::Isolate* isolate, const ScriptValue& value, const String& keyPath, const String& expected)
{
- RefPtr<IDBKey> idbKey = checkKeyFromValueAndKeyPathInternal(value, keyPath);
- ASSERT_TRUE(idbKey.get());
+ IDBKey* idbKey = checkKeyFromValueAndKeyPathInternal(isolate, value, keyPath);
+ ASSERT_TRUE(idbKey);
ASSERT_EQ(IDBKey::StringType, idbKey->type());
ASSERT_TRUE(expected == idbKey->string());
}
-void checkKeyPathNumberValue(const ScriptValue& value, const String& keyPath, int expected)
+void checkKeyPathNumberValue(v8::Isolate* isolate, const ScriptValue& value, const String& keyPath, int expected)
{
- RefPtr<IDBKey> idbKey = checkKeyFromValueAndKeyPathInternal(value, keyPath);
- ASSERT_TRUE(idbKey.get());
+ IDBKey* idbKey = checkKeyFromValueAndKeyPathInternal(isolate, value, keyPath);
+ ASSERT_TRUE(idbKey);
ASSERT_EQ(IDBKey::NumberType, idbKey->type());
ASSERT_TRUE(expected == idbKey->number());
}
@@ -93,49 +89,52 @@ void checkKeyPathNumberValue(const ScriptValue& value, const String& keyPath, in
class IDBKeyFromValueAndKeyPathTest : public testing::Test {
public:
IDBKeyFromValueAndKeyPathTest()
- : m_handleScope(v8::Isolate::GetCurrent())
- , m_scope(v8::Context::New(v8::Isolate::GetCurrent()))
+ : m_scope(v8::Isolate::GetCurrent())
{
}
+ ScriptState* scriptState() const { return m_scope.scriptState(); }
+
private:
- v8::HandleScope m_handleScope;
- v8::Context::Scope m_scope;
+ V8TestingScope m_scope;
};
TEST_F(IDBKeyFromValueAndKeyPathTest, TopLevelPropertyStringValue)
{
- v8::Local<v8::Object> object = v8::Object::New();
- object->Set(v8::String::NewFromUtf8(v8::Isolate::GetCurrent(), "foo"), v8::String::NewFromUtf8(v8::Isolate::GetCurrent(), "zoo"));
+ v8::Isolate* isolate = v8::Isolate::GetCurrent();
+ v8::Local<v8::Object> object = v8::Object::New(isolate);
+ object->Set(v8AtomicString(isolate, "foo"), v8AtomicString(isolate, "zoo"));
- ScriptValue scriptValue(object, v8::Isolate::GetCurrent());
+ ScriptValue scriptValue(scriptState(), object);
- checkKeyPathStringValue(scriptValue, "foo", "zoo");
- checkKeyPathNullValue(scriptValue, "bar");
+ checkKeyPathStringValue(isolate, scriptValue, "foo", "zoo");
+ checkKeyPathNullValue(isolate, scriptValue, "bar");
}
TEST_F(IDBKeyFromValueAndKeyPathTest, TopLevelPropertyNumberValue)
{
- v8::Local<v8::Object> object = v8::Object::New();
- object->Set(v8::String::NewFromUtf8(v8::Isolate::GetCurrent(), "foo"), v8::Number::New(456));
+ v8::Isolate* isolate = v8::Isolate::GetCurrent();
+ v8::Local<v8::Object> object = v8::Object::New(isolate);
+ object->Set(v8AtomicString(isolate, "foo"), v8::Number::New(isolate, 456));
- ScriptValue scriptValue(object, v8::Isolate::GetCurrent());
+ ScriptValue scriptValue(scriptState(), object);
- checkKeyPathNumberValue(scriptValue, "foo", 456);
- checkKeyPathNullValue(scriptValue, "bar");
+ checkKeyPathNumberValue(isolate, scriptValue, "foo", 456);
+ checkKeyPathNullValue(isolate, scriptValue, "bar");
}
TEST_F(IDBKeyFromValueAndKeyPathTest, SubProperty)
{
- v8::Local<v8::Object> object = v8::Object::New();
- v8::Local<v8::Object> subProperty = v8::Object::New();
- subProperty->Set(v8::String::NewFromUtf8(v8::Isolate::GetCurrent(), "bar"), v8::String::NewFromUtf8(v8::Isolate::GetCurrent(), "zee"));
- object->Set(v8::String::NewFromUtf8(v8::Isolate::GetCurrent(), "foo"), subProperty);
+ v8::Isolate* isolate = v8::Isolate::GetCurrent();
+ v8::Local<v8::Object> object = v8::Object::New(isolate);
+ v8::Local<v8::Object> subProperty = v8::Object::New(isolate);
+ subProperty->Set(v8AtomicString(isolate, "bar"), v8AtomicString(isolate, "zee"));
+ object->Set(v8AtomicString(isolate, "foo"), subProperty);
- ScriptValue scriptValue(object, v8::Isolate::GetCurrent());
+ ScriptValue scriptValue(scriptState(), object);
- checkKeyPathStringValue(scriptValue, "foo.bar", "zee");
- checkKeyPathNullValue(scriptValue, "bar");
+ checkKeyPathStringValue(isolate, scriptValue, "foo.bar", "zee");
+ checkKeyPathNullValue(isolate, scriptValue, "bar");
}
class InjectIDBKeyTest : public IDBKeyFromValueAndKeyPathTest {
@@ -143,33 +142,35 @@ class InjectIDBKeyTest : public IDBKeyFromValueAndKeyPathTest {
TEST_F(InjectIDBKeyTest, TopLevelPropertyStringValue)
{
- v8::Local<v8::Object> object = v8::Object::New();
- object->Set(v8::String::NewFromUtf8(v8::Isolate::GetCurrent(), "foo"), v8::String::NewFromUtf8(v8::Isolate::GetCurrent(), "zoo"));
+ v8::Isolate* isolate = v8::Isolate::GetCurrent();
+ v8::Local<v8::Object> object = v8::Object::New(isolate);
+ object->Set(v8AtomicString(isolate, "foo"), v8AtomicString(isolate, "zoo"));
- ScriptValue foozoo(object, v8::Isolate::GetCurrent());
- checkInjection(IDBKey::createString("myNewKey"), foozoo, "bar");
- checkInjection(IDBKey::createNumber(1234), foozoo, "bar");
+ ScriptValue foozoo(scriptState(), object);
+ checkInjection(scriptState(), IDBKey::createString("myNewKey"), foozoo, "bar");
+ checkInjection(scriptState(), IDBKey::createNumber(1234), foozoo, "bar");
- checkInjectionFails(IDBKey::createString("key"), foozoo, "foo.bar");
+ checkInjectionFails(scriptState(), IDBKey::createString("key"), foozoo, "foo.bar");
}
TEST_F(InjectIDBKeyTest, SubProperty)
{
- v8::Local<v8::Object> object = v8::Object::New();
- v8::Local<v8::Object> subProperty = v8::Object::New();
- subProperty->Set(v8::String::NewFromUtf8(v8::Isolate::GetCurrent(), "bar"), v8::String::NewFromUtf8(v8::Isolate::GetCurrent(), "zee"));
- object->Set(v8::String::NewFromUtf8(v8::Isolate::GetCurrent(), "foo"), subProperty);
-
- ScriptValue scriptObject(object, v8::Isolate::GetCurrent());
- checkInjection(IDBKey::createString("myNewKey"), scriptObject, "foo.baz");
- checkInjection(IDBKey::createNumber(789), scriptObject, "foo.baz");
- checkInjection(IDBKey::createDate(4567), scriptObject, "foo.baz");
- checkInjection(IDBKey::createDate(4567), scriptObject, "bar");
- checkInjection(IDBKey::createArray(IDBKey::KeyArray()), scriptObject, "foo.baz");
- checkInjection(IDBKey::createArray(IDBKey::KeyArray()), scriptObject, "bar");
-
- checkInjectionFails(IDBKey::createString("zoo"), scriptObject, "foo.bar.baz");
- checkInjection(IDBKey::createString("zoo"), scriptObject, "foo.xyz.foo");
+ v8::Isolate* isolate = v8::Isolate::GetCurrent();
+ v8::Local<v8::Object> object = v8::Object::New(isolate);
+ v8::Local<v8::Object> subProperty = v8::Object::New(isolate);
+ subProperty->Set(v8AtomicString(isolate, "bar"), v8AtomicString(isolate, "zee"));
+ object->Set(v8AtomicString(isolate, "foo"), subProperty);
+
+ ScriptValue scriptObject(scriptState(), object);
+ checkInjection(scriptState(), IDBKey::createString("myNewKey"), scriptObject, "foo.baz");
+ checkInjection(scriptState(), IDBKey::createNumber(789), scriptObject, "foo.baz");
+ checkInjection(scriptState(), IDBKey::createDate(4567), scriptObject, "foo.baz");
+ checkInjection(scriptState(), IDBKey::createDate(4567), scriptObject, "bar");
+ checkInjection(scriptState(), IDBKey::createArray(IDBKey::KeyArray()), scriptObject, "foo.baz");
+ checkInjection(scriptState(), IDBKey::createArray(IDBKey::KeyArray()), scriptObject, "bar");
+
+ checkInjectionFails(scriptState(), IDBKey::createString("zoo"), scriptObject, "foo.bar.baz");
+ checkInjection(scriptState(), IDBKey::createString("zoo"), scriptObject, "foo.xyz.foo");
}
} // namespace
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/NPV8Object.cpp b/chromium/third_party/WebKit/Source/bindings/v8/NPV8Object.cpp
index e094bf92563..11f34a44d97 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/NPV8Object.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/NPV8Object.cpp
@@ -38,8 +38,8 @@
#include "bindings/v8/WrapperTypeInfo.h"
#include "bindings/v8/npruntime_impl.h"
#include "bindings/v8/npruntime_priv.h"
-#include "core/frame/DOMWindow.h"
-#include "core/frame/Frame.h"
+#include "core/frame/LocalDOMWindow.h"
+#include "core/frame/LocalFrame.h"
#include "platform/UserGestureIndicator.h"
#include "wtf/OwnPtr.h"
@@ -53,7 +53,7 @@ namespace WebCore {
const WrapperTypeInfo* npObjectTypeInfo()
{
- static const WrapperTypeInfo typeInfo = { gin::kEmbedderBlink, 0, 0, 0, 0, 0, 0, 0, WrapperTypeObjectPrototype };
+ static const WrapperTypeInfo typeInfo = { gin::kEmbedderBlink, 0, 0, 0, 0, 0, 0, 0, WrapperTypeObjectPrototype, RefCountedObject };
return &typeInfo;
}
@@ -77,14 +77,16 @@ static NPClass V8NPObjectClass = {
0, 0, 0, 0, 0, 0, 0, 0, 0, 0
};
-static v8::Local<v8::Context> toV8Context(NPP npp, NPObject* npObject)
+static ScriptState* mainWorldScriptState(v8::Isolate* isolate, NPP npp, NPObject* npObject)
{
ASSERT(npObject->_class == &V8NPObjectClass);
V8NPObject* object = reinterpret_cast<V8NPObject*>(npObject);
- DOMWindow* window = object->rootObject;
+ LocalDOMWindow* window = object->rootObject;
if (!window || !window->isCurrentlyDisplayedInFrame())
- return v8::Local<v8::Context>();
- return ScriptController::mainWorldContext(object->rootObject->frame());
+ return 0;
+ v8::HandleScope handleScope(isolate);
+ v8::Handle<v8::Context> context = toV8Context(object->rootObject->frame(), DOMWrapperWorld::mainWorld());
+ return ScriptState::from(context);
}
static PassOwnPtr<v8::Handle<v8::Value>[]> createValueListFromVariantArgs(const NPVariant* arguments, uint32_t argumentCount, NPObject* owner, v8::Isolate* isolate)
@@ -114,7 +116,7 @@ NPObject* v8ObjectToNPObject(v8::Handle<v8::Object> object)
return reinterpret_cast<NPObject*>(object->GetAlignedPointerFromInternalField(v8DOMWrapperObjectIndex));
}
-NPObject* npCreateV8ScriptObject(NPP npp, v8::Handle<v8::Object> object, DOMWindow* root, v8::Isolate* isolate)
+NPObject* npCreateV8ScriptObject(NPP npp, v8::Handle<v8::Object> object, LocalDOMWindow* root, v8::Isolate* isolate)
{
// Check to see if this object is already wrapped.
if (object->InternalFieldCount() == npObjectInternalFieldCount) {
@@ -141,10 +143,10 @@ NPObject* npCreateV8ScriptObject(NPP npp, v8::Handle<v8::Object> object, DOMWind
return reinterpret_cast<NPObject*>(v8npObject);
}
}
+ objectVector = &iter->value;
} else {
- iter = v8NPObjectMap->set(v8ObjectHash, V8NPObjectVector()).iterator;
+ objectVector = &v8NPObjectMap->set(v8ObjectHash, V8NPObjectVector()).storedValue->value;
}
- objectVector = &iter->value;
}
V8NPObject* v8npObject = reinterpret_cast<V8NPObject*>(_NPN_CreateObject(npp, &V8NPObjectClass));
@@ -230,13 +232,12 @@ bool _NPN_Invoke(NPP npp, NPObject* npObject, NPIdentifier methodName, const NPV
return _NPN_Evaluate(npp, npObject, const_cast<NPString*>(&arguments[0].value.stringValue), result);
}
- v8::HandleScope handleScope(isolate);
// FIXME: should use the plugin's owner frame as the security context.
- v8::Handle<v8::Context> context = toV8Context(npp, npObject);
- if (context.IsEmpty())
+ ScriptState* scriptState = mainWorldScriptState(isolate, npp, npObject);
+ if (!scriptState)
return false;
- v8::Context::Scope scope(context);
+ ScriptState::Scope scope(scriptState);
ExceptionCatcher exceptionCatcher;
v8::Handle<v8::Object> v8Object = v8::Local<v8::Object>::New(isolate, v8NpObject->v8Object);
@@ -250,7 +251,7 @@ bool _NPN_Invoke(NPP npp, NPObject* npObject, NPIdentifier methodName, const NPV
return false;
}
- Frame* frame = v8NpObject->rootObject->frame();
+ LocalFrame* frame = v8NpObject->rootObject->frame();
ASSERT(frame);
// Call the function object.
@@ -286,12 +287,11 @@ bool _NPN_InvokeDefault(NPP npp, NPObject* npObject, const NPVariant* arguments,
VOID_TO_NPVARIANT(*result);
- v8::HandleScope handleScope(isolate);
- v8::Handle<v8::Context> context = toV8Context(npp, npObject);
- if (context.IsEmpty())
+ ScriptState* scriptState = mainWorldScriptState(isolate, npp, npObject);
+ if (!scriptState)
return false;
- v8::Context::Scope scope(context);
+ ScriptState::Scope scope(scriptState);
ExceptionCatcher exceptionCatcher;
// Lookup the function object and call it.
@@ -302,7 +302,7 @@ bool _NPN_InvokeDefault(NPP npp, NPObject* npObject, const NPVariant* arguments,
v8::Local<v8::Value> resultObject;
v8::Handle<v8::Function> function = v8::Local<v8::Function>::Cast(functionObject);
if (!function->IsNull()) {
- Frame* frame = v8NpObject->rootObject->frame();
+ LocalFrame* frame = v8NpObject->rootObject->frame();
ASSERT(frame);
OwnPtr<v8::Handle<v8::Value>[]> argv = createValueListFromVariantArgs(arguments, argumentCount, npObject, isolate);
@@ -335,12 +335,11 @@ bool _NPN_EvaluateHelper(NPP npp, bool popupsAllowed, NPObject* npObject, NPStri
return false;
v8::Isolate* isolate = v8::Isolate::GetCurrent();
- v8::HandleScope handleScope(isolate);
- v8::Handle<v8::Context> context = toV8Context(npp, npObject);
- if (context.IsEmpty())
+ ScriptState* scriptState = mainWorldScriptState(isolate, npp, npObject);
+ if (!scriptState)
return false;
- v8::Context::Scope scope(context);
+ ScriptState::Scope scope(scriptState);
ExceptionCatcher exceptionCatcher;
// FIXME: Is this branch still needed after switching to using UserGestureIndicator?
@@ -348,13 +347,13 @@ bool _NPN_EvaluateHelper(NPP npp, bool popupsAllowed, NPObject* npObject, NPStri
if (!popupsAllowed)
filename = "npscript";
- Frame* frame = v8NpObject->rootObject->frame();
+ LocalFrame* frame = v8NpObject->rootObject->frame();
ASSERT(frame);
String script = String::fromUTF8(npScript->UTF8Characters, npScript->UTF8Length);
UserGestureIndicator gestureIndicator(popupsAllowed ? DefinitelyProcessingNewUserGesture : PossiblyProcessingUserGesture);
- v8::Local<v8::Value> v8result = frame->script().executeScriptAndReturnValue(context, ScriptSourceCode(script, KURL(ParsedURLString, filename)));
+ v8::Local<v8::Value> v8result = frame->script().executeScriptAndReturnValue(scriptState->context(), ScriptSourceCode(script, KURL(ParsedURLString, filename)));
if (v8result.IsEmpty())
return false;
@@ -371,12 +370,11 @@ bool _NPN_GetProperty(NPP npp, NPObject* npObject, NPIdentifier propertyName, NP
if (V8NPObject* object = npObjectToV8NPObject(npObject)) {
v8::Isolate* isolate = v8::Isolate::GetCurrent();
- v8::HandleScope handleScope(isolate);
- v8::Handle<v8::Context> context = toV8Context(npp, npObject);
- if (context.IsEmpty())
+ ScriptState* scriptState = mainWorldScriptState(isolate, npp, npObject);
+ if (!scriptState)
return false;
- v8::Context::Scope scope(context);
+ ScriptState::Scope scope(scriptState);
ExceptionCatcher exceptionCatcher;
v8::Handle<v8::Object> obj = v8::Local<v8::Object>::New(isolate, object->v8Object);
@@ -405,16 +403,15 @@ bool _NPN_SetProperty(NPP npp, NPObject* npObject, NPIdentifier propertyName, co
if (V8NPObject* object = npObjectToV8NPObject(npObject)) {
v8::Isolate* isolate = v8::Isolate::GetCurrent();
- v8::HandleScope handleScope(isolate);
- v8::Handle<v8::Context> context = toV8Context(npp, npObject);
- if (context.IsEmpty())
+ ScriptState* scriptState = mainWorldScriptState(isolate, npp, npObject);
+ if (!scriptState)
return false;
- v8::Context::Scope scope(context);
+ ScriptState::Scope scope(scriptState);
ExceptionCatcher exceptionCatcher;
v8::Handle<v8::Object> obj = v8::Local<v8::Object>::New(isolate, object->v8Object);
- obj->Set(npIdentifierToV8Identifier(propertyName, context->GetIsolate()), convertNPVariantToV8Object(value, object->rootObject->frame()->script().windowScriptNPObject(), context->GetIsolate()));
+ obj->Set(npIdentifierToV8Identifier(propertyName, isolate), convertNPVariantToV8Object(value, object->rootObject->frame()->script().windowScriptNPObject(), isolate));
return true;
}
@@ -434,11 +431,10 @@ bool _NPN_RemoveProperty(NPP npp, NPObject* npObject, NPIdentifier propertyName)
return false;
v8::Isolate* isolate = v8::Isolate::GetCurrent();
- v8::HandleScope handleScope(isolate);
- v8::Handle<v8::Context> context = toV8Context(npp, npObject);
- if (context.IsEmpty())
+ ScriptState* scriptState = mainWorldScriptState(isolate, npp, npObject);
+ if (!scriptState)
return false;
- v8::Context::Scope scope(context);
+ ScriptState::Scope scope(scriptState);
ExceptionCatcher exceptionCatcher;
v8::Handle<v8::Object> obj = v8::Local<v8::Object>::New(isolate, object->v8Object);
@@ -454,11 +450,10 @@ bool _NPN_HasProperty(NPP npp, NPObject* npObject, NPIdentifier propertyName)
if (V8NPObject* object = npObjectToV8NPObject(npObject)) {
v8::Isolate* isolate = v8::Isolate::GetCurrent();
- v8::HandleScope handleScope(isolate);
- v8::Handle<v8::Context> context = toV8Context(npp, npObject);
- if (context.IsEmpty())
+ ScriptState* scriptState = mainWorldScriptState(isolate, npp, npObject);
+ if (!scriptState)
return false;
- v8::Context::Scope scope(context);
+ ScriptState::Scope scope(scriptState);
ExceptionCatcher exceptionCatcher;
v8::Handle<v8::Object> obj = v8::Local<v8::Object>::New(isolate, object->v8Object);
@@ -477,11 +472,10 @@ bool _NPN_HasMethod(NPP npp, NPObject* npObject, NPIdentifier methodName)
if (V8NPObject* object = npObjectToV8NPObject(npObject)) {
v8::Isolate* isolate = v8::Isolate::GetCurrent();
- v8::HandleScope handleScope(isolate);
- v8::Handle<v8::Context> context = toV8Context(npp, npObject);
- if (context.IsEmpty())
+ ScriptState* scriptState = mainWorldScriptState(isolate, npp, npObject);
+ if (!scriptState)
return false;
- v8::Context::Scope scope(context);
+ ScriptState::Scope scope(scriptState);
ExceptionCatcher exceptionCatcher;
v8::Handle<v8::Object> obj = v8::Local<v8::Object>::New(isolate, object->v8Object);
@@ -503,15 +497,15 @@ void _NPN_SetException(NPObject* npObject, const NPUTF8 *message)
return;
}
- v8::HandleScope handleScope(v8::Isolate::GetCurrent());
- v8::Handle<v8::Context> context = toV8Context(0, npObject);
- if (context.IsEmpty())
+ v8::Isolate* isolate = v8::Isolate::GetCurrent();
+ ScriptState* scriptState = mainWorldScriptState(isolate, 0, npObject);
+ if (!scriptState)
return;
- v8::Context::Scope scope(context);
+ ScriptState::Scope scope(scriptState);
ExceptionCatcher exceptionCatcher;
- throwError(v8GeneralError, message, context->GetIsolate());
+ throwError(v8GeneralError, message, isolate);
}
bool _NPN_Enumerate(NPP npp, NPObject* npObject, NPIdentifier** identifier, uint32_t* count)
@@ -521,11 +515,10 @@ bool _NPN_Enumerate(NPP npp, NPObject* npObject, NPIdentifier** identifier, uint
if (V8NPObject* object = npObjectToV8NPObject(npObject)) {
v8::Isolate* isolate = v8::Isolate::GetCurrent();
- v8::HandleScope handleScope(isolate);
- v8::Local<v8::Context> context = toV8Context(npp, npObject);
- if (context.IsEmpty())
+ ScriptState* scriptState = mainWorldScriptState(isolate, npp, npObject);
+ if (!scriptState)
return false;
- v8::Context::Scope scope(context);
+ ScriptState::Scope scope(scriptState);
ExceptionCatcher exceptionCatcher;
v8::Handle<v8::Object> obj = v8::Local<v8::Object>::New(isolate, object->v8Object);
@@ -542,22 +535,22 @@ bool _NPN_Enumerate(NPP npp, NPObject* npObject, NPIdentifier** identifier, uint
" }"
" return props;"
"});";
- v8::Handle<v8::String> source = v8::String::NewFromUtf8(isolate, enumeratorCode);
- v8::Handle<v8::Value> result = V8ScriptRunner::compileAndRunInternalScript(source, context->GetIsolate());
+ v8::Handle<v8::String> source = v8AtomicString(isolate, enumeratorCode);
+ v8::Handle<v8::Value> result = V8ScriptRunner::compileAndRunInternalScript(source, isolate);
ASSERT(!result.IsEmpty());
ASSERT(result->IsFunction());
v8::Handle<v8::Function> enumerator = v8::Handle<v8::Function>::Cast(result);
v8::Handle<v8::Value> argv[] = { obj };
- v8::Local<v8::Value> propsObj = V8ScriptRunner::callInternalFunction(enumerator, v8::Handle<v8::Object>::Cast(result), WTF_ARRAY_LENGTH(argv), argv, context->GetIsolate());
+ v8::Local<v8::Value> propsObj = V8ScriptRunner::callInternalFunction(enumerator, v8::Handle<v8::Object>::Cast(result), WTF_ARRAY_LENGTH(argv), argv, isolate);
if (propsObj.IsEmpty())
return false;
// Convert the results into an array of NPIdentifiers.
v8::Handle<v8::Array> props = v8::Handle<v8::Array>::Cast(propsObj);
*count = props->Length();
- *identifier = static_cast<NPIdentifier*>(malloc(sizeof(NPIdentifier*) * *count));
+ *identifier = static_cast<NPIdentifier*>(calloc(*count, sizeof(NPIdentifier)));
for (uint32_t i = 0; i < *count; ++i) {
- v8::Local<v8::Value> name = props->Get(v8::Integer::New(i, context->GetIsolate()));
+ v8::Local<v8::Value> name = props->Get(v8::Integer::New(isolate, i));
(*identifier)[i] = getStringIdentifier(v8::Local<v8::String>::Cast(name));
}
return true;
@@ -577,11 +570,10 @@ bool _NPN_Construct(NPP npp, NPObject* npObject, const NPVariant* arguments, uin
v8::Isolate* isolate = v8::Isolate::GetCurrent();
if (V8NPObject* object = npObjectToV8NPObject(npObject)) {
- v8::HandleScope handleScope(isolate);
- v8::Handle<v8::Context> context = toV8Context(npp, npObject);
- if (context.IsEmpty())
+ ScriptState* scriptState = mainWorldScriptState(isolate, npp, npObject);
+ if (!scriptState)
return false;
- v8::Context::Scope scope(context);
+ ScriptState::Scope scope(scriptState);
ExceptionCatcher exceptionCatcher;
// Lookup the constructor function.
@@ -593,10 +585,10 @@ bool _NPN_Construct(NPP npp, NPObject* npObject, const NPVariant* arguments, uin
v8::Local<v8::Value> resultObject;
v8::Handle<v8::Function> ctor = v8::Handle<v8::Function>::Cast(ctorObj);
if (!ctor->IsNull()) {
- Frame* frame = object->rootObject->frame();
+ LocalFrame* frame = object->rootObject->frame();
ASSERT(frame);
OwnPtr<v8::Handle<v8::Value>[]> argv = createValueListFromVariantArgs(arguments, argumentCount, npObject, isolate);
- resultObject = V8ObjectConstructor::newInstanceInDocument(ctor, argumentCount, argv.get(), frame ? frame->document() : 0);
+ resultObject = V8ObjectConstructor::newInstanceInDocument(isolate, ctor, argumentCount, argv.get(), frame ? frame->document() : 0);
}
if (resultObject.IsEmpty())
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/NPV8Object.h b/chromium/third_party/WebKit/Source/bindings/v8/NPV8Object.h
index 435f778d151..3e7db341956 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/NPV8Object.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/NPV8Object.h
@@ -39,7 +39,7 @@
namespace WebCore {
-class DOMWindow;
+class LocalDOMWindow;
static const int npObjectInternalFieldCount = v8DefaultWrapperInternalFieldCount + 0;
@@ -53,7 +53,7 @@ struct V8NPObject {
public:
NPObject object;
v8::Persistent<v8::Object> v8Object;
- DOMWindow* rootObject;
+ LocalDOMWindow* rootObject;
};
struct PrivateIdentifier {
@@ -64,7 +64,7 @@ struct PrivateIdentifier {
bool isString;
};
-NPObject* npCreateV8ScriptObject(NPP, v8::Handle<v8::Object>, DOMWindow*, v8::Isolate*);
+NPObject* npCreateV8ScriptObject(NPP, v8::Handle<v8::Object>, LocalDOMWindow*, v8::Isolate*);
NPObject* v8ObjectToNPObject(v8::Handle<v8::Object>);
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/Nullable.h b/chromium/third_party/WebKit/Source/bindings/v8/Nullable.h
new file mode 100644
index 00000000000..0f8356c472d
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/bindings/v8/Nullable.h
@@ -0,0 +1,51 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef Nullable_h
+#define Nullable_h
+
+#include "wtf/Assertions.h"
+
+namespace WebCore {
+
+template <typename T>
+class Nullable {
+public:
+ Nullable()
+ : m_value()
+ , m_isNull(true) { }
+
+ Nullable(const T& value)
+ : m_value(value)
+ , m_isNull(false) { }
+
+ Nullable(const Nullable& other)
+ : m_value(other.m_value)
+ , m_isNull(other.m_isNull) { }
+
+ Nullable& operator=(const Nullable& other)
+ {
+ m_value = other.m_value;
+ m_isNull = other.m_isNull;
+ return *this;
+ }
+
+ T get() const { ASSERT(!m_isNull); return m_value; }
+ bool isNull() const { return m_isNull; }
+
+ operator bool() const { return !m_isNull && m_value; }
+
+ bool operator==(const Nullable& other) const
+ {
+ return (m_isNull && other.m_isNull) || (!m_isNull && !other.m_isNull && m_value == other.m_value);
+ }
+
+private:
+ T m_value;
+ bool m_isNull;
+};
+
+} // namespace WebCore
+
+#endif // Nullable_h
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/PageScriptDebugServer.cpp b/chromium/third_party/WebKit/Source/bindings/v8/PageScriptDebugServer.cpp
index 44a2b48a22c..5901fba1eaf 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/PageScriptDebugServer.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/PageScriptDebugServer.cpp
@@ -32,15 +32,20 @@
#include "bindings/v8/PageScriptDebugServer.h"
-#include "V8Window.h"
+#include "bindings/core/v8/V8Window.h"
+#include "bindings/v8/DOMWrapperWorld.h"
#include "bindings/v8/ScriptController.h"
#include "bindings/v8/ScriptSourceCode.h"
#include "bindings/v8/V8Binding.h"
#include "bindings/v8/V8ScriptRunner.h"
#include "bindings/v8/V8WindowShell.h"
+#include "core/frame/FrameConsole.h"
+#include "core/frame/FrameHost.h"
+#include "core/frame/LocalFrame.h"
+#include "core/frame/UseCounter.h"
#include "core/inspector/InspectorInstrumentation.h"
+#include "core/inspector/InspectorTraceEvents.h"
#include "core/inspector/ScriptDebugListener.h"
-#include "core/frame/Frame.h"
#include "core/page/Page.h"
#include "wtf/OwnPtr.h"
#include "wtf/PassOwnPtr.h"
@@ -50,17 +55,20 @@
namespace WebCore {
-static Frame* retrieveFrameWithGlobalObjectCheck(v8::Handle<v8::Context> context)
+static LocalFrame* retrieveFrameWithGlobalObjectCheck(v8::Handle<v8::Context> context)
{
if (context.IsEmpty())
return 0;
- // Test that context has associated global dom window object.
- v8::Handle<v8::Object> global = context->Global();
- if (global.IsEmpty())
+ // FIXME: This is a temporary hack for crbug.com/345014.
+ // Currently it's possible that V8 can trigger Debugger::ProcessDebugEvent for a context
+ // that is being initialized (i.e., inside Context::New() of the context).
+ // We should fix the V8 side so that it won't trigger the event for a half-baked context
+ // because there is no way in the embedder side to check if the context is half-baked or not.
+ if (isMainThread() && DOMWrapperWorld::windowIsBeingInitialized())
return 0;
- global = global->FindInstanceInPrototypeChain(V8Window::domTemplate(context->GetIsolate(), worldTypeInMainThread(context->GetIsolate())));
+ v8::Handle<v8::Value> global = V8Window::findInstanceInPrototypeChain(context->Global(), context->GetIsolate());
if (global.IsEmpty())
return 0;
@@ -82,31 +90,44 @@ PageScriptDebugServer& PageScriptDebugServer::shared()
return server;
}
+v8::Isolate* PageScriptDebugServer::s_mainThreadIsolate = 0;
+
+void PageScriptDebugServer::setMainThreadIsolate(v8::Isolate* isolate)
+{
+ s_mainThreadIsolate = isolate;
+}
+
PageScriptDebugServer::PageScriptDebugServer()
- : ScriptDebugServer(v8::Isolate::GetCurrent())
+ : ScriptDebugServer(s_mainThreadIsolate)
, m_pausedPage(0)
{
}
+PageScriptDebugServer::~PageScriptDebugServer()
+{
+}
+
void PageScriptDebugServer::addListener(ScriptDebugListener* listener, Page* page)
{
- ScriptController& scriptController = page->mainFrame()->script();
+ ScriptController& scriptController = page->deprecatedLocalMainFrame()->script();
if (!scriptController.canExecuteScripts(NotAboutToExecuteScript))
return;
v8::HandleScope scope(m_isolate);
- v8::Local<v8::Context> debuggerContext = v8::Debug::GetDebugContext();
- v8::Context::Scope contextScope(debuggerContext);
- v8::Local<v8::Object> debuggerScript = m_debuggerScript.newLocal(m_isolate);
if (!m_listenersMap.size()) {
+ v8::Debug::SetDebugEventListener(&PageScriptDebugServer::v8DebugEventCallback, v8::External::New(m_isolate, this));
ensureDebuggerScriptCompiled();
- ASSERT(!debuggerScript->IsUndefined());
- v8::Debug::SetDebugEventListener2(&PageScriptDebugServer::v8DebugEventCallback, v8::External::New(m_isolate, this));
}
+
+ v8::Local<v8::Context> debuggerContext = v8::Debug::GetDebugContext();
+ v8::Context::Scope contextScope(debuggerContext);
+
+ v8::Local<v8::Object> debuggerScript = m_debuggerScript.newLocal(m_isolate);
+ ASSERT(!debuggerScript->IsUndefined());
m_listenersMap.set(page, listener);
- V8WindowShell* shell = scriptController.existingWindowShell(mainThreadNormalWorld());
+ V8WindowShell* shell = scriptController.existingWindowShell(DOMWrapperWorld::mainWorld());
if (!shell || !shell->isContextInitialized())
return;
v8::Local<v8::Context> context = shell->context();
@@ -118,7 +139,7 @@ void PageScriptDebugServer::addListener(ScriptDebugListener* listener, Page* pag
ASSERT(!value->IsUndefined() && value->IsArray());
v8::Handle<v8::Array> scriptsArray = v8::Handle<v8::Array>::Cast(value);
for (unsigned i = 0; i < scriptsArray->Length(); ++i)
- dispatchDidParseSource(listener, v8::Handle<v8::Object>::Cast(scriptsArray->Get(v8::Integer::New(i, m_isolate))));
+ dispatchDidParseSource(listener, v8::Handle<v8::Object>::Cast(scriptsArray->Get(v8::Integer::New(m_isolate, i))));
}
void PageScriptDebugServer::removeListener(ScriptDebugListener* listener, Page* page)
@@ -131,9 +152,16 @@ void PageScriptDebugServer::removeListener(ScriptDebugListener* listener, Page*
m_listenersMap.remove(page);
- if (m_listenersMap.isEmpty())
- v8::Debug::SetDebugEventListener2(0);
- // FIXME: Remove all breakpoints set by the agent.
+ if (m_listenersMap.isEmpty()) {
+ discardDebuggerScript();
+ v8::Debug::SetDebugEventListener(0);
+ // FIXME: Remove all breakpoints set by the agent.
+ }
+}
+
+void PageScriptDebugServer::interruptAndRun(PassOwnPtr<Task> task)
+{
+ ScriptDebugServer::interruptAndRun(task, s_mainThreadIsolate);
}
void PageScriptDebugServer::setClientMessageLoop(PassOwnPtr<ClientMessageLoop> clientMessageLoop)
@@ -141,11 +169,11 @@ void PageScriptDebugServer::setClientMessageLoop(PassOwnPtr<ClientMessageLoop> c
m_clientMessageLoop = clientMessageLoop;
}
-void PageScriptDebugServer::compileScript(ScriptState* state, const String& expression, const String& sourceURL, String* scriptId, String* exceptionMessage)
+void PageScriptDebugServer::compileScript(ScriptState* scriptState, const String& expression, const String& sourceURL, String* scriptId, String* exceptionDetailsText, int* lineNumber, int* columnNumber, RefPtrWillBeRawPtr<ScriptCallStack>* stackTrace)
{
- ExecutionContext* executionContext = state->executionContext();
- RefPtr<Frame> protect = toDocument(executionContext)->frame();
- ScriptDebugServer::compileScript(state, expression, sourceURL, scriptId, exceptionMessage);
+ ExecutionContext* executionContext = scriptState->executionContext();
+ RefPtr<LocalFrame> protect = toDocument(executionContext)->frame();
+ ScriptDebugServer::compileScript(scriptState, expression, sourceURL, scriptId, exceptionDetailsText, lineNumber, columnNumber, stackTrace);
if (!scriptId->isNull())
m_compiledScriptURLs.set(*scriptId, sourceURL);
}
@@ -156,27 +184,31 @@ void PageScriptDebugServer::clearCompiledScripts()
m_compiledScriptURLs.clear();
}
-void PageScriptDebugServer::runScript(ScriptState* state, const String& scriptId, ScriptValue* result, bool* wasThrown, String* exceptionMessage)
+void PageScriptDebugServer::runScript(ScriptState* scriptState, const String& scriptId, ScriptValue* result, bool* wasThrown, String* exceptionDetailsText, int* lineNumber, int* columnNumber, RefPtrWillBeRawPtr<ScriptCallStack>* stackTrace)
{
String sourceURL = m_compiledScriptURLs.take(scriptId);
- ExecutionContext* executionContext = state->executionContext();
- Frame* frame = toDocument(executionContext)->frame();
+ ExecutionContext* executionContext = scriptState->executionContext();
+ LocalFrame* frame = toDocument(executionContext)->frame();
+ TRACE_EVENT1(TRACE_DISABLED_BY_DEFAULT("devtools.timeline"), "EvaluateScript", "data", InspectorEvaluateScriptEvent::data(frame, sourceURL, TextPosition::minimumPosition().m_line.oneBasedInt()));
+ TRACE_EVENT_INSTANT1(TRACE_DISABLED_BY_DEFAULT("devtools.timeline.stack"), "CallStack", "stack", InspectorCallStackEvent::currentCallStack());
+ // FIXME(361045): remove InspectorInstrumentation calls once DevTools Timeline migrates to tracing.
InspectorInstrumentationCookie cookie;
if (frame)
cookie = InspectorInstrumentation::willEvaluateScript(frame, sourceURL, TextPosition::minimumPosition().m_line.oneBasedInt());
- RefPtr<Frame> protect = frame;
- ScriptDebugServer::runScript(state, scriptId, result, wasThrown, exceptionMessage);
+ RefPtr<LocalFrame> protect = frame;
+ ScriptDebugServer::runScript(scriptState, scriptId, result, wasThrown, exceptionDetailsText, lineNumber, columnNumber, stackTrace);
if (frame)
InspectorInstrumentation::didEvaluateScript(cookie);
+ TRACE_EVENT_INSTANT1(TRACE_DISABLED_BY_DEFAULT("devtools.timeline"), "UpdateCounters", "data", InspectorUpdateCountersEvent::data());
}
ScriptDebugListener* PageScriptDebugServer::getDebugListenerForContext(v8::Handle<v8::Context> context)
{
v8::HandleScope scope(m_isolate);
- Frame* frame = retrieveFrameWithGlobalObjectCheck(context);
+ LocalFrame* frame = retrieveFrameWithGlobalObjectCheck(context);
if (!frame)
return 0;
return m_listenersMap.get(frame->page());
@@ -185,7 +217,7 @@ ScriptDebugListener* PageScriptDebugServer::getDebugListenerForContext(v8::Handl
void PageScriptDebugServer::runMessageLoopOnPause(v8::Handle<v8::Context> context)
{
v8::HandleScope scope(m_isolate);
- Frame* frame = retrieveFrameWithGlobalObjectCheck(context);
+ LocalFrame* frame = retrieveFrameWithGlobalObjectCheck(context);
m_pausedPage = frame->page();
// Wait for continue or step command.
@@ -206,7 +238,7 @@ void PageScriptDebugServer::quitMessageLoopOnPause()
void PageScriptDebugServer::preprocessBeforeCompile(const v8::Debug::EventDetails& eventDetails)
{
v8::Handle<v8::Context> eventContext = eventDetails.GetEventContext();
- Frame* frame = retrieveFrameWithGlobalObjectCheck(eventContext);
+ LocalFrame* frame = retrieveFrameWithGlobalObjectCheck(eventContext);
if (!frame)
return;
@@ -236,7 +268,7 @@ void PageScriptDebugServer::preprocessBeforeCompile(const v8::Debug::EventDetail
static bool isCreatingPreprocessor = false;
-bool PageScriptDebugServer::canPreprocess(Frame* frame)
+bool PageScriptDebugServer::canPreprocess(LocalFrame* frame)
{
ASSERT(frame);
@@ -247,7 +279,7 @@ bool PageScriptDebugServer::canPreprocess(Frame* frame)
// Web page to ensure that the debugger's console initialization code has completed.
if (!m_scriptPreprocessor) {
TemporaryChange<bool> isPreprocessing(isCreatingPreprocessor, true);
- m_scriptPreprocessor = adoptPtr(new ScriptPreprocessor(*m_preprocessorSourceCode.get(), frame->script(), frame->page()->console()));
+ m_scriptPreprocessor = adoptPtr(new ScriptPreprocessor(*m_preprocessorSourceCode.get(), frame));
}
if (m_scriptPreprocessor->isValid())
@@ -260,7 +292,7 @@ bool PageScriptDebugServer::canPreprocess(Frame* frame)
}
// Source to Source processing iff debugger enabled and it has loaded a preprocessor.
-PassOwnPtr<ScriptSourceCode> PageScriptDebugServer::preprocess(Frame* frame, const ScriptSourceCode& sourceCode)
+PassOwnPtr<ScriptSourceCode> PageScriptDebugServer::preprocess(LocalFrame* frame, const ScriptSourceCode& sourceCode)
{
if (!canPreprocess(frame))
return PassOwnPtr<ScriptSourceCode>();
@@ -269,7 +301,7 @@ PassOwnPtr<ScriptSourceCode> PageScriptDebugServer::preprocess(Frame* frame, con
return adoptPtr(new ScriptSourceCode(preprocessedSource, sourceCode.url()));
}
-String PageScriptDebugServer::preprocessEventListener(Frame* frame, const String& source, const String& url, const String& functionName)
+String PageScriptDebugServer::preprocessEventListener(LocalFrame* frame, const String& source, const String& url, const String& functionName)
{
if (!canPreprocess(frame))
return source;
@@ -277,4 +309,16 @@ String PageScriptDebugServer::preprocessEventListener(Frame* frame, const String
return m_scriptPreprocessor->preprocessSourceCode(source, url, functionName);
}
+void PageScriptDebugServer::muteWarningsAndDeprecations()
+{
+ FrameConsole::mute();
+ UseCounter::muteForInspector();
+}
+
+void PageScriptDebugServer::unmuteWarningsAndDeprecations()
+{
+ FrameConsole::unmute();
+ UseCounter::unmuteForInspector();
+}
+
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/PageScriptDebugServer.h b/chromium/third_party/WebKit/Source/bindings/v8/PageScriptDebugServer.h
index 78fde09e688..96f8779f223 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/PageScriptDebugServer.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/PageScriptDebugServer.h
@@ -31,11 +31,11 @@
#ifndef PageScriptDebugServer_h
#define PageScriptDebugServer_h
-
#include "bindings/v8/ScriptDebugServer.h"
#include "bindings/v8/ScriptPreprocessor.h"
#include "wtf/Forward.h"
#include "wtf/RefCounted.h"
+#include <v8.h>
namespace WebCore {
@@ -44,14 +44,18 @@ class ScriptController;
class ScriptPreprocessor;
class ScriptSourceCode;
-class PageScriptDebugServer : public ScriptDebugServer {
+class PageScriptDebugServer FINAL : public ScriptDebugServer {
WTF_MAKE_NONCOPYABLE(PageScriptDebugServer);
public:
static PageScriptDebugServer& shared();
+ static void setMainThreadIsolate(v8::Isolate*);
+
void addListener(ScriptDebugListener*, Page*);
void removeListener(ScriptDebugListener*, Page*);
+ static void interruptAndRun(PassOwnPtr<Task>);
+
class ClientMessageLoop {
public:
virtual ~ClientMessageLoop() { }
@@ -60,21 +64,24 @@ public:
};
void setClientMessageLoop(PassOwnPtr<ClientMessageLoop>);
- virtual void compileScript(ScriptState*, const String& expression, const String& sourceURL, String* scriptId, String* exceptionMessage);
- virtual void clearCompiledScripts();
- virtual void runScript(ScriptState*, const String& scriptId, ScriptValue* result, bool* wasThrown, String* exceptionMessage);
- virtual void setPreprocessorSource(const String&);
- virtual void preprocessBeforeCompile(const v8::Debug::EventDetails&);
- virtual PassOwnPtr<ScriptSourceCode> preprocess(Frame*, const ScriptSourceCode&);
- virtual String preprocessEventListener(Frame*, const String& source, const String& url, const String& functionName);
+ virtual void compileScript(ScriptState*, const String& expression, const String& sourceURL, String* scriptId, String* exceptionDetailsText, int* lineNumber, int* columnNumber, RefPtrWillBeRawPtr<ScriptCallStack>* stackTrace) OVERRIDE;
+ virtual void clearCompiledScripts() OVERRIDE;
+ virtual void runScript(ScriptState*, const String& scriptId, ScriptValue* result, bool* wasThrown, String* exceptionDetailsText, int* lineNumber, int* columnNumber, RefPtrWillBeRawPtr<ScriptCallStack>* stackTrace) OVERRIDE;
+ virtual void setPreprocessorSource(const String&) OVERRIDE;
+ virtual void preprocessBeforeCompile(const v8::Debug::EventDetails&) OVERRIDE;
+ virtual PassOwnPtr<ScriptSourceCode> preprocess(LocalFrame*, const ScriptSourceCode&) OVERRIDE;
+ virtual String preprocessEventListener(LocalFrame*, const String& source, const String& url, const String& functionName) OVERRIDE;
+
+ virtual void muteWarningsAndDeprecations() OVERRIDE;
+ virtual void unmuteWarningsAndDeprecations() OVERRIDE;
private:
PageScriptDebugServer();
- virtual ~PageScriptDebugServer() { }
+ virtual ~PageScriptDebugServer();
- virtual ScriptDebugListener* getDebugListenerForContext(v8::Handle<v8::Context>);
- virtual void runMessageLoopOnPause(v8::Handle<v8::Context>);
- virtual void quitMessageLoopOnPause();
+ virtual ScriptDebugListener* getDebugListenerForContext(v8::Handle<v8::Context>) OVERRIDE;
+ virtual void runMessageLoopOnPause(v8::Handle<v8::Context>) OVERRIDE;
+ virtual void quitMessageLoopOnPause() OVERRIDE;
typedef HashMap<Page*, ScriptDebugListener*> ListenersMap;
ListenersMap m_listenersMap;
@@ -84,7 +91,8 @@ private:
OwnPtr<ScriptSourceCode> m_preprocessorSourceCode;
OwnPtr<ScriptPreprocessor> m_scriptPreprocessor;
- bool canPreprocess(Frame*);
+ bool canPreprocess(LocalFrame*);
+ static v8::Isolate* s_mainThreadIsolate;
};
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/RetainedDOMInfo.h b/chromium/third_party/WebKit/Source/bindings/v8/RetainedDOMInfo.h
index 52709997cfc..2138c0b9937 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/RetainedDOMInfo.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/RetainedDOMInfo.h
@@ -32,23 +32,24 @@
#define RetainedDOMInfo_h
#include "bindings/v8/RetainedObjectInfo.h"
+#include <v8-profiler.h>
namespace WebCore {
class Node;
// Implements v8::RetainedObjectInfo.
-class RetainedDOMInfo : public RetainedObjectInfo {
+class RetainedDOMInfo FINAL : public RetainedObjectInfo {
public:
explicit RetainedDOMInfo(Node* root);
virtual ~RetainedDOMInfo();
- virtual void Dispose();
- virtual bool IsEquivalent(v8::RetainedObjectInfo* other);
- virtual intptr_t GetHash();
- virtual const char* GetGroupLabel();
- virtual const char* GetLabel();
- virtual intptr_t GetElementCount();
- virtual intptr_t GetEquivalenceClass();
+ virtual void Dispose() OVERRIDE;
+ virtual bool IsEquivalent(v8::RetainedObjectInfo* other) OVERRIDE;
+ virtual intptr_t GetHash() OVERRIDE;
+ virtual const char* GetGroupLabel() OVERRIDE;
+ virtual const char* GetLabel() OVERRIDE;
+ virtual intptr_t GetElementCount() OVERRIDE;
+ virtual intptr_t GetEquivalenceClass() OVERRIDE;
private:
// V8 guarantees to keep RetainedObjectInfos alive only during a GC or heap snapshotting round, when renderer
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ScheduledAction.cpp b/chromium/third_party/WebKit/Source/bindings/v8/ScheduledAction.cpp
index 1de2039ec15..0f669f310e8 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/ScheduledAction.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ScheduledAction.cpp
@@ -38,41 +38,39 @@
#include "bindings/v8/V8ScriptRunner.h"
#include "core/dom/Document.h"
#include "core/dom/ExecutionContext.h"
-#include "core/frame/Frame.h"
+#include "core/frame/LocalFrame.h"
#include "core/workers/WorkerGlobalScope.h"
#include "core/workers/WorkerThread.h"
#include "platform/TraceEvent.h"
namespace WebCore {
-ScheduledAction::ScheduledAction(v8::Handle<v8::Context> context, v8::Handle<v8::Function> function, int argc, v8::Handle<v8::Value> argv[], v8::Isolate* isolate)
- : m_context(isolate, context)
+ScheduledAction::ScheduledAction(ScriptState* scriptState, v8::Handle<v8::Function> function, int argc, v8::Handle<v8::Value> argv[], v8::Isolate* isolate)
+ : m_scriptState(scriptState)
, m_function(isolate, function)
+ , m_info(isolate)
, m_code(String(), KURL(), TextPosition::belowRangePosition())
- , m_isolate(isolate)
{
- m_info.reserveCapacity(argc);
+ m_info.ReserveCapacity(argc);
for (int i = 0; i < argc; ++i)
- m_info.append(UnsafePersistent<v8::Value>(m_isolate, argv[i]));
+ m_info.Append(argv[i]);
}
-ScheduledAction::ScheduledAction(v8::Handle<v8::Context> context, const String& code, const KURL& url, v8::Isolate* isolate)
- : m_context(isolate, context)
+ScheduledAction::ScheduledAction(ScriptState* scriptState, const String& code, const KURL& url, v8::Isolate* isolate)
+ : m_scriptState(scriptState)
+ , m_info(isolate)
, m_code(code, url)
- , m_isolate(isolate)
{
}
ScheduledAction::~ScheduledAction()
{
- for (size_t i = 0; i < m_info.size(); ++i)
- m_info[i].dispose();
}
void ScheduledAction::execute(ExecutionContext* context)
{
if (context->isDocument()) {
- Frame* frame = toDocument(context)->frame();
+ LocalFrame* frame = toDocument(context)->frame();
if (!frame)
return;
if (!frame->script().canExecuteScripts(AboutToExecuteScript))
@@ -83,23 +81,19 @@ void ScheduledAction::execute(ExecutionContext* context)
}
}
-void ScheduledAction::execute(Frame* frame)
+void ScheduledAction::execute(LocalFrame* frame)
{
- v8::HandleScope handleScope(m_isolate);
-
- v8::Handle<v8::Context> context = m_context.newLocal(m_isolate);
- if (context.IsEmpty())
+ if (m_scriptState->contextIsEmpty())
return;
TRACE_EVENT0("v8", "ScheduledAction::execute");
-
+ ScriptState::Scope scope(m_scriptState.get());
if (!m_function.isEmpty()) {
- v8::Context::Scope scope(context);
Vector<v8::Handle<v8::Value> > info;
createLocalHandlesForArgs(&info);
- frame->script().callFunction(m_function.newLocal(m_isolate), context->Global(), info.size(), info.data());
+ frame->script().callFunction(m_function.newLocal(m_scriptState->isolate()), m_scriptState->context()->Global(), info.size(), info.data());
} else {
- frame->script().executeScriptAndReturnValue(context, ScriptSourceCode(m_code));
+ frame->script().executeScriptAndReturnValue(m_scriptState->context(), ScriptSourceCode(m_code));
}
// The frame might be invalid at this point because JavaScript could have released it.
@@ -108,23 +102,22 @@ void ScheduledAction::execute(Frame* frame)
void ScheduledAction::execute(WorkerGlobalScope* worker)
{
ASSERT(worker->thread()->isCurrentThread());
- v8::HandleScope handleScope(m_isolate);
- v8::Handle<v8::Context> context = m_context.newLocal(m_isolate);
- ASSERT(!context.IsEmpty());
- v8::Context::Scope scope(context);
+ ASSERT(!m_scriptState->contextIsEmpty());
if (!m_function.isEmpty()) {
+ ScriptState::Scope scope(m_scriptState.get());
Vector<v8::Handle<v8::Value> > info;
createLocalHandlesForArgs(&info);
- V8ScriptRunner::callFunction(m_function.newLocal(m_isolate), worker, context->Global(), info.size(), info.data(), m_isolate);
- } else
+ V8ScriptRunner::callFunction(m_function.newLocal(m_scriptState->isolate()), worker, m_scriptState->context()->Global(), info.size(), info.data(), m_scriptState->isolate());
+ } else {
worker->script()->evaluate(m_code);
+ }
}
void ScheduledAction::createLocalHandlesForArgs(Vector<v8::Handle<v8::Value> >* handles)
{
- handles->reserveCapacity(m_info.size());
- for (size_t i = 0; i < m_info.size(); ++i)
- handles->append(m_info[i].newLocal(m_isolate));
+ handles->reserveCapacity(m_info.Size());
+ for (size_t i = 0; i < m_info.Size(); ++i)
+ handles->append(m_info.Get(i));
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ScheduledAction.h b/chromium/third_party/WebKit/Source/bindings/v8/ScheduledAction.h
index 9b03a027305..351ef3bed7e 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/ScheduledAction.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ScheduledAction.h
@@ -33,36 +33,35 @@
#include "bindings/v8/ScopedPersistent.h"
#include "bindings/v8/ScriptSourceCode.h"
-#include "bindings/v8/UnsafePersistent.h"
+#include "bindings/v8/ScriptState.h"
+#include "bindings/v8/V8PersistentValueVector.h"
#include <v8.h>
#include "wtf/Forward.h"
-#include "wtf/Vector.h"
namespace WebCore {
-class Frame;
+class LocalFrame;
class ExecutionContext;
class WorkerGlobalScope;
class ScheduledAction {
WTF_MAKE_NONCOPYABLE(ScheduledAction);
public:
- ScheduledAction(v8::Handle<v8::Context>, v8::Handle<v8::Function>, int argc, v8::Handle<v8::Value> argv[], v8::Isolate*);
- ScheduledAction(v8::Handle<v8::Context>, const String&, const KURL&, v8::Isolate*);
+ ScheduledAction(ScriptState*, v8::Handle<v8::Function>, int argc, v8::Handle<v8::Value> argv[], v8::Isolate*);
+ ScheduledAction(ScriptState*, const String&, const KURL&, v8::Isolate*);
~ScheduledAction();
void execute(ExecutionContext*);
private:
- void execute(Frame*);
+ void execute(LocalFrame*);
void execute(WorkerGlobalScope*);
void createLocalHandlesForArgs(Vector<v8::Handle<v8::Value> >* handles);
- ScopedPersistent<v8::Context> m_context;
+ ScriptStateProtectingContext m_scriptState;
ScopedPersistent<v8::Function> m_function;
- Vector<UnsafePersistent<v8::Value> > m_info;
+ V8PersistentValueVector<v8::Value> m_info;
ScriptSourceCode m_code;
- v8::Isolate* m_isolate;
};
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ScopedPersistent.h b/chromium/third_party/WebKit/Source/bindings/v8/ScopedPersistent.h
index 84b6beea6ce..a383f780c37 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/ScopedPersistent.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ScopedPersistent.h
@@ -64,6 +64,7 @@ public:
}
bool isEmpty() const { return m_handle.IsEmpty(); }
+ bool isWeak() const { return m_handle.IsWeak(); }
void set(v8::Isolate* isolate, v8::Handle<T> handle)
{
@@ -81,6 +82,12 @@ public:
return m_handle == other.m_handle;
}
+ template <class S>
+ bool operator==(const v8::Handle<S> other) const
+ {
+ return m_handle == other;
+ }
+
private:
// FIXME: This function does an unsafe handle access. Remove it.
friend class V8AbstractEventListener;
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ScriptCallStackFactory.cpp b/chromium/third_party/WebKit/Source/bindings/v8/ScriptCallStackFactory.cpp
index 81dea4584c6..8c68a9ddd4a 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/ScriptCallStackFactory.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ScriptCallStackFactory.cpp
@@ -31,10 +31,8 @@
#include "config.h"
#include "bindings/v8/ScriptCallStackFactory.h"
-#include "bindings/v8/ScriptScope.h"
#include "bindings/v8/ScriptValue.h"
#include "bindings/v8/V8Binding.h"
-#include "bindings/v8/V8Utilities.h"
#include "core/inspector/InspectorInstrumentation.h"
#include "core/inspector/ScriptArguments.h"
#include "core/inspector/ScriptCallFrame.h"
@@ -86,7 +84,7 @@ static void toScriptCallFramesVector(v8::Handle<v8::StackTrace> stackTrace, Vect
}
}
-static PassRefPtr<ScriptCallStack> createScriptCallStack(v8::Handle<v8::StackTrace> stackTrace, size_t maxStackSize, bool emptyStackIsAllowed, v8::Isolate* isolate)
+static PassRefPtrWillBeRawPtr<ScriptCallStack> createScriptCallStack(v8::Handle<v8::StackTrace> stackTrace, size_t maxStackSize, bool emptyStackIsAllowed, v8::Isolate* isolate)
{
ASSERT(isolate->InContext());
v8::HandleScope scope(isolate);
@@ -95,44 +93,38 @@ static PassRefPtr<ScriptCallStack> createScriptCallStack(v8::Handle<v8::StackTra
return ScriptCallStack::create(scriptCallFrames);
}
-PassRefPtr<ScriptCallStack> createScriptCallStack(v8::Handle<v8::StackTrace> stackTrace, size_t maxStackSize, v8::Isolate* isolate)
+PassRefPtrWillBeRawPtr<ScriptCallStack> createScriptCallStack(v8::Handle<v8::StackTrace> stackTrace, size_t maxStackSize, v8::Isolate* isolate)
{
return createScriptCallStack(stackTrace, maxStackSize, true, isolate);
}
-PassRefPtr<ScriptCallStack> createScriptCallStack(size_t maxStackSize, bool emptyStackIsAllowed)
+PassRefPtrWillBeRawPtr<ScriptCallStack> createScriptCallStack(size_t maxStackSize, bool emptyStackIsAllowed)
{
v8::Isolate* isolate = v8::Isolate::GetCurrent();
if (!isolate->InContext())
- return 0;
+ return nullptr;
v8::HandleScope handleScope(isolate);
v8::Handle<v8::StackTrace> stackTrace(v8::StackTrace::CurrentStackTrace(isolate, maxStackSize, stackTraceOptions));
return createScriptCallStack(stackTrace, maxStackSize, emptyStackIsAllowed, isolate);
}
-PassRefPtr<ScriptCallStack> createScriptCallStackForConsole(size_t maxStackSize)
+PassRefPtrWillBeRawPtr<ScriptCallStack> createScriptCallStackForConsole(ScriptState* scriptState, size_t maxStackSize)
{
size_t stackSize = 1;
if (InspectorInstrumentation::hasFrontends()) {
- ExecutionContext* executionContext = getExecutionContext();
- if (InspectorInstrumentation::consoleAgentEnabled(executionContext))
+ if (InspectorInstrumentation::consoleAgentEnabled(scriptState->executionContext()))
stackSize = maxStackSize;
}
return createScriptCallStack(stackSize);
}
-PassRefPtr<ScriptArguments> createScriptArguments(const v8::FunctionCallbackInfo<v8::Value>& v8arguments, unsigned skipArgumentCount)
+PassRefPtrWillBeRawPtr<ScriptArguments> createScriptArguments(ScriptState* scriptState, const v8::FunctionCallbackInfo<v8::Value>& v8arguments, unsigned skipArgumentCount)
{
- v8::Isolate* isolate = v8arguments.GetIsolate();
- v8::HandleScope scope(isolate);
- v8::Local<v8::Context> context = isolate->GetCurrentContext();
- ScriptState* state = ScriptState::forContext(context);
-
Vector<ScriptValue> arguments;
for (int i = skipArgumentCount; i < v8arguments.Length(); ++i)
- arguments.append(ScriptValue(v8arguments[i], isolate));
+ arguments.append(ScriptValue(scriptState, v8arguments[i]));
- return ScriptArguments::create(state, arguments);
+ return ScriptArguments::create(scriptState, arguments);
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ScriptCallStackFactory.h b/chromium/third_party/WebKit/Source/bindings/v8/ScriptCallStackFactory.h
index ff225e30714..6654b67aab6 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/ScriptCallStackFactory.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ScriptCallStackFactory.h
@@ -48,10 +48,10 @@ const v8::StackTrace::StackTraceOptions stackTraceOptions = static_cast<v8::Stac
| v8::StackTrace::kScriptNameOrSourceURL
| v8::StackTrace::kFunctionName);
-PassRefPtr<ScriptCallStack> createScriptCallStack(v8::Handle<v8::StackTrace>, size_t maxStackSize, v8::Isolate*);
-PassRefPtr<ScriptCallStack> createScriptCallStack(size_t maxStackSize, bool emptyStackIsAllowed = false);
-PassRefPtr<ScriptCallStack> createScriptCallStackForConsole(size_t maxStackSize = ScriptCallStack::maxCallStackSizeToCapture);
-PassRefPtr<ScriptArguments> createScriptArguments(const v8::FunctionCallbackInfo<v8::Value>& v8arguments, unsigned skipArgumentCount);
+PassRefPtrWillBeRawPtr<ScriptCallStack> createScriptCallStack(v8::Handle<v8::StackTrace>, size_t maxStackSize, v8::Isolate*);
+PassRefPtrWillBeRawPtr<ScriptCallStack> createScriptCallStack(size_t maxStackSize, bool emptyStackIsAllowed = false);
+PassRefPtrWillBeRawPtr<ScriptCallStack> createScriptCallStackForConsole(ScriptState*, size_t maxStackSize = ScriptCallStack::maxCallStackSizeToCapture);
+PassRefPtrWillBeRawPtr<ScriptArguments> createScriptArguments(ScriptState*, const v8::FunctionCallbackInfo<v8::Value>& v8arguments, unsigned skipArgumentCount);
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ScriptController.cpp b/chromium/third_party/WebKit/Source/bindings/v8/ScriptController.cpp
index b60a5c74cca..d7049069670 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/ScriptController.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ScriptController.cpp
@@ -32,9 +32,9 @@
#include "config.h"
#include "bindings/v8/ScriptController.h"
-#include "V8Event.h"
-#include "V8HTMLElement.h"
-#include "V8Window.h"
+#include "bindings/core/v8/V8Event.h"
+#include "bindings/core/v8/V8HTMLElement.h"
+#include "bindings/core/v8/V8Window.h"
#include "bindings/v8/BindingSecurity.h"
#include "bindings/v8/NPV8Object.h"
#include "bindings/v8/ScriptCallStackFactory.h"
@@ -42,7 +42,6 @@
#include "bindings/v8/ScriptValue.h"
#include "bindings/v8/V8Binding.h"
#include "bindings/v8/V8GCController.h"
-#include "bindings/v8/V8HiddenPropertyName.h"
#include "bindings/v8/V8NPObject.h"
#include "bindings/v8/V8PerContextData.h"
#include "bindings/v8/V8ScriptRunner.h"
@@ -54,17 +53,17 @@
#include "core/dom/ScriptableDocumentParser.h"
#include "core/events/Event.h"
#include "core/events/EventListener.h"
-#include "core/events/ThreadLocalEventNames.h"
+#include "core/frame/LocalDOMWindow.h"
+#include "core/frame/LocalFrame.h"
+#include "core/frame/Settings.h"
+#include "core/frame/csp/ContentSecurityPolicy.h"
#include "core/html/HTMLPlugInElement.h"
#include "core/inspector/InspectorInstrumentation.h"
+#include "core/inspector/InspectorTraceEvents.h"
#include "core/inspector/ScriptCallStack.h"
#include "core/loader/DocumentLoader.h"
#include "core/loader/FrameLoader.h"
#include "core/loader/FrameLoaderClient.h"
-#include "core/frame/ContentSecurityPolicy.h"
-#include "core/frame/DOMWindow.h"
-#include "core/frame/Frame.h"
-#include "core/frame/Settings.h"
#include "core/plugins/PluginView.h"
#include "platform/NotImplemented.h"
#include "platform/TraceEvent.h"
@@ -81,23 +80,27 @@
namespace WebCore {
-bool ScriptController::canAccessFromCurrentOrigin(Frame *frame)
+bool ScriptController::canAccessFromCurrentOrigin(LocalFrame *frame)
{
- return !v8::Isolate::GetCurrent()->InContext() || BindingSecurity::shouldAllowAccessToFrame(frame);
+ if (!frame)
+ return false;
+ v8::Isolate* isolate = toIsolate(frame);
+ return !isolate->InContext() || BindingSecurity::shouldAllowAccessToFrame(isolate, frame);
}
-ScriptController::ScriptController(Frame* frame)
+ScriptController::ScriptController(LocalFrame* frame)
: m_frame(frame)
, m_sourceURL(0)
, m_isolate(v8::Isolate::GetCurrent())
- , m_windowShell(V8WindowShell::create(frame, mainThreadNormalWorld(), m_isolate))
+ , m_windowShell(V8WindowShell::create(frame, DOMWrapperWorld::mainWorld(), m_isolate))
, m_windowScriptNPObject(0)
{
}
ScriptController::~ScriptController()
{
- clearForClose(true);
+ // V8WindowShell::clearForClose() must be invoked before destruction starts.
+ ASSERT(!m_windowShell->isContextInitialized());
}
void ScriptController::clearScriptObjects()
@@ -120,61 +123,39 @@ void ScriptController::clearScriptObjects()
}
}
-void ScriptController::clearForOutOfMemory()
-{
- clearForClose(true);
-}
-
-void ScriptController::clearForClose(bool destroyGlobal)
-{
- m_windowShell->clearForClose(destroyGlobal);
- for (IsolatedWorldMap::iterator iter = m_isolatedWorlds.begin(); iter != m_isolatedWorlds.end(); ++iter)
- iter->value->clearForClose(destroyGlobal);
- V8GCController::hintForCollectGarbage();
-}
-
void ScriptController::clearForClose()
{
double start = currentTime();
- clearForClose(false);
+ m_windowShell->clearForClose();
+ for (IsolatedWorldMap::iterator iter = m_isolatedWorlds.begin(); iter != m_isolatedWorlds.end(); ++iter)
+ iter->value->clearForClose();
blink::Platform::current()->histogramCustomCounts("WebCore.ScriptController.clearForClose", (currentTime() - start) * 1000, 0, 10000, 50);
}
-void ScriptController::updateSecurityOrigin()
+void ScriptController::updateSecurityOrigin(SecurityOrigin* origin)
{
- m_windowShell->updateSecurityOrigin();
+ m_windowShell->updateSecurityOrigin(origin);
}
-v8::Local<v8::Value> ScriptController::callFunction(v8::Handle<v8::Function> function, v8::Handle<v8::Object> receiver, int argc, v8::Handle<v8::Value> info[])
+v8::Local<v8::Value> ScriptController::callFunction(v8::Handle<v8::Function> function, v8::Handle<v8::Value> receiver, int argc, v8::Handle<v8::Value> info[])
{
- // Keep Frame (and therefore ScriptController) alive.
- RefPtr<Frame> protect(m_frame);
+ // Keep LocalFrame (and therefore ScriptController) alive.
+ RefPtr<LocalFrame> protect(m_frame);
return ScriptController::callFunction(m_frame->document(), function, receiver, argc, info, m_isolate);
}
-static bool resourceInfo(const v8::Handle<v8::Function> function, String& resourceName, int& lineNumber)
-{
- v8::ScriptOrigin origin = function->GetScriptOrigin();
- if (origin.ResourceName().IsEmpty()) {
- resourceName = "undefined";
- lineNumber = 1;
- } else {
- V8TRYCATCH_FOR_V8STRINGRESOURCE_RETURN(V8StringResource<>, stringResourceName, origin.ResourceName(), false);
- resourceName = stringResourceName;
- lineNumber = function->GetScriptLineNumber() + 1;
- }
- return true;
-}
-
-v8::Local<v8::Value> ScriptController::callFunction(ExecutionContext* context, v8::Handle<v8::Function> function, v8::Handle<v8::Object> receiver, int argc, v8::Handle<v8::Value> info[], v8::Isolate* isolate)
+v8::Local<v8::Value> ScriptController::callFunction(ExecutionContext* context, v8::Handle<v8::Function> function, v8::Handle<v8::Value> receiver, int argc, v8::Handle<v8::Value> info[], v8::Isolate* isolate)
{
+ TRACE_EVENT1(TRACE_DISABLED_BY_DEFAULT("devtools.timeline"), "FunctionCall", "data", devToolsTraceEventData(context, function, isolate));
+ TRACE_EVENT_INSTANT1(TRACE_DISABLED_BY_DEFAULT("devtools.timeline.stack"), "CallStack", "stack", InspectorCallStackEvent::currentCallStack());
+ // FIXME(361045): remove InspectorInstrumentation calls once DevTools Timeline migrates to tracing.
InspectorInstrumentationCookie cookie;
if (InspectorInstrumentation::timelineAgentEnabled(context)) {
+ int scriptId = 0;
String resourceName;
- int lineNumber;
- if (!resourceInfo(function, resourceName, lineNumber))
- return v8::Local<v8::Value>();
- cookie = InspectorInstrumentation::willCallFunction(context, resourceName, lineNumber);
+ int lineNumber = 1;
+ GetDevToolsFunctionInfo(function, isolate, scriptId, resourceName, lineNumber);
+ cookie = InspectorInstrumentation::willCallFunction(context, scriptId, resourceName, lineNumber);
}
v8::Local<v8::Value> result = V8ScriptRunner::callFunction(function, context, receiver, argc, info, isolate);
@@ -185,9 +166,10 @@ v8::Local<v8::Value> ScriptController::callFunction(ExecutionContext* context, v
v8::Local<v8::Value> ScriptController::executeScriptAndReturnValue(v8::Handle<v8::Context> context, const ScriptSourceCode& source, AccessControlStatus corsStatus)
{
- v8::Context::Scope scope(context);
-
- InspectorInstrumentationCookie cookie = InspectorInstrumentation::willEvaluateScript(m_frame, source.url().isNull() ? String() : source.url().string(), source.startLine());
+ TRACE_EVENT1(TRACE_DISABLED_BY_DEFAULT("devtools.timeline"), "EvaluateScript", "data", InspectorEvaluateScriptEvent::data(m_frame, source.url().string(), source.startLine()));
+ TRACE_EVENT_INSTANT1(TRACE_DISABLED_BY_DEFAULT("devtools.timeline.stack"), "CallStack", "stack", InspectorCallStackEvent::currentCallStack());
+ // FIXME(361045): remove InspectorInstrumentation calls once DevTools Timeline migrates to tracing.
+ InspectorInstrumentationCookie cookie = InspectorInstrumentation::willEvaluateScript(m_frame, source.url().string(), source.startLine());
v8::Local<v8::Value> result;
{
@@ -198,20 +180,16 @@ v8::Local<v8::Value> ScriptController::executeScriptAndReturnValue(v8::Handle<v8
v8::TryCatch tryCatch;
tryCatch.SetVerbose(true);
- v8::Handle<v8::String> code = v8String(m_isolate, source.source());
- OwnPtr<v8::ScriptData> scriptData = V8ScriptRunner::precompileScript(code, source.resource());
+ v8::Handle<v8::Script> script = V8ScriptRunner::compileScript(source, m_isolate, corsStatus);
- // NOTE: For compatibility with WebCore, ScriptSourceCode's line starts at
- // 1, whereas v8 starts at 0.
- v8::Handle<v8::Script> script = V8ScriptRunner::compileScript(code, source.url(), source.startPosition(), scriptData.get(), m_isolate, corsStatus);
-
- // Keep Frame (and therefore ScriptController) alive.
- RefPtr<Frame> protect(m_frame);
+ // Keep LocalFrame (and therefore ScriptController) alive.
+ RefPtr<LocalFrame> protect(m_frame);
result = V8ScriptRunner::runCompiledScript(script, m_frame->document(), m_isolate);
ASSERT(!tryCatch.HasCaught() || result.IsEmpty());
}
InspectorInstrumentation::didEvaluateScript(cookie);
+ TRACE_EVENT_INSTANT1(TRACE_DISABLED_BY_DEFAULT("devtools.timeline"), "UpdateCounters", "data", InspectorUpdateCountersEvent::data());
return result;
}
@@ -220,59 +198,47 @@ bool ScriptController::initializeMainWorld()
{
if (m_windowShell->isContextInitialized())
return false;
- return windowShell(mainThreadNormalWorld())->isContextInitialized();
+ return windowShell(DOMWrapperWorld::mainWorld())->isContextInitialized();
}
-V8WindowShell* ScriptController::existingWindowShell(DOMWrapperWorld* world)
+V8WindowShell* ScriptController::existingWindowShell(DOMWrapperWorld& world)
{
- ASSERT(world);
-
- if (world->isMainWorld())
+ if (world.isMainWorld())
return m_windowShell->isContextInitialized() ? m_windowShell.get() : 0;
- // FIXME: Remove this block. See comment with existingWindowShellWorkaroundWorld().
- if (world == existingWindowShellWorkaroundWorld())
- return m_windowShell.get();
-
- IsolatedWorldMap::iterator iter = m_isolatedWorlds.find(world->worldId());
+ IsolatedWorldMap::iterator iter = m_isolatedWorlds.find(world.worldId());
if (iter == m_isolatedWorlds.end())
return 0;
return iter->value->isContextInitialized() ? iter->value.get() : 0;
}
-V8WindowShell* ScriptController::windowShell(DOMWrapperWorld* world)
+V8WindowShell* ScriptController::windowShell(DOMWrapperWorld& world)
{
- ASSERT(world);
-
V8WindowShell* shell = 0;
- if (world->isMainWorld())
+ if (world.isMainWorld())
shell = m_windowShell.get();
else {
- IsolatedWorldMap::iterator iter = m_isolatedWorlds.find(world->worldId());
+ IsolatedWorldMap::iterator iter = m_isolatedWorlds.find(world.worldId());
if (iter != m_isolatedWorlds.end())
shell = iter->value.get();
else {
OwnPtr<V8WindowShell> isolatedWorldShell = V8WindowShell::create(m_frame, world, m_isolate);
shell = isolatedWorldShell.get();
- m_isolatedWorlds.set(world->worldId(), isolatedWorldShell.release());
- }
- }
- if (!shell->isContextInitialized() && shell->initializeIfNeeded()) {
- if (world->isMainWorld()) {
- // FIXME: Remove this if clause. See comment with existingWindowShellWorkaroundWorld().
- m_frame->loader().dispatchDidClearWindowObjectInWorld(existingWindowShellWorkaroundWorld());
- } else {
- m_frame->loader().dispatchDidClearWindowObjectInWorld(world);
+ m_isolatedWorlds.set(world.worldId(), isolatedWorldShell.release());
}
}
+ if (!shell->isContextInitialized() && shell->initializeIfNeeded() && world.isMainWorld())
+ m_frame->loader().dispatchDidClearWindowObjectInMainWorld();
return shell;
}
bool ScriptController::shouldBypassMainWorldContentSecurityPolicy()
{
- if (DOMWrapperWorld* world = isolatedWorldForEnteredContext(m_isolate))
- return world->isolatedWorldHasContentSecurityPolicy();
- return false;
+ v8::Handle<v8::Context> context = m_isolate->GetCurrentContext();
+ if (context.IsEmpty() || !toDOMWindow(context))
+ return false;
+ DOMWrapperWorld& world = DOMWrapperWorld::current(m_isolate);
+ return world.isIsolatedWorld() ? world.isolatedWorldHasContentSecurityPolicy() : false;
}
TextPosition ScriptController::eventHandlerPosition() const
@@ -283,57 +249,18 @@ TextPosition ScriptController::eventHandlerPosition() const
return TextPosition::minimumPosition();
}
-static inline v8::Local<v8::Context> contextForWorld(ScriptController& scriptController, DOMWrapperWorld* world)
-{
- return scriptController.windowShell(world)->context();
-}
-
-v8::Local<v8::Context> ScriptController::currentWorldContext()
-{
- if (!isolate()->InContext())
- return contextForWorld(*this, mainThreadNormalWorld());
-
- v8::Handle<v8::Context> context = isolate()->GetEnteredContext();
- DOMWrapperWorld* isolatedWorld = DOMWrapperWorld::isolatedWorld(context);
- if (!isolatedWorld)
- return contextForWorld(*this, mainThreadNormalWorld());
-
- Frame* frame = toFrameIfNotDetached(context);
- if (m_frame == frame)
- return v8::Local<v8::Context>::New(m_isolate, context);
-
- return contextForWorld(*this, isolatedWorld);
-}
-
-v8::Local<v8::Context> ScriptController::mainWorldContext()
-{
- return contextForWorld(*this, mainThreadNormalWorld());
-}
-
-v8::Local<v8::Context> ScriptController::mainWorldContext(Frame* frame)
-{
- if (!frame)
- return v8::Local<v8::Context>();
-
- return contextForWorld(frame->script(), mainThreadNormalWorld());
-}
-
// Create a V8 object with an interceptor of NPObjectPropertyGetter.
-void ScriptController::bindToWindowObject(Frame* frame, const String& key, NPObject* object)
+void ScriptController::bindToWindowObject(LocalFrame* frame, const String& key, NPObject* object)
{
- v8::HandleScope handleScope(m_isolate);
-
- v8::Handle<v8::Context> v8Context = ScriptController::mainWorldContext(frame);
- if (v8Context.IsEmpty())
+ ScriptState* scriptState = ScriptState::forMainWorld(frame);
+ if (scriptState->contextIsEmpty())
return;
- v8::Context::Scope scope(v8Context);
-
+ ScriptState::Scope scope(scriptState);
v8::Handle<v8::Object> value = createV8ObjectForNPObject(object, 0, m_isolate);
// Attach to the global object.
- v8::Handle<v8::Object> global = v8Context->Global();
- global->Set(v8String(m_isolate, key), value);
+ scriptState->context()->Global()->Set(v8String(m_isolate, key), value);
}
void ScriptController::enableEval()
@@ -359,13 +286,13 @@ PassRefPtr<SharedPersistent<v8::Object> > ScriptController::createPluginWrapper(
ASSERT(widget);
if (!widget->isPluginView())
- return 0;
+ return nullptr;
NPObject* npObject = toPluginView(widget)->scriptableObject();
if (!npObject)
- return 0;
+ return nullptr;
- // Frame Memory Management for NPObjects
+ // LocalFrame Memory Management for NPObjects
// -------------------------------------
// NPObjects are treated differently than other objects wrapped by JS.
// NPObjects can be created either by the browser (e.g. the main
@@ -374,7 +301,7 @@ PassRefPtr<SharedPersistent<v8::Object> > ScriptController::createPluginWrapper(
// is especially careful to ensure NPObjects terminate at frame teardown because
// if a plugin leaks a reference, it could leak its objects (or the browser's objects).
//
- // The Frame maintains a list of plugin objects (m_pluginObjects)
+ // The LocalFrame maintains a list of plugin objects (m_pluginObjects)
// which it can use to quickly find the wrapped embed object.
//
// Inside the NPRuntime, we've added a few methods for registering
@@ -430,18 +357,16 @@ static NPObject* createNoScriptObject()
return 0;
}
-static NPObject* createScriptObject(Frame* frame, v8::Isolate* isolate)
+static NPObject* createScriptObject(LocalFrame* frame, v8::Isolate* isolate)
{
- v8::HandleScope handleScope(isolate);
- v8::Handle<v8::Context> v8Context = ScriptController::mainWorldContext(frame);
- if (v8Context.IsEmpty())
+ ScriptState* scriptState = ScriptState::forMainWorld(frame);
+ if (scriptState->contextIsEmpty())
return createNoScriptObject();
- v8::Context::Scope scope(v8Context);
- DOMWindow* window = frame->domWindow();
- v8::Handle<v8::Value> global = toV8(window, v8::Handle<v8::Object>(), v8Context->GetIsolate());
+ ScriptState::Scope scope(scriptState);
+ LocalDOMWindow* window = frame->domWindow();
+ v8::Handle<v8::Value> global = toV8(window, scriptState->context()->Global(), scriptState->isolate());
ASSERT(global->IsObject());
-
return npCreateV8ScriptObject(0, v8::Handle<v8::Object>::Cast(global), window, isolate);
}
@@ -470,18 +395,17 @@ NPObject* ScriptController::createScriptObjectForPluginElement(HTMLPlugInElement
if (!canExecuteScripts(NotAboutToExecuteScript))
return createNoScriptObject();
- v8::HandleScope handleScope(m_isolate);
- v8::Handle<v8::Context> v8Context = ScriptController::mainWorldContext(m_frame);
- if (v8Context.IsEmpty())
+ ScriptState* scriptState = ScriptState::forMainWorld(m_frame);
+ if (scriptState->contextIsEmpty())
return createNoScriptObject();
- v8::Context::Scope scope(v8Context);
- DOMWindow* window = m_frame->domWindow();
- v8::Handle<v8::Value> v8plugin = toV8(plugin, v8::Handle<v8::Object>(), v8Context->GetIsolate());
+ ScriptState::Scope scope(scriptState);
+ LocalDOMWindow* window = m_frame->domWindow();
+ v8::Handle<v8::Value> v8plugin = toV8(plugin, scriptState->context()->Global(), scriptState->isolate());
if (!v8plugin->IsObject())
return createNoScriptObject();
- return npCreateV8ScriptObject(0, v8::Handle<v8::Object>::Cast(v8plugin), window, v8Context->GetIsolate());
+ return npCreateV8ScriptObject(0, v8::Handle<v8::Object>::Cast(v8plugin), window, scriptState->isolate());
}
void ScriptController::clearWindowShell()
@@ -492,7 +416,7 @@ void ScriptController::clearWindowShell()
m_windowShell->clearForNavigation();
for (IsolatedWorldMap::iterator iter = m_isolatedWorlds.begin(); iter != m_isolatedWorlds.end(); ++iter)
iter->value->clearForNavigation();
- V8GCController::hintForCollectGarbage();
+ clearScriptObjects();
blink::Platform::current()->histogramCustomCounts("WebCore.ScriptController.clearWindowShell", (currentTime() - start) * 1000, 0, 10000, 50);
}
@@ -503,17 +427,14 @@ void ScriptController::setCaptureCallStackForUncaughtExceptions(bool value)
void ScriptController::collectIsolatedContexts(Vector<std::pair<ScriptState*, SecurityOrigin*> >& result)
{
- v8::HandleScope handleScope(m_isolate);
for (IsolatedWorldMap::iterator it = m_isolatedWorlds.begin(); it != m_isolatedWorlds.end(); ++it) {
V8WindowShell* isolatedWorldShell = it->value.get();
- SecurityOrigin* origin = isolatedWorldShell->world()->isolatedWorldSecurityOrigin();
+ SecurityOrigin* origin = isolatedWorldShell->world().isolatedWorldSecurityOrigin();
if (!origin)
continue;
- v8::Local<v8::Context> v8Context = isolatedWorldShell->context();
- if (v8Context.IsEmpty())
+ if (!isolatedWorldShell->isContextInitialized())
continue;
- ScriptState* scriptState = ScriptState::forContext(v8Context);
- result.append(std::pair<ScriptState*, SecurityOrigin*>(scriptState, origin));
+ result.append(std::pair<ScriptState*, SecurityOrigin*>(isolatedWorldShell->scriptState(), origin));
}
}
@@ -534,22 +455,22 @@ int ScriptController::contextDebugId(v8::Handle<v8::Context> context)
void ScriptController::updateDocument()
{
- // For an uninitialized main window shell, do not incur the cost of context initialization during FrameLoader::init().
- if ((!m_windowShell->isContextInitialized() || !m_windowShell->isGlobalInitialized()) && m_frame->loader().stateMachine()->creatingInitialEmptyDocument())
+ // For an uninitialized main window shell, do not incur the cost of context initialization.
+ if (!m_windowShell->isGlobalInitialized())
return;
if (!initializeMainWorld())
- windowShell(mainThreadNormalWorld())->updateDocument();
+ windowShell(DOMWrapperWorld::mainWorld())->updateDocument();
}
void ScriptController::namedItemAdded(HTMLDocument* doc, const AtomicString& name)
{
- windowShell(mainThreadNormalWorld())->namedItemAdded(doc, name);
+ windowShell(DOMWrapperWorld::mainWorld())->namedItemAdded(doc, name);
}
void ScriptController::namedItemRemoved(HTMLDocument* doc, const AtomicString& name)
{
- windowShell(mainThreadNormalWorld())->namedItemRemoved(doc, name);
+ windowShell(DOMWrapperWorld::mainWorld())->namedItemRemoved(doc, name);
}
bool ScriptController::canExecuteScripts(ReasonForCallingCanExecuteScripts reason)
@@ -567,7 +488,7 @@ bool ScriptController::canExecuteScripts(ReasonForCallingCanExecuteScripts reaso
}
Settings* settings = m_frame->settings();
- const bool allowed = m_frame->loader().client()->allowScript(settings && settings->isScriptEnabled());
+ const bool allowed = m_frame->loader().client()->allowScript(settings && settings->scriptEnabled());
if (!allowed && reason == AboutToExecuteScript)
m_frame->loader().client()->didNotAllowScript();
return allowed;
@@ -582,30 +503,30 @@ bool ScriptController::executeScriptIfJavaScriptURL(const KURL& url)
|| !m_frame->document()->contentSecurityPolicy()->allowJavaScriptURLs(m_frame->document()->url(), eventHandlerPosition().m_line))
return true;
- // We need to hold onto the Frame here because executing script can
+ // We need to hold onto the LocalFrame here because executing script can
// destroy the frame.
- RefPtr<Frame> protector(m_frame);
- RefPtr<Document> ownerDocument(m_frame->document());
+ RefPtr<LocalFrame> protector(m_frame);
+ RefPtrWillBeRawPtr<Document> ownerDocument(m_frame->document());
const int javascriptSchemeLength = sizeof("javascript:") - 1;
bool locationChangeBefore = m_frame->navigationScheduler().locationChangePending();
String decodedURL = decodeURLEscapeSequences(url.string());
- ScriptValue result = evaluateScriptInMainWorld(ScriptSourceCode(decodedURL.substring(javascriptSchemeLength)), NotSharableCrossOrigin, DoNotExecuteScriptWhenScriptsDisabled);
+ v8::HandleScope handleScope(m_isolate);
+ v8::Local<v8::Value> result = evaluateScriptInMainWorld(ScriptSourceCode(decodedURL.substring(javascriptSchemeLength)), NotSharableCrossOrigin, DoNotExecuteScriptWhenScriptsDisabled);
// If executing script caused this frame to be removed from the page, we
// don't want to try to replace its document!
if (!m_frame->page())
return true;
- String scriptResult;
- if (!result.getString(scriptResult))
+ if (result.IsEmpty() || !result->IsString())
return true;
+ String scriptResult = toCoreString(v8::Handle<v8::String>::Cast(result));
// We're still in a frame, so there should be a DocumentLoader.
ASSERT(m_frame->document()->loader());
-
if (!locationChangeBefore && m_frame->navigationScheduler().locationChangePending())
return true;
@@ -620,80 +541,77 @@ bool ScriptController::executeScriptIfJavaScriptURL(const KURL& url)
void ScriptController::executeScriptInMainWorld(const String& script, ExecuteScriptPolicy policy)
{
+ v8::HandleScope handleScope(m_isolate);
evaluateScriptInMainWorld(ScriptSourceCode(script), NotSharableCrossOrigin, policy);
}
void ScriptController::executeScriptInMainWorld(const ScriptSourceCode& sourceCode, AccessControlStatus corsStatus)
{
+ v8::HandleScope handleScope(m_isolate);
evaluateScriptInMainWorld(sourceCode, corsStatus, DoNotExecuteScriptWhenScriptsDisabled);
}
-ScriptValue ScriptController::executeScriptInMainWorldAndReturnValue(const ScriptSourceCode& sourceCode)
+v8::Local<v8::Value> ScriptController::executeScriptInMainWorldAndReturnValue(const ScriptSourceCode& sourceCode)
{
return evaluateScriptInMainWorld(sourceCode, NotSharableCrossOrigin, DoNotExecuteScriptWhenScriptsDisabled);
}
-ScriptValue ScriptController::evaluateScriptInMainWorld(const ScriptSourceCode& sourceCode, AccessControlStatus corsStatus, ExecuteScriptPolicy policy)
+v8::Local<v8::Value> ScriptController::evaluateScriptInMainWorld(const ScriptSourceCode& sourceCode, AccessControlStatus corsStatus, ExecuteScriptPolicy policy)
{
if (policy == DoNotExecuteScriptWhenScriptsDisabled && !canExecuteScripts(AboutToExecuteScript))
- return ScriptValue();
+ return v8::Local<v8::Value>();
String sourceURL = sourceCode.url();
const String* savedSourceURL = m_sourceURL;
m_sourceURL = &sourceURL;
- v8::HandleScope handleScope(m_isolate);
- v8::Handle<v8::Context> v8Context = ScriptController::mainWorldContext(m_frame);
- if (v8Context.IsEmpty())
- return ScriptValue();
+ ScriptState* scriptState = ScriptState::forMainWorld(m_frame);
+ if (scriptState->contextIsEmpty())
+ return v8::Local<v8::Value>();
+
+ v8::EscapableHandleScope handleScope(scriptState->isolate());
+ ScriptState::Scope scope(scriptState);
- RefPtr<Frame> protect(m_frame);
+ RefPtr<LocalFrame> protect(m_frame);
if (m_frame->loader().stateMachine()->isDisplayingInitialEmptyDocument())
m_frame->loader().didAccessInitialDocument();
OwnPtr<ScriptSourceCode> maybeProcessedSourceCode = InspectorInstrumentation::preprocess(m_frame, sourceCode);
const ScriptSourceCode& sourceCodeToCompile = maybeProcessedSourceCode ? *maybeProcessedSourceCode : sourceCode;
- v8::Local<v8::Value> object = executeScriptAndReturnValue(v8Context, sourceCodeToCompile, corsStatus);
+ v8::Local<v8::Value> object = executeScriptAndReturnValue(scriptState->context(), sourceCodeToCompile, corsStatus);
m_sourceURL = savedSourceURL;
if (object.IsEmpty())
- return ScriptValue();
+ return v8::Local<v8::Value>();
- return ScriptValue(object, m_isolate);
+ return handleScope.Escape(object);
}
-void ScriptController::executeScriptInIsolatedWorld(int worldID, const Vector<ScriptSourceCode>& sources, int extensionGroup, Vector<ScriptValue>* results)
+void ScriptController::executeScriptInIsolatedWorld(int worldID, const Vector<ScriptSourceCode>& sources, int extensionGroup, Vector<v8::Local<v8::Value> >* results)
{
ASSERT(worldID > 0);
- v8::HandleScope handleScope(m_isolate);
- v8::Local<v8::Array> v8Results;
- {
- v8::EscapableHandleScope evaluateHandleScope(m_isolate);
- RefPtr<DOMWrapperWorld> world = DOMWrapperWorld::ensureIsolatedWorld(worldID, extensionGroup);
- V8WindowShell* isolatedWorldShell = windowShell(world.get());
-
- if (!isolatedWorldShell->isContextInitialized())
- return;
-
- v8::Local<v8::Context> context = isolatedWorldShell->context();
- v8::Context::Scope contextScope(context);
- v8::Local<v8::Array> resultArray = v8::Array::New(m_isolate, sources.size());
+ RefPtr<DOMWrapperWorld> world = DOMWrapperWorld::ensureIsolatedWorld(worldID, extensionGroup);
+ V8WindowShell* isolatedWorldShell = windowShell(*world);
+ if (!isolatedWorldShell->isContextInitialized())
+ return;
- for (size_t i = 0; i < sources.size(); ++i) {
- v8::Local<v8::Value> evaluationResult = executeScriptAndReturnValue(context, sources[i]);
- if (evaluationResult.IsEmpty())
- evaluationResult = v8::Local<v8::Value>::New(m_isolate, v8::Undefined(m_isolate));
- resultArray->Set(i, evaluationResult);
- }
+ ScriptState* scriptState = isolatedWorldShell->scriptState();
+ v8::EscapableHandleScope handleScope(scriptState->isolate());
+ ScriptState::Scope scope(scriptState);
+ v8::Local<v8::Array> resultArray = v8::Array::New(m_isolate, sources.size());
- v8Results = evaluateHandleScope.Escape(resultArray);
+ for (size_t i = 0; i < sources.size(); ++i) {
+ v8::Local<v8::Value> evaluationResult = executeScriptAndReturnValue(scriptState->context(), sources[i]);
+ if (evaluationResult.IsEmpty())
+ evaluationResult = v8::Local<v8::Value>::New(m_isolate, v8::Undefined(m_isolate));
+ resultArray->Set(i, evaluationResult);
}
- if (results && !v8Results.IsEmpty()) {
- for (size_t i = 0; i < v8Results->Length(); ++i)
- results->append(ScriptValue(v8Results->Get(i), m_isolate));
+ if (results) {
+ for (size_t i = 0; i < resultArray->Length(); ++i)
+ results->append(handleScope.Escape(resultArray->Get(i)));
}
}
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ScriptController.h b/chromium/third_party/WebKit/Source/bindings/v8/ScriptController.h
index 83793c7a96a..3da4d2c6662 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/ScriptController.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ScriptController.h
@@ -49,12 +49,12 @@ namespace WebCore {
class DOMWrapperWorld;
class ExecutionContext;
class Event;
-class Frame;
class HTMLDocument;
class HTMLPlugInElement;
class KURL;
-class ScriptSourceCode;
+class LocalFrame;
class ScriptState;
+class ScriptSourceCode;
class SecurityOrigin;
class V8WindowShell;
class Widget;
@@ -73,17 +73,17 @@ public:
DoNotExecuteScriptWhenScriptsDisabled
};
- ScriptController(Frame*);
+ ScriptController(LocalFrame*);
~ScriptController();
bool initializeMainWorld();
- V8WindowShell* windowShell(DOMWrapperWorld*);
- V8WindowShell* existingWindowShell(DOMWrapperWorld*);
+ V8WindowShell* windowShell(DOMWrapperWorld&);
+ V8WindowShell* existingWindowShell(DOMWrapperWorld&);
// Evaluate JavaScript in the main world.
void executeScriptInMainWorld(const String&, ExecuteScriptPolicy = DoNotExecuteScriptWhenScriptsDisabled);
void executeScriptInMainWorld(const ScriptSourceCode&, AccessControlStatus = NotSharableCrossOrigin);
- ScriptValue executeScriptInMainWorldAndReturnValue(const ScriptSourceCode&);
+ v8::Local<v8::Value> executeScriptInMainWorldAndReturnValue(const ScriptSourceCode&);
v8::Local<v8::Value> executeScriptAndReturnValue(v8::Handle<v8::Context>, const ScriptSourceCode&, AccessControlStatus = NotSharableCrossOrigin);
// Executes JavaScript in an isolated world. The script gets its own global scope,
@@ -94,13 +94,13 @@ public:
// Otherwise, a new world is created.
//
// FIXME: Get rid of extensionGroup here.
- void executeScriptInIsolatedWorld(int worldID, const Vector<ScriptSourceCode>& sources, int extensionGroup, Vector<ScriptValue>* results);
+ void executeScriptInIsolatedWorld(int worldID, const Vector<ScriptSourceCode>& sources, int extensionGroup, Vector<v8::Local<v8::Value> >* results);
// Returns true if argument is a JavaScript URL.
bool executeScriptIfJavaScriptURL(const KURL&);
- v8::Local<v8::Value> callFunction(v8::Handle<v8::Function>, v8::Handle<v8::Object>, int argc, v8::Handle<v8::Value> argv[]);
- static v8::Local<v8::Value> callFunction(ExecutionContext*, v8::Handle<v8::Function>, v8::Handle<v8::Object> receiver, int argc, v8::Handle<v8::Value> info[], v8::Isolate*);
+ v8::Local<v8::Value> callFunction(v8::Handle<v8::Function>, v8::Handle<v8::Value>, int argc, v8::Handle<v8::Value> argv[]);
+ static v8::Local<v8::Value> callFunction(ExecutionContext*, v8::Handle<v8::Function>, v8::Handle<v8::Value> receiver, int argc, v8::Handle<v8::Value> info[], v8::Isolate*);
// Returns true if the current world is isolated, and has its own Content
// Security Policy. In this case, the policy of the main world should be
@@ -108,42 +108,33 @@ public:
bool shouldBypassMainWorldContentSecurityPolicy();
// Creates a property of the global object of a frame.
- void bindToWindowObject(Frame*, const String& key, NPObject*);
+ void bindToWindowObject(LocalFrame*, const String& key, NPObject*);
PassRefPtr<SharedPersistent<v8::Object> > createPluginWrapper(Widget*);
void enableEval();
void disableEval(const String& errorMessage);
- static bool canAccessFromCurrentOrigin(Frame*);
+ static bool canAccessFromCurrentOrigin(LocalFrame*);
static void setCaptureCallStackForUncaughtExceptions(bool);
void collectIsolatedContexts(Vector<std::pair<ScriptState*, SecurityOrigin*> >&);
bool canExecuteScripts(ReasonForCallingCanExecuteScripts);
- // Returns V8 Context. If none exists, creates a new context.
- // It is potentially slow and consumes memory.
- static v8::Local<v8::Context> mainWorldContext(Frame*);
- v8::Local<v8::Context> mainWorldContext();
- v8::Local<v8::Context> currentWorldContext();
-
TextPosition eventHandlerPosition() const;
- const String* sourceURL() const { return m_sourceURL; } // 0 if we are not evaluating any script.
-
void clearWindowShell();
void updateDocument();
void namedItemAdded(HTMLDocument*, const AtomicString&);
void namedItemRemoved(HTMLDocument*, const AtomicString&);
- void updateSecurityOrigin();
+ void updateSecurityOrigin(SecurityOrigin*);
void clearScriptObjects();
void cleanupScriptObjectsForPlugin(Widget*);
void clearForClose();
- void clearForOutOfMemory();
NPObject* createScriptObjectForPluginElement(HTMLPlugInElement*);
NPObject* windowScriptNPObject();
@@ -163,10 +154,9 @@ private:
typedef HashMap<int, OwnPtr<V8WindowShell> > IsolatedWorldMap;
typedef HashMap<Widget*, NPObject*> PluginObjectMap;
- ScriptValue evaluateScriptInMainWorld(const ScriptSourceCode&, AccessControlStatus, ExecuteScriptPolicy);
- void clearForClose(bool destroyGlobal);
+ v8::Local<v8::Value> evaluateScriptInMainWorld(const ScriptSourceCode&, AccessControlStatus, ExecuteScriptPolicy);
- Frame* m_frame;
+ LocalFrame* m_frame;
const String* m_sourceURL;
v8::Isolate* m_isolate;
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ScriptDebugServer.cpp b/chromium/third_party/WebKit/Source/bindings/v8/ScriptDebugServer.cpp
index 4195a44baa2..7b100c6cffb 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/ScriptDebugServer.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ScriptDebugServer.cpp
@@ -31,16 +31,18 @@
#include "config.h"
#include "bindings/v8/ScriptDebugServer.h"
-#include "DebuggerScriptSource.h"
-#include "V8JavaScriptCallFrame.h"
+#include "bindings/core/v8/V8JavaScriptCallFrame.h"
#include "bindings/v8/ScopedPersistent.h"
+#include "bindings/v8/ScriptCallStackFactory.h"
#include "bindings/v8/ScriptController.h"
-#include "bindings/v8/ScriptObject.h"
#include "bindings/v8/ScriptSourceCode.h"
+#include "bindings/v8/ScriptValue.h"
#include "bindings/v8/V8Binding.h"
#include "bindings/v8/V8ScriptRunner.h"
+#include "core/DebuggerScriptSource.h"
#include "core/inspector/JavaScriptCallFrame.h"
#include "core/inspector/ScriptDebugListener.h"
+#include "platform/JSONValues.h"
#include "wtf/StdLibExtras.h"
#include "wtf/Vector.h"
#include "wtf/dtoa/utils.h"
@@ -89,16 +91,16 @@ String ScriptDebugServer::setBreakpoint(const String& sourceID, const ScriptBrea
v8::Local<v8::Context> debuggerContext = v8::Debug::GetDebugContext();
v8::Context::Scope contextScope(debuggerContext);
- v8::Local<v8::Object> info = v8::Object::New();
+ v8::Local<v8::Object> info = v8::Object::New(m_isolate);
info->Set(v8AtomicString(m_isolate, "sourceID"), v8String(debuggerContext->GetIsolate(), sourceID));
- info->Set(v8AtomicString(m_isolate, "lineNumber"), v8::Integer::New(scriptBreakpoint.lineNumber, debuggerContext->GetIsolate()));
- info->Set(v8AtomicString(m_isolate, "columnNumber"), v8::Integer::New(scriptBreakpoint.columnNumber, debuggerContext->GetIsolate()));
+ info->Set(v8AtomicString(m_isolate, "lineNumber"), v8::Integer::New(debuggerContext->GetIsolate(), scriptBreakpoint.lineNumber));
+ info->Set(v8AtomicString(m_isolate, "columnNumber"), v8::Integer::New(debuggerContext->GetIsolate(), scriptBreakpoint.columnNumber));
info->Set(v8AtomicString(m_isolate, "interstatementLocation"), v8Boolean(interstatementLocation, debuggerContext->GetIsolate()));
info->Set(v8AtomicString(m_isolate, "condition"), v8String(debuggerContext->GetIsolate(), scriptBreakpoint.condition));
v8::Handle<v8::Function> setBreakpointFunction = v8::Local<v8::Function>::Cast(m_debuggerScript.newLocal(m_isolate)->Get(v8AtomicString(m_isolate, "setBreakpoint")));
v8::Handle<v8::Value> breakpointId = v8::Debug::Call(setBreakpointFunction, info);
- if (!breakpointId->IsString())
+ if (breakpointId.IsEmpty() || !breakpointId->IsString())
return "";
*actualLineNumber = info->Get(v8AtomicString(m_isolate, "lineNumber"))->Int32Value();
*actualColumnNumber = info->Get(v8AtomicString(m_isolate, "columnNumber"))->Int32Value();
@@ -111,7 +113,7 @@ void ScriptDebugServer::removeBreakpoint(const String& breakpointId)
v8::Local<v8::Context> debuggerContext = v8::Debug::GetDebugContext();
v8::Context::Scope contextScope(debuggerContext);
- v8::Local<v8::Object> info = v8::Object::New();
+ v8::Local<v8::Object> info = v8::Object::New(m_isolate);
info->Set(v8AtomicString(m_isolate, "breakpointId"), v8String(debuggerContext->GetIsolate(), breakpointId));
v8::Handle<v8::Function> removeBreakpointFunction = v8::Local<v8::Function>::Cast(m_debuggerScript.newLocal(m_isolate)->Get(v8AtomicString(m_isolate, "removeBreakpoint")));
@@ -136,7 +138,7 @@ void ScriptDebugServer::setBreakpointsActivated(bool activated)
v8::Local<v8::Context> debuggerContext = v8::Debug::GetDebugContext();
v8::Context::Scope contextScope(debuggerContext);
- v8::Local<v8::Object> info = v8::Object::New();
+ v8::Local<v8::Object> info = v8::Object::New(m_isolate);
info->Set(v8AtomicString(m_isolate, "enabled"), v8::Boolean::New(m_isolate, activated));
v8::Handle<v8::Function> setBreakpointsActivated = v8::Local<v8::Function>::Cast(m_debuggerScript.newLocal(m_isolate)->Get(v8AtomicString(m_isolate, "setBreakpointsActivated")));
v8::Debug::Call(setBreakpointsActivated, info);
@@ -161,14 +163,13 @@ void ScriptDebugServer::setPauseOnExceptionsState(PauseOnExceptionsState pauseOn
v8::HandleScope scope(m_isolate);
v8::Context::Scope contextScope(v8::Debug::GetDebugContext());
- v8::Handle<v8::Value> argv[] = { v8::Int32::New(pauseOnExceptionsState, m_isolate) };
+ v8::Handle<v8::Value> argv[] = { v8::Int32::New(m_isolate, pauseOnExceptionsState) };
callDebuggerMethod("setPauseOnExceptionsState", 1, argv);
}
void ScriptDebugServer::setPauseOnNextStatement(bool pause)
{
- if (isPaused())
- return;
+ ASSERT(!isPaused());
if (pause)
v8::Debug::DebugBreak(m_isolate);
else
@@ -179,8 +180,7 @@ bool ScriptDebugServer::canBreakProgram()
{
if (!m_breakpointsActivated)
return false;
- v8::HandleScope scope(m_isolate);
- return !m_isolate->GetCurrentContext().IsEmpty();
+ return m_isolate->InContext();
}
void ScriptDebugServer::breakProgram()
@@ -195,65 +195,56 @@ void ScriptDebugServer::breakProgram()
m_breakProgramCallbackTemplate.set(m_isolate, templ);
}
- m_pausedContext = m_isolate->GetCurrentContext();
v8::Handle<v8::Function> breakProgramFunction = m_breakProgramCallbackTemplate.newLocal(m_isolate)->GetFunction();
v8::Debug::Call(breakProgramFunction);
- m_pausedContext.Clear();
}
void ScriptDebugServer::continueProgram()
{
if (isPaused())
quitMessageLoopOnPause();
- m_executionState.clear();
+ m_pausedScriptState.clear();
+ m_executionState.Clear();
}
void ScriptDebugServer::stepIntoStatement()
{
ASSERT(isPaused());
+ ASSERT(!m_executionState.IsEmpty());
v8::HandleScope handleScope(m_isolate);
- v8::Handle<v8::Value> argv[] = { m_executionState.newLocal(m_isolate) };
+ v8::Handle<v8::Value> argv[] = { m_executionState };
callDebuggerMethod(stepIntoV8MethodName, 1, argv);
continueProgram();
}
-void ScriptDebugServer::stepCommandWithFrame(const char* functionName, const ScriptValue& frame)
+void ScriptDebugServer::stepOverStatement()
{
ASSERT(isPaused());
+ ASSERT(!m_executionState.IsEmpty());
v8::HandleScope handleScope(m_isolate);
- v8::Handle<v8::Value> callFrame;
- if (frame.hasNoValue()) {
- callFrame = v8::Undefined(m_isolate);
- } else {
- JavaScriptCallFrame* impl = V8JavaScriptCallFrame::toNative(v8::Handle<v8::Object>::Cast(frame.v8Value()));
- callFrame = impl->innerCallFrame();
- }
-
- v8::Handle<v8::Value> argv[] = {
- m_executionState.newLocal(m_isolate),
- callFrame
- };
-
- callDebuggerMethod(functionName, 2, argv);
+ v8::Handle<v8::Value> argv[] = { m_executionState };
+ callDebuggerMethod("stepOverStatement", 1, argv);
continueProgram();
}
-void ScriptDebugServer::stepOverStatement(const ScriptValue& frame)
+void ScriptDebugServer::stepOutOfFunction()
{
- stepCommandWithFrame("stepOverStatement", frame);
-}
-
-void ScriptDebugServer::stepOutOfFunction(const ScriptValue& frame)
-{
- stepCommandWithFrame(stepOutV8MethodName, frame);
+ ASSERT(isPaused());
+ ASSERT(!m_executionState.IsEmpty());
+ v8::HandleScope handleScope(m_isolate);
+ v8::Handle<v8::Value> argv[] = { m_executionState };
+ callDebuggerMethod(stepOutV8MethodName, 1, argv);
+ continueProgram();
}
-bool ScriptDebugServer::setScriptSource(const String& sourceID, const String& newContent, bool preview, String* error, RefPtr<TypeBuilder::Debugger::SetScriptSourceError>& errorData, ScriptValue* newCallFrames, ScriptObject* result)
+bool ScriptDebugServer::setScriptSource(const String& sourceID, const String& newContent, bool preview, String* error, RefPtr<TypeBuilder::Debugger::SetScriptSourceError>& errorData, ScriptValue* newCallFrames, RefPtr<JSONObject>* result)
{
class EnableLiveEditScope {
public:
- EnableLiveEditScope() { v8::Debug::SetLiveEditEnabled(true); }
- ~EnableLiveEditScope() { v8::Debug::SetLiveEditEnabled(false); }
+ explicit EnableLiveEditScope(v8::Isolate* isolate) : m_isolate(isolate) { v8::Debug::SetLiveEditEnabled(m_isolate, true); }
+ ~EnableLiveEditScope() { v8::Debug::SetLiveEditEnabled(m_isolate, false); }
+ private:
+ v8::Isolate* m_isolate;
};
ensureDebuggerScriptCompiled();
@@ -264,11 +255,11 @@ bool ScriptDebugServer::setScriptSource(const String& sourceID, const String& ne
if (!isPaused())
contextScope = adoptPtr(new v8::Context::Scope(debuggerContext));
- v8::Handle<v8::Value> argv[] = { v8String(debuggerContext->GetIsolate(), sourceID), v8String(debuggerContext->GetIsolate(), newContent), v8Boolean(preview, debuggerContext->GetIsolate()) };
+ v8::Handle<v8::Value> argv[] = { v8String(m_isolate, sourceID), v8String(m_isolate, newContent), v8Boolean(preview, m_isolate) };
v8::Local<v8::Value> v8result;
{
- EnableLiveEditScope enableLiveEditScope;
+ EnableLiveEditScope enableLiveEditScope(m_isolate);
v8::TryCatch tryCatch;
tryCatch.SetVerbose(false);
v8result = callDebuggerMethod("liveEditScriptSource", 3, argv);
@@ -288,8 +279,9 @@ bool ScriptDebugServer::setScriptSource(const String& sourceID, const String& ne
case 0:
{
v8::Local<v8::Value> normalResult = resultTuple->Get(1);
- if (normalResult->IsObject())
- *result = ScriptObject(ScriptState::current(), normalResult->ToObject());
+ RefPtr<JSONValue> jsonResult = v8ToJSONValue(m_isolate, normalResult, JSONValue::maxDepth);
+ if (jsonResult)
+ *result = jsonResult->asObject();
// Call stack may have changed after if the edited function was on the stack.
if (!preview && isPaused())
*newCallFrames = currentCallFrames();
@@ -314,40 +306,71 @@ bool ScriptDebugServer::setScriptSource(const String& sourceID, const String& ne
return false;
}
-PassRefPtr<JavaScriptCallFrame> ScriptDebugServer::wrapCallFrames(v8::Handle<v8::Object> executionState, int maximumLimit)
+int ScriptDebugServer::frameCount()
{
+ ASSERT(isPaused());
+ ASSERT(!m_executionState.IsEmpty());
+ v8::Handle<v8::Value> argv[] = { m_executionState };
+ v8::Handle<v8::Value> result = callDebuggerMethod("frameCount", WTF_ARRAY_LENGTH(argv), argv);
+ if (result->IsInt32())
+ return result->Int32Value();
+ return 0;
+}
+
+PassRefPtrWillBeRawPtr<JavaScriptCallFrame> ScriptDebugServer::wrapCallFrames(int maximumLimit, ScopeInfoDetails scopeDetails)
+{
+ const int scopeBits = 2;
+ COMPILE_ASSERT(NoScopes < (1 << scopeBits), not_enough_bits_to_encode_ScopeInfoDetails);
+
+ ASSERT(maximumLimit >= 0);
+ int data = (maximumLimit << scopeBits) | scopeDetails;
v8::Handle<v8::Value> currentCallFrameV8;
- if (executionState.IsEmpty()) {
+ if (m_executionState.IsEmpty()) {
v8::Handle<v8::Function> currentCallFrameFunction = v8::Local<v8::Function>::Cast(m_debuggerScript.newLocal(m_isolate)->Get(v8AtomicString(m_isolate, "currentCallFrame")));
- currentCallFrameV8 = v8::Debug::Call(currentCallFrameFunction, v8::Integer::New(maximumLimit, m_isolate));
+ currentCallFrameV8 = v8::Debug::Call(currentCallFrameFunction, v8::Integer::New(m_isolate, data));
} else {
- v8::Handle<v8::Value> argv[] = { executionState, v8::Integer::New(maximumLimit, m_isolate) };
- currentCallFrameV8 = callDebuggerMethod("currentCallFrame", 2, argv);
+ v8::Handle<v8::Value> argv[] = { m_executionState, v8::Integer::New(m_isolate, data) };
+ currentCallFrameV8 = callDebuggerMethod("currentCallFrame", WTF_ARRAY_LENGTH(argv), argv);
}
ASSERT(!currentCallFrameV8.IsEmpty());
if (!currentCallFrameV8->IsObject())
- return PassRefPtr<JavaScriptCallFrame>();
+ return nullptr;
return JavaScriptCallFrame::create(v8::Debug::GetDebugContext(), v8::Handle<v8::Object>::Cast(currentCallFrameV8));
}
-ScriptValue ScriptDebugServer::currentCallFrames()
+ScriptValue ScriptDebugServer::currentCallFramesInner(ScopeInfoDetails scopeDetails)
{
- v8::HandleScope scope(m_isolate);
- v8::Handle<v8::Context> pausedContext = m_pausedContext.IsEmpty() ? m_isolate->GetCurrentContext() : m_pausedContext;
- if (pausedContext.IsEmpty())
+ if (!m_isolate->InContext())
return ScriptValue();
+ v8::HandleScope handleScope(m_isolate);
- RefPtr<JavaScriptCallFrame> currentCallFrame = wrapCallFrames(m_executionState.newLocal(m_isolate), -1);
+ RefPtrWillBeRawPtr<JavaScriptCallFrame> currentCallFrame = wrapCallFrames(0, scopeDetails);
if (!currentCallFrame)
return ScriptValue();
- v8::Context::Scope contextScope(pausedContext);
- return ScriptValue(toV8(currentCallFrame.release(), v8::Handle<v8::Object>(), pausedContext->GetIsolate()), pausedContext->GetIsolate());
+ ScriptState* scriptState = m_pausedScriptState ? m_pausedScriptState.get() : ScriptState::current(m_isolate);
+ ScriptState::Scope scope(scriptState);
+ return ScriptValue(scriptState, toV8(currentCallFrame.release(), scriptState->context()->Global(), m_isolate));
+}
+
+ScriptValue ScriptDebugServer::currentCallFrames()
+{
+ return currentCallFramesInner(AllScopes);
+}
+
+ScriptValue ScriptDebugServer::currentCallFramesForAsyncStack()
+{
+ return currentCallFramesInner(FastAsyncScopes);
+}
+
+PassRefPtrWillBeRawPtr<JavaScriptCallFrame> ScriptDebugServer::topCallFrameNoScopes()
+{
+ return wrapCallFrames(1, NoScopes);
}
void ScriptDebugServer::interruptAndRun(PassOwnPtr<Task> task, v8::Isolate* isolate)
{
- v8::Debug::DebugBreakForCommand(new ClientDataImpl(task), isolate);
+ v8::Debug::DebugBreakForCommand(isolate, new ClientDataImpl(task));
}
void ScriptDebugServer::runPendingTasks()
@@ -365,18 +388,19 @@ void ScriptDebugServer::breakProgramCallback(const v8::FunctionCallbackInfo<v8::
{
ASSERT(2 == info.Length());
ScriptDebugServer* thisPtr = toScriptDebugServer(info.Data());
+ ScriptState* pausedScriptState = ScriptState::current(thisPtr->m_isolate);
v8::Handle<v8::Value> exception;
v8::Handle<v8::Array> hitBreakpoints;
- thisPtr->handleProgramBreak(v8::Handle<v8::Object>::Cast(info[0]), exception, hitBreakpoints);
+ thisPtr->handleProgramBreak(pausedScriptState, v8::Handle<v8::Object>::Cast(info[0]), exception, hitBreakpoints);
}
-void ScriptDebugServer::handleProgramBreak(v8::Handle<v8::Object> executionState, v8::Handle<v8::Value> exception, v8::Handle<v8::Array> hitBreakpointNumbers)
+void ScriptDebugServer::handleProgramBreak(ScriptState* pausedScriptState, v8::Handle<v8::Object> executionState, v8::Handle<v8::Value> exception, v8::Handle<v8::Array> hitBreakpointNumbers)
{
// Don't allow nested breaks.
if (isPaused())
return;
- ScriptDebugListener* listener = getDebugListenerForContext(m_pausedContext);
+ ScriptDebugListener* listener = getDebugListenerForContext(pausedScriptState->context());
if (!listener)
return;
@@ -390,20 +414,24 @@ void ScriptDebugServer::handleProgramBreak(v8::Handle<v8::Object> executionState
}
}
- m_executionState.set(m_isolate, executionState);
- ScriptState* currentCallFrameState = ScriptState::forContext(m_pausedContext);
- listener->didPause(currentCallFrameState, currentCallFrames(), ScriptValue(exception, currentCallFrameState->isolate()), breakpointIds);
-
- m_runningNestedMessageLoop = true;
- runMessageLoopOnPause(m_pausedContext);
- m_runningNestedMessageLoop = false;
-}
-
-void ScriptDebugServer::handleProgramBreak(const v8::Debug::EventDetails& eventDetails, v8::Handle<v8::Value> exception, v8::Handle<v8::Array> hitBreakpointNumbers)
-{
- m_pausedContext = eventDetails.GetEventContext();
- handleProgramBreak(eventDetails.GetExecutionState(), exception, hitBreakpointNumbers);
- m_pausedContext.Clear();
+ m_pausedScriptState = pausedScriptState;
+ m_executionState = executionState;
+ ScriptDebugListener::SkipPauseRequest result = listener->didPause(pausedScriptState, currentCallFrames(), ScriptValue(pausedScriptState, exception), breakpointIds);
+ if (result == ScriptDebugListener::NoSkip) {
+ m_runningNestedMessageLoop = true;
+ runMessageLoopOnPause(pausedScriptState->context());
+ m_runningNestedMessageLoop = false;
+ }
+ m_pausedScriptState.clear();
+ m_executionState.Clear();
+
+ if (result == ScriptDebugListener::StepInto) {
+ v8::Handle<v8::Value> argv[] = { executionState };
+ callDebuggerMethod(stepIntoV8MethodName, 1, argv);
+ } else if (result == ScriptDebugListener::StepOut) {
+ v8::Handle<v8::Value> argv[] = { executionState };
+ callDebuggerMethod(stepOutV8MethodName, 1, argv);
+ }
}
void ScriptDebugServer::v8DebugEventCallback(const v8::Debug::EventDetails& eventDetails)
@@ -412,22 +440,6 @@ void ScriptDebugServer::v8DebugEventCallback(const v8::Debug::EventDetails& even
thisPtr->handleV8DebugEvent(eventDetails);
}
-bool ScriptDebugServer::executeSkipPauseRequest(ScriptDebugListener::SkipPauseRequest request, v8::Handle<v8::Object> executionState)
-{
- switch (request) {
- case ScriptDebugListener::NoSkip:
- return false;
- case ScriptDebugListener::Continue:
- return true;
- case ScriptDebugListener::StepInto:
- case ScriptDebugListener::StepOut:
- break;
- }
- v8::Handle<v8::Value> argv[] = { executionState };
- callDebuggerMethod(stepIntoV8MethodName, 1, argv);
- return true;
-}
-
void ScriptDebugServer::handleV8DebugEvent(const v8::Debug::EventDetails& eventDetails)
{
v8::DebugEvent event = eventDetails.GetEvent();
@@ -463,28 +475,17 @@ void ScriptDebugServer::handleV8DebugEvent(const v8::Debug::EventDetails& eventD
// Stack trace is empty in case of syntax error. Silently continue execution in such cases.
if (!stackTrace->GetFrameCount())
return;
- RefPtr<JavaScriptCallFrame> topFrame = wrapCallFrames(eventDetails.GetExecutionState(), 1);
- if (executeSkipPauseRequest(listener->shouldSkipExceptionPause(topFrame), eventDetails.GetExecutionState()))
- return;
v8::Handle<v8::Object> eventData = eventDetails.GetEventData();
v8::Handle<v8::Value> exceptionGetterValue = eventData->Get(v8AtomicString(m_isolate, "exception"));
ASSERT(!exceptionGetterValue.IsEmpty() && exceptionGetterValue->IsFunction());
v8::Handle<v8::Value> exception = V8ScriptRunner::callInternalFunction(v8::Handle<v8::Function>::Cast(exceptionGetterValue), eventData, 0, 0, m_isolate);
- handleProgramBreak(eventDetails, exception, v8::Handle<v8::Array>());
+ handleProgramBreak(ScriptState::from(eventContext), eventDetails.GetExecutionState(), exception, v8::Handle<v8::Array>());
} else if (event == v8::Break) {
v8::Handle<v8::Function> getBreakpointNumbersFunction = v8::Local<v8::Function>::Cast(debuggerScript->Get(v8AtomicString(m_isolate, "getBreakpointNumbers")));
v8::Handle<v8::Value> argv[] = { eventDetails.GetEventData() };
v8::Handle<v8::Value> hitBreakpoints = V8ScriptRunner::callInternalFunction(getBreakpointNumbersFunction, debuggerScript, WTF_ARRAY_LENGTH(argv), argv, m_isolate);
ASSERT(hitBreakpoints->IsArray());
- RefPtr<JavaScriptCallFrame> topFrame = wrapCallFrames(eventDetails.GetExecutionState(), 1);
- ScriptDebugListener::SkipPauseRequest skipRequest;
- if (v8::Handle<v8::Array>::Cast(hitBreakpoints)->Length())
- skipRequest = listener->shouldSkipBreakpointPause(topFrame);
- else
- skipRequest = listener->shouldSkipStepPause(topFrame);
- if (executeSkipPauseRequest(skipRequest, eventDetails.GetExecutionState()))
- return;
- handleProgramBreak(eventDetails, v8::Handle<v8::Value>(), hitBreakpoints.As<v8::Array>());
+ handleProgramBreak(ScriptState::from(eventContext), eventDetails.GetExecutionState(), v8::Handle<v8::Value>(), hitBreakpoints.As<v8::Array>());
}
}
}
@@ -522,6 +523,12 @@ void ScriptDebugServer::ensureDebuggerScriptCompiled()
m_debuggerScript.set(m_isolate, v8::Handle<v8::Object>::Cast(value));
}
+void ScriptDebugServer::discardDebuggerScript()
+{
+ ASSERT(!m_debuggerScript.isEmpty());
+ m_debuggerScript.clear();
+}
+
v8::Local<v8::Value> ScriptDebugServer::functionScopes(v8::Handle<v8::Function> function)
{
ensureDebuggerScriptCompiled();
@@ -547,7 +554,7 @@ v8::Handle<v8::Value> ScriptDebugServer::setFunctionVariableValue(v8::Handle<v8:
v8::Handle<v8::Value> argv[] = {
functionValue,
- v8::Handle<v8::Value>(v8::Integer::New(scopeNumber, debuggerContext->GetIsolate())),
+ v8::Handle<v8::Value>(v8::Integer::New(debuggerContext->GetIsolate(), scopeNumber)),
v8String(debuggerContext->GetIsolate(), variableName),
newValue
};
@@ -557,30 +564,32 @@ v8::Handle<v8::Value> ScriptDebugServer::setFunctionVariableValue(v8::Handle<v8:
bool ScriptDebugServer::isPaused()
{
- return !m_executionState.isEmpty();
+ return m_pausedScriptState;
}
-void ScriptDebugServer::compileScript(ScriptState* state, const String& expression, const String& sourceURL, String* scriptId, String* exceptionMessage)
+void ScriptDebugServer::compileScript(ScriptState* scriptState, const String& expression, const String& sourceURL, String* scriptId, String* exceptionDetailsText, int* lineNumber, int* columnNumber, RefPtrWillBeRawPtr<ScriptCallStack>* stackTrace)
{
- v8::HandleScope handleScope(m_isolate);
- v8::Handle<v8::Context> context = state->context();
- if (context.IsEmpty())
+ if (scriptState->contextIsEmpty())
return;
- v8::Context::Scope contextScope(context);
+ ScriptState::Scope scope(scriptState);
v8::Handle<v8::String> source = v8String(m_isolate, expression);
v8::TryCatch tryCatch;
v8::Local<v8::Script> script = V8ScriptRunner::compileScript(source, sourceURL, TextPosition(), 0, m_isolate);
if (tryCatch.HasCaught()) {
v8::Local<v8::Message> message = tryCatch.Message();
- if (!message.IsEmpty())
- *exceptionMessage = toCoreStringWithUndefinedOrNullCheck(message->Get());
+ if (!message.IsEmpty()) {
+ *exceptionDetailsText = toCoreStringWithUndefinedOrNullCheck(message->Get());
+ *lineNumber = message->GetLineNumber();
+ *columnNumber = message->GetStartColumn();
+ *stackTrace = createScriptCallStack(message->GetStackTrace(), message->GetStackTrace()->GetFrameCount(), m_isolate);
+ }
return;
}
if (script.IsEmpty())
return;
- *scriptId = String::number(script->GetId());
+ *scriptId = String::number(script->GetUnboundScript()->GetId());
m_compiledScripts.set(*scriptId, adoptPtr(new ScopedPersistent<v8::Script>(m_isolate, script)));
}
@@ -589,7 +598,7 @@ void ScriptDebugServer::clearCompiledScripts()
m_compiledScripts.clear();
}
-void ScriptDebugServer::runScript(ScriptState* state, const String& scriptId, ScriptValue* result, bool* wasThrown, String* exceptionMessage)
+void ScriptDebugServer::runScript(ScriptState* scriptState, const String& scriptId, ScriptValue* result, bool* wasThrown, String* exceptionDetailsText, int* lineNumber, int* columnNumber, RefPtrWillBeRawPtr<ScriptCallStack>* stackTrace)
{
if (!m_compiledScripts.contains(scriptId))
return;
@@ -600,30 +609,33 @@ void ScriptDebugServer::runScript(ScriptState* state, const String& scriptId, Sc
if (script.IsEmpty())
return;
- v8::Handle<v8::Context> context = state->context();
- if (context.IsEmpty())
+ if (scriptState->contextIsEmpty())
return;
- v8::Context::Scope contextScope(context);
+ ScriptState::Scope scope(scriptState);
v8::TryCatch tryCatch;
- v8::Local<v8::Value> value = V8ScriptRunner::runCompiledScript(script, state->executionContext(), m_isolate);
+ v8::Local<v8::Value> value = V8ScriptRunner::runCompiledScript(script, scriptState->executionContext(), m_isolate);
*wasThrown = false;
if (tryCatch.HasCaught()) {
*wasThrown = true;
- *result = ScriptValue(tryCatch.Exception(), m_isolate);
+ *result = ScriptValue(scriptState, tryCatch.Exception());
v8::Local<v8::Message> message = tryCatch.Message();
- if (!message.IsEmpty())
- *exceptionMessage = toCoreStringWithUndefinedOrNullCheck(message->Get());
+ if (!message.IsEmpty()) {
+ *exceptionDetailsText = toCoreStringWithUndefinedOrNullCheck(message->Get());
+ *lineNumber = message->GetLineNumber();
+ *columnNumber = message->GetStartColumn();
+ *stackTrace = createScriptCallStack(message->GetStackTrace(), message->GetStackTrace()->GetFrameCount(), m_isolate);
+ }
} else {
- *result = ScriptValue(value, m_isolate);
+ *result = ScriptValue(scriptState, value);
}
}
-PassOwnPtr<ScriptSourceCode> ScriptDebugServer::preprocess(Frame*, const ScriptSourceCode&)
+PassOwnPtr<ScriptSourceCode> ScriptDebugServer::preprocess(LocalFrame*, const ScriptSourceCode&)
{
return PassOwnPtr<ScriptSourceCode>();
}
-String ScriptDebugServer::preprocessEventListener(Frame*, const String& source, const String& url, const String& functionName)
+String ScriptDebugServer::preprocessEventListener(LocalFrame*, const String& source, const String& url, const String& functionName)
{
return source;
}
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ScriptDebugServer.h b/chromium/third_party/WebKit/Source/bindings/v8/ScriptDebugServer.h
index 3d0e07a954f..ea8d35f3dcd 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/ScriptDebugServer.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ScriptDebugServer.h
@@ -31,25 +31,26 @@
#ifndef ScriptDebugServer_h
#define ScriptDebugServer_h
-#include "InspectorBackendDispatcher.h"
#include "bindings/v8/ScopedPersistent.h"
+#include "core/InspectorBackendDispatcher.h"
#include "core/inspector/ScriptBreakpoint.h"
+#include "core/inspector/ScriptCallStack.h"
#include "core/inspector/ScriptDebugListener.h"
-#include <v8-debug.h>
#include "wtf/HashMap.h"
#include "wtf/Noncopyable.h"
#include "wtf/PassOwnPtr.h"
#include "wtf/Vector.h"
#include "wtf/text/StringHash.h"
#include "wtf/text/WTFString.h"
+#include <v8-debug.h>
+#include <v8.h>
namespace WebCore {
+class ScriptState;
class ScriptController;
class ScriptDebugListener;
-class ScriptObject;
class ScriptSourceCode;
-class ScriptState;
class ScriptValue;
class JavaScriptCallFrame;
@@ -74,11 +75,14 @@ public:
void breakProgram();
void continueProgram();
void stepIntoStatement();
- void stepOverStatement(const ScriptValue& frame);
- void stepOutOfFunction(const ScriptValue& frame);
+ void stepOverStatement();
+ void stepOutOfFunction();
- bool setScriptSource(const String& sourceID, const String& newContent, bool preview, String* error, RefPtr<TypeBuilder::Debugger::SetScriptSourceError>&, ScriptValue* newCallFrames, ScriptObject* result);
+ bool setScriptSource(const String& sourceID, const String& newContent, bool preview, String* error, RefPtr<TypeBuilder::Debugger::SetScriptSourceError>&, ScriptValue* newCallFrames, RefPtr<JSONObject>* result);
ScriptValue currentCallFrames();
+ ScriptValue currentCallFramesForAsyncStack();
+ PassRefPtrWillBeRawPtr<JavaScriptCallFrame> topCallFrameNoScopes();
+ int frameCount();
class Task {
public:
@@ -96,13 +100,16 @@ public:
v8::Handle<v8::Value> setFunctionVariableValue(v8::Handle<v8::Value> functionValue, int scopeNumber, const String& variableName, v8::Handle<v8::Value> newValue);
v8::Local<v8::Value> callDebuggerMethod(const char* functionName, int argc, v8::Handle<v8::Value> argv[]);
- virtual void compileScript(ScriptState*, const String& expression, const String& sourceURL, String* scriptId, String* exceptionMessage);
+ virtual void compileScript(ScriptState*, const String& expression, const String& sourceURL, String* scriptId, String* exceptionDetailsText, int* lineNumber, int* columnNumber, RefPtrWillBeRawPtr<ScriptCallStack>* stackTrace);
virtual void clearCompiledScripts();
- virtual void runScript(ScriptState*, const String& scriptId, ScriptValue* result, bool* wasThrown, String* exceptionMessage);
+ virtual void runScript(ScriptState*, const String& scriptId, ScriptValue* result, bool* wasThrown, String* exceptionDetailsText, int* lineNumber, int* columnNumber, RefPtrWillBeRawPtr<ScriptCallStack>* stackTrace);
virtual void setPreprocessorSource(const String&) { }
virtual void preprocessBeforeCompile(const v8::Debug::EventDetails&) { }
- virtual PassOwnPtr<ScriptSourceCode> preprocess(Frame*, const ScriptSourceCode&);
- virtual String preprocessEventListener(Frame*, const String& source, const String& url, const String& functionName);
+ virtual PassOwnPtr<ScriptSourceCode> preprocess(LocalFrame*, const ScriptSourceCode&);
+ virtual String preprocessEventListener(LocalFrame*, const String& source, const String& url, const String& functionName);
+
+ virtual void muteWarningsAndDeprecations() { }
+ virtual void unmuteWarningsAndDeprecations() { }
protected:
explicit ScriptDebugServer(v8::Isolate*);
@@ -113,8 +120,7 @@ protected:
virtual void quitMessageLoopOnPause() = 0;
static void breakProgramCallback(const v8::FunctionCallbackInfo<v8::Value>&);
- void handleProgramBreak(v8::Handle<v8::Object> executionState, v8::Handle<v8::Value> exception, v8::Handle<v8::Array> hitBreakpoints);
- void handleProgramBreak(const v8::Debug::EventDetails&, v8::Handle<v8::Value> exception, v8::Handle<v8::Array> hitBreakpointNumbers);
+ void handleProgramBreak(ScriptState* pausedScriptState, v8::Handle<v8::Object> executionState, v8::Handle<v8::Value> exception, v8::Handle<v8::Array> hitBreakpoints);
static void v8DebugEventCallback(const v8::Debug::EventDetails& eventDetails);
void handleV8DebugEvent(const v8::Debug::EventDetails& eventDetails);
@@ -122,20 +128,27 @@ protected:
void dispatchDidParseSource(ScriptDebugListener* listener, v8::Handle<v8::Object> sourceObject);
void ensureDebuggerScriptCompiled();
+ void discardDebuggerScript();
PauseOnExceptionsState m_pauseOnExceptionsState;
ScopedPersistent<v8::Object> m_debuggerScript;
- ScopedPersistent<v8::Object> m_executionState;
- v8::Handle<v8::Context> m_pausedContext;
+ v8::Local<v8::Object> m_executionState;
+ RefPtr<ScriptState> m_pausedScriptState;
bool m_breakpointsActivated;
ScopedPersistent<v8::FunctionTemplate> m_breakProgramCallbackTemplate;
HashMap<String, OwnPtr<ScopedPersistent<v8::Script> > > m_compiledScripts;
v8::Isolate* m_isolate;
private:
- void stepCommandWithFrame(const char* functionName, const ScriptValue& frame);
- PassRefPtr<JavaScriptCallFrame> wrapCallFrames(v8::Handle<v8::Object> executionState, int maximumLimit);
- bool executeSkipPauseRequest(ScriptDebugListener::SkipPauseRequest, v8::Handle<v8::Object> executionState);
+ enum ScopeInfoDetails {
+ AllScopes,
+ FastAsyncScopes,
+ NoScopes // Should be the last option.
+ };
+
+ ScriptValue currentCallFramesInner(ScopeInfoDetails);
+
+ PassRefPtrWillBeRawPtr<JavaScriptCallFrame> wrapCallFrames(int maximumLimit, ScopeInfoDetails);
bool m_runningNestedMessageLoop;
};
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ScriptEventListener.cpp b/chromium/third_party/WebKit/Source/bindings/v8/ScriptEventListener.cpp
index 8329708acc5..f720c88a021 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/ScriptEventListener.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ScriptEventListener.cpp
@@ -32,7 +32,6 @@
#include "bindings/v8/ScriptEventListener.h"
#include "bindings/v8/ScriptController.h"
-#include "bindings/v8/ScriptScope.h"
#include "bindings/v8/ScriptState.h"
#include "bindings/v8/V8AbstractEventListener.h"
#include "bindings/v8/V8Binding.h"
@@ -40,58 +39,70 @@
#include "core/dom/Document.h"
#include "core/dom/DocumentParser.h"
#include "core/events/EventListener.h"
-#include "core/frame/Frame.h"
+#include "core/frame/LocalFrame.h"
+#include <v8.h>
namespace WebCore {
-static const AtomicString& eventParameterName(bool isSVGEvent)
-{
- DEFINE_STATIC_LOCAL(const AtomicString, eventString, ("event"));
- DEFINE_STATIC_LOCAL(const AtomicString, evtString, ("evt"));
- return isSVGEvent ? evtString : eventString;
-}
-
-PassRefPtr<V8LazyEventListener> createAttributeEventListener(Node* node, const QualifiedName& name, const AtomicString& value)
+PassRefPtr<V8LazyEventListener> createAttributeEventListener(Node* node, const QualifiedName& name, const AtomicString& value, const AtomicString& eventParameterName)
{
ASSERT(node);
if (value.isNull())
- return 0;
+ return nullptr;
// FIXME: Very strange: we initialize zero-based number with '1'.
TextPosition position(OrdinalNumber::fromZeroBasedInt(1), OrdinalNumber::first());
String sourceURL;
v8::Isolate* isolate;
- if (Frame* frame = node->document().frame()) {
+ if (LocalFrame* frame = node->document().frame()) {
isolate = toIsolate(frame);
ScriptController& scriptController = frame->script();
if (!scriptController.canExecuteScripts(AboutToExecuteScript))
- return 0;
+ return nullptr;
position = scriptController.eventHandlerPosition();
sourceURL = node->document().url().string();
} else {
isolate = v8::Isolate::GetCurrent();
}
- return V8LazyEventListener::create(name.localName(), eventParameterName(node->isSVGElement()), value, sourceURL, position, node, isolate);
+ return V8LazyEventListener::create(name.localName(), eventParameterName, value, sourceURL, position, node, isolate);
}
-PassRefPtr<V8LazyEventListener> createAttributeEventListener(Frame* frame, const QualifiedName& name, const AtomicString& value)
+PassRefPtr<V8LazyEventListener> createAttributeEventListener(LocalFrame* frame, const QualifiedName& name, const AtomicString& value, const AtomicString& eventParameterName)
{
if (!frame)
- return 0;
+ return nullptr;
if (value.isNull())
- return 0;
+ return nullptr;
ScriptController& scriptController = frame->script();
if (!scriptController.canExecuteScripts(AboutToExecuteScript))
- return 0;
+ return nullptr;
TextPosition position = scriptController.eventHandlerPosition();
String sourceURL = frame->document()->url().string();
- return V8LazyEventListener::create(name.localName(), eventParameterName(frame->document()->isSVGDocument()), value, sourceURL, position, 0, toIsolate(frame));
+ return V8LazyEventListener::create(name.localName(), eventParameterName, value, sourceURL, position, 0, toIsolate(frame));
+}
+
+static v8::Handle<v8::Function> eventListenerEffectiveFunction(v8::Isolate* isolate, v8::Handle<v8::Object> listenerObject)
+{
+ v8::Handle<v8::Function> function;
+ if (listenerObject->IsFunction()) {
+ function = v8::Handle<v8::Function>::Cast(listenerObject);
+ } else if (listenerObject->IsObject()) {
+ // Try the "handleEvent" method (EventListener interface).
+ v8::Handle<v8::Value> property = listenerObject->Get(v8AtomicString(isolate, "handleEvent"));
+ if (property.IsEmpty() || !property->IsFunction()) {
+ // Fall back to the "constructor" property.
+ property = listenerObject->Get(v8AtomicString(isolate, "constructor"));
+ }
+ if (!property.IsEmpty() && property->IsFunction())
+ function = v8::Handle<v8::Function>::Cast(property);
+ }
+ return function;
}
String eventListenerHandlerBody(Document* document, EventListener* listener)
@@ -103,11 +114,14 @@ String eventListenerHandlerBody(Document* document, EventListener* listener)
V8AbstractEventListener* v8Listener = static_cast<V8AbstractEventListener*>(listener);
v8::Handle<v8::Context> context = toV8Context(document, v8Listener->world());
v8::Context::Scope contextScope(context);
- v8::Handle<v8::Value> function = v8Listener->getListenerObject(document);
+ v8::Handle<v8::Object> object = v8Listener->getListenerObject(document);
+ if (object.IsEmpty())
+ return "";
+ v8::Handle<v8::Function> function = eventListenerEffectiveFunction(scope.GetIsolate(), object);
if (function.IsEmpty())
return "";
- V8TRYCATCH_FOR_V8STRINGRESOURCE_RETURN(V8StringResource<WithNullCheck>, functionString, function, "");
+ TOSTRING_DEFAULT(V8StringResource<WithNullCheck>, functionString, function, "");
return functionString;
}
@@ -124,17 +138,17 @@ ScriptValue eventListenerHandler(Document* document, EventListener* listener)
v8::Handle<v8::Object> function = v8Listener->getListenerObject(document);
if (function.IsEmpty())
return ScriptValue();
- return ScriptValue(function, isolate);
+ return ScriptValue(ScriptState::from(context), function);
}
-ScriptState* eventListenerHandlerScriptState(Frame* frame, EventListener* listener)
+ScriptState* eventListenerHandlerScriptState(LocalFrame* frame, EventListener* listener)
{
if (listener->type() != EventListener::JSEventListenerType)
return 0;
V8AbstractEventListener* v8Listener = static_cast<V8AbstractEventListener*>(listener);
v8::HandleScope scope(toIsolate(frame));
v8::Handle<v8::Context> v8Context = frame->script().windowShell(v8Listener->world())->context();
- return ScriptState::forContext(v8Context);
+ return ScriptState::from(v8Context);
}
bool eventListenerHandlerLocation(Document* document, EventListener* listener, String& sourceName, String& scriptId, int& lineNumber)
@@ -146,19 +160,21 @@ bool eventListenerHandlerLocation(Document* document, EventListener* listener, S
V8AbstractEventListener* v8Listener = static_cast<V8AbstractEventListener*>(listener);
v8::Handle<v8::Context> context = toV8Context(document, v8Listener->world());
v8::Context::Scope contextScope(context);
- v8::Handle<v8::Object> object = v8Listener->getListenerObject(document);
- if (object.IsEmpty() || !object->IsFunction())
+ v8::Local<v8::Object> object = v8Listener->getListenerObject(document);
+ if (object.IsEmpty())
return false;
-
- v8::Handle<v8::Function> function = v8::Handle<v8::Function>::Cast(object);
- int scriptIdValue = function->ScriptId();
+ v8::Handle<v8::Function> function = eventListenerEffectiveFunction(scope.GetIsolate(), object);
+ if (function.IsEmpty())
+ return false;
+ v8::Handle<v8::Function> originalFunction = getBoundFunction(function);
+ int scriptIdValue = originalFunction->ScriptId();
scriptId = String::number(scriptIdValue);
- v8::ScriptOrigin origin = function->GetScriptOrigin();
+ v8::ScriptOrigin origin = originalFunction->GetScriptOrigin();
if (!origin.ResourceName().IsEmpty() && origin.ResourceName()->IsString())
sourceName = toCoreString(origin.ResourceName().As<v8::String>());
else
sourceName = "";
- lineNumber = function->GetScriptLineNumber();
+ lineNumber = originalFunction->GetScriptLineNumber();
return true;
}
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ScriptEventListener.h b/chromium/third_party/WebKit/Source/bindings/v8/ScriptEventListener.h
index bfb75ebaa03..097675defbd 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/ScriptEventListener.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ScriptEventListener.h
@@ -33,22 +33,21 @@
#include "bindings/v8/ScriptValue.h"
#include "bindings/v8/V8LazyEventListener.h"
-
#include "wtf/PassRefPtr.h"
namespace WebCore {
class Document;
class EventListener;
- class Frame;
+ class LocalFrame;
class Node;
class QualifiedName;
- PassRefPtr<V8LazyEventListener> createAttributeEventListener(Node*, const QualifiedName&, const AtomicString& value);
- PassRefPtr<V8LazyEventListener> createAttributeEventListener(Frame*, const QualifiedName&, const AtomicString& value);
+ PassRefPtr<V8LazyEventListener> createAttributeEventListener(Node*, const QualifiedName&, const AtomicString& value, const AtomicString& eventParameterName);
+ PassRefPtr<V8LazyEventListener> createAttributeEventListener(LocalFrame*, const QualifiedName&, const AtomicString& value, const AtomicString& eventParameterName);
String eventListenerHandlerBody(Document*, EventListener*);
ScriptValue eventListenerHandler(Document*, EventListener*);
- ScriptState* eventListenerHandlerScriptState(Frame*, EventListener*);
+ ScriptState* eventListenerHandlerScriptState(LocalFrame*, EventListener*);
bool eventListenerHandlerLocation(Document*, EventListener*, String& sourceName, String& scriptId, int& lineNumber);
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ScriptFunction.cpp b/chromium/third_party/WebKit/Source/bindings/v8/ScriptFunction.cpp
new file mode 100644
index 00000000000..18315a4b6e3
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ScriptFunction.cpp
@@ -0,0 +1,32 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "config.h"
+#include "bindings/v8/ScriptFunction.h"
+
+#include "bindings/v8/V8Binding.h"
+
+namespace WebCore {
+
+void ScriptFunction::callCallback(const v8::FunctionCallbackInfo<v8::Value>& args)
+{
+ v8::Isolate* isolate = args.GetIsolate();
+ ASSERT(!args.Data().IsEmpty());
+ ScriptFunction* function = ScriptFunction::Cast(args.Data());
+ v8::Local<v8::Value> value = args.Length() > 0 ? args[0] : v8::Local<v8::Value>(v8::Undefined(isolate));
+
+ ScriptValue result = function->call(ScriptValue(ScriptState::current(isolate), value));
+
+ v8SetReturnValue(args, result.v8Value());
+}
+
+v8::Handle<v8::Function> ScriptFunction::adoptByGarbageCollector(PassOwnPtr<ScriptFunction> function)
+{
+ if (!function)
+ return v8::Handle<v8::Function>();
+ v8::Isolate* isolate = function->isolate();
+ return createClosure(&ScriptFunction::callCallback, function.leakPtr()->releaseToV8GarbageCollector(), isolate);
+}
+
+} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8MIDIOutputCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/ScriptFunction.h
index fa3b69afea6..acb379d0f7d 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8MIDIOutputCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ScriptFunction.h
@@ -28,25 +28,29 @@
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
-#include "config.h"
-#include "V8MIDIOutput.h"
+#ifndef ScriptFunction_h
+#define ScriptFunction_h
-#include "V8MIDIAccess.h"
-#include "bindings/v8/V8HiddenPropertyName.h"
+#include "bindings/v8/ScriptValue.h"
+#include "bindings/v8/V8GarbageCollected.h"
+#include "wtf/RefCounted.h"
+#include <v8.h>
namespace WebCore {
-v8::Handle<v8::Object> wrap(MIDIOutput* output, v8::Handle<v8::Object> creationContext, v8::Isolate* isolate)
-{
- ASSERT(output);
- ASSERT(!DOMDataStore::containsWrapper<V8MIDIOutput>(output, isolate));
+class ScriptFunction : public V8GarbageCollected<ScriptFunction> {
+public:
+ virtual ~ScriptFunction() { }
+ static v8::Handle<v8::Function> adoptByGarbageCollector(PassOwnPtr<ScriptFunction>);
- v8::Handle<v8::Object> wrapper = V8MIDIOutput::createWrapper(output, creationContext, isolate);
+protected:
+ ScriptFunction(v8::Isolate* isolate) : V8GarbageCollected<ScriptFunction>(isolate) { }
- if (output->midiAccess())
- V8HiddenPropertyName::setNamedHiddenReference(wrapper, "access", toV8(output->midiAccess(), creationContext, isolate));
-
- return wrapper;
-}
+private:
+ virtual ScriptValue call(ScriptValue) = 0;
+ static void callCallback(const v8::FunctionCallbackInfo<v8::Value>& args);
+};
} // namespace WebCore
+
+#endif
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ScriptFunctionCall.cpp b/chromium/third_party/WebKit/Source/bindings/v8/ScriptFunctionCall.cpp
index e8c618e9030..56637ded2af 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/ScriptFunctionCall.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ScriptFunctionCall.cpp
@@ -32,19 +32,17 @@
#include "bindings/v8/ScriptFunctionCall.h"
#include "bindings/v8/ScriptController.h"
-#include "bindings/v8/ScriptScope.h"
#include "bindings/v8/ScriptState.h"
#include "bindings/v8/ScriptValue.h"
#include "bindings/v8/V8Binding.h"
#include "bindings/v8/V8ObjectConstructor.h"
#include "bindings/v8/V8ScriptRunner.h"
-#include "bindings/v8/V8Utilities.h"
#include <v8.h>
namespace WebCore {
-void ScriptCallArgumentHandler::appendArgument(const ScriptObject& argument)
+void ScriptCallArgumentHandler::appendArgument(const ScriptValue& argument)
{
if (argument.scriptState() != m_scriptState) {
ASSERT_NOT_REACHED();
@@ -53,67 +51,72 @@ void ScriptCallArgumentHandler::appendArgument(const ScriptObject& argument)
m_arguments.append(argument);
}
-void ScriptCallArgumentHandler::appendArgument(const ScriptValue& argument)
-{
- m_arguments.append(argument);
-}
-
void ScriptCallArgumentHandler::appendArgument(const String& argument)
{
v8::Isolate* isolate = m_scriptState->isolate();
- ScriptScope scope(m_scriptState);
- m_arguments.append(ScriptValue(v8String(isolate, argument), isolate));
+ ScriptState::Scope scope(m_scriptState.get());
+ m_arguments.append(ScriptValue(m_scriptState.get(), v8String(isolate, argument)));
}
void ScriptCallArgumentHandler::appendArgument(const char* argument)
{
v8::Isolate* isolate = m_scriptState->isolate();
- ScriptScope scope(m_scriptState);
- m_arguments.append(ScriptValue(v8String(isolate, argument), isolate));
+ ScriptState::Scope scope(m_scriptState.get());
+ m_arguments.append(ScriptValue(m_scriptState.get(), v8String(isolate, argument)));
}
void ScriptCallArgumentHandler::appendArgument(long argument)
{
v8::Isolate* isolate = m_scriptState->isolate();
- ScriptScope scope(m_scriptState);
- m_arguments.append(ScriptValue(v8::Number::New(isolate, argument), isolate));
+ ScriptState::Scope scope(m_scriptState.get());
+ m_arguments.append(ScriptValue(m_scriptState.get(), v8::Number::New(isolate, argument)));
}
void ScriptCallArgumentHandler::appendArgument(long long argument)
{
v8::Isolate* isolate = m_scriptState->isolate();
- ScriptScope scope(m_scriptState);
- m_arguments.append(ScriptValue(v8::Number::New(isolate, argument), isolate));
+ ScriptState::Scope scope(m_scriptState.get());
+ m_arguments.append(ScriptValue(m_scriptState.get(), v8::Number::New(isolate, argument)));
}
-void ScriptCallArgumentHandler::appendArgument(unsigned int argument)
+void ScriptCallArgumentHandler::appendArgument(unsigned argument)
{
v8::Isolate* isolate = m_scriptState->isolate();
- ScriptScope scope(m_scriptState);
- m_arguments.append(ScriptValue(v8::Number::New(isolate, argument), isolate));
+ ScriptState::Scope scope(m_scriptState.get());
+ m_arguments.append(ScriptValue(m_scriptState.get(), v8::Number::New(isolate, argument)));
}
void ScriptCallArgumentHandler::appendArgument(unsigned long argument)
{
v8::Isolate* isolate = m_scriptState->isolate();
- ScriptScope scope(m_scriptState);
- m_arguments.append(ScriptValue(v8::Number::New(isolate, argument), isolate));
+ ScriptState::Scope scope(m_scriptState.get());
+ m_arguments.append(ScriptValue(m_scriptState.get(), v8::Number::New(isolate, argument)));
}
void ScriptCallArgumentHandler::appendArgument(int argument)
{
v8::Isolate* isolate = m_scriptState->isolate();
- ScriptScope scope(m_scriptState);
- m_arguments.append(ScriptValue(v8::Number::New(isolate, argument), isolate));
+ ScriptState::Scope scope(m_scriptState.get());
+ m_arguments.append(ScriptValue(m_scriptState.get(), v8::Number::New(isolate, argument)));
}
void ScriptCallArgumentHandler::appendArgument(bool argument)
{
v8::Isolate* isolate = m_scriptState->isolate();
- m_arguments.append(ScriptValue(v8Boolean(argument, isolate), isolate));
+ m_arguments.append(ScriptValue(m_scriptState.get(), v8Boolean(argument, isolate)));
}
-ScriptFunctionCall::ScriptFunctionCall(const ScriptObject& thisObject, const String& name)
+void ScriptCallArgumentHandler::appendArgument(const Vector<ScriptValue>& argument)
+{
+ v8::Isolate* isolate = m_scriptState->isolate();
+ ScriptState::Scope scope(m_scriptState.get());
+ v8::Handle<v8::Array> result = v8::Array::New(isolate, argument.size());
+ for (size_t i = 0; i < argument.size(); ++i)
+ result->Set(v8::Integer::New(isolate, i), argument[i].v8Value());
+ m_arguments.append(ScriptValue(m_scriptState.get(), result));
+}
+
+ScriptFunctionCall::ScriptFunctionCall(const ScriptValue& thisObject, const String& name)
: ScriptCallArgumentHandler(thisObject.scriptState())
, m_thisObject(thisObject)
, m_name(name)
@@ -122,11 +125,13 @@ ScriptFunctionCall::ScriptFunctionCall(const ScriptObject& thisObject, const Str
ScriptValue ScriptFunctionCall::call(bool& hadException, bool reportExceptions)
{
- ScriptScope scope(m_scriptState, reportExceptions);
+ ScriptState::Scope scope(m_scriptState.get());
+ v8::TryCatch tryCatch;
+ tryCatch.SetVerbose(reportExceptions);
- v8::Handle<v8::Object> thisObject = m_thisObject.v8Object();
+ v8::Handle<v8::Object> thisObject = v8::Handle<v8::Object>::Cast(m_thisObject.v8Value());
v8::Local<v8::Value> value = thisObject->Get(v8String(m_scriptState->isolate(), m_name));
- if (!scope.success()) {
+ if (tryCatch.HasCaught()) {
hadException = true;
return ScriptValue();
}
@@ -140,13 +145,13 @@ ScriptValue ScriptFunctionCall::call(bool& hadException, bool reportExceptions)
ASSERT(!info[i].IsEmpty());
}
- v8::Local<v8::Value> result = V8ScriptRunner::callFunction(function, getExecutionContext(), thisObject, m_arguments.size(), info.get(), m_scriptState->isolate());
- if (!scope.success()) {
+ v8::Local<v8::Value> result = V8ScriptRunner::callFunction(function, m_scriptState->executionContext(), thisObject, m_arguments.size(), info.get(), m_scriptState->isolate());
+ if (tryCatch.HasCaught()) {
hadException = true;
return ScriptValue();
}
- return ScriptValue(result, m_scriptState->isolate());
+ return ScriptValue(m_scriptState.get(), result);
}
ScriptValue ScriptFunctionCall::call()
@@ -155,15 +160,17 @@ ScriptValue ScriptFunctionCall::call()
return call(hadException);
}
-ScriptObject ScriptFunctionCall::construct(bool& hadException, bool reportExceptions)
+ScriptValue ScriptFunctionCall::construct(bool& hadException, bool reportExceptions)
{
- ScriptScope scope(m_scriptState, reportExceptions);
+ ScriptState::Scope scope(m_scriptState.get());
+ v8::TryCatch tryCatch;
+ tryCatch.SetVerbose(reportExceptions);
- v8::Handle<v8::Object> thisObject = m_thisObject.v8Object();
+ v8::Handle<v8::Object> thisObject = v8::Handle<v8::Object>::Cast(m_thisObject.v8Value());
v8::Local<v8::Value> value = thisObject->Get(v8String(m_scriptState->isolate(), m_name));
- if (!scope.success()) {
+ if (tryCatch.HasCaught()) {
hadException = true;
- return ScriptObject();
+ return ScriptValue();
}
ASSERT(value->IsFunction());
@@ -173,39 +180,13 @@ ScriptObject ScriptFunctionCall::construct(bool& hadException, bool reportExcept
for (size_t i = 0; i < m_arguments.size(); ++i)
info[i] = m_arguments[i].v8Value();
- v8::Local<v8::Object> result = V8ObjectConstructor::newInstance(constructor, m_arguments.size(), info.get());
- if (!scope.success()) {
+ v8::Local<v8::Object> result = V8ObjectConstructor::newInstance(m_scriptState->isolate(), constructor, m_arguments.size(), info.get());
+ if (tryCatch.HasCaught()) {
hadException = true;
- return ScriptObject();
+ return ScriptValue();
}
- return ScriptObject(m_scriptState, result);
-}
-
-ScriptCallback::ScriptCallback(ScriptState* state, const ScriptValue& function)
- : ScriptCallArgumentHandler(state)
- , m_scriptState(state)
- , m_function(function)
-{
-}
-
-ScriptValue ScriptCallback::call()
-{
- v8::Isolate* isolate = v8::Isolate::GetCurrent();
- ASSERT(isolate->InContext());
- ASSERT(m_function.v8Value()->IsFunction());
-
- v8::TryCatch exceptionCatcher;
- exceptionCatcher.SetVerbose(true);
- v8::Handle<v8::Object> object = isolate->GetCurrentContext()->Global();
- v8::Handle<v8::Function> function = v8::Handle<v8::Function>::Cast(m_function.v8Value());
-
- OwnPtr<v8::Handle<v8::Value>[]> info = adoptArrayPtr(new v8::Handle<v8::Value>[m_arguments.size()]);
- for (size_t i = 0; i < m_arguments.size(); ++i)
- info[i] = m_arguments[i].v8Value();
-
- v8::Handle<v8::Value> result = ScriptController::callFunction(m_scriptState->executionContext(), function, object, m_arguments.size(), info.get(), m_scriptState->isolate());
- return ScriptValue(result, m_scriptState->isolate());
+ return ScriptValue(m_scriptState.get(), result);
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ScriptFunctionCall.h b/chromium/third_party/WebKit/Source/bindings/v8/ScriptFunctionCall.h
index 032b6a0b0ce..f323c3f6359 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/ScriptFunctionCall.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ScriptFunctionCall.h
@@ -31,58 +31,46 @@
#ifndef ScriptFunctionCall_h
#define ScriptFunctionCall_h
-#include "bindings/v8/ScriptObject.h"
+#include "bindings/v8/ScriptValue.h"
#include "wtf/Vector.h"
#include "wtf/text/WTFString.h"
namespace WebCore {
class ScriptValue;
- class ScriptState;
class ScriptCallArgumentHandler {
public:
ScriptCallArgumentHandler(ScriptState* scriptState) : m_scriptState(scriptState) { }
- void appendArgument(const ScriptObject&);
void appendArgument(const ScriptValue&);
void appendArgument(const String&);
void appendArgument(const char*);
void appendArgument(long);
void appendArgument(long long);
- void appendArgument(unsigned int);
+ void appendArgument(unsigned);
void appendArgument(unsigned long);
void appendArgument(int);
void appendArgument(bool);
+ void appendArgument(const Vector<ScriptValue>&);
protected:
- ScriptState* m_scriptState;
+ RefPtr<ScriptState> m_scriptState;
Vector<ScriptValue> m_arguments;
};
class ScriptFunctionCall : public ScriptCallArgumentHandler {
public:
- ScriptFunctionCall(const ScriptObject& thisObject, const String& name);
+ ScriptFunctionCall(const ScriptValue& thisObject, const String& name);
ScriptValue call(bool& hadException, bool reportExceptions = true);
ScriptValue call();
- ScriptObject construct(bool& hadException, bool reportExceptions = true);
+ ScriptValue construct(bool& hadException, bool reportExceptions = true);
protected:
- ScriptObject m_thisObject;
+ ScriptValue m_thisObject;
String m_name;
};
- class ScriptCallback : public ScriptCallArgumentHandler {
- public:
- ScriptCallback(ScriptState*, const ScriptValue&);
-
- ScriptValue call();
-
- private:
- ScriptState* m_scriptState;
- ScriptValue m_function;
- };
-
} // namespace WebCore
#endif // ScriptFunctionCall
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ScriptGCEvent.cpp b/chromium/third_party/WebKit/Source/bindings/v8/ScriptGCEvent.cpp
index 361d8e3e965..9cc90eb4672 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/ScriptGCEvent.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ScriptGCEvent.cpp
@@ -41,7 +41,7 @@ namespace WebCore {
static GCEventData* isolateGCEventData()
{
- V8PerIsolateData* isolateData = V8PerIsolateData::current();
+ V8PerIsolateData* isolateData = V8PerIsolateData::from(v8::Isolate::GetCurrent());
ASSERT(isolateData);
return isolateData->gcEventData();
}
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ScriptGCEvent.h b/chromium/third_party/WebKit/Source/bindings/v8/ScriptGCEvent.h
index 3f95e7f46c7..ee042b5b8af 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/ScriptGCEvent.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ScriptGCEvent.h
@@ -31,8 +31,8 @@
#ifndef ScriptGCEvent_h
#define ScriptGCEvent_h
-#include "v8.h"
#include "wtf/Vector.h"
+#include <v8.h>
namespace WebCore {
@@ -80,6 +80,7 @@ private:
};
+// FIXME(361045): remove ScriptGCEvent once DevTools Timeline migrates to tracing.
class ScriptGCEvent
{
public:
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ScriptHeapSnapshot.cpp b/chromium/third_party/WebKit/Source/bindings/v8/ScriptHeapSnapshot.cpp
index 6077b57febd..b5c2c7f9e71 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/ScriptHeapSnapshot.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ScriptHeapSnapshot.cpp
@@ -51,25 +51,15 @@ String ScriptHeapSnapshot::title() const
return toCoreString(m_snapshot->GetTitle());
}
-unsigned int ScriptHeapSnapshot::uid() const
-{
- return m_snapshot->GetUid();
-}
-
-SnapshotObjectId ScriptHeapSnapshot::maxSnapshotJSObjectId() const
-{
- return m_snapshot->GetMaxSnapshotJSObjectId();
-}
-
namespace {
-class OutputStreamAdapter : public v8::OutputStream {
+class OutputStreamAdapter FINAL : public v8::OutputStream {
public:
OutputStreamAdapter(ScriptHeapSnapshot::OutputStream* output)
: m_output(output) { }
- void EndOfStream() { m_output->Close(); }
- int GetChunkSize() { return 102400; }
- WriteResult WriteAsciiChunk(char* data, int size)
+ virtual void EndOfStream() OVERRIDE { m_output->Close(); }
+ virtual int GetChunkSize() OVERRIDE { return 102400; }
+ virtual WriteResult WriteAsciiChunk(char* data, int size) OVERRIDE
{
m_output->Write(String(data, size));
return kContinue;
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ScriptHeapSnapshot.h b/chromium/third_party/WebKit/Source/bindings/v8/ScriptHeapSnapshot.h
index 1e168599bdb..3ca4f5e9e81 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/ScriptHeapSnapshot.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ScriptHeapSnapshot.h
@@ -33,15 +33,10 @@
#include "wtf/RefCounted.h"
#include "wtf/text/WTFString.h"
-
-namespace v8 {
-class HeapSnapshot;
-}
+#include <v8-profiler.h>
namespace WebCore {
-typedef uint32_t SnapshotObjectId;
-
class ScriptHeapSnapshot FINAL : public RefCounted<ScriptHeapSnapshot> {
public:
class OutputStream {
@@ -58,9 +53,7 @@ public:
~ScriptHeapSnapshot();
String title() const;
- unsigned int uid() const;
void writeJSON(OutputStream* stream);
- SnapshotObjectId maxSnapshotJSObjectId() const;
private:
ScriptHeapSnapshot(const v8::HeapSnapshot* snapshot)
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ScriptObject.h b/chromium/third_party/WebKit/Source/bindings/v8/ScriptObject.h
deleted file mode 100644
index 072313d49be..00000000000
--- a/chromium/third_party/WebKit/Source/bindings/v8/ScriptObject.h
+++ /dev/null
@@ -1,66 +0,0 @@
-/*
- * Copyright (C) 2009 Google Inc. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions are
- * met:
- *
- * * Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * * Redistributions in binary form must reproduce the above
- * copyright notice, this list of conditions and the following disclaimer
- * in the documentation and/or other materials provided with the
- * distribution.
- * * Neither the name of Google Inc. nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
- * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
- * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
- * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
- * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
- * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
- * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
- * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
- * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-#ifndef ScriptObject_h
-#define ScriptObject_h
-
-#include "bindings/v8/ScriptValue.h"
-
-#include <v8.h>
-
-namespace WebCore {
- class InjectedScriptHost;
- class InspectorFrontendHost;
- class ScriptState;
-
- class ScriptObject : public ScriptValue {
- public:
- ScriptObject(ScriptState*, v8::Handle<v8::Object>);
- ScriptObject(ScriptState*, const ScriptValue&);
- ScriptObject() : m_scriptState(0) { };
- virtual ~ScriptObject() { }
-
- v8::Handle<v8::Object> v8Object() const;
- ScriptState* scriptState() const { return m_scriptState; }
- protected:
- ScriptState* m_scriptState;
- };
-
- class ScriptGlobalObject {
- public:
- static bool set(ScriptState*, const char* name, InspectorFrontendHost*);
- static bool get(ScriptState*, const char* name, ScriptObject&);
- private:
- ScriptGlobalObject() { }
- };
-
-}
-
-#endif // ScriptObject_h
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ScriptPreprocessor.cpp b/chromium/third_party/WebKit/Source/bindings/v8/ScriptPreprocessor.cpp
index c9674b96c7a..3c38767e8ff 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/ScriptPreprocessor.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ScriptPreprocessor.cpp
@@ -34,39 +34,41 @@
#include "bindings/v8/ScriptController.h"
#include "bindings/v8/ScriptSourceCode.h"
#include "bindings/v8/ScriptValue.h"
+#include "bindings/v8/V8Binding.h"
#include "bindings/v8/V8ScriptRunner.h"
-#include "core/page/PageConsole.h"
+#include "core/frame/FrameConsole.h"
+#include "core/frame/FrameHost.h"
+#include "core/frame/LocalFrame.h"
#include "wtf/TemporaryChange.h"
namespace WebCore {
-ScriptPreprocessor::ScriptPreprocessor(const ScriptSourceCode& preprocessorSourceCode, ScriptController& controller, PageConsole& console)
+ScriptPreprocessor::ScriptPreprocessor(const ScriptSourceCode& preprocessorSourceCode, LocalFrame* frame)
: m_isPreprocessing(false)
{
+ RefPtr<DOMWrapperWorld> world = DOMWrapperWorld::ensureIsolatedWorld(ScriptPreprocessorIsolatedWorldId, DOMWrapperWorld::mainWorldExtensionGroup);
+ m_scriptState = ScriptState::from(toV8Context(frame, *world));
+
+ v8::HandleScope handleScope(m_scriptState->isolate());
+ ASSERT(frame);
v8::TryCatch tryCatch;
tryCatch.SetVerbose(true);
Vector<ScriptSourceCode> sources;
sources.append(preprocessorSourceCode);
- Vector<ScriptValue> scriptResults;
- controller.executeScriptInIsolatedWorld(ScriptPreprocessorIsolatedWorldId, sources, DOMWrapperWorld::mainWorldExtensionGroup, &scriptResults);
+ Vector<v8::Local<v8::Value> > scriptResults;
+ frame->script().executeScriptInIsolatedWorld(ScriptPreprocessorIsolatedWorldId, sources, DOMWrapperWorld::mainWorldExtensionGroup, &scriptResults);
if (scriptResults.size() != 1) {
- console.addMessage(JSMessageSource, ErrorMessageLevel, "ScriptPreprocessor internal error, one ScriptSourceCode must give exactly one result.");
+ frame->console().addMessage(JSMessageSource, ErrorMessageLevel, "ScriptPreprocessor internal error, one ScriptSourceCode must give exactly one result.");
return;
}
- ScriptValue preprocessorFunction = scriptResults[0];
- if (!preprocessorFunction.isFunction()) {
- console.addMessage(JSMessageSource, ErrorMessageLevel, "The preprocessor must compile to a function.");
+ v8::Local<v8::Value> preprocessorFunction = scriptResults[0];
+ if (preprocessorFunction.IsEmpty() || !preprocessorFunction->IsFunction()) {
+ frame->console().addMessage(JSMessageSource, ErrorMessageLevel, "The preprocessor must compile to a function.");
return;
}
-
- m_world = DOMWrapperWorld::ensureIsolatedWorld(ScriptPreprocessorIsolatedWorldId, DOMWrapperWorld::mainWorldExtensionGroup);
- v8::Local<v8::Context> context = m_world->context(controller);
- m_isolate = context->GetIsolate();
-
- m_context.set(m_isolate, context);
- m_preprocessorFunction.set(m_isolate, v8::Handle<v8::Function>::Cast(preprocessorFunction.v8Value()));
+ m_preprocessorFunction.set(m_scriptState->isolate(), v8::Handle<v8::Function>::Cast(preprocessorFunction));
}
String ScriptPreprocessor::preprocessSourceCode(const String& sourceCode, const String& sourceName)
@@ -74,7 +76,7 @@ String ScriptPreprocessor::preprocessSourceCode(const String& sourceCode, const
if (!isValid())
return sourceCode;
- return preprocessSourceCode(sourceCode, sourceName, v8::Undefined(m_isolate));
+ return preprocessSourceCode(sourceCode, sourceName, v8::Undefined(m_scriptState->isolate()));
}
String ScriptPreprocessor::preprocessSourceCode(const String& sourceCode, const String& sourceName, const String& functionName)
@@ -82,7 +84,7 @@ String ScriptPreprocessor::preprocessSourceCode(const String& sourceCode, const
if (!isValid())
return sourceCode;
- v8::Handle<v8::String> functionNameString = v8String(m_isolate, functionName);
+ v8::Handle<v8::String> functionNameString = v8String(m_scriptState->isolate(), functionName);
return preprocessSourceCode(sourceCode, sourceName, functionNameString);
}
@@ -91,17 +93,17 @@ String ScriptPreprocessor::preprocessSourceCode(const String& sourceCode, const
if (!isValid())
return sourceCode;
- v8::HandleScope handleScope(m_isolate);
- v8::Context::Scope contextScope(m_context.newLocal(m_isolate));
+ v8::Isolate* isolate = m_scriptState->isolate();
+ ScriptState::Scope scope(m_scriptState.get());
- v8::Handle<v8::String> sourceCodeString = v8String(m_isolate, sourceCode);
- v8::Handle<v8::String> sourceNameString = v8String(m_isolate, sourceName);
+ v8::Handle<v8::String> sourceCodeString = v8String(isolate, sourceCode);
+ v8::Handle<v8::String> sourceNameString = v8String(isolate, sourceName);
v8::Handle<v8::Value> argv[] = { sourceCodeString, sourceNameString, functionName};
v8::TryCatch tryCatch;
tryCatch.SetVerbose(true);
TemporaryChange<bool> isPreprocessing(m_isPreprocessing, true);
- v8::Handle<v8::Value> resultValue = V8ScriptRunner::callAsFunction(m_preprocessorFunction.newLocal(m_isolate), m_context.newLocal(m_isolate)->Global(), WTF_ARRAY_LENGTH(argv), argv);
+ v8::Handle<v8::Value> resultValue = V8ScriptRunner::callAsFunction(isolate, m_preprocessorFunction.newLocal(isolate), m_scriptState->context()->Global(), WTF_ARRAY_LENGTH(argv), argv);
if (!resultValue.IsEmpty() && resultValue->IsString())
return toCoreStringWithNullCheck(resultValue.As<v8::String>());
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ScriptPreprocessor.h b/chromium/third_party/WebKit/Source/bindings/v8/ScriptPreprocessor.h
index 823c8be95ef..20e8ac09cb9 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/ScriptPreprocessor.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ScriptPreprocessor.h
@@ -40,12 +40,11 @@ namespace WebCore {
class ScriptController;
class ScriptSourceCode;
class ScriptDebugServer;
-class PageConsole;
class ScriptPreprocessor {
WTF_MAKE_NONCOPYABLE(ScriptPreprocessor);
public:
- ScriptPreprocessor(const ScriptSourceCode&, ScriptController&, PageConsole&);
+ ScriptPreprocessor(const ScriptSourceCode&, LocalFrame*);
String preprocessSourceCode(const String& sourceCode, const String& sourceName);
String preprocessSourceCode(const String& sourceCode, const String& sourceName, const String& functionName);
bool isPreprocessing() { return m_isPreprocessing; }
@@ -53,9 +52,7 @@ public:
private:
String preprocessSourceCode(const String& sourceCode, const String& sourceName, v8::Handle<v8::Value> functionName);
- RefPtr<DOMWrapperWorld> m_world;
- ScopedPersistent<v8::Context> m_context;
- v8::Isolate* m_isolate;
+ RefPtr<ScriptState> m_scriptState;
ScopedPersistent<v8::Function> m_preprocessorFunction;
bool m_isPreprocessing;
};
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ScriptProfiler.cpp b/chromium/third_party/WebKit/Source/bindings/v8/ScriptProfiler.cpp
index 914a943a206..07a65f74a49 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/ScriptProfiler.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ScriptProfiler.cpp
@@ -31,12 +31,11 @@
#include "config.h"
#include "bindings/v8/ScriptProfiler.h"
-#include "V8Node.h"
-#include "V8Window.h"
+#include "bindings/core/v8/V8Node.h"
+#include "bindings/core/v8/V8Window.h"
#include "bindings/v8/RetainedDOMInfo.h"
-#include "bindings/v8/ScriptObject.h"
+#include "bindings/v8/ScriptValue.h"
#include "bindings/v8/V8Binding.h"
-#include "bindings/v8/V8DOMWrapper.h"
#include "bindings/v8/WrapperTypeInfo.h"
#include "core/dom/Document.h"
#include "core/inspector/BindingVisitors.h"
@@ -70,19 +69,19 @@ void ScriptProfiler::start(const String& title)
if (!profiler)
return;
v8::HandleScope handleScope(isolate);
- profiler->StartCpuProfiling(v8String(isolate, title), true);
+ profiler->StartProfiling(v8String(isolate, title), true);
}
-PassRefPtr<ScriptProfile> ScriptProfiler::stop(const String& title)
+PassRefPtrWillBeRawPtr<ScriptProfile> ScriptProfiler::stop(const String& title)
{
v8::Isolate* isolate = v8::Isolate::GetCurrent();
v8::CpuProfiler* profiler = isolate->GetCpuProfiler();
if (!profiler)
- return 0;
+ return nullptr;
v8::HandleScope handleScope(isolate);
- const v8::CpuProfile* profile = profiler->StopCpuProfiling(v8String(isolate, title));
+ v8::CpuProfile* profile = profiler->StopProfiling(v8String(isolate, title));
if (!profile)
- return 0;
+ return nullptr;
String profileTitle = toCoreString(profile->GetTitle());
double idleTime = 0.0;
@@ -101,28 +100,14 @@ void ScriptProfiler::collectGarbage()
v8::V8::LowMemoryNotification();
}
-ScriptObject ScriptProfiler::objectByHeapObjectId(unsigned id)
+ScriptValue ScriptProfiler::objectByHeapObjectId(unsigned id)
{
v8::Isolate* isolate = v8::Isolate::GetCurrent();
v8::HeapProfiler* profiler = isolate->GetHeapProfiler();
- if (!profiler)
- return ScriptObject();
- // As ids are unique, it doesn't matter which HeapSnapshot owns HeapGraphNode.
- // We need to find first HeapSnapshot containing a node with the specified id.
- const v8::HeapGraphNode* node = 0;
- for (int i = 0, l = profiler->GetSnapshotCount(); i < l; ++i) {
- const v8::HeapSnapshot* snapshot = profiler->GetHeapSnapshot(i);
- node = snapshot->GetNodeById(id);
- if (node)
- break;
- }
- if (!node)
- return ScriptObject();
-
v8::HandleScope handleScope(isolate);
- v8::Handle<v8::Value> value = node->GetHeapValue();
- if (!value->IsObject())
- return ScriptObject();
+ v8::Handle<v8::Value> value = profiler->FindObjectById(id);
+ if (value.IsEmpty() || !value->IsObject())
+ return ScriptValue();
v8::Handle<v8::Object> object = value.As<v8::Object>();
@@ -131,11 +116,11 @@ ScriptObject ScriptProfiler::objectByHeapObjectId(unsigned id)
// Skip wrapper boilerplates which are like regular wrappers but don't have
// native object.
if (!wrapper.IsEmpty() && wrapper->IsUndefined())
- return ScriptObject();
+ return ScriptValue();
}
- ScriptState* scriptState = ScriptState::forContext(object->CreationContext());
- return ScriptObject(scriptState, object);
+ ScriptState* scriptState = ScriptState::from(object->CreationContext());
+ return ScriptValue(scriptState, object);
}
unsigned ScriptProfiler::getHeapObjectId(const ScriptValue& value)
@@ -146,13 +131,20 @@ unsigned ScriptProfiler::getHeapObjectId(const ScriptValue& value)
return id;
}
+void ScriptProfiler::clearHeapObjectIds()
+{
+ v8::Isolate* isolate = v8::Isolate::GetCurrent();
+ v8::HeapProfiler* profiler = isolate->GetHeapProfiler();
+ profiler->ClearObjectIds();
+}
+
namespace {
-class ActivityControlAdapter : public v8::ActivityControl {
+class ActivityControlAdapter FINAL : public v8::ActivityControl {
public:
ActivityControlAdapter(ScriptProfiler::HeapSnapshotProgress* progress)
: m_progress(progress), m_firstReport(true) { }
- ControlOption ReportProgressValue(int done, int total)
+ virtual ControlOption ReportProgressValue(int done, int total) OVERRIDE
{
ControlOption result = m_progress->isCanceled() ? kAbort : kContinue;
if (m_firstReport) {
@@ -169,19 +161,16 @@ private:
bool m_firstReport;
};
-class GlobalObjectNameResolver : public v8::HeapProfiler::ObjectNameResolver {
+class GlobalObjectNameResolver FINAL : public v8::HeapProfiler::ObjectNameResolver {
public:
- virtual const char* GetName(v8::Handle<v8::Object> object)
+ virtual const char* GetName(v8::Handle<v8::Object> object) OVERRIDE
{
- if (V8DOMWrapper::isWrapperOfType(object, &V8Window::wrapperTypeInfo)) {
- DOMWindow* window = V8Window::toNative(object);
- if (window) {
- CString url = window->document()->url().string().utf8();
- m_strings.append(url);
- return url.data();
- }
- }
- return 0;
+ LocalDOMWindow* window = toDOMWindow(object, v8::Isolate::GetCurrent());
+ if (!window)
+ return 0;
+ CString url = window->document()->url().string().utf8();
+ m_strings.append(url);
+ return url.data();
}
private:
@@ -190,9 +179,9 @@ private:
} // namespace
-void ScriptProfiler::startTrackingHeapObjects()
+void ScriptProfiler::startTrackingHeapObjects(bool trackAllocations)
{
- v8::Isolate::GetCurrent()->GetHeapProfiler()->StartTrackingHeapObjects();
+ v8::Isolate::GetCurrent()->GetHeapProfiler()->StartTrackingHeapObjects(trackAllocations);
}
namespace {
@@ -244,13 +233,13 @@ PassRefPtr<ScriptHeapSnapshot> ScriptProfiler::takeHeapSnapshot(const String& ti
v8::Isolate* isolate = v8::Isolate::GetCurrent();
v8::HeapProfiler* profiler = isolate->GetHeapProfiler();
if (!profiler)
- return 0;
+ return nullptr;
v8::HandleScope handleScope(isolate);
ASSERT(control);
ActivityControlAdapter adapter(control);
GlobalObjectNameResolver resolver;
const v8::HeapSnapshot* snapshot = profiler->TakeHeapSnapshot(v8String(isolate, title), &adapter, &resolver);
- return snapshot ? ScriptHeapSnapshot::create(snapshot) : 0;
+ return snapshot ? ScriptHeapSnapshot::create(snapshot) : nullptr;
}
static v8::RetainedObjectInfo* retainedDOMInfo(uint16_t classId, v8::Handle<v8::Value> wrapper)
@@ -292,7 +281,7 @@ void ScriptProfiler::visitNodeWrappers(WrappedNodeVisitor* visitor)
// Casting to Handle is safe here, since the Persistent cannot get
// GCd during visiting.
v8::Handle<v8::Object>* wrapper = reinterpret_cast<v8::Handle<v8::Object>*>(value);
- ASSERT_UNUSED(m_isolate, V8Node::hasInstanceInAnyWorld(*wrapper, m_isolate));
+ ASSERT_UNUSED(m_isolate, V8Node::hasInstance(*wrapper, m_isolate));
ASSERT((*wrapper)->IsObject());
m_visitor->visitNode(V8Node::toNative(*wrapper));
}
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ScriptProfiler.h b/chromium/third_party/WebKit/Source/bindings/v8/ScriptProfiler.h
index f406c520764..167da66bf81 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/ScriptProfiler.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ScriptProfiler.h
@@ -32,7 +32,6 @@
#define ScriptProfiler_h
#include "bindings/v8/ScriptHeapSnapshot.h"
-#include "bindings/v8/ScriptState.h"
#include "core/inspector/ScriptProfile.h"
#include "wtf/Forward.h"
@@ -41,11 +40,9 @@
namespace WebCore {
-class ExternalArrayVisitor;
class ExternalStringVisitor;
class WrappedNodeVisitor;
class Page;
-class ScriptObject;
class ScriptValue;
class WorkerGlobalScope;
@@ -68,13 +65,14 @@ public:
};
static void collectGarbage();
- static ScriptObject objectByHeapObjectId(unsigned id);
+ static ScriptValue objectByHeapObjectId(unsigned id);
static unsigned getHeapObjectId(const ScriptValue&);
+ static void clearHeapObjectIds();
static void setSamplingInterval(int intervalUs);
static void start(const String& title);
- static PassRefPtr<ScriptProfile> stop(const String& title);
+ static PassRefPtrWillBeRawPtr<ScriptProfile> stop(const String& title);
static PassRefPtr<ScriptHeapSnapshot> takeHeapSnapshot(const String& title, HeapSnapshotProgress*);
- static void startTrackingHeapObjects();
+ static void startTrackingHeapObjects(bool trackAllocations);
static void stopTrackingHeapObjects();
static unsigned requestHeapStatsUpdate(OutputStream*);
static void initialize();
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ScriptPromise.cpp b/chromium/third_party/WebKit/Source/bindings/v8/ScriptPromise.cpp
index bdf4105edde..d6d8b317e0b 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/ScriptPromise.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ScriptPromise.cpp
@@ -31,31 +31,105 @@
#include "config.h"
#include "bindings/v8/ScriptPromise.h"
+#include "bindings/v8/ScriptPromiseResolver.h"
#include "bindings/v8/V8Binding.h"
-#include "bindings/v8/V8DOMWrapper.h"
-#include "bindings/v8/custom/V8PromiseCustom.h"
+#include "core/dom/DOMException.h"
#include <v8.h>
namespace WebCore {
-ScriptPromise ScriptPromise::createPending(ExecutionContext* context)
+namespace {
+
+struct WithScriptState {
+ // Used by ToV8Value<WithScriptState, ScriptState*>.
+ static v8::Handle<v8::Object> getCreationContext(ScriptState* scriptState)
+ {
+ return scriptState->context()->Global();
+ }
+};
+
+} // namespace
+
+ScriptPromise::ScriptPromise(ScriptState* scriptState, v8::Handle<v8::Value> value)
+ : m_scriptState(scriptState)
+{
+ if (value.IsEmpty())
+ return;
+
+ if (!value->IsPromise()) {
+ m_promise = ScriptValue(scriptState, v8::Handle<v8::Value>());
+ V8ThrowException::throwTypeError("the given value is not a Promise", scriptState->isolate());
+ return;
+ }
+ m_promise = ScriptValue(scriptState, value);
+}
+
+ScriptPromise ScriptPromise::then(PassOwnPtr<ScriptFunction> onFulfilled, PassOwnPtr<ScriptFunction> onRejected)
+{
+ if (m_promise.isEmpty())
+ return ScriptPromise();
+
+ v8::Local<v8::Object> promise = m_promise.v8Value().As<v8::Object>();
+ v8::Local<v8::Function> v8OnFulfilled = ScriptFunction::adoptByGarbageCollector(onFulfilled);
+ v8::Local<v8::Function> v8OnRejected = ScriptFunction::adoptByGarbageCollector(onRejected);
+
+ ASSERT(promise->IsPromise());
+ // Return this Promise if no handlers are given.
+ // In fact it is not the exact bahavior of Promise.prototype.then
+ // but that is not a problem in this case.
+ v8::Local<v8::Promise> resultPromise = promise.As<v8::Promise>();
+ if (!v8OnFulfilled.IsEmpty()) {
+ resultPromise = resultPromise->Then(v8OnFulfilled);
+ if (resultPromise.IsEmpty()) {
+ // v8::Promise::Then may return an empty value, for example when
+ // the stack is exhausted.
+ return ScriptPromise();
+ }
+ }
+ if (!v8OnRejected.IsEmpty())
+ resultPromise = resultPromise->Catch(v8OnRejected);
+
+ return ScriptPromise(m_scriptState.get(), resultPromise);
+}
+
+ScriptPromise ScriptPromise::cast(ScriptState* scriptState, const ScriptValue& value)
+{
+ return ScriptPromise::cast(scriptState, value.v8Value());
+}
+
+ScriptPromise ScriptPromise::cast(ScriptState* scriptState, v8::Handle<v8::Value> value)
+{
+ if (value.IsEmpty())
+ return ScriptPromise();
+ if (value->IsPromise()) {
+ return ScriptPromise(scriptState, value);
+ }
+ RefPtr<ScriptPromiseResolver> resolver = ScriptPromiseResolver::create(scriptState);
+ ScriptPromise promise = resolver->promise();
+ resolver->resolve(value);
+ return promise;
+}
+
+ScriptPromise ScriptPromise::reject(ScriptState* scriptState, const ScriptValue& value)
+{
+ return ScriptPromise::reject(scriptState, value.v8Value());
+}
+
+ScriptPromise ScriptPromise::reject(ScriptState* scriptState, v8::Handle<v8::Value> value)
{
- ASSERT(context);
- v8::Isolate* isolate = toIsolate(context);
- ASSERT(isolate->InContext());
- v8::Handle<v8::Context> v8Context = toV8Context(context, DOMWrapperWorld::current());
- v8::Handle<v8::Object> creationContext = v8Context.IsEmpty() ? v8::Object::New() : v8Context->Global();
- v8::Handle<v8::Object> promise = V8PromiseCustom::createPromise(creationContext, isolate);
- return ScriptPromise(promise, isolate);
+ if (value.IsEmpty())
+ return ScriptPromise();
+ RefPtr<ScriptPromiseResolver> resolver = ScriptPromiseResolver::create(scriptState);
+ ScriptPromise promise = resolver->promise();
+ resolver->reject(value);
+ return promise;
}
-ScriptPromise ScriptPromise::createPending()
+ScriptPromise ScriptPromise::rejectWithDOMException(ScriptState* scriptState, PassRefPtrWillBeRawPtr<DOMException> exception)
{
- v8::Isolate* isolate = v8::Isolate::GetCurrent();
- ASSERT(isolate->InContext());
- v8::Handle<v8::Object> promise = V8PromiseCustom::createPromise(v8::Object::New(), isolate);
- return ScriptPromise(promise, isolate);
+ ASSERT(scriptState->isolate()->InContext());
+ return reject(scriptState, ToV8Value<WithScriptState, v8::Handle<v8::Object> >::toV8Value(exception, scriptState->context()->Global(), scriptState->isolate()));
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ScriptPromise.h b/chromium/third_party/WebKit/Source/bindings/v8/ScriptPromise.h
index 0a93b10f3b4..eb79e4e3b17 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/ScriptPromise.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ScriptPromise.h
@@ -31,14 +31,16 @@
#ifndef ScriptPromise_h
#define ScriptPromise_h
-#include "bindings/v8/ScopedPersistent.h"
+#include "bindings/v8/ScriptFunction.h"
#include "bindings/v8/ScriptValue.h"
-#include "bindings/v8/V8ScriptRunner.h"
+#include "platform/heap/Handle.h"
+#include "wtf/PassOwnPtr.h"
+#include "wtf/PassRefPtr.h"
#include <v8.h>
namespace WebCore {
-class ExecutionContext;
+class DOMException;
// ScriptPromise is the class for representing Promise values in C++ world.
// ScriptPromise holds a Promise.
@@ -48,22 +50,13 @@ class ExecutionContext;
class ScriptPromise {
public:
// Constructs an empty promise.
- ScriptPromise()
- : m_promise()
- {
- }
+ ScriptPromise() { }
- explicit ScriptPromise(const ScriptValue& promise)
- : m_promise(promise)
- {
- ASSERT(!m_promise.hasNoValue());
- }
+ // Constructs a ScriptPromise from |promise|.
+ // If |promise| is not a Promise object, throws a v8 TypeError.
+ ScriptPromise(ScriptState*, v8::Handle<v8::Value> promise);
- ScriptPromise(v8::Handle<v8::Value> promise, v8::Isolate* isolate)
- : m_promise(promise, isolate)
- {
- ASSERT(!m_promise.hasNoValue());
- }
+ ScriptPromise then(PassOwnPtr<ScriptFunction> onFulfilled, PassOwnPtr<ScriptFunction> onRejected = PassOwnPtr<ScriptFunction>());
bool isObject() const
{
@@ -90,9 +83,9 @@ public:
return m_promise.isolate();
}
- bool hasNoValue() const
+ bool isEmpty() const
{
- return m_promise.hasNoValue();
+ return m_promise.isEmpty();
}
void clear()
@@ -100,10 +93,20 @@ public:
m_promise.clear();
}
- static ScriptPromise createPending();
- static ScriptPromise createPending(ExecutionContext*);
+ // Constructs and returns a ScriptPromise from |value|.
+ // if |value| is not a Promise object, returns a Promise object
+ // resolved with |value|.
+ // Returns |value| itself if it is a Promise.
+ static ScriptPromise cast(ScriptState*, const ScriptValue& /*value*/);
+ static ScriptPromise cast(ScriptState*, v8::Handle<v8::Value> /*value*/);
+
+ static ScriptPromise reject(ScriptState*, const ScriptValue&);
+ static ScriptPromise reject(ScriptState*, v8::Handle<v8::Value>);
+
+ static ScriptPromise rejectWithDOMException(ScriptState*, PassRefPtrWillBeRawPtr<DOMException>);
private:
+ RefPtr<ScriptState> m_scriptState;
ScriptValue m_promise;
};
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ScriptPromiseResolver.cpp b/chromium/third_party/WebKit/Source/bindings/v8/ScriptPromiseResolver.cpp
index fec672fcc15..ea7a6476b3f 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/ScriptPromiseResolver.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ScriptPromiseResolver.cpp
@@ -31,20 +31,21 @@
#include "config.h"
#include "bindings/v8/ScriptPromiseResolver.h"
-#include "bindings/v8/ScriptState.h"
#include "bindings/v8/ScriptValue.h"
#include "bindings/v8/V8Binding.h"
#include "bindings/v8/V8DOMWrapper.h"
-#include "bindings/v8/custom/V8PromiseCustom.h"
#include <v8.h>
namespace WebCore {
-ScriptPromiseResolver::ScriptPromiseResolver(ScriptPromise promise)
- : m_isolate(promise.isolate())
- , m_promise(promise)
+ScriptPromiseResolver::ScriptPromiseResolver(ScriptState* scriptState)
+ : m_scriptState(scriptState)
{
+ v8::Isolate* isolate = m_scriptState->isolate();
+ ASSERT(!m_scriptState->contextIsEmpty());
+ ASSERT(isolate->InContext());
+ m_resolver = ScriptValue(scriptState, v8::Promise::Resolver::New(isolate));
}
ScriptPromiseResolver::~ScriptPromiseResolver()
@@ -52,61 +53,42 @@ ScriptPromiseResolver::~ScriptPromiseResolver()
// We don't call "reject" here because it requires a caller
// to be in a v8 context.
- m_promise.clear();
+ m_resolver.clear();
}
-PassRefPtr<ScriptPromiseResolver> ScriptPromiseResolver::create(ScriptPromise promise, ExecutionContext* context)
+ScriptPromise ScriptPromiseResolver::promise()
{
- ASSERT(promise.isolate()->InContext());
- ASSERT(context);
- return adoptRef(new ScriptPromiseResolver(promise));
+ ASSERT(!m_scriptState->contextIsEmpty());
+ ASSERT(m_scriptState->isolate()->InContext());
+ if (!m_resolver.isEmpty()) {
+ v8::Local<v8::Promise::Resolver> v8Resolver = m_resolver.v8Value().As<v8::Promise::Resolver>();
+ return ScriptPromise(m_scriptState.get(), v8Resolver->GetPromise());
+ }
+ return ScriptPromise();
}
-PassRefPtr<ScriptPromiseResolver> ScriptPromiseResolver::create(ScriptPromise promise)
+PassRefPtr<ScriptPromiseResolver> ScriptPromiseResolver::create(ScriptState* scriptState)
{
- ASSERT(promise.isolate()->InContext());
- return adoptRef(new ScriptPromiseResolver(promise));
-}
-
-bool ScriptPromiseResolver::isPending() const
-{
- ASSERT(m_isolate->InContext());
- if (m_promise.hasNoValue())
- return false;
- v8::Local<v8::Object> promise = m_promise.v8Value().As<v8::Object>();
- v8::Local<v8::Object> internal = V8PromiseCustom::getInternal(promise);
- V8PromiseCustom::PromiseState state = V8PromiseCustom::getState(internal);
- return state == V8PromiseCustom::Pending;
+ ASSERT(scriptState->isolate()->InContext());
+ return adoptRef(new ScriptPromiseResolver(scriptState));
}
void ScriptPromiseResolver::resolve(v8::Handle<v8::Value> value)
{
- ASSERT(m_isolate->InContext());
- if (!isPending())
- return;
- V8PromiseCustom::resolve(m_promise.v8Value().As<v8::Object>(), value, m_isolate);
- m_promise.clear();
+ ASSERT(m_scriptState->isolate()->InContext());
+ if (!m_resolver.isEmpty()) {
+ m_resolver.v8Value().As<v8::Promise::Resolver>()->Resolve(value);
+ }
+ m_resolver.clear();
}
void ScriptPromiseResolver::reject(v8::Handle<v8::Value> value)
{
- ASSERT(m_isolate->InContext());
- if (!isPending())
- return;
- V8PromiseCustom::reject(m_promise.v8Value().As<v8::Object>(), value, m_isolate);
- m_promise.clear();
-}
-
-void ScriptPromiseResolver::resolve(ScriptValue value)
-{
- ASSERT(m_isolate->InContext());
- resolve(value.v8Value());
-}
-
-void ScriptPromiseResolver::reject(ScriptValue value)
-{
- ASSERT(m_isolate->InContext());
- reject(value.v8Value());
+ ASSERT(m_scriptState->isolate()->InContext());
+ if (!m_resolver.isEmpty()) {
+ m_resolver.v8Value().As<v8::Promise::Resolver>()->Reject(value);
+ }
+ m_resolver.clear();
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ScriptPromiseResolver.h b/chromium/third_party/WebKit/Source/bindings/v8/ScriptPromiseResolver.h
index 0379b244be5..513abab924b 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/ScriptPromiseResolver.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ScriptPromiseResolver.h
@@ -31,9 +31,6 @@
#ifndef ScriptPromiseResolver_h
#define ScriptPromiseResolver_h
-#include "bindings/v8/DOMWrapperWorld.h"
-#include "bindings/v8/ScopedPersistent.h"
-#include "bindings/v8/ScriptObject.h"
#include "bindings/v8/ScriptPromise.h"
#include "bindings/v8/ScriptState.h"
#include "bindings/v8/ScriptValue.h"
@@ -50,25 +47,28 @@ class ExecutionContext;
// (resolve / reject) from C++ world.
// ScriptPromiseResolver holds a PromiseResolver.
// Here is a typical usage:
-// 1. Create a ScriptPromiseResolver from a ScriptPromise.
-// 2. Pass the promise object of the holder to a JavaScript program
+// 1. Create a ScriptPromiseResolver.
+// 2. Pass the associated promise object to a JavaScript program
// (such as XMLHttpRequest return value).
// 3. Call resolve or reject when the operation completes or
// the operation fails respectively.
//
// Most methods including constructors must be called within a v8 context.
// To use ScriptPromiseResolver out of a v8 context the caller must
-// enter a v8 context, for example by using ScriptScope and ScriptState.
+// enter a v8 context. Please use ScriptPromiseResolverWithContext
+// in such cases.
//
// To prevent memory leaks, you should release the reference manually
// by calling resolve or reject.
// Destroying the object will also release the reference.
-//
+// Note that ScriptPromiseResolver::promise returns an empty value when the
+// resolver is already resolved or rejected. If you want to resolve a resolver
+// immediately and return the associated promise, you should get the promise
+// before resolving.
class ScriptPromiseResolver : public RefCounted<ScriptPromiseResolver> {
WTF_MAKE_NONCOPYABLE(ScriptPromiseResolver);
public:
- static PassRefPtr<ScriptPromiseResolver> create(ScriptPromise, ExecutionContext*);
- static PassRefPtr<ScriptPromiseResolver> create(ScriptPromise);
+ static PassRefPtr<ScriptPromiseResolver> create(ScriptState*);
// A ScriptPromiseResolver should be resolved / rejected before
// its destruction.
@@ -76,90 +76,75 @@ public:
// entering a v8 context.
~ScriptPromiseResolver();
- // Return true if the promise object is in pending state.
- bool isPending() const;
+ // Returns the underlying Promise.
+ // Note that the underlying Promise is cleared when |resolve| or |reject|
+ // is called.
+ ScriptPromise promise();
- ScriptPromise promise()
+ template<typename T>
+ void resolve(const T& value, ExecutionContext* executionContext)
{
- ASSERT(m_promise.isolate()->InContext());
- return m_promise;
+ ASSERT(m_scriptState->isolate()->InContext());
+ // You should use ScriptPromiseResolverWithContext when you want
+ // to resolve a Promise in a non-original V8 context.
+ return resolve(value);
}
-
- // To use following template methods, T must be a DOM class.
-
- // This method will be implemented by the code generator.
- template<typename T>
- void resolve(T* value, v8::Handle<v8::Object> creationContext) { resolve(toV8NoInline(value, creationContext, m_isolate)); }
template<typename T>
- void reject(T* value, v8::Handle<v8::Object> creationContext) { reject(toV8NoInline(value, creationContext, m_isolate)); }
-
+ void reject(const T& value, ExecutionContext* executionContext)
+ {
+ ASSERT(m_scriptState->isolate()->InContext());
+ // You should use ScriptPromiseResolverWithContext when you want
+ // to reject a Promise in a non-original V8 context.
+ return reject(value);
+ }
template<typename T>
- void resolve(PassRefPtr<T> value, v8::Handle<v8::Object> creationContext) { resolve(value.get(), creationContext); }
+ void resolve(const T& value)
+ {
+ ASSERT(m_scriptState->isolate()->InContext());
+ resolve(toV8Value(value));
+ }
template<typename T>
- void reject(PassRefPtr<T> value, v8::Handle<v8::Object> creationContext) { reject(value.get(), creationContext); }
+ void reject(const T& value)
+ {
+ ASSERT(m_scriptState->isolate()->InContext());
+ reject(toV8Value(value));
+ }
+ template<typename T> void resolve(const T& value, v8::Handle<v8::Object> creationContext)
+ {
+ ASSERT(m_scriptState->isolate()->InContext());
+ resolve(toV8Value(value, creationContext));
+ }
+ template<typename T> void reject(const T& value, v8::Handle<v8::Object> creationContext)
+ {
+ ASSERT(m_scriptState->isolate()->InContext());
+ reject(toV8Value(value, creationContext));
+ }
- template<typename T>
- inline void resolve(T* value, ExecutionContext*);
- template<typename T>
- inline void reject(T* value, ExecutionContext*);
+ v8::Isolate* isolate() const { return m_scriptState->isolate(); }
- template<typename T>
- void resolve(PassRefPtr<T> value, ExecutionContext* context) { resolve(value.get(), context); }
- template<typename T>
- void reject(PassRefPtr<T> value, ExecutionContext* context) { reject(value.get(), context); }
+ void resolve(v8::Handle<v8::Value>);
+ void reject(v8::Handle<v8::Value>);
+private:
template<typename T>
- inline void resolve(T* value);
- template<typename T>
- inline void reject(T* value);
+ v8::Handle<v8::Value> toV8Value(const T& value, v8::Handle<v8::Object> creationContext)
+ {
+ return ToV8Value<ScriptPromiseResolver, v8::Handle<v8::Object> >::toV8Value(value, creationContext, m_scriptState->isolate());
+ }
template<typename T>
- void resolve(PassRefPtr<T> value) { resolve(value.get()); }
- template<typename T>
- void reject(PassRefPtr<T> value) { reject(value.get()); }
-
- void resolve(ScriptValue);
- void reject(ScriptValue);
+ v8::Handle<v8::Value> toV8Value(const T& value)
+ {
+ return ToV8Value<ScriptPromiseResolver, v8::Handle<v8::Object> >::toV8Value(value, m_scriptState->context()->Global(), m_scriptState->isolate());
+ }
-private:
- ScriptPromiseResolver(ScriptPromise);
- void resolve(v8::Handle<v8::Value>);
- void reject(v8::Handle<v8::Value>);
+ explicit ScriptPromiseResolver(ScriptState*);
- v8::Isolate* m_isolate;
- ScriptPromise m_promise;
+ // FIXME: Remove this once ScriptValue::scriptState() becomes available.
+ RefPtr<ScriptState> m_scriptState;
+ ScriptValue m_resolver;
};
-template<typename T>
-void ScriptPromiseResolver::resolve(T* value, ExecutionContext* context)
-{
- ASSERT(m_isolate->InContext());
- v8::Handle<v8::Context> v8Context = toV8Context(context, DOMWrapperWorld::current());
- resolve(value, v8Context->Global());
-}
-
-template<typename T>
-void ScriptPromiseResolver::reject(T* value, ExecutionContext* context)
-{
- ASSERT(m_isolate->InContext());
- v8::Handle<v8::Context> v8Context = toV8Context(context, DOMWrapperWorld::current());
- reject(value, v8Context->Global());
-}
-
-template<typename T>
-void ScriptPromiseResolver::resolve(T* value)
-{
- ASSERT(m_isolate->InContext());
- resolve(value, v8::Object::New(m_isolate));
-}
-
-template<typename T>
-void ScriptPromiseResolver::reject(T* value)
-{
- ASSERT(m_isolate->InContext());
- reject(value, v8::Object::New(m_isolate));
-}
-
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ScriptPromiseResolverTest.cpp b/chromium/third_party/WebKit/Source/bindings/v8/ScriptPromiseResolverTest.cpp
index 26b796dd892..8a21cf7896b 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/ScriptPromiseResolverTest.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ScriptPromiseResolverTest.cpp
@@ -33,7 +33,6 @@
#include "bindings/v8/ScriptPromise.h"
#include "bindings/v8/V8Binding.h"
-#include "bindings/v8/custom/V8PromiseCustom.h"
#include <gtest/gtest.h>
#include <v8.h>
@@ -42,132 +41,145 @@ namespace WebCore {
namespace {
-class ScriptPromiseResolverTest : public testing::Test {
+class Function : public ScriptFunction {
public:
- ScriptPromiseResolverTest()
- : m_isolate(v8::Isolate::GetCurrent())
- , m_handleScope(m_isolate)
- , m_context(m_isolate, v8::Context::New(m_isolate))
- , m_contextScope(m_context.newLocal(m_isolate))
+ static PassOwnPtr<Function> create(v8::Isolate* isolate, String* value)
{
+ return adoptPtr(new Function(isolate, value));
}
- void SetUp()
+ virtual ScriptValue call(ScriptValue value) OVERRIDE
{
- v8::Handle<v8::Context> context(m_context.newLocal(m_isolate));
- V8PerContextDataHolder::install(context);
- m_perContextData = V8PerContextData::create(context);
- m_perContextData->init();
- m_promise = ScriptPromise::createPending();
- m_resolver = ScriptPromiseResolver::create(m_promise);
+ ASSERT(!value.isEmpty());
+ *m_value = toCoreString(value.v8Value()->ToString());
+ return value;
}
- void TearDown()
- {
- m_resolver = 0;
- m_promise.clear();
- m_perContextData.clear();
- }
+private:
+ Function(v8::Isolate* isolate, String* value) : ScriptFunction(isolate), m_value(value) { }
- V8PromiseCustom::PromiseState state()
- {
- return V8PromiseCustom::getState(V8PromiseCustom::getInternal(promise()));
- }
+ String* m_value;
+};
- v8::Local<v8::Value> result()
+class ScriptPromiseResolverTest : public testing::Test {
+public:
+ ScriptPromiseResolverTest()
+ : m_scope(v8::Isolate::GetCurrent())
{
- return V8PromiseCustom::getInternal(promise())->GetInternalField(V8PromiseCustom::InternalResultIndex);
+ m_resolver = ScriptPromiseResolver::create(m_scope.scriptState());
}
- v8::Local<v8::Object> promise()
+ virtual ~ScriptPromiseResolverTest()
{
- ASSERT(!m_promise.hasNoValue());
- return m_promise.v8Value().As<v8::Object>();
+ // Run all pending microtasks here.
+ isolate()->RunMicrotasks();
}
+ v8::Isolate* isolate() { return m_scope.isolate(); }
+
protected:
- v8::Isolate* m_isolate;
- v8::HandleScope m_handleScope;
- ScopedPersistent<v8::Context> m_context;
- v8::Context::Scope m_contextScope;
RefPtr<ScriptPromiseResolver> m_resolver;
- ScriptPromise m_promise;
- OwnPtr<V8PerContextData> m_perContextData;
+ V8TestingScope m_scope;
};
TEST_F(ScriptPromiseResolverTest, initialState)
{
- EXPECT_TRUE(m_resolver->isPending());
- EXPECT_EQ(V8PromiseCustom::Pending, state());
- EXPECT_TRUE(result()->IsUndefined());
+ ScriptPromise promise = m_resolver->promise();
+ ASSERT_FALSE(promise.isEmpty());
+ String onFulfilled, onRejected;
+ promise.then(Function::create(isolate(), &onFulfilled), Function::create(isolate(), &onRejected));
+
+ EXPECT_EQ(String(), onFulfilled);
+ EXPECT_EQ(String(), onRejected);
+
+ isolate()->RunMicrotasks();
+
+ EXPECT_EQ(String(), onFulfilled);
+ EXPECT_EQ(String(), onRejected);
}
TEST_F(ScriptPromiseResolverTest, resolve)
{
- EXPECT_TRUE(m_resolver->isPending());
- EXPECT_EQ(V8PromiseCustom::Pending, state());
- EXPECT_TRUE(result()->IsUndefined());
+ ScriptPromise promise = m_resolver->promise();
+ ASSERT_FALSE(promise.isEmpty());
+ String onFulfilled, onRejected;
+ promise.then(Function::create(isolate(), &onFulfilled), Function::create(isolate(), &onRejected));
+
+ EXPECT_EQ(String(), onFulfilled);
+ EXPECT_EQ(String(), onRejected);
- m_resolver->resolve(ScriptValue(v8::Integer::New(3, m_isolate), m_isolate));
+ m_resolver->resolve("hello");
+ EXPECT_TRUE(m_resolver->promise().isEmpty());
+ isolate()->RunMicrotasks();
- EXPECT_FALSE(m_resolver->isPending());
- EXPECT_EQ(V8PromiseCustom::Fulfilled, state());
- ASSERT_TRUE(result()->IsNumber());
- EXPECT_EQ(3, result().As<v8::Integer>()->Value());
+ EXPECT_EQ("hello", onFulfilled);
+ EXPECT_EQ(String(), onRejected);
}
TEST_F(ScriptPromiseResolverTest, reject)
{
- EXPECT_TRUE(m_resolver->isPending());
- EXPECT_EQ(V8PromiseCustom::Pending, state());
- EXPECT_TRUE(result()->IsUndefined());
+ ScriptPromise promise = m_resolver->promise();
+ ASSERT_FALSE(promise.isEmpty());
+ String onFulfilled, onRejected;
+ promise.then(Function::create(isolate(), &onFulfilled), Function::create(isolate(), &onRejected));
- m_resolver->reject(ScriptValue(v8::Integer::New(3, m_isolate), m_isolate));
+ EXPECT_EQ(String(), onFulfilled);
+ EXPECT_EQ(String(), onRejected);
- EXPECT_FALSE(m_resolver->isPending());
- EXPECT_EQ(V8PromiseCustom::Rejected, state());
- ASSERT_TRUE(result()->IsNumber());
- EXPECT_EQ(3, result().As<v8::Integer>()->Value());
+ m_resolver->reject("hello");
+ EXPECT_TRUE(m_resolver->promise().isEmpty());
+ isolate()->RunMicrotasks();
+
+ EXPECT_EQ(String(), onFulfilled);
+ EXPECT_EQ("hello", onRejected);
}
TEST_F(ScriptPromiseResolverTest, resolveOverResolve)
{
- EXPECT_TRUE(m_resolver->isPending());
- EXPECT_EQ(V8PromiseCustom::Pending, state());
- EXPECT_TRUE(result()->IsUndefined());
-
- m_resolver->resolve(ScriptValue(v8::Integer::New(3, m_isolate), m_isolate));
-
- EXPECT_FALSE(m_resolver->isPending());
- EXPECT_EQ(V8PromiseCustom::Fulfilled, state());
- ASSERT_TRUE(result()->IsNumber());
- EXPECT_EQ(3, result().As<v8::Integer>()->Value());
-
- m_resolver->resolve(ScriptValue(v8::Integer::New(4, m_isolate), m_isolate));
- EXPECT_FALSE(m_resolver->isPending());
- EXPECT_EQ(V8PromiseCustom::Fulfilled, state());
- ASSERT_TRUE(result()->IsNumber());
- EXPECT_EQ(3, result().As<v8::Integer>()->Value());
+ ScriptPromise promise = m_resolver->promise();
+ ASSERT_FALSE(promise.isEmpty());
+ String onFulfilled, onRejected;
+ promise.then(Function::create(isolate(), &onFulfilled), Function::create(isolate(), &onRejected));
+
+ EXPECT_EQ(String(), onFulfilled);
+ EXPECT_EQ(String(), onRejected);
+
+ m_resolver->resolve("hello");
+ EXPECT_TRUE(m_resolver->promise().isEmpty());
+ isolate()->RunMicrotasks();
+
+ EXPECT_EQ("hello", onFulfilled);
+ EXPECT_EQ(String(), onRejected);
+
+ m_resolver->resolve("world");
+ isolate()->RunMicrotasks();
+
+ EXPECT_EQ("hello", onFulfilled);
+ EXPECT_EQ(String(), onRejected);
}
TEST_F(ScriptPromiseResolverTest, rejectOverResolve)
{
- EXPECT_TRUE(m_resolver->isPending());
- EXPECT_EQ(V8PromiseCustom::Pending, state());
- EXPECT_TRUE(result()->IsUndefined());
-
- m_resolver->resolve(ScriptValue(v8::Integer::New(3, m_isolate), m_isolate));
-
- EXPECT_FALSE(m_resolver->isPending());
- EXPECT_EQ(V8PromiseCustom::Fulfilled, state());
- ASSERT_TRUE(result()->IsNumber());
- EXPECT_EQ(3, result().As<v8::Integer>()->Value());
-
- m_resolver->reject(ScriptValue(v8::Integer::New(4, m_isolate), m_isolate));
- EXPECT_FALSE(m_resolver->isPending());
- EXPECT_EQ(V8PromiseCustom::Fulfilled, state());
- ASSERT_TRUE(result()->IsNumber());
- EXPECT_EQ(3, result().As<v8::Integer>()->Value());
+ ScriptPromise promise = m_resolver->promise();
+ ASSERT_FALSE(promise.isEmpty());
+ String onFulfilled, onRejected;
+ promise.then(Function::create(isolate(), &onFulfilled), Function::create(isolate(), &onRejected));
+
+ EXPECT_EQ(String(), onFulfilled);
+ EXPECT_EQ(String(), onRejected);
+
+ m_resolver->resolve("hello");
+ EXPECT_TRUE(m_resolver->promise().isEmpty());
+ isolate()->RunMicrotasks();
+
+ EXPECT_EQ("hello", onFulfilled);
+ EXPECT_EQ(String(), onRejected);
+
+ m_resolver->reject("world");
+ isolate()->RunMicrotasks();
+
+ EXPECT_EQ("hello", onFulfilled);
+ EXPECT_EQ(String(), onRejected);
}
} // namespace
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ScriptPromiseResolverWithContext.cpp b/chromium/third_party/WebKit/Source/bindings/v8/ScriptPromiseResolverWithContext.cpp
new file mode 100644
index 00000000000..6cd7ab8b5ef
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ScriptPromiseResolverWithContext.cpp
@@ -0,0 +1,101 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "config.h"
+#include "bindings/v8/ScriptPromiseResolverWithContext.h"
+
+#include "bindings/v8/V8RecursionScope.h"
+
+namespace WebCore {
+
+ScriptPromiseResolverWithContext::ScriptPromiseResolverWithContext(ScriptState* scriptState)
+ : ActiveDOMObject(scriptState->executionContext())
+ , m_state(Pending)
+ , m_scriptState(scriptState)
+ , m_mode(Default)
+ , m_timer(this, &ScriptPromiseResolverWithContext::onTimerFired)
+ , m_resolver(ScriptPromiseResolver::create(m_scriptState.get()))
+#if ASSERTION_ENABLED
+ , m_isPromiseCalled(false)
+#endif
+{
+ if (executionContext()->activeDOMObjectsAreStopped())
+ m_state = ResolvedOrRejected;
+}
+
+void ScriptPromiseResolverWithContext::suspend()
+{
+ m_timer.stop();
+}
+
+void ScriptPromiseResolverWithContext::resume()
+{
+ if (m_state == Resolving || m_state == Rejecting)
+ m_timer.startOneShot(0, FROM_HERE);
+}
+
+void ScriptPromiseResolverWithContext::stop()
+{
+ m_timer.stop();
+ clear();
+}
+
+void ScriptPromiseResolverWithContext::keepAliveWhilePending()
+{
+ if (m_state == ResolvedOrRejected || m_mode == KeepAliveWhilePending)
+ return;
+
+ // Keep |this| while the promise is Pending.
+ // deref() will be called in clear().
+ m_mode = KeepAliveWhilePending;
+ ref();
+}
+
+void ScriptPromiseResolverWithContext::onTimerFired(Timer<ScriptPromiseResolverWithContext>*)
+{
+ ScriptState::Scope scope(m_scriptState.get());
+ resolveOrRejectImmediately();
+}
+
+void ScriptPromiseResolverWithContext::resolveOrRejectImmediately()
+{
+ ASSERT(!executionContext()->activeDOMObjectsAreStopped());
+ ASSERT(!executionContext()->activeDOMObjectsAreSuspended());
+ {
+ // FIXME: The V8RecursionScope is only necessary to force microtask delivery for promises
+ // resolved or rejected in workers. It can be removed once worker threads run microtasks
+ // at the end of every task (rather than just the main thread).
+ V8RecursionScope scope(m_scriptState->isolate(), m_scriptState->executionContext());
+ if (m_state == Resolving) {
+ m_resolver->resolve(m_value.newLocal(m_scriptState->isolate()));
+ } else {
+ ASSERT(m_state == Rejecting);
+ m_resolver->reject(m_value.newLocal(m_scriptState->isolate()));
+ }
+ }
+ clear();
+}
+
+void ScriptPromiseResolverWithContext::clear()
+{
+ if (m_state == ResolvedOrRejected)
+ return;
+ ResolutionState state = m_state;
+ m_state = ResolvedOrRejected;
+ m_resolver.clear();
+ m_value.clear();
+ if (m_mode == KeepAliveWhilePending) {
+ // |ref| was called in |keepAliveWhilePending|.
+ deref();
+ }
+ // |this| may be deleted here, but it is safe to check |state| because
+ // it doesn't depend on |this|. When |this| is deleted, |state| can't be
+ // |Resolving| nor |Rejecting| and hence |this->deref()| can't be executed.
+ if (state == Resolving || state == Rejecting) {
+ // |ref| was called in |resolveOrReject|.
+ deref();
+ }
+}
+
+} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ScriptPromiseResolverWithContext.h b/chromium/third_party/WebKit/Source/bindings/v8/ScriptPromiseResolverWithContext.h
new file mode 100644
index 00000000000..729fb15beed
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ScriptPromiseResolverWithContext.h
@@ -0,0 +1,145 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef ScriptPromiseResolverWithContext_h
+#define ScriptPromiseResolverWithContext_h
+
+#include "bindings/v8/ScopedPersistent.h"
+#include "bindings/v8/ScriptPromise.h"
+#include "bindings/v8/ScriptPromiseResolver.h"
+#include "bindings/v8/ScriptState.h"
+#include "bindings/v8/V8Binding.h"
+#include "core/dom/ActiveDOMObject.h"
+#include "core/dom/ExecutionContext.h"
+#include "platform/Timer.h"
+#include "wtf/RefCounted.h"
+#include "wtf/Vector.h"
+#include <v8.h>
+
+namespace WebCore {
+
+// This class wraps ScriptPromiseResolver and provides the following
+// functionalities in addition to ScriptPromiseResolver's.
+// - A ScriptPromiseResolverWithContext retains a ScriptState. A caller
+// can call resolve or reject from outside of a V8 context.
+// - This class is an ActiveDOMObject and keeps track of the associated
+// ExecutionContext state. When the ExecutionContext is suspended,
+// resolve or reject will be delayed. When it is stopped, resolve or reject
+// will be ignored.
+class ScriptPromiseResolverWithContext : public ActiveDOMObject, public RefCounted<ScriptPromiseResolverWithContext> {
+ WTF_MAKE_NONCOPYABLE(ScriptPromiseResolverWithContext);
+
+public:
+ static PassRefPtr<ScriptPromiseResolverWithContext> create(ScriptState* scriptState)
+ {
+ RefPtr<ScriptPromiseResolverWithContext> resolver = adoptRef(new ScriptPromiseResolverWithContext(scriptState));
+ resolver->suspendIfNeeded();
+ return resolver.release();
+ }
+
+ virtual ~ScriptPromiseResolverWithContext()
+ {
+ // This assertion fails if:
+ // - promise() is called at least once and
+ // - this resolver is destructed before it is resolved, rejected or
+ // the associated ExecutionContext is stopped.
+ ASSERT(m_state == ResolvedOrRejected || !m_isPromiseCalled);
+ }
+
+ // Anything that can be passed to toV8Value can be passed to this function.
+ template <typename T>
+ void resolve(T value)
+ {
+ resolveOrReject(value, Resolving);
+ }
+
+ // Anything that can be passed to toV8Value can be passed to this function.
+ template <typename T>
+ void reject(T value)
+ {
+ resolveOrReject(value, Rejecting);
+ }
+
+ ScriptState* scriptState() { return m_scriptState.get(); }
+
+ // Note that an empty ScriptPromise will be returned after resolve or
+ // reject is called.
+ ScriptPromise promise()
+ {
+#if ASSERT_ENABLED
+ m_isPromiseCalled = true;
+#endif
+ return m_resolver ? m_resolver->promise() : ScriptPromise();
+ }
+
+ ScriptState* scriptState() const { return m_scriptState.get(); }
+
+ // ActiveDOMObject implementation.
+ virtual void suspend() OVERRIDE;
+ virtual void resume() OVERRIDE;
+ virtual void stop() OVERRIDE;
+
+ // Once this function is called this resolver stays alive while the
+ // promise is pending and the associated ExecutionContext isn't stopped.
+ void keepAliveWhilePending();
+
+protected:
+ // You need to call suspendIfNeeded after the construction because
+ // this is an ActiveDOMObject.
+ explicit ScriptPromiseResolverWithContext(ScriptState*);
+
+private:
+ enum ResolutionState {
+ Pending,
+ Resolving,
+ Rejecting,
+ ResolvedOrRejected,
+ };
+ enum LifetimeMode {
+ Default,
+ KeepAliveWhilePending,
+ };
+
+ template<typename T>
+ v8::Handle<v8::Value> toV8Value(const T& value)
+ {
+ return ToV8Value<ScriptPromiseResolverWithContext, v8::Handle<v8::Object> >::toV8Value(value, m_scriptState->context()->Global(), m_scriptState->isolate());
+ }
+
+ template <typename T>
+ void resolveOrReject(T value, ResolutionState newState)
+ {
+ if (m_state != Pending || !executionContext() || executionContext()->activeDOMObjectsAreStopped())
+ return;
+ ASSERT(newState == Resolving || newState == Rejecting);
+ m_state = newState;
+ // Retain this object until it is actually resolved or rejected.
+ // |deref| will be called in |clear|.
+ ref();
+
+ ScriptState::Scope scope(m_scriptState.get());
+ m_value.set(m_scriptState->isolate(), toV8Value(value));
+ if (!executionContext()->activeDOMObjectsAreSuspended())
+ resolveOrRejectImmediately();
+ }
+
+ void resolveOrRejectImmediately();
+ void onTimerFired(Timer<ScriptPromiseResolverWithContext>*);
+ void clear();
+
+ ResolutionState m_state;
+ const RefPtr<ScriptState> m_scriptState;
+ LifetimeMode m_mode;
+ Timer<ScriptPromiseResolverWithContext> m_timer;
+ RefPtr<ScriptPromiseResolver> m_resolver;
+ ScopedPersistent<v8::Value> m_value;
+#if ASSERT_ENABLED
+ // True if promise() is called.
+ bool m_isPromiseCalled;
+#endif
+};
+
+} // namespace WebCore
+
+#endif // #ifndef ScriptPromiseResolverWithContext_h
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ScriptPromiseTest.cpp b/chromium/third_party/WebKit/Source/bindings/v8/ScriptPromiseTest.cpp
new file mode 100644
index 00000000000..618b38ea91b
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ScriptPromiseTest.cpp
@@ -0,0 +1,260 @@
+/*
+ * Copyright (C) 2014 Google Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are
+ * met:
+ *
+ * * Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * * Redistributions in binary form must reproduce the above
+ * copyright notice, this list of conditions and the following disclaimer
+ * in the documentation and/or other materials provided with the
+ * distribution.
+ * * Neither the name of Google Inc. nor the names of its
+ * contributors may be used to endorse or promote products derived from
+ * this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+ * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+ * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+ * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include "config.h"
+#include "bindings/v8/ScriptPromise.h"
+
+#include "bindings/v8/ScriptFunction.h"
+#include "bindings/v8/ScriptPromiseResolver.h"
+#include "bindings/v8/ScriptValue.h"
+#include "bindings/v8/V8Binding.h"
+#include "core/dom/DOMException.h"
+#include "core/dom/ExceptionCode.h"
+
+#include <gtest/gtest.h>
+#include <v8.h>
+
+namespace WebCore {
+
+namespace {
+
+void callback(const v8::FunctionCallbackInfo<v8::Value>& info) { }
+
+class Function : public ScriptFunction {
+public:
+ static PassOwnPtr<Function> create(v8::Isolate* isolate, String* value)
+ {
+ return adoptPtr(new Function(isolate, value));
+ }
+
+ virtual ScriptValue call(ScriptValue value) OVERRIDE
+ {
+ ASSERT(!value.isEmpty());
+ *m_value = toCoreString(value.v8Value()->ToString());
+ return value;
+ }
+
+private:
+ Function(v8::Isolate* isolate, String* value) : ScriptFunction(isolate), m_value(value) { }
+
+ String* m_value;
+};
+
+class ScriptPromiseTest : public testing::Test {
+public:
+ ScriptPromiseTest()
+ : m_scope(v8::Isolate::GetCurrent())
+ {
+ }
+
+ ~ScriptPromiseTest()
+ {
+ // FIXME: We put this statement here to clear an exception from the isolate.
+ createClosure(callback, v8::Undefined(m_scope.isolate()), m_scope.isolate());
+
+ // Execute all pending microtasks
+ isolate()->RunMicrotasks();
+ }
+
+ ScriptState* scriptState() const { return m_scope.scriptState(); }
+ v8::Isolate* isolate() const { return m_scope.isolate(); }
+
+protected:
+ V8TestingScope m_scope;
+};
+
+TEST_F(ScriptPromiseTest, constructFromNonPromise)
+{
+ v8::TryCatch trycatch;
+ ScriptPromise promise(scriptState(), v8::Undefined(isolate()));
+ ASSERT_TRUE(trycatch.HasCaught());
+ ASSERT_TRUE(promise.isEmpty());
+}
+
+TEST_F(ScriptPromiseTest, thenResolve)
+{
+ RefPtr<ScriptPromiseResolver> resolver = ScriptPromiseResolver::create(scriptState());
+ ScriptPromise promise = resolver->promise();
+ String onFulfilled, onRejected;
+ promise.then(Function::create(isolate(), &onFulfilled), Function::create(isolate(), &onRejected));
+
+ ASSERT_FALSE(promise.isEmpty());
+ EXPECT_EQ(String(), onFulfilled);
+ EXPECT_EQ(String(), onRejected);
+
+ isolate()->RunMicrotasks();
+ resolver->resolve("hello");
+
+ EXPECT_EQ(String(), onFulfilled);
+ EXPECT_EQ(String(), onRejected);
+
+ isolate()->RunMicrotasks();
+
+ EXPECT_EQ("hello", onFulfilled);
+ EXPECT_EQ(String(), onRejected);
+}
+
+TEST_F(ScriptPromiseTest, resolveThen)
+{
+ RefPtr<ScriptPromiseResolver> resolver = ScriptPromiseResolver::create(scriptState());
+ ScriptPromise promise = resolver->promise();
+ String onFulfilled, onRejected;
+ resolver->resolve("hello");
+ promise.then(Function::create(isolate(), &onFulfilled), Function::create(isolate(), &onRejected));
+
+ ASSERT_FALSE(promise.isEmpty());
+ EXPECT_EQ(String(), onFulfilled);
+ EXPECT_EQ(String(), onRejected);
+
+ isolate()->RunMicrotasks();
+
+ EXPECT_EQ("hello", onFulfilled);
+ EXPECT_EQ(String(), onRejected);
+}
+
+TEST_F(ScriptPromiseTest, thenReject)
+{
+ RefPtr<ScriptPromiseResolver> resolver = ScriptPromiseResolver::create(scriptState());
+ ScriptPromise promise = resolver->promise();
+ String onFulfilled, onRejected;
+ promise.then(Function::create(isolate(), &onFulfilled), Function::create(isolate(), &onRejected));
+
+ ASSERT_FALSE(promise.isEmpty());
+ EXPECT_EQ(String(), onFulfilled);
+ EXPECT_EQ(String(), onRejected);
+
+ isolate()->RunMicrotasks();
+ resolver->reject("hello");
+
+ EXPECT_EQ(String(), onFulfilled);
+ EXPECT_EQ(String(), onRejected);
+
+ isolate()->RunMicrotasks();
+
+ EXPECT_EQ(String(), onFulfilled);
+ EXPECT_EQ("hello", onRejected);
+}
+
+TEST_F(ScriptPromiseTest, rejectThen)
+{
+ RefPtr<ScriptPromiseResolver> resolver = ScriptPromiseResolver::create(scriptState());
+ ScriptPromise promise = resolver->promise();
+ String onFulfilled, onRejected;
+ resolver->reject("hello");
+ promise.then(Function::create(isolate(), &onFulfilled), Function::create(isolate(), &onRejected));
+
+ ASSERT_FALSE(promise.isEmpty());
+ EXPECT_EQ(String(), onFulfilled);
+ EXPECT_EQ(String(), onRejected);
+
+ isolate()->RunMicrotasks();
+
+ EXPECT_EQ(String(), onFulfilled);
+ EXPECT_EQ("hello", onRejected);
+}
+
+TEST_F(ScriptPromiseTest, castPromise)
+{
+ ScriptPromise promise = ScriptPromiseResolver::create(scriptState())->promise();
+ ScriptPromise newPromise = ScriptPromise::cast(scriptState(), promise.v8Value());
+
+ ASSERT_FALSE(promise.isEmpty());
+ EXPECT_EQ(promise.v8Value(), newPromise.v8Value());
+}
+
+TEST_F(ScriptPromiseTest, castNonPromise)
+{
+ String onFulfilled1, onFulfilled2, onRejected1, onRejected2;
+
+ ScriptValue value = ScriptValue(scriptState(), v8String(isolate(), "hello"));
+ ScriptPromise promise1 = ScriptPromise::cast(scriptState(), ScriptValue(value));
+ ScriptPromise promise2 = ScriptPromise::cast(scriptState(), ScriptValue(value));
+ promise1.then(Function::create(isolate(), &onFulfilled1), Function::create(isolate(), &onRejected1));
+ promise2.then(Function::create(isolate(), &onFulfilled2), Function::create(isolate(), &onRejected2));
+
+ ASSERT_FALSE(promise1.isEmpty());
+ ASSERT_FALSE(promise2.isEmpty());
+ EXPECT_NE(promise1.v8Value(), promise2.v8Value());
+
+ ASSERT_TRUE(promise1.v8Value()->IsPromise());
+ ASSERT_TRUE(promise2.v8Value()->IsPromise());
+
+ EXPECT_EQ(String(), onFulfilled1);
+ EXPECT_EQ(String(), onFulfilled2);
+ EXPECT_EQ(String(), onRejected1);
+ EXPECT_EQ(String(), onRejected2);
+
+ isolate()->RunMicrotasks();
+
+ EXPECT_EQ("hello", onFulfilled1);
+ EXPECT_EQ("hello", onFulfilled2);
+ EXPECT_EQ(String(), onRejected1);
+ EXPECT_EQ(String(), onRejected2);
+}
+
+TEST_F(ScriptPromiseTest, reject)
+{
+ String onFulfilled, onRejected;
+
+ ScriptValue value = ScriptValue(scriptState(), v8String(isolate(), "hello"));
+ ScriptPromise promise = ScriptPromise::reject(scriptState(), ScriptValue(value));
+ promise.then(Function::create(isolate(), &onFulfilled), Function::create(isolate(), &onRejected));
+
+ ASSERT_FALSE(promise.isEmpty());
+ ASSERT_TRUE(promise.v8Value()->IsPromise());
+
+ EXPECT_EQ(String(), onFulfilled);
+ EXPECT_EQ(String(), onRejected);
+
+ isolate()->RunMicrotasks();
+
+ EXPECT_EQ(String(), onFulfilled);
+ EXPECT_EQ("hello", onRejected);
+}
+
+TEST_F(ScriptPromiseTest, rejectWithExceptionState)
+{
+ String onFulfilled, onRejected;
+ ScriptPromise promise = ScriptPromise::rejectWithDOMException(scriptState(), DOMException::create(SyntaxError, "some syntax error"));
+ promise.then(Function::create(isolate(), &onFulfilled), Function::create(isolate(), &onRejected));
+
+ ASSERT_FALSE(promise.isEmpty());
+ EXPECT_EQ(String(), onFulfilled);
+ EXPECT_EQ(String(), onRejected);
+
+ isolate()->RunMicrotasks();
+
+ EXPECT_EQ(String(), onFulfilled);
+ EXPECT_EQ("SyntaxError: some syntax error", onRejected);
+}
+
+} // namespace
+
+} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ScriptRegexp.cpp b/chromium/third_party/WebKit/Source/bindings/v8/ScriptRegexp.cpp
index d0be2a1ec28..b4e25188288 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/ScriptRegexp.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ScriptRegexp.cpp
@@ -31,7 +31,8 @@
#include "bindings/v8/V8Binding.h"
#include "bindings/v8/V8PerIsolateData.h"
-#include "bindings/v8/V8RecursionScope.h"
+#include "bindings/v8/V8ScriptRunner.h"
+#include "core/dom/ScriptForbiddenScope.h"
namespace WebCore {
@@ -39,8 +40,8 @@ ScriptRegexp::ScriptRegexp(const String& pattern, TextCaseSensitivity caseSensit
{
v8::Isolate* isolate = v8::Isolate::GetCurrent();
v8::HandleScope handleScope(isolate);
- v8::Local<v8::Context> context = V8PerIsolateData::from(isolate)->ensureRegexContext();
- v8::Context::Scope scope(context);
+ v8::Context::Scope contextScope(V8PerIsolateData::from(isolate)->ensureScriptRegexpContext());
+ v8::TryCatch tryCatch;
unsigned flags = v8::RegExp::kNone;
if (caseSensitivity == TextCaseInsensitive)
@@ -48,8 +49,7 @@ ScriptRegexp::ScriptRegexp(const String& pattern, TextCaseSensitivity caseSensit
if (multilineMode == MultilineEnabled)
flags |= v8::RegExp::kMultiline;
- v8::TryCatch tryCatch;
- v8::Local<v8::RegExp> regex = v8::RegExp::New(v8String(context->GetIsolate(), pattern), static_cast<v8::RegExp::Flags>(flags));
+ v8::Local<v8::RegExp> regex = v8::RegExp::New(v8String(isolate, pattern), static_cast<v8::RegExp::Flags>(flags));
// If the regex failed to compile we'll get an empty handle.
if (!regex.IsEmpty())
@@ -68,19 +68,20 @@ int ScriptRegexp::match(const String& string, int startFrom, int* matchLength) c
if (string.length() > INT_MAX)
return -1;
+ ScriptForbiddenScope::AllowUserAgentScript allowScript;
+
v8::Isolate* isolate = v8::Isolate::GetCurrent();
v8::HandleScope handleScope(isolate);
- v8::Local<v8::Context> context = V8PerIsolateData::current()->ensureRegexContext();
- v8::Context::Scope scope(context);
+ v8::Context::Scope contextScope(V8PerIsolateData::from(isolate)->ensureScriptRegexpContext());
v8::TryCatch tryCatch;
- V8RecursionScope::MicrotaskSuppression microtaskScope;
-
v8::Local<v8::RegExp> regex = m_regex.newLocal(isolate);
v8::Local<v8::Function> exec = regex->Get(v8AtomicString(isolate, "exec")).As<v8::Function>();
+ v8::Handle<v8::Value> argv[] = { v8String(isolate, string.substring(startFrom)) };
+ v8::Local<v8::Value> returnValue = V8ScriptRunner::callInternalFunction(exec, regex, WTF_ARRAY_LENGTH(argv), argv, isolate);
- v8::Handle<v8::Value> argv[] = { v8String(context->GetIsolate(), string.substring(startFrom)) };
- v8::Local<v8::Value> returnValue = exec->Call(regex, 1, argv);
+ if (tryCatch.HasCaught())
+ return -1;
// RegExp#exec returns null if there's no match, otherwise it returns an
// Array of strings with the first being the whole match string and others
@@ -89,12 +90,12 @@ int ScriptRegexp::match(const String& string, int startFrom, int* matchLength) c
//
// https://developer.mozilla.org/en-US/docs/JavaScript/Reference/Global_Objects/RegExp/exec
+ ASSERT(!returnValue.IsEmpty());
if (!returnValue->IsArray())
return -1;
v8::Local<v8::Array> result = returnValue.As<v8::Array>();
int matchOffset = result->Get(v8AtomicString(isolate, "index"))->ToInt32()->Value();
-
if (matchLength) {
v8::Local<v8::String> match = result->Get(0).As<v8::String>();
*matchLength = match->Length();
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ScriptScope.cpp b/chromium/third_party/WebKit/Source/bindings/v8/ScriptScope.cpp
deleted file mode 100644
index 70815114cae..00000000000
--- a/chromium/third_party/WebKit/Source/bindings/v8/ScriptScope.cpp
+++ /dev/null
@@ -1,58 +0,0 @@
-/*
- * Copyright (C) 2009 Google Inc. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions are
- * met:
- *
- * * Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * * Redistributions in binary form must reproduce the above
- * copyright notice, this list of conditions and the following disclaimer
- * in the documentation and/or other materials provided with the
- * distribution.
- * * Neither the name of Google Inc. nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
- * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
- * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
- * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
- * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
- * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
- * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
- * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
- * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-#include "config.h"
-#include "bindings/v8/ScriptScope.h"
-
-#include "bindings/v8/ScriptState.h"
-#include "wtf/Assertions.h"
-
-#include <v8.h>
-
-namespace WebCore {
-
-ScriptScope::ScriptScope(ScriptState* scriptState, bool reportExceptions)
- : m_handleScope(scriptState->isolate())
- , m_context(scriptState->context())
- , m_scope(m_context)
-{
- m_exceptionCatcher.SetVerbose(reportExceptions);
- ASSERT(!m_context.IsEmpty());
-}
-
-bool ScriptScope::success()
-{
- if (!m_exceptionCatcher.HasCaught())
- return true;
- m_exceptionCatcher.Reset();
- return false;
-}
-
-} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ScriptScope.h b/chromium/third_party/WebKit/Source/bindings/v8/ScriptScope.h
deleted file mode 100644
index ed2cf2f2e87..00000000000
--- a/chromium/third_party/WebKit/Source/bindings/v8/ScriptScope.h
+++ /dev/null
@@ -1,55 +0,0 @@
-/*
- * Copyright (C) 2009 Google Inc. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions are
- * met:
- *
- * * Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * * Redistributions in binary form must reproduce the above
- * copyright notice, this list of conditions and the following disclaimer
- * in the documentation and/or other materials provided with the
- * distribution.
- * * Neither the name of Google Inc. nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
- * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
- * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
- * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
- * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
- * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
- * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
- * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
- * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-#ifndef ScriptScope_h
-#define ScriptScope_h
-
-#include <v8.h>
-
-namespace WebCore {
- class ScriptState;
-
- class ScriptScope {
- public:
- ScriptScope(ScriptState* scriptState, bool reportExceptions = true);
- bool success();
-
- v8::Local<v8::Object> global() const { return m_context->Global(); }
-
- private:
- v8::HandleScope m_handleScope;
- v8::Local<v8::Context> m_context;
- v8::Context::Scope m_scope;
- v8::TryCatch m_exceptionCatcher;
- };
-
-}
-
-#endif // ScriptScope_h
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ScriptSourceCode.h b/chromium/third_party/WebKit/Source/bindings/v8/ScriptSourceCode.h
index d5ddbccd082..92944bd9064 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/ScriptSourceCode.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ScriptSourceCode.h
@@ -38,8 +38,6 @@
#include "wtf/text/TextPosition.h"
#include "wtf/text/WTFString.h"
-#include <v8.h>
-
namespace WebCore {
class ScriptSourceCode {
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ScriptState.cpp b/chromium/third_party/WebKit/Source/bindings/v8/ScriptState.cpp
index 0eda05f2ce6..5e17e4c6da8 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/ScriptState.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ScriptState.cpp
@@ -1,126 +1,114 @@
-/*
- * Copyright (C) 2009, 2011 Google Inc. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions are
- * met:
- *
- * * Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * * Redistributions in binary form must reproduce the above
- * copyright notice, this list of conditions and the following disclaimer
- * in the documentation and/or other materials provided with the
- * distribution.
- * * Neither the name of Google Inc. nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
- * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
- * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
- * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
- * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
- * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
- * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
- * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
- * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
#include "config.h"
#include "bindings/v8/ScriptState.h"
-#include "V8Window.h"
-#include "V8WorkerGlobalScope.h"
-#include "bindings/v8/ScriptController.h"
-#include "bindings/v8/V8HiddenPropertyName.h"
-#include "bindings/v8/WorkerScriptController.h"
-#include "core/frame/Frame.h"
-#include "core/workers/WorkerGlobalScope.h"
-#include <v8.h>
-#include "wtf/Assertions.h"
+#include "bindings/v8/V8Binding.h"
+#include "core/dom/ExecutionContext.h"
+#include "core/frame/LocalFrame.h"
namespace WebCore {
-ScriptState::ScriptState(v8::Handle<v8::Context> context)
- : m_context(context->GetIsolate(), context)
- , m_isolate(context->GetIsolate())
+PassRefPtr<ScriptState> ScriptState::create(v8::Handle<v8::Context> context, PassRefPtr<DOMWrapperWorld> world)
{
- m_context.setWeak(this, &setWeakCallback);
+ RefPtr<ScriptState> scriptState = adoptRef(new ScriptState(context, world));
+ // This ref() is for keeping this ScriptState alive as long as the v8::Context is alive.
+ // This is deref()ed in the weak callback of the v8::Context.
+ scriptState->ref();
+ return scriptState;
+}
+
+static void weakCallback(const v8::WeakCallbackData<v8::Context, ScriptState>& data)
+{
+ data.GetValue()->SetAlignedPointerInEmbedderData(v8ContextPerContextDataIndex, 0);
+ data.GetParameter()->clearContext();
+ data.GetParameter()->deref();
+}
+
+ScriptState::ScriptState(v8::Handle<v8::Context> context, PassRefPtr<DOMWrapperWorld> world)
+ : m_isolate(context->GetIsolate())
+ , m_context(m_isolate, context)
+ , m_world(world)
+ , m_perContextData(V8PerContextData::create(context))
+{
+ ASSERT(m_world);
+ m_context.setWeak(this, &weakCallback);
+ context->SetAlignedPointerInEmbedderData(v8ContextPerContextDataIndex, this);
}
ScriptState::~ScriptState()
{
+ ASSERT(!m_perContextData);
+ ASSERT(m_context.isEmpty());
}
-DOMWindow* ScriptState::domWindow() const
+bool ScriptState::evalEnabled() const
{
v8::HandleScope handleScope(m_isolate);
- return toDOMWindow(m_context.newLocal(m_isolate));
+ return context()->IsCodeGenerationFromStringsAllowed();
}
-ExecutionContext* ScriptState::executionContext() const
+void ScriptState::setEvalEnabled(bool enabled)
{
v8::HandleScope handleScope(m_isolate);
- return toExecutionContext(m_context.newLocal(m_isolate));
+ return context()->AllowCodeGenerationFromStrings(enabled);
}
-ScriptState* ScriptState::forContext(v8::Handle<v8::Context> context)
+ScriptValue ScriptState::getFromGlobalObject(const char* name)
{
- v8::Context::Scope contextScope(context);
-
- v8::Local<v8::Object> innerGlobal = v8::Local<v8::Object>::Cast(context->Global()->GetPrototype());
-
- v8::Local<v8::Value> scriptStateWrapper = innerGlobal->GetHiddenValue(V8HiddenPropertyName::scriptState(context->GetIsolate()));
- if (!scriptStateWrapper.IsEmpty() && scriptStateWrapper->IsExternal())
- return static_cast<ScriptState*>(v8::External::Cast(*scriptStateWrapper)->Value());
+ v8::HandleScope handleScope(m_isolate);
+ v8::Local<v8::Value> v8Value = context()->Global()->Get(v8AtomicString(isolate(), name));
+ return ScriptValue(this, v8Value);
+}
- ScriptState* scriptState = new ScriptState(context);
- innerGlobal->SetHiddenValue(V8HiddenPropertyName::scriptState(context->GetIsolate()), v8::External::New(context->GetIsolate(), scriptState));
- return scriptState;
+ExecutionContext* ScriptState::executionContext() const
+{
+ v8::HandleScope scope(m_isolate);
+ return toExecutionContext(context());
}
-ScriptState* ScriptState::current()
+void ScriptState::setExecutionContext(ExecutionContext*)
{
- v8::Isolate* isolate = v8::Isolate::GetCurrent();
- v8::HandleScope handleScope(isolate);
- v8::Local<v8::Context> context = isolate->GetCurrentContext();
- ASSERT(!context.IsEmpty());
- return ScriptState::forContext(context);
+ ASSERT_NOT_REACHED();
}
-void ScriptState::setWeakCallback(const v8::WeakCallbackData<v8::Context, ScriptState>& data)
+LocalDOMWindow* ScriptState::domWindow() const
{
- delete data.GetParameter();
+ v8::HandleScope scope(m_isolate);
+ return toDOMWindow(context());
}
-bool ScriptState::evalEnabled() const
+ScriptState* ScriptState::forMainWorld(LocalFrame* frame)
{
- v8::HandleScope handleScope(m_isolate);
- return context()->IsCodeGenerationFromStringsAllowed();
+ v8::Isolate* isolate = toIsolate(frame);
+ v8::HandleScope handleScope(isolate);
+ return ScriptState::from(toV8Context(frame, DOMWrapperWorld::mainWorld()));
}
-void ScriptState::setEvalEnabled(bool enabled)
+PassRefPtr<ScriptStateForTesting> ScriptStateForTesting::create(v8::Handle<v8::Context> context, PassRefPtr<DOMWrapperWorld> world)
{
- v8::HandleScope handleScope(m_isolate);
- return context()->AllowCodeGenerationFromStrings(enabled);
+ RefPtr<ScriptStateForTesting> scriptState = adoptRef(new ScriptStateForTesting(context, world));
+ // This ref() is for keeping this ScriptState alive as long as the v8::Context is alive.
+ // This is deref()ed in the weak callback of the v8::Context.
+ scriptState->ref();
+ return scriptState;
}
-ScriptState* mainWorldScriptState(Frame* frame)
+ScriptStateForTesting::ScriptStateForTesting(v8::Handle<v8::Context> context, PassRefPtr<DOMWrapperWorld> world)
+ : ScriptState(context, world)
{
- v8::HandleScope handleScope(toIsolate(frame));
- return ScriptState::forContext(frame->script().mainWorldContext());
}
-ScriptState* scriptStateFromWorkerGlobalScope(WorkerGlobalScope* workerGlobalScope)
+ExecutionContext* ScriptStateForTesting::executionContext() const
{
- WorkerScriptController* script = workerGlobalScope->script();
- if (!script)
- return 0;
+ return m_executionContext;
+}
- v8::HandleScope handleScope(script->isolate());
- return ScriptState::forContext(script->context());
+void ScriptStateForTesting::setExecutionContext(ExecutionContext* executionContext)
+{
+ m_executionContext = executionContext;
}
}
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ScriptState.h b/chromium/third_party/WebKit/Source/bindings/v8/ScriptState.h
index ac93b551167..81bc5840070 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/ScriptState.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ScriptState.h
@@ -1,130 +1,145 @@
-/*
- * Copyright (C) 2008, 2009, 2011 Google Inc. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions are
- * met:
- *
- * * Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * * Redistributions in binary form must reproduce the above
- * copyright notice, this list of conditions and the following disclaimer
- * in the documentation and/or other materials provided with the
- * distribution.
- * * Neither the name of Google Inc. nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
- * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
- * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
- * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
- * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
- * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
- * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
- * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
- * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
#ifndef ScriptState_h
#define ScriptState_h
#include "bindings/v8/ScopedPersistent.h"
-#include "bindings/v8/V8Utilities.h"
+#include "bindings/v8/V8PerContextData.h"
+#include "wtf/RefCounted.h"
#include <v8.h>
-#include "wtf/Noncopyable.h"
namespace WebCore {
-class DOMWindow;
+class LocalDOMWindow;
class DOMWrapperWorld;
-class Frame;
class ExecutionContext;
-class WorkerGlobalScope;
+class LocalFrame;
+class ScriptValue;
-class ScriptState {
+// ScriptState is created when v8::Context is created.
+// ScriptState is destroyed when v8::Context is garbage-collected and
+// all V8 proxy objects that have references to the ScriptState are destructed.
+class ScriptState : public RefCounted<ScriptState> {
WTF_MAKE_NONCOPYABLE(ScriptState);
public:
- bool hadException() { return !m_exception.isEmpty(); }
- void setException(v8::Local<v8::Value> exception)
+ class Scope {
+ public:
+ // You need to make sure that scriptState->context() is not empty before creating a Scope.
+ explicit Scope(ScriptState* scriptState)
+ : m_handleScope(scriptState->isolate())
+ , m_context(scriptState->context())
+ {
+ ASSERT(!m_context.IsEmpty());
+ m_context->Enter();
+ }
+
+ ~Scope()
+ {
+ m_context->Exit();
+ }
+
+ private:
+ v8::HandleScope m_handleScope;
+ v8::Handle<v8::Context> m_context;
+ };
+
+ static PassRefPtr<ScriptState> create(v8::Handle<v8::Context>, PassRefPtr<DOMWrapperWorld>);
+ virtual ~ScriptState();
+
+ static ScriptState* current(v8::Isolate* isolate)
{
- m_exception.set(m_isolate, exception);
+ return from(isolate->GetCurrentContext());
}
- v8::Local<v8::Value> exception() { return m_exception.newLocal(m_isolate); }
- void clearException() { m_exception.clear(); }
- v8::Local<v8::Context> context() const
+ static ScriptState* from(v8::Handle<v8::Context> context)
{
- return m_context.newLocal(m_isolate);
+ ASSERT(!context.IsEmpty());
+ ScriptState* scriptState = static_cast<ScriptState*>(context->GetAlignedPointerFromEmbedderData(v8ContextPerContextDataIndex));
+ // ScriptState::from() must not be called for a context that does not have
+ // valid embedder data in the embedder field.
+ RELEASE_ASSERT_WITH_SECURITY_IMPLICATION(scriptState);
+ RELEASE_ASSERT_WITH_SECURITY_IMPLICATION(scriptState->context() == context);
+ return scriptState;
}
- v8::Isolate* isolate()
- {
- return m_isolate;
- }
+ static ScriptState* forMainWorld(LocalFrame*);
+
+ v8::Isolate* isolate() const { return m_isolate; }
+ DOMWrapperWorld& world() const { return *m_world; }
+ LocalDOMWindow* domWindow() const;
+ virtual ExecutionContext* executionContext() const;
+ virtual void setExecutionContext(ExecutionContext*);
+
+ // This can return an empty handle if the v8::Context is gone.
+ v8::Handle<v8::Context> context() const { return m_context.newLocal(m_isolate); }
+ bool contextIsEmpty() const { return m_context.isEmpty(); }
+ void clearContext() { return m_context.clear(); }
+
+ V8PerContextData* perContextData() const { return m_perContextData.get(); }
+ void disposePerContextData() { m_perContextData = nullptr; }
- DOMWindow* domWindow() const;
- ExecutionContext* executionContext() const;
bool evalEnabled() const;
void setEvalEnabled(bool);
-
- static ScriptState* forContext(v8::Handle<v8::Context>);
- static ScriptState* current();
+ ScriptValue getFromGlobalObject(const char* name);
protected:
- ScriptState()
- : m_isolate(v8::Isolate::GetCurrent())
- {
- }
-
- ~ScriptState();
+ ScriptState(v8::Handle<v8::Context>, PassRefPtr<DOMWrapperWorld>);
private:
- friend ScriptState* mainWorldScriptState(Frame*);
- explicit ScriptState(v8::Handle<v8::Context>);
+ v8::Isolate* m_isolate;
+ // This persistent handle is weak.
+ ScopedPersistent<v8::Context> m_context;
- static void setWeakCallback(const v8::WeakCallbackData<v8::Context, ScriptState>&);
+ // This RefPtr doesn't cause a cycle because all persistent handles that DOMWrapperWorld holds are weak.
+ RefPtr<DOMWrapperWorld> m_world;
- ScopedPersistent<v8::Value> m_exception;
- ScopedPersistent<v8::Context> m_context;
- v8::Isolate* m_isolate;
+ // This OwnPtr causes a cycle:
+ // V8PerContextData --(Persistent)--> v8::Context --(RefPtr)--> ScriptState --(OwnPtr)--> V8PerContextData
+ // So you must explicitly clear the OwnPtr by calling disposePerContextData()
+ // once you no longer need V8PerContextData. Otherwise, the v8::Context will leak.
+ OwnPtr<V8PerContextData> m_perContextData;
};
-class EmptyScriptState : public ScriptState {
+class ScriptStateForTesting : public ScriptState {
public:
- EmptyScriptState() : ScriptState() { }
- ~EmptyScriptState() { }
+ static PassRefPtr<ScriptStateForTesting> create(v8::Handle<v8::Context>, PassRefPtr<DOMWrapperWorld>);
+
+ virtual ExecutionContext* executionContext() const OVERRIDE;
+ virtual void setExecutionContext(ExecutionContext*) OVERRIDE;
+
+private:
+ ScriptStateForTesting(v8::Handle<v8::Context>, PassRefPtr<DOMWrapperWorld>);
+
+ ExecutionContext* m_executionContext;
};
-class ScriptStateProtectedPtr {
- WTF_MAKE_NONCOPYABLE(ScriptStateProtectedPtr);
+// ScriptStateProtectingContext keeps the context associated with the ScriptState alive.
+// You need to call clear() once you no longer need the context. Otherwise, the context will leak.
+class ScriptStateProtectingContext {
+ WTF_MAKE_NONCOPYABLE(ScriptStateProtectingContext);
public:
- ScriptStateProtectedPtr()
- : m_scriptState(0)
+ ScriptStateProtectingContext(ScriptState* scriptState)
+ : m_scriptState(scriptState)
{
+ if (m_scriptState)
+ m_context.set(m_scriptState->isolate(), m_scriptState->context());
}
- ScriptStateProtectedPtr(ScriptState* scriptState)
- : m_scriptState(scriptState)
+ ScriptState* operator->() const { return m_scriptState.get(); }
+ ScriptState* get() const { return m_scriptState.get(); }
+ void clear()
{
- v8::HandleScope handleScope(scriptState->isolate());
- // Keep the context from being GC'ed. ScriptState is guaranteed to be live while the context is live.
- m_context.set(scriptState->isolate(), scriptState->context());
+ m_scriptState = nullptr;
+ m_context.clear();
}
- ScriptState* get() const { return m_scriptState; }
-
private:
- ScriptState* m_scriptState;
+ RefPtr<ScriptState> m_scriptState;
ScopedPersistent<v8::Context> m_context;
};
-ScriptState* mainWorldScriptState(Frame*);
-
-ScriptState* scriptStateFromWorkerGlobalScope(WorkerGlobalScope*);
-
}
#endif // ScriptState_h
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ScriptString.cpp b/chromium/third_party/WebKit/Source/bindings/v8/ScriptString.cpp
index fe1ea3ecec2..aa75fde16ad 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/ScriptString.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ScriptString.cpp
@@ -31,26 +31,53 @@
#include "config.h"
#include "bindings/v8/ScriptString.h"
+#include "bindings/v8/V8Binding.h"
+
namespace WebCore {
+ScriptString::ScriptString()
+ : m_isolate(0)
+{
+}
+
+ScriptString::ScriptString(v8::Isolate* isolate, v8::Handle<v8::String> string)
+ : m_isolate(isolate)
+ , m_string(SharedPersistent<v8::String>::create(string, m_isolate))
+{
+}
+
+ScriptString& ScriptString::operator=(const ScriptString& string)
+{
+ if (this != &string) {
+ m_isolate = string.m_isolate;
+ m_string = string.m_string;
+ }
+ return *this;
+}
+
+v8::Handle<v8::String> ScriptString::v8Value()
+{
+ if (isEmpty())
+ return v8::Handle<v8::String>();
+ return m_string->newLocal(isolate());
+}
+
ScriptString ScriptString::concatenateWith(const String& string)
{
v8::Isolate* nonNullIsolate = isolate();
v8::HandleScope handleScope(nonNullIsolate);
- v8::Handle<v8::String> b = v8String(nonNullIsolate, string);
- if (hasNoValue())
- return ScriptString(b, nonNullIsolate);
- v8::Handle<v8::String> a = v8::Handle<v8::String>::Cast(v8Value());
- return ScriptString(v8::String::Concat(a, b), nonNullIsolate);
+ v8::Handle<v8::String> targetString = v8String(nonNullIsolate, string);
+ if (isEmpty())
+ return ScriptString(nonNullIsolate, targetString);
+ return ScriptString(nonNullIsolate, v8::String::Concat(v8Value(), targetString));
}
-String ScriptString::flattenToString() const
+String ScriptString::flattenToString()
{
- if (hasNoValue())
+ if (isEmpty())
return String();
v8::HandleScope handleScope(isolate());
- v8::Handle<v8::String> value = v8::Handle<v8::String>::Cast(v8Value());
- return v8StringToWebCoreString<String>(value, Externalize);
+ return v8StringToWebCoreString<String>(v8Value(), Externalize);
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ScriptString.h b/chromium/third_party/WebKit/Source/bindings/v8/ScriptString.h
index ed493f8bf48..2638f44836d 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/ScriptString.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ScriptString.h
@@ -31,19 +31,34 @@
#ifndef ScriptString_h
#define ScriptString_h
-#include "bindings/v8/ScriptValue.h"
-#include "bindings/v8/V8Binding.h"
+#include "bindings/v8/SharedPersistent.h"
+#include "wtf/RefPtr.h"
#include "wtf/text/WTFString.h"
+#include <v8.h>
namespace WebCore {
-class ScriptString : public ScriptValue {
+class ScriptString FINAL {
public:
- ScriptString() { }
- ScriptString(v8::Handle<v8::String> value, v8::Isolate* isolate) : ScriptValue(value, isolate) { }
+ ScriptString();
+ ScriptString(v8::Isolate*, v8::Handle<v8::String>);
+ ScriptString& operator=(const ScriptString&);
+ v8::Isolate* isolate()
+ {
+ if (!m_isolate)
+ m_isolate = v8::Isolate::GetCurrent();
+ return m_isolate;
+ }
+ bool isEmpty() const { return !m_string || m_string->isEmpty(); }
+ void clear() { m_string = nullptr; }
+ v8::Handle<v8::String> v8Value();
ScriptString concatenateWith(const String&);
- String flattenToString() const;
+ String flattenToString();
+
+private:
+ v8::Isolate* m_isolate;
+ RefPtr<SharedPersistent<v8::String> > m_string;
};
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ScriptValue.cpp b/chromium/third_party/WebKit/Source/bindings/v8/ScriptValue.cpp
index 04b2287f9c2..bdfbe082258 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/ScriptValue.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ScriptValue.cpp
@@ -31,7 +31,6 @@
#include "config.h"
#include "bindings/v8/ScriptValue.h"
-#include "bindings/v8/ScriptScope.h"
#include "bindings/v8/ScriptState.h"
#include "bindings/v8/V8Binding.h"
#include "platform/JSONValues.h"
@@ -42,88 +41,41 @@ ScriptValue::~ScriptValue()
{
}
-bool ScriptValue::getString(String& result) const
+v8::Handle<v8::Value> ScriptValue::v8Value() const
{
- if (hasNoValue())
- return false;
+ if (isEmpty())
+ return v8::Handle<v8::Value>();
- v8::HandleScope handleScope(m_isolate);
- v8::Handle<v8::Value> string = v8Value();
- if (string.IsEmpty() || !string->IsString())
- return false;
- result = toCoreString(string.As<v8::String>());
- return true;
-}
+ ASSERT(isolate()->InContext());
-String ScriptValue::toString() const
-{
- v8::TryCatch block;
- v8::Handle<v8::String> string = v8Value()->ToString();
- if (block.HasCaught())
- return String();
- return v8StringToWebCoreString<String>(string, DoNotExternalize);
+ // This is a check to validate that you don't return a ScriptValue to a world different
+ // from the world that created the ScriptValue.
+ // Probably this could be:
+ // if (&m_scriptState->world() == &DOMWrapperWorld::current(isolate()))
+ // return v8::Handle<v8::Value>();
+ // instead of triggering RELEASE_ASSERT.
+ RELEASE_ASSERT(&m_scriptState->world() == &DOMWrapperWorld::current(isolate()));
+ return m_value->newLocal(isolate());
}
-static PassRefPtr<JSONValue> v8ToJSONValue(v8::Handle<v8::Value> value, int maxDepth, v8::Isolate* isolate)
+bool ScriptValue::toString(String& result) const
{
- if (value.IsEmpty()) {
- ASSERT_NOT_REACHED();
- return 0;
- }
-
- if (!maxDepth)
- return 0;
- maxDepth--;
+ if (isEmpty())
+ return false;
- if (value->IsNull() || value->IsUndefined())
- return JSONValue::null();
- if (value->IsBoolean())
- return JSONBasicValue::create(value->BooleanValue());
- if (value->IsNumber())
- return JSONBasicValue::create(value->NumberValue());
- if (value->IsString())
- return JSONString::create(toCoreString(value.As<v8::String>()));
- if (value->IsArray()) {
- v8::Handle<v8::Array> array = v8::Handle<v8::Array>::Cast(value);
- RefPtr<JSONArray> inspectorArray = JSONArray::create();
- uint32_t length = array->Length();
- for (uint32_t i = 0; i < length; i++) {
- v8::Local<v8::Value> value = array->Get(v8::Int32::New(i, isolate));
- RefPtr<JSONValue> element = v8ToJSONValue(value, maxDepth, isolate);
- if (!element)
- return 0;
- inspectorArray->pushValue(element);
- }
- return inspectorArray;
- }
- if (value->IsObject()) {
- RefPtr<JSONObject> jsonObject = JSONObject::create();
- v8::Handle<v8::Object> object = v8::Handle<v8::Object>::Cast(value);
- v8::Local<v8::Array> propertyNames = object->GetPropertyNames();
- uint32_t length = propertyNames->Length();
- for (uint32_t i = 0; i < length; i++) {
- v8::Local<v8::Value> name = propertyNames->Get(v8::Int32::New(i, isolate));
- // FIXME(yurys): v8::Object should support GetOwnPropertyNames
- if (name->IsString() && !object->HasRealNamedProperty(v8::Handle<v8::String>::Cast(name)))
- continue;
- RefPtr<JSONValue> propertyValue = v8ToJSONValue(object->Get(name), maxDepth, isolate);
- if (!propertyValue)
- return 0;
- V8TRYCATCH_FOR_V8STRINGRESOURCE_RETURN(V8StringResource<WithNullCheck>, nameString, name, 0);
- jsonObject->setValue(nameString, propertyValue);
- }
- return jsonObject;
- }
- ASSERT_NOT_REACHED();
- return 0;
+ ScriptState::Scope scope(m_scriptState.get());
+ v8::Handle<v8::Value> string = v8Value();
+ if (string.IsEmpty() || !string->IsString())
+ return false;
+ result = toCoreString(v8::Handle<v8::String>::Cast(string));
+ return true;
}
PassRefPtr<JSONValue> ScriptValue::toJSONValue(ScriptState* scriptState) const
{
- v8::HandleScope handleScope(scriptState->isolate());
- // v8::Object::GetPropertyNames() expects current context to be not null.
- v8::Context::Scope contextScope(scriptState->context());
- return v8ToJSONValue(v8Value(), JSONValue::maxDepth, scriptState->isolate());
+ ASSERT(!scriptState->contextIsEmpty());
+ ScriptState::Scope scope(scriptState);
+ return v8ToJSONValue(scriptState->isolate(), v8Value(), JSONValue::maxDepth);
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ScriptValue.h b/chromium/third_party/WebKit/Source/bindings/v8/ScriptValue.h
index 42b5fe7962b..41c76847987 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/ScriptValue.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ScriptValue.h
@@ -31,6 +31,7 @@
#ifndef ScriptValue_h
#define ScriptValue_h
+#include "bindings/v8/ScriptState.h"
#include "bindings/v8/SharedPersistent.h"
#include "wtf/PassRefPtr.h"
#include "wtf/RefPtr.h"
@@ -40,26 +41,36 @@
namespace WebCore {
class JSONValue;
-class ScriptState;
class ScriptValue {
public:
ScriptValue()
: m_isolate(0)
- { }
+ , m_scriptState(nullptr)
+ {
+ }
virtual ~ScriptValue();
- ScriptValue(v8::Handle<v8::Value> value, v8::Isolate* isolate)
- : m_isolate(isolate)
- , m_value(value.IsEmpty() ? 0 : SharedPersistent<v8::Value>::create(value, isolate))
+ ScriptValue(ScriptState* scriptState, v8::Handle<v8::Value> value)
+ : m_isolate(scriptState->isolate())
+ , m_scriptState(scriptState)
+ , m_value(value.IsEmpty() ? nullptr : SharedPersistent<v8::Value>::create(value, scriptState->isolate()))
{
+ ASSERT(isEmpty() || m_scriptState);
}
ScriptValue(const ScriptValue& value)
: m_isolate(value.m_isolate)
+ , m_scriptState(value.m_scriptState)
, m_value(value.m_value)
{
+ ASSERT(isEmpty() || m_scriptState);
+ }
+
+ ScriptState* scriptState() const
+ {
+ return m_scriptState.get();
}
v8::Isolate* isolate() const
@@ -69,108 +80,80 @@ public:
return m_isolate;
}
- static ScriptValue createUndefined(v8::Isolate* isolate)
- {
- return ScriptValue(v8::Undefined(isolate), isolate);
- }
-
- static ScriptValue createNull()
- {
- v8::Isolate* isolate = v8::Isolate::GetCurrent();
- return ScriptValue(v8::Null(isolate), isolate);
- }
- static ScriptValue createBoolean(bool b)
- {
- v8::Isolate* isolate = v8::Isolate::GetCurrent();
- return ScriptValue(b ? v8::True(isolate) : v8::False(isolate), isolate);
- }
-
ScriptValue& operator=(const ScriptValue& value)
{
if (this != &value) {
- m_value = value.m_value;
m_isolate = value.m_isolate;
+ m_scriptState = value.m_scriptState;
+ m_value = value.m_value;
}
return *this;
}
bool operator==(const ScriptValue& value) const
{
- if (hasNoValue())
- return value.hasNoValue();
- if (value.hasNoValue())
+ if (isEmpty())
+ return value.isEmpty();
+ if (value.isEmpty())
return false;
return *m_value == *value.m_value;
}
- bool isEqual(ScriptState*, const ScriptValue& value) const
+ bool operator!=(const ScriptValue& value) const
{
- return operator==(value);
+ return !operator==(value);
}
- // Note: This creates a new local Handle; not to be used in cases where is
- // is an efficiency problem.
+ // This creates a new local Handle; Don't use this in performance-sensitive places.
bool isFunction() const
{
- ASSERT(!hasNoValue());
+ ASSERT(!isEmpty());
v8::Handle<v8::Value> value = v8Value();
return !value.IsEmpty() && value->IsFunction();
}
- bool operator!=(const ScriptValue& value) const
- {
- return !operator==(value);
- }
-
- // Note: This creates a new local Handle; not to be used in cases where is
- // is an efficiency problem.
+ // This creates a new local Handle; Don't use this in performance-sensitive places.
bool isNull() const
{
- ASSERT(!hasNoValue());
+ ASSERT(!isEmpty());
v8::Handle<v8::Value> value = v8Value();
return !value.IsEmpty() && value->IsNull();
}
- // Note: This creates a new local Handle; not to be used in cases where is
- // is an efficiency problem.
+ // This creates a new local Handle; Don't use this in performance-sensitive places.
bool isUndefined() const
{
- ASSERT(!hasNoValue());
+ ASSERT(!isEmpty());
v8::Handle<v8::Value> value = v8Value();
return !value.IsEmpty() && value->IsUndefined();
}
- // Note: This creates a new local Handle; not to be used in cases where is
- // is an efficiency problem.
+ // This creates a new local Handle; Don't use this in performance-sensitive places.
bool isObject() const
{
- ASSERT(!hasNoValue());
+ ASSERT(!isEmpty());
v8::Handle<v8::Value> value = v8Value();
return !value.IsEmpty() && value->IsObject();
}
- bool hasNoValue() const
+ bool isEmpty() const
{
return !m_value.get() || m_value->isEmpty();
}
void clear()
{
- m_value = 0;
- }
-
- v8::Handle<v8::Value> v8Value() const
- {
- return m_value.get() ? m_value->newLocal(m_isolate) : v8::Handle<v8::Value>();
+ m_value = nullptr;
}
- bool getString(String& result) const;
- String toString() const;
+ v8::Handle<v8::Value> v8Value() const;
+ bool toString(String&) const;
PassRefPtr<JSONValue> toJSONValue(ScriptState*) const;
private:
mutable v8::Isolate* m_isolate;
+ mutable RefPtr<ScriptState> m_scriptState;
RefPtr<SharedPersistent<v8::Value> > m_value;
};
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ScriptWrappable.h b/chromium/third_party/WebKit/Source/bindings/v8/ScriptWrappable.h
index 72ab761ee4f..c81fda0e6e1 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/ScriptWrappable.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/ScriptWrappable.h
@@ -31,9 +31,8 @@
#ifndef ScriptWrappable_h
#define ScriptWrappable_h
-#include "bindings/v8/UnsafePersistent.h"
-#include "bindings/v8/V8Utilities.h"
#include "bindings/v8/WrapperTypeInfo.h"
+#include "platform/heap/Handle.h"
#include <v8.h>
// Helper to call webCoreInitializeScriptWrappableForInterface in the global namespace.
@@ -45,6 +44,35 @@ template <class C> inline void initializeScriptWrappableHelper(C* object)
namespace WebCore {
+/**
+ * ScriptWrappable wraps a V8 object and its WrapperTypeInfo.
+ *
+ * ScriptWrappable acts much like a v8::Persistent<> in that it keeps a
+ * V8 object alive. Under the hood, however, it keeps either a TypeInfo
+ * object or an actual v8 persistent (or is empty).
+ *
+ * The physical state space of ScriptWrappable is:
+ * - uintptr_t m_wrapperOrTypeInfo;
+ * - if 0: the ScriptWrappable is uninitialized/empty.
+ * - if even: a pointer to WebCore::TypeInfo
+ * - if odd: a pointer to v8::Persistent<v8::Object> + 1.
+ *
+ * In other words, one integer represents one of two object pointers,
+ * depending on its least signficiant bit, plus an uninitialized state.
+ * This class is meant to mask the logistics behind this.
+ *
+ * typeInfo() and newLocalWrapper will return appropriate values (possibly
+ * 0/empty) in all physical states.
+ *
+ * The state transitions are:
+ * - new: an empty and invalid ScriptWrappable.
+ * - init (to be called by all subclasses in their constructor):
+ * needs to call setTypeInfo
+ * - setTypeInfo: install a WrapperTypeInfo
+ * - setWrapper: install a v8::Persistent (or empty)
+ * - disposeWrapper (via setWeakCallback, triggered by V8 garbage collecter):
+ * remove v8::Persistent and install a TypeInfo of the previous value.
+ */
class ScriptWrappable {
public:
ScriptWrappable() : m_wrapperOrTypeInfo(0) { }
@@ -77,7 +105,9 @@ public:
v8::Local<v8::Object> newLocalWrapper(v8::Isolate* isolate) const
{
- return unsafePersistent().newLocal(isolate);
+ v8::Persistent<v8::Object> persistent;
+ getPersistent(&persistent);
+ return v8::Local<v8::Object>::New(isolate, persistent);
}
const WrapperTypeInfo* typeInfo()
@@ -85,102 +115,134 @@ public:
if (containsTypeInfo())
return reinterpret_cast<const WrapperTypeInfo*>(m_wrapperOrTypeInfo);
- if (containsWrapper())
- return toWrapperTypeInfo(*(unsafePersistent().persistent()));
+ if (containsWrapper()) {
+ v8::Persistent<v8::Object> persistent;
+ getPersistent(&persistent);
+ return toWrapperTypeInfo(persistent);
+ }
return 0;
}
- void setTypeInfo(const WrapperTypeInfo* info)
+ void setTypeInfo(const WrapperTypeInfo* typeInfo)
{
- m_wrapperOrTypeInfo = reinterpret_cast<uintptr_t>(info);
+ m_wrapperOrTypeInfo = reinterpret_cast<uintptr_t>(typeInfo);
ASSERT(containsTypeInfo());
}
+ bool isEqualTo(const v8::Local<v8::Object>& other) const
+ {
+ v8::Persistent<v8::Object> persistent;
+ getPersistent(&persistent);
+ return persistent == other;
+ }
+
static bool wrapperCanBeStoredInObject(const void*) { return false; }
static bool wrapperCanBeStoredInObject(const ScriptWrappable*) { return true; }
- static void setWrapperInObject(void*, v8::Handle<v8::Object>, v8::Isolate*, const WrapperConfiguration&)
+ static ScriptWrappable* fromObject(const void*)
{
ASSERT_NOT_REACHED();
+ return 0;
}
- static void setWrapperInObject(ScriptWrappable* object, v8::Handle<v8::Object> wrapper, v8::Isolate* isolate, const WrapperConfiguration& configuration)
+ static ScriptWrappable* fromObject(ScriptWrappable* object)
{
- object->setWrapper(wrapper, isolate, configuration);
+ return object;
}
- static const WrapperTypeInfo* getTypeInfoFromObject(void* object)
+ bool setReturnValue(v8::ReturnValue<v8::Value> returnValue)
{
- ASSERT_NOT_REACHED();
- return 0;
+ v8::Persistent<v8::Object> persistent;
+ getPersistent(&persistent);
+ returnValue.Set(persistent);
+ return containsWrapper();
}
- static const WrapperTypeInfo* getTypeInfoFromObject(ScriptWrappable* object)
+ void markAsDependentGroup(ScriptWrappable* groupRoot, v8::Isolate* isolate)
{
- return object->typeInfo();
+ ASSERT(containsWrapper());
+ ASSERT(groupRoot && groupRoot->containsWrapper());
+
+ v8::UniqueId groupId(groupRoot->m_wrapperOrTypeInfo);
+ v8::Persistent<v8::Object> wrapper;
+ getPersistent(&wrapper);
+ wrapper.MarkPartiallyDependent();
+ isolate->SetObjectGroupId(v8::Persistent<v8::Value>::Cast(wrapper), groupId);
}
- static void setTypeInfoInObject(void* object, const WrapperTypeInfo* info)
+ void setReference(const v8::Persistent<v8::Object>& parent, v8::Isolate* isolate)
{
- ASSERT_NOT_REACHED();
+ v8::Persistent<v8::Object> persistent;
+ getPersistent(&persistent);
+ isolate->SetReference(parent, persistent);
}
- static void setTypeInfoInObject(ScriptWrappable* object, const WrapperTypeInfo* info)
+ template<typename V8T, typename T>
+ static void assertWrapperSanity(v8::Local<v8::Object> object, T* objectAsT)
{
- object->setTypeInfo(info);
+ ASSERT(objectAsT);
+ RELEASE_ASSERT_WITH_SECURITY_IMPLICATION(object.IsEmpty()
+ || object->GetAlignedPointerFromInternalField(v8DOMWrapperObjectIndex) == V8T::toInternalPointer(objectAsT));
}
template<typename V8T, typename T>
- static bool setReturnValueWithSecurityCheck(v8::ReturnValue<v8::Value> returnValue, T* object)
+ static void assertWrapperSanity(void* object, T* objectAsT)
{
- return ScriptWrappable::getUnsafeWrapperFromObject(object).template setReturnValueWithSecurityCheck<V8T>(returnValue, object);
+ ASSERT_NOT_REACHED();
}
- template<typename T>
- static bool setReturnValue(v8::ReturnValue<v8::Value> returnValue, T* object)
+ template<typename V8T, typename T>
+ static void assertWrapperSanity(ScriptWrappable* object, T* objectAsT)
{
- return ScriptWrappable::getUnsafeWrapperFromObject(object).setReturnValue(returnValue);
+ ASSERT(object);
+ ASSERT(objectAsT);
+ v8::Object* value = object->getRawValue();
+ RELEASE_ASSERT_WITH_SECURITY_IMPLICATION(value == 0
+ || value->GetAlignedPointerFromInternalField(v8DOMWrapperObjectIndex) == V8T::toInternalPointer(objectAsT));
}
+ inline bool containsWrapper() const { return (m_wrapperOrTypeInfo & 1); }
+ inline bool containsTypeInfo() const { return m_wrapperOrTypeInfo && !(m_wrapperOrTypeInfo & 1); }
+
protected:
~ScriptWrappable()
{
- ASSERT(m_wrapperOrTypeInfo); // Assert initialization via init() even if not subsequently wrapped.
- m_wrapperOrTypeInfo = 0; // Break UAF attempts to wrap.
+ // We must not get deleted as long as we contain a wrapper. If this happens, we screwed up ref
+ // counting somewhere. Crash here instead of crashing during a later gc cycle.
+ RELEASE_ASSERT_WITH_SECURITY_IMPLICATION(!containsWrapper());
+ ASSERT(m_wrapperOrTypeInfo); // Assert initialization via init() even if not subsequently wrapped.
+ m_wrapperOrTypeInfo = 0; // Break UAF attempts to wrap.
}
private:
- // For calling unsafePersistent and getWrapperFromObject.
- friend class MinorGCWrapperVisitor;
- friend class DOMDataStore;
-
- UnsafePersistent<v8::Object> unsafePersistent() const
+ void getPersistent(v8::Persistent<v8::Object>* persistent) const
{
- v8::Object* object = containsWrapper() ? reinterpret_cast<v8::Object*>(m_wrapperOrTypeInfo & ~1) : 0;
- return UnsafePersistent<v8::Object>(object);
- }
+ ASSERT(persistent);
- static UnsafePersistent<v8::Object> getUnsafeWrapperFromObject(void*)
- {
- ASSERT_NOT_REACHED();
- return UnsafePersistent<v8::Object>();
+ // Horrible and super unsafe: Cast the Persistent to an Object*, so
+ // that we can inject the wrapped value. This only works because
+ // we previously 'stole' the object pointer from a Persistent in
+ // the setWrapper() method.
+ *reinterpret_cast<v8::Object**>(persistent) = getRawValue();
}
- static UnsafePersistent<v8::Object> getUnsafeWrapperFromObject(ScriptWrappable* object)
+ inline v8::Object* getRawValue() const
{
- return object->unsafePersistent();
+ v8::Object* object = containsWrapper() ? reinterpret_cast<v8::Object*>(m_wrapperOrTypeInfo & ~1) : 0;
+ return object;
}
- inline bool containsWrapper() const { return (m_wrapperOrTypeInfo & 1) == 1; }
- inline bool containsTypeInfo() const { return m_wrapperOrTypeInfo && (m_wrapperOrTypeInfo & 1) == 0; }
-
- inline void disposeWrapper(v8::Local<v8::Object> value, const WrapperTypeInfo* info)
+ inline void disposeWrapper(v8::Local<v8::Object> wrapper)
{
ASSERT(containsWrapper());
- ASSERT(value == *unsafePersistent().persistent());
- unsafePersistent().dispose();
- setTypeInfo(info);
+
+ v8::Persistent<v8::Object> persistent;
+ getPersistent(&persistent);
+
+ ASSERT(wrapper == persistent);
+ persistent.Reset();
+ setTypeInfo(toWrapperTypeInfo(wrapper));
}
// If zero, then this contains nothing, otherwise:
@@ -190,18 +252,15 @@ private:
static void setWeakCallback(const v8::WeakCallbackData<v8::Object, ScriptWrappable>& data)
{
- ASSERT(*data.GetParameter()->unsafePersistent().persistent() == data.GetValue());
-
- // Note: |object| might not be equal to |data|.GetParameter(), e.g., if ScriptWrappable isn't a left-most base class.
- void* object = toNative(data.GetValue());
- const WrapperTypeInfo* info = toWrapperTypeInfo(data.GetValue());
- ASSERT(info->derefObjectFunction);
+ v8::Persistent<v8::Object> persistent;
+ data.GetParameter()->getPersistent(&persistent);
+ ASSERT(persistent == data.GetValue());
+ data.GetParameter()->disposeWrapper(data.GetValue());
- data.GetParameter()->disposeWrapper(data.GetValue(), info);
// FIXME: I noticed that 50%~ of minor GC cycle times can be consumed
// inside data.GetParameter()->deref(), which causes Node destructions. We should
// make Node destructions incremental.
- info->derefObject(object);
+ releaseObject(data.GetValue());
}
};
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/SerializedScriptValue.cpp b/chromium/third_party/WebKit/Source/bindings/v8/SerializedScriptValue.cpp
index 72f35602748..8da614f47cc 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/SerializedScriptValue.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/SerializedScriptValue.cpp
@@ -31,16 +31,16 @@
#include "config.h"
#include "bindings/v8/SerializedScriptValue.h"
-#include "V8Blob.h"
-#include "V8DOMFileSystem.h"
-#include "V8File.h"
-#include "V8FileList.h"
-#include "V8ImageData.h"
-#include "V8MessagePort.h"
-#include "bindings/v8/ScriptScope.h"
-#include "bindings/v8/ScriptState.h"
+#include "bindings/core/v8/V8Blob.h"
+#include "bindings/core/v8/V8File.h"
+#include "bindings/core/v8/V8FileList.h"
+#include "bindings/core/v8/V8ImageData.h"
+#include "bindings/core/v8/V8MessagePort.h"
+#include "bindings/modules/v8/V8DOMFileSystem.h"
+#include "bindings/modules/v8/V8Key.h"
+#include "bindings/v8/ExceptionState.h"
#include "bindings/v8/V8Binding.h"
-#include "bindings/v8/V8Utilities.h"
+#include "bindings/v8/WorkerScriptController.h"
#include "bindings/v8/custom/V8ArrayBufferCustom.h"
#include "bindings/v8/custom/V8ArrayBufferViewCustom.h"
#include "bindings/v8/custom/V8DataViewCustom.h"
@@ -61,6 +61,12 @@
#include "core/html/ImageData.h"
#include "core/html/canvas/DataView.h"
#include "platform/SharedBuffer.h"
+#include "platform/heap/Handle.h"
+#include "public/platform/Platform.h"
+#include "public/platform/WebBlobInfo.h"
+#include "public/platform/WebCrypto.h"
+#include "public/platform/WebCryptoKey.h"
+#include "public/platform/WebCryptoKeyAlgorithm.h"
#include "wtf/ArrayBuffer.h"
#include "wtf/ArrayBufferContents.h"
#include "wtf/ArrayBufferView.h"
@@ -133,6 +139,12 @@ private:
// need to rehash after every garbage collection because a key object may have been moved.
template<typename G>
struct V8HandlePtrHash {
+ static v8::Handle<G> unsafeHandleFromRawValue(const G* value)
+ {
+ const v8::Handle<G>* handle = reinterpret_cast<const v8::Handle<G>*>(&value);
+ return *handle;
+ }
+
static unsigned hash(const G* key)
{
return static_cast<unsigned>(unsafeHandleFromRawValue(key)->GetIdentityHash());
@@ -186,10 +198,13 @@ enum SerializationTag {
DateTag = 'D', // value:double -> Date (ref)
MessagePortTag = 'M', // index:int -> MessagePort. Fills the result with transferred MessagePort.
NumberTag = 'N', // value:double -> Number
- BlobTag = 'b', // url:WebCoreString, type:WebCoreString, size:uint64_t -> Blob (ref)
+ BlobTag = 'b', // uuid:WebCoreString, type:WebCoreString, size:uint64_t -> Blob (ref)
+ BlobIndexTag = 'i', // index:int32_t -> Blob (ref)
FileTag = 'f', // file:RawFile -> File (ref)
- DOMFileSystemTag = 'd', // type:int32_t, name:WebCoreString, url:WebCoreString -> FileSystem (ref)
+ FileIndexTag = 'e', // index:int32_t -> File (ref)
+ DOMFileSystemTag = 'd', // type:int32_t, name:WebCoreString, uuid:WebCoreString -> FileSystem (ref)
FileListTag = 'l', // length:uint32_t, files:RawFile[length] -> FileList (ref)
+ FileListIndexTag = 'L', // length:uint32_t, files:int32_t[length] -> FileList (ref)
ImageDataTag = '#', // width:uint32_t, height:uint32_t, pixelDataLength:uint32_t, data:byte[pixelDataLength] -> ImageData (ref)
ObjectTag = '{', // numProperties:uint32_t -> pops the last object from the open stack;
// fills it with the last numProperties name,value pairs pushed onto the deserialization stack
@@ -201,6 +216,13 @@ enum SerializationTag {
ArrayBufferTag = 'B', // byteLength:uint32_t, data:byte[byteLength] -> ArrayBuffer (ref)
ArrayBufferTransferTag = 't', // index:uint32_t -> ArrayBuffer. For ArrayBuffer transfer
ArrayBufferViewTag = 'V', // subtag:byte, byteOffset:uint32_t, byteLength:uint32_t -> ArrayBufferView (ref). Consumes an ArrayBuffer from the top of the deserialization stack.
+ CryptoKeyTag = 'K', // subtag:byte, props, usages:uint32_t, keyDataLength:uint32_t, keyData:byte[keyDataLength]
+ // If subtag=AesKeyTag:
+ // props = keyLengthBytes:uint32_t, algorithmId:uint32_t
+ // If subtag=HmacKeyTag:
+ // props = keyLengthBytes:uint32_t, hashId:uint32_t
+ // If subtag=RsaHashedKeyTag:
+ // props = algorithmId:uint32_t, type:uint32_t, modulusLengthBits:uint32_t, publicExponentLength:uint32_t, publicExponent:byte[publicExponentLength], hashId:uint32_t
ObjectReferenceTag = '^', // ref:uint32_t -> reference table[ref]
GenerateFreshObjectTag = 'o', // -> empty object allocated an object ID and pushed onto the open stack (ref)
GenerateFreshSparseArrayTag = 'a', // length:uint32_t -> empty array[length] allocated an object ID and pushed onto the open stack (ref)
@@ -226,6 +248,52 @@ enum ArrayBufferViewSubTag {
DataViewTag = '?'
};
+enum CryptoKeySubTag {
+ AesKeyTag = 1,
+ HmacKeyTag = 2,
+ // ID 3 was used by RsaKeyTag, while still behind experimental flag.
+ RsaHashedKeyTag = 4,
+ // Maximum allowed value is 255
+};
+
+enum AssymetricCryptoKeyType {
+ PublicKeyType = 1,
+ PrivateKeyType = 2,
+ // Maximum allowed value is 2^32-1
+};
+
+enum CryptoKeyAlgorithmTag {
+ AesCbcTag = 1,
+ HmacTag = 2,
+ RsaSsaPkcs1v1_5Tag = 3,
+ // ID 4 was used by RsaEs, while still behind experimental flag.
+ Sha1Tag = 5,
+ Sha256Tag = 6,
+ Sha384Tag = 7,
+ Sha512Tag = 8,
+ AesGcmTag = 9,
+ RsaOaepTag = 10,
+ AesCtrTag = 11,
+ AesKwTag = 12,
+ // Maximum allowed value is 2^32-1
+};
+
+enum CryptoKeyUsage {
+ // Extractability is not a "usage" in the WebCryptoKeyUsages sense, however
+ // it fits conveniently into this bitfield.
+ ExtractableUsage = 1 << 0,
+
+ EncryptUsage = 1 << 1,
+ DecryptUsage = 1 << 2,
+ SignUsage = 1 << 3,
+ VerifyUsage = 1 << 4,
+ DeriveKeyUsage = 1 << 5,
+ WrapKeyUsage = 1 << 6,
+ UnwrapKeyUsage = 1 << 7,
+ DeriveBitsUsage = 1 << 8,
+ // Maximum allowed value is 1 << 31
+};
+
static bool shouldCheckForCycles(int depth)
{
ASSERT(depth >= 0);
@@ -272,9 +340,8 @@ private:
class Writer {
WTF_MAKE_NONCOPYABLE(Writer);
public:
- explicit Writer(v8::Isolate* isolate)
+ Writer()
: m_position(0)
- , m_isolate(isolate)
{
}
@@ -392,6 +459,13 @@ public:
doWriteUint64(size);
}
+ void writeBlobIndex(int blobIndex)
+ {
+ ASSERT(blobIndex >= 0);
+ append(BlobIndexTag);
+ doWriteUint32(blobIndex);
+ }
+
void writeDOMFileSystem(int type, const String& name, const String& url)
{
append(DOMFileSystemTag);
@@ -406,6 +480,12 @@ public:
doWriteFile(file);
}
+ void writeFileIndex(int blobIndex)
+ {
+ append(FileIndexTag);
+ doWriteUint32(blobIndex);
+ }
+
void writeFileList(const FileList& fileList)
{
append(FileListTag);
@@ -415,6 +495,45 @@ public:
doWriteFile(*fileList.item(i));
}
+ void writeFileListIndex(const Vector<int>& blobIndices)
+ {
+ append(FileListIndexTag);
+ uint32_t length = blobIndices.size();
+ doWriteUint32(length);
+ for (unsigned i = 0; i < length; ++i)
+ doWriteUint32(blobIndices[i]);
+ }
+
+ bool writeCryptoKey(const blink::WebCryptoKey& key)
+ {
+ append(static_cast<uint8_t>(CryptoKeyTag));
+
+ switch (key.algorithm().paramsType()) {
+ case blink::WebCryptoKeyAlgorithmParamsTypeAes:
+ doWriteAesKey(key);
+ break;
+ case blink::WebCryptoKeyAlgorithmParamsTypeHmac:
+ doWriteHmacKey(key);
+ break;
+ case blink::WebCryptoKeyAlgorithmParamsTypeRsaHashed:
+ doWriteRsaHashedKey(key);
+ break;
+ case blink::WebCryptoKeyAlgorithmParamsTypeNone:
+ ASSERT_NOT_REACHED();
+ return false;
+ }
+
+ doWriteKeyUsages(key.usages(), key.extractable());
+
+ blink::WebVector<uint8_t> keyData;
+ if (!blink::Platform::current()->crypto()->serializeKeyForClone(key, keyData))
+ return false;
+
+ doWriteUint32(keyData.size());
+ append(keyData.data(), keyData.size());
+ return true;
+ }
+
void writeArrayBuffer(const ArrayBuffer& arrayBuffer)
{
append(ArrayBufferTag);
@@ -429,7 +548,7 @@ public:
ASSERT(static_cast<const uint8_t*>(arrayBuffer.data()) + arrayBufferView.byteOffset() ==
static_cast<const uint8_t*>(arrayBufferView.baseAddress()));
#endif
- ArrayBufferView::ViewType type = arrayBufferView.getType();
+ ArrayBufferView::ViewType type = arrayBufferView.type();
if (type == ArrayBufferView::TypeInt8)
append(ByteArrayTag);
@@ -544,8 +663,6 @@ public:
doWriteUint32(length);
}
- v8::Isolate* getIsolate() { return m_isolate; }
-
private:
void doWriteFile(const File& file)
{
@@ -588,6 +705,112 @@ private:
doWriteString(stringUTF8.data(), stringUTF8.length());
}
+ void doWriteHmacKey(const blink::WebCryptoKey& key)
+ {
+ ASSERT(key.algorithm().paramsType() == blink::WebCryptoKeyAlgorithmParamsTypeHmac);
+
+ append(static_cast<uint8_t>(HmacKeyTag));
+ ASSERT(!(key.algorithm().hmacParams()->lengthBits() % 8));
+ doWriteUint32(key.algorithm().hmacParams()->lengthBits() / 8);
+ doWriteAlgorithmId(key.algorithm().hmacParams()->hash().id());
+ }
+
+ void doWriteAesKey(const blink::WebCryptoKey& key)
+ {
+ ASSERT(key.algorithm().paramsType() == blink::WebCryptoKeyAlgorithmParamsTypeAes);
+
+ append(static_cast<uint8_t>(AesKeyTag));
+ doWriteAlgorithmId(key.algorithm().id());
+ // Converting the key length from bits to bytes is lossless and makes
+ // it fit in 1 byte.
+ ASSERT(!(key.algorithm().aesParams()->lengthBits() % 8));
+ doWriteUint32(key.algorithm().aesParams()->lengthBits() / 8);
+ }
+
+ void doWriteRsaHashedKey(const blink::WebCryptoKey& key)
+ {
+ ASSERT(key.algorithm().rsaHashedParams());
+ append(static_cast<uint8_t>(RsaHashedKeyTag));
+
+ doWriteAlgorithmId(key.algorithm().id());
+
+ switch (key.type()) {
+ case blink::WebCryptoKeyTypePublic:
+ doWriteUint32(PublicKeyType);
+ break;
+ case blink::WebCryptoKeyTypePrivate:
+ doWriteUint32(PrivateKeyType);
+ break;
+ case blink::WebCryptoKeyTypeSecret:
+ ASSERT_NOT_REACHED();
+ }
+
+ const blink::WebCryptoRsaHashedKeyAlgorithmParams* params = key.algorithm().rsaHashedParams();
+ doWriteUint32(params->modulusLengthBits());
+ doWriteUint32(params->publicExponent().size());
+ append(params->publicExponent().data(), params->publicExponent().size());
+ doWriteAlgorithmId(key.algorithm().rsaHashedParams()->hash().id());
+ }
+
+ void doWriteAlgorithmId(blink::WebCryptoAlgorithmId id)
+ {
+ switch (id) {
+ case blink::WebCryptoAlgorithmIdAesCbc:
+ return doWriteUint32(AesCbcTag);
+ case blink::WebCryptoAlgorithmIdHmac:
+ return doWriteUint32(HmacTag);
+ case blink::WebCryptoAlgorithmIdRsaSsaPkcs1v1_5:
+ return doWriteUint32(RsaSsaPkcs1v1_5Tag);
+ case blink::WebCryptoAlgorithmIdSha1:
+ return doWriteUint32(Sha1Tag);
+ case blink::WebCryptoAlgorithmIdSha256:
+ return doWriteUint32(Sha256Tag);
+ case blink::WebCryptoAlgorithmIdSha384:
+ return doWriteUint32(Sha384Tag);
+ case blink::WebCryptoAlgorithmIdSha512:
+ return doWriteUint32(Sha512Tag);
+ case blink::WebCryptoAlgorithmIdAesGcm:
+ return doWriteUint32(AesGcmTag);
+ case blink::WebCryptoAlgorithmIdRsaOaep:
+ return doWriteUint32(RsaOaepTag);
+ case blink::WebCryptoAlgorithmIdAesCtr:
+ return doWriteUint32(AesCtrTag);
+ case blink::WebCryptoAlgorithmIdAesKw:
+ return doWriteUint32(AesKwTag);
+ }
+ ASSERT_NOT_REACHED();
+ }
+
+ void doWriteKeyUsages(const blink::WebCryptoKeyUsageMask usages, bool extractable)
+ {
+ // Reminder to update this when adding new key usages.
+ COMPILE_ASSERT(blink::EndOfWebCryptoKeyUsage == (1 << 7) + 1, UpdateMe);
+
+ uint32_t value = 0;
+
+ if (extractable)
+ value |= ExtractableUsage;
+
+ if (usages & blink::WebCryptoKeyUsageEncrypt)
+ value |= EncryptUsage;
+ if (usages & blink::WebCryptoKeyUsageDecrypt)
+ value |= DecryptUsage;
+ if (usages & blink::WebCryptoKeyUsageSign)
+ value |= SignUsage;
+ if (usages & blink::WebCryptoKeyUsageVerify)
+ value |= VerifyUsage;
+ if (usages & blink::WebCryptoKeyUsageDeriveKey)
+ value |= DeriveKeyUsage;
+ if (usages & blink::WebCryptoKeyUsageWrapKey)
+ value |= WrapKeyUsage;
+ if (usages & blink::WebCryptoKeyUsageUnwrapKey)
+ value |= UnwrapKeyUsage;
+ if (usages & blink::WebCryptoKeyUsageDeriveBits)
+ value |= DeriveBitsUsage;
+
+ doWriteUint32(value);
+ }
+
int bytesNeededToWireEncode(uint32_t value)
{
int bytes = 1;
@@ -675,23 +898,22 @@ private:
Vector<BufferValueType> m_buffer;
unsigned m_position;
- v8::Isolate* m_isolate;
};
-static v8::Handle<v8::Object> toV8Object(MessagePort* impl, v8::Isolate* isolate)
+static v8::Handle<v8::Object> toV8Object(MessagePort* impl, v8::Handle<v8::Object> creationContext, v8::Isolate* isolate)
{
if (!impl)
return v8::Handle<v8::Object>();
- v8::Handle<v8::Value> wrapper = toV8(impl, v8::Handle<v8::Object>(), isolate);
+ v8::Handle<v8::Value> wrapper = toV8(impl, creationContext, isolate);
ASSERT(wrapper->IsObject());
return wrapper.As<v8::Object>();
}
-static v8::Handle<v8::ArrayBuffer> toV8Object(ArrayBuffer* impl, v8::Isolate* isolate)
+static v8::Handle<v8::ArrayBuffer> toV8Object(ArrayBuffer* impl, v8::Handle<v8::Object> creationContext, v8::Isolate* isolate)
{
if (!impl)
return v8::Handle<v8::ArrayBuffer>();
- v8::Handle<v8::Value> wrapper = toV8(impl, v8::Handle<v8::Object>(), isolate);
+ v8::Handle<v8::Value> wrapper = toV8(impl, creationContext, isolate);
ASSERT(wrapper->IsArrayBuffer());
return wrapper.As<v8::ArrayBuffer>();
}
@@ -703,28 +925,28 @@ public:
Success,
InputError,
DataCloneError,
- InvalidStateError,
- JSException,
- JSFailure
+ JSException
};
- Serializer(Writer& writer, MessagePortArray* messagePorts, ArrayBufferArray* arrayBuffers, BlobDataHandleMap& blobDataHandles, v8::TryCatch& tryCatch, v8::Isolate* isolate)
- : m_writer(writer)
+ Serializer(Writer& writer, MessagePortArray* messagePorts, ArrayBufferArray* arrayBuffers, WebBlobInfoArray* blobInfo, BlobDataHandleMap& blobDataHandles, v8::TryCatch& tryCatch, ScriptState* scriptState)
+ : m_scriptState(scriptState)
+ , m_writer(writer)
, m_tryCatch(tryCatch)
, m_depth(0)
, m_status(Success)
, m_nextObjectReference(0)
+ , m_blobInfo(blobInfo)
, m_blobDataHandles(blobDataHandles)
- , m_isolate(isolate)
{
ASSERT(!tryCatch.HasCaught());
+ v8::Handle<v8::Object> creationContext = m_scriptState->context()->Global();
if (messagePorts) {
for (size_t i = 0; i < messagePorts->size(); i++)
- m_transferredMessagePorts.set(toV8Object(messagePorts->at(i).get(), m_writer.getIsolate()), i);
+ m_transferredMessagePorts.set(toV8Object(messagePorts->at(i).get(), creationContext, isolate()), i);
}
if (arrayBuffers) {
for (size_t i = 0; i < arrayBuffers->size(); i++) {
- v8::Handle<v8::Object> v8ArrayBuffer = toV8Object(arrayBuffers->at(i).get(), m_writer.getIsolate());
+ v8::Handle<v8::Object> v8ArrayBuffer = toV8Object(arrayBuffers->at(i).get(), creationContext, isolate());
// Coalesce multiple occurences of the same buffer to the first index.
if (!m_transferredArrayBuffers.contains(v8ArrayBuffer))
m_transferredArrayBuffers.set(v8ArrayBuffer, i);
@@ -732,9 +954,11 @@ public:
}
}
+ v8::Isolate* isolate() { return m_scriptState->isolate(); }
+
Status serialize(v8::Handle<v8::Value> value)
{
- v8::HandleScope scope(m_isolate);
+ v8::HandleScope scope(isolate());
m_writer.writeVersion();
StateBase* state = doSerialize(value, 0);
while (state)
@@ -742,6 +966,8 @@ public:
return m_status;
}
+ String errorMessage() { return m_errorMessage; }
+
// Functions used by serialization states.
StateBase* doSerialize(v8::Handle<v8::Value>, StateBase* next);
@@ -752,12 +978,7 @@ public:
StateBase* checkException(StateBase* state)
{
- return m_tryCatch.HasCaught() ? handleError(JSException, state) : 0;
- }
-
- StateBase* reportFailure(StateBase* state)
- {
- return handleError(JSFailure, state);
+ return m_tryCatch.HasCaught() ? handleError(JSException, "", state) : 0;
}
StateBase* writeObject(uint32_t numProperties, StateBase* state)
@@ -796,10 +1017,6 @@ private:
// state.
virtual StateBase* advance(Serializer&) = 0;
- // Returns 1 if this state is currently serializing a property
- // via an accessor and 0 otherwise.
- virtual uint32_t execDepth() const { return 0; }
-
protected:
StateBase(v8::Handle<v8::Value> composite, StateBase* next)
: m_composite(composite)
@@ -813,14 +1030,14 @@ private:
};
// Dummy state that is used to signal serialization errors.
- class ErrorState : public StateBase {
+ class ErrorState FINAL : public StateBase {
public:
ErrorState()
: StateBase(v8Undefined(), 0)
{
}
- virtual StateBase* advance(Serializer&)
+ virtual StateBase* advance(Serializer&) OVERRIDE
{
delete this;
return 0;
@@ -860,7 +1077,7 @@ private:
if (StateBase* newState = serializer.checkException(this))
return newState;
if (propertyName.IsEmpty())
- return serializer.reportFailure(this);
+ return serializer.handleError(InputError, "Empty property names cannot be cloned.", this);
bool hasStringProperty = propertyName->IsString() && composite()->HasRealNamedProperty(propertyName.As<v8::String>());
if (StateBase* newState = serializer.checkException(this))
return newState;
@@ -905,33 +1122,33 @@ private:
bool m_nameDone;
};
- class ObjectState : public AbstractObjectState {
+ class ObjectState FINAL : public AbstractObjectState {
public:
ObjectState(v8::Handle<v8::Object> object, StateBase* next)
: AbstractObjectState(object, next)
{
}
- virtual StateBase* advance(Serializer& serializer)
+ virtual StateBase* advance(Serializer& serializer) OVERRIDE
{
if (m_propertyNames.IsEmpty()) {
m_propertyNames = composite()->GetPropertyNames();
if (StateBase* newState = serializer.checkException(this))
return newState;
if (m_propertyNames.IsEmpty())
- return serializer.reportFailure(this);
+ return serializer.handleError(InputError, "Empty property names cannot be cloned.", nextState());
}
return serializeProperties(false, serializer);
}
protected:
- virtual StateBase* objectDone(unsigned numProperties, Serializer& serializer)
+ virtual StateBase* objectDone(unsigned numProperties, Serializer& serializer) OVERRIDE
{
return serializer.writeObject(numProperties, this);
}
};
- class DenseArrayState : public AbstractObjectState {
+ class DenseArrayState FINAL : public AbstractObjectState {
public:
DenseArrayState(v8::Handle<v8::Array> array, v8::Handle<v8::Array> propertyNames, StateBase* next, v8::Isolate* isolate)
: AbstractObjectState(array, next)
@@ -941,7 +1158,7 @@ private:
m_propertyNames = v8::Local<v8::Array>::New(isolate, propertyNames);
}
- virtual StateBase* advance(Serializer& serializer)
+ virtual StateBase* advance(Serializer& serializer) OVERRIDE
{
while (m_arrayIndex < m_arrayLength) {
v8::Handle<v8::Value> value = composite().As<v8::Array>()->Get(m_arrayIndex);
@@ -955,7 +1172,7 @@ private:
}
protected:
- virtual StateBase* objectDone(unsigned numProperties, Serializer& serializer)
+ virtual StateBase* objectDone(unsigned numProperties, Serializer& serializer) OVERRIDE
{
return serializer.writeDenseArray(numProperties, m_arrayLength, this);
}
@@ -965,7 +1182,7 @@ private:
uint32_t m_arrayLength;
};
- class SparseArrayState : public AbstractObjectState {
+ class SparseArrayState FINAL : public AbstractObjectState {
public:
SparseArrayState(v8::Handle<v8::Array> array, v8::Handle<v8::Array> propertyNames, StateBase* next, v8::Isolate* isolate)
: AbstractObjectState(array, next)
@@ -973,13 +1190,13 @@ private:
m_propertyNames = v8::Local<v8::Array>::New(isolate, propertyNames);
}
- virtual StateBase* advance(Serializer& serializer)
+ virtual StateBase* advance(Serializer& serializer) OVERRIDE
{
return serializeProperties(false, serializer);
}
protected:
- virtual StateBase* objectDone(unsigned numProperties, Serializer& serializer)
+ virtual StateBase* objectDone(unsigned numProperties, Serializer& serializer) OVERRIDE
{
return serializer.writeSparseArray(numProperties, composite().As<v8::Array>()->Length(), this);
}
@@ -989,7 +1206,7 @@ private:
{
ASSERT(state);
++m_depth;
- return checkComposite(state) ? state : handleError(InputError, state);
+ return checkComposite(state) ? state : handleError(InputError, "Value being cloned is either cyclic or too deeply nested.", state);
}
StateBase* pop(StateBase* state)
@@ -1001,10 +1218,11 @@ private:
return next;
}
- StateBase* handleError(Status errorStatus, StateBase* state)
+ StateBase* handleError(Status errorStatus, const String& message, StateBase* state)
{
ASSERT(errorStatus != Success);
m_status = errorStatus;
+ m_errorMessage = message;
while (state) {
StateBase* tmp = state->nextState();
delete state;
@@ -1056,13 +1274,20 @@ private:
m_writer.writeBooleanObject(booleanObject->ValueOf());
}
- void writeBlob(v8::Handle<v8::Value> value)
+ StateBase* writeBlob(v8::Handle<v8::Value> value, StateBase* next)
{
Blob* blob = V8Blob::toNative(value.As<v8::Object>());
if (!blob)
- return;
- m_writer.writeBlob(blob->uuid(), blob->type(), blob->size());
- m_blobDataHandles.add(blob->uuid(), blob->blobDataHandle());
+ return 0;
+ if (blob->hasBeenClosed())
+ return handleError(DataCloneError, "A Blob object has been closed, and could therefore not be cloned.", next);
+ int blobIndex = -1;
+ m_blobDataHandles.set(blob->uuid(), blob->blobDataHandle());
+ if (appendBlobInfo(blob->uuid(), blob->type(), blob->size(), &blobIndex))
+ m_writer.writeBlobIndex(blobIndex);
+ else
+ m_writer.writeBlob(blob->uuid(), blob->type(), blob->size());
+ return 0;
}
StateBase* writeDOMFileSystem(v8::Handle<v8::Value> value, StateBase* next)
@@ -1071,29 +1296,61 @@ private:
if (!fs)
return 0;
if (!fs->clonable())
- return handleError(DataCloneError, next);
+ return handleError(DataCloneError, "A FileSystem object could not be cloned.", next);
m_writer.writeDOMFileSystem(fs->type(), fs->name(), fs->rootURL().string());
return 0;
}
- void writeFile(v8::Handle<v8::Value> value)
+ StateBase* writeFile(v8::Handle<v8::Value> value, StateBase* next)
{
File* file = V8File::toNative(value.As<v8::Object>());
if (!file)
- return;
- m_writer.writeFile(*file);
- m_blobDataHandles.add(file->uuid(), file->blobDataHandle());
+ return 0;
+ if (file->hasBeenClosed())
+ return handleError(DataCloneError, "A File object has been closed, and could therefore not be cloned.", next);
+ int blobIndex = -1;
+ m_blobDataHandles.set(file->uuid(), file->blobDataHandle());
+ if (appendFileInfo(file, &blobIndex)) {
+ ASSERT(blobIndex >= 0);
+ m_writer.writeFileIndex(blobIndex);
+ } else {
+ m_writer.writeFile(*file);
+ }
+ return 0;
}
- void writeFileList(v8::Handle<v8::Value> value)
+ StateBase* writeFileList(v8::Handle<v8::Value> value, StateBase* next)
{
FileList* fileList = V8FileList::toNative(value.As<v8::Object>());
if (!fileList)
- return;
- m_writer.writeFileList(*fileList);
+ return 0;
unsigned length = fileList->length();
- for (unsigned i = 0; i < length; ++i)
- m_blobDataHandles.add(fileList->item(i)->uuid(), fileList->item(i)->blobDataHandle());
+ Vector<int> blobIndices;
+ for (unsigned i = 0; i < length; ++i) {
+ int blobIndex = -1;
+ const File* file = fileList->item(i);
+ if (file->hasBeenClosed())
+ return handleError(DataCloneError, "A File object has been closed, and could therefore not be cloned.", next);
+ m_blobDataHandles.set(file->uuid(), file->blobDataHandle());
+ if (appendFileInfo(file, &blobIndex)) {
+ ASSERT(!i || blobIndex > 0);
+ ASSERT(blobIndex >= 0);
+ blobIndices.append(blobIndex);
+ }
+ }
+ if (!blobIndices.isEmpty())
+ m_writer.writeFileListIndex(blobIndices);
+ else
+ m_writer.writeFileList(*fileList);
+ return 0;
+ }
+
+ bool writeCryptoKey(v8::Handle<v8::Value> value)
+ {
+ Key* key = V8Key::toNative(value.As<v8::Object>());
+ if (!key)
+ return false;
+ return m_writer.writeCryptoKey(key->key());
}
void writeImageData(v8::Handle<v8::Value> value)
@@ -1118,10 +1375,10 @@ private:
if (!arrayBufferView)
return 0;
if (!arrayBufferView->buffer())
- return handleError(DataCloneError, next);
- v8::Handle<v8::Value> underlyingBuffer = toV8(arrayBufferView->buffer(), v8::Handle<v8::Object>(), m_writer.getIsolate());
+ return handleError(DataCloneError, "An ArrayBuffer could not be cloned.", next);
+ v8::Handle<v8::Value> underlyingBuffer = toV8(arrayBufferView->buffer(), m_scriptState->context()->Global(), isolate());
if (underlyingBuffer.IsEmpty())
- return handleError(DataCloneError, next);
+ return handleError(DataCloneError, "An ArrayBuffer could not be cloned.", next);
StateBase* stateOut = doSerializeArrayBuffer(underlyingBuffer, next);
if (stateOut)
return stateOut;
@@ -1146,7 +1403,7 @@ private:
if (!arrayBuffer)
return 0;
if (arrayBuffer->isNeutered())
- return handleError(InvalidStateError, next);
+ return handleError(DataCloneError, "An ArrayBuffer is neutered and could not be cloned.", next);
ASSERT(!m_transferredArrayBuffers.contains(value.As<v8::Object>()));
m_writer.writeArrayBuffer(*arrayBuffer);
return 0;
@@ -1158,7 +1415,7 @@ private:
if (!arrayBuffer)
return 0;
if (arrayBuffer->isNeutered())
- return handleError(DataCloneError, next);
+ return handleError(DataCloneError, "An ArrayBuffer is neutered and could not be cloned.", next);
m_writer.writeTransferredArrayBuffer(index);
return 0;
}
@@ -1181,11 +1438,11 @@ private:
if (shouldSerializeDensely(length, propertyNames->Length())) {
m_writer.writeGenerateFreshDenseArray(length);
- return push(new DenseArrayState(array, propertyNames, next, m_isolate));
+ return push(new DenseArrayState(array, propertyNames, next, isolate()));
}
m_writer.writeGenerateFreshSparseArray(length);
- return push(new SparseArrayState(array, propertyNames, next, m_isolate));
+ return push(new SparseArrayState(array, propertyNames, next, isolate()));
}
StateBase* startObjectState(v8::Handle<v8::Object> object, StateBase* next)
@@ -1204,34 +1461,68 @@ private:
m_objectPool.set(object, objectReference);
}
+ bool appendBlobInfo(const String& uuid, const String& type, unsigned long long size, int* index)
+ {
+ if (!m_blobInfo)
+ return false;
+ *index = m_blobInfo->size();
+ m_blobInfo->append(blink::WebBlobInfo(uuid, type, size));
+ return true;
+ }
+
+ bool appendFileInfo(const File* file, int* index)
+ {
+ if (!m_blobInfo)
+ return false;
+
+ long long size = -1;
+ double lastModified = invalidFileTime();
+ file->captureSnapshot(size, lastModified);
+ *index = m_blobInfo->size();
+ m_blobInfo->append(blink::WebBlobInfo(file->uuid(), file->path(), file->name(), file->type(), lastModified, size));
+ return true;
+ }
+
+ RefPtr<ScriptState> m_scriptState;
Writer& m_writer;
v8::TryCatch& m_tryCatch;
int m_depth;
Status m_status;
+ String m_errorMessage;
typedef V8ObjectMap<v8::Object, uint32_t> ObjectPool;
ObjectPool m_objectPool;
ObjectPool m_transferredMessagePorts;
ObjectPool m_transferredArrayBuffers;
uint32_t m_nextObjectReference;
+ WebBlobInfoArray* m_blobInfo;
BlobDataHandleMap& m_blobDataHandles;
- v8::Isolate* m_isolate;
};
+// Returns true if the provided object is to be considered a 'host object', as used in the
+// HTML5 structured clone algorithm.
+static bool isHostObject(v8::Handle<v8::Object> object)
+{
+ // If the object has any internal fields, then we won't be able to serialize or deserialize
+ // them; conveniently, this is also a quick way to detect DOM wrapper objects, because
+ // the mechanism for these relies on data stored in these fields. We should
+ // catch external array data as a special case.
+ return object->InternalFieldCount() || object->HasIndexedPropertiesInExternalArrayData();
+}
+
Serializer::StateBase* Serializer::doSerialize(v8::Handle<v8::Value> value, StateBase* next)
{
m_writer.writeReferenceCount(m_nextObjectReference);
uint32_t objectReference;
uint32_t arrayBufferIndex;
- WrapperWorldType currentWorldType = worldType(m_isolate);
if ((value->IsObject() || value->IsDate() || value->IsRegExp())
&& m_objectPool.tryGet(value.As<v8::Object>(), &objectReference)) {
// Note that IsObject() also detects wrappers (eg, it will catch the things
// that we grey and write below).
ASSERT(!value->IsString());
m_writer.writeObjectReference(objectReference);
- } else if (value.IsEmpty())
- return reportFailure(next);
- else if (value->IsUndefined())
+ } else if (value.IsEmpty()) {
+ return handleError(InputError, "The empty property name cannot be cloned.", next);
+ } else if (value->IsUndefined())
m_writer.writeUndefined();
else if (value->IsNull())
m_writer.writeNull();
@@ -1245,22 +1536,22 @@ Serializer::StateBase* Serializer::doSerialize(v8::Handle<v8::Value> value, Stat
m_writer.writeUint32(value->Uint32Value());
else if (value->IsNumber())
m_writer.writeNumber(value.As<v8::Number>()->Value());
- else if (V8ArrayBufferView::hasInstance(value, m_isolate, currentWorldType))
+ else if (V8ArrayBufferView::hasInstance(value, isolate()))
return writeAndGreyArrayBufferView(value.As<v8::Object>(), next);
else if (value->IsString())
writeString(value);
- else if (V8MessagePort::hasInstance(value, m_isolate, currentWorldType)) {
+ else if (V8MessagePort::hasInstance(value, isolate())) {
uint32_t messagePortIndex;
if (m_transferredMessagePorts.tryGet(value.As<v8::Object>(), &messagePortIndex))
m_writer.writeTransferredMessagePort(messagePortIndex);
else
- return handleError(DataCloneError, next);
- } else if (V8ArrayBuffer::hasInstance(value, m_isolate, currentWorldType) && m_transferredArrayBuffers.tryGet(value.As<v8::Object>(), &arrayBufferIndex))
+ return handleError(DataCloneError, "A MessagePort could not be cloned.", next);
+ } else if (V8ArrayBuffer::hasInstance(value, isolate()) && m_transferredArrayBuffers.tryGet(value.As<v8::Object>(), &arrayBufferIndex))
return writeTransferredArrayBuffer(value, arrayBufferIndex, next);
else {
v8::Handle<v8::Object> jsObject = value.As<v8::Object>();
if (jsObject.IsEmpty())
- return handleError(DataCloneError, next);
+ return handleError(DataCloneError, "An object could not be cloned.", next);
greyObject(jsObject);
if (value->IsDate())
m_writer.writeDate(value->NumberValue());
@@ -1272,26 +1563,29 @@ Serializer::StateBase* Serializer::doSerialize(v8::Handle<v8::Value> value, Stat
writeBooleanObject(value);
else if (value->IsArray()) {
return startArrayState(value.As<v8::Array>(), next);
- } else if (V8File::hasInstance(value, m_isolate, currentWorldType))
- writeFile(value);
- else if (V8Blob::hasInstance(value, m_isolate, currentWorldType))
- writeBlob(value);
- else if (V8DOMFileSystem::hasInstance(value, m_isolate, currentWorldType))
+ } else if (V8File::hasInstance(value, isolate()))
+ return writeFile(value, next);
+ else if (V8Blob::hasInstance(value, isolate()))
+ return writeBlob(value, next);
+ else if (V8DOMFileSystem::hasInstance(value, isolate()))
return writeDOMFileSystem(value, next);
- else if (V8FileList::hasInstance(value, m_isolate, currentWorldType))
- writeFileList(value);
- else if (V8ImageData::hasInstance(value, m_isolate, currentWorldType))
+ else if (V8FileList::hasInstance(value, isolate()))
+ return writeFileList(value, next);
+ else if (V8Key::hasInstance(value, isolate())) {
+ if (!writeCryptoKey(value))
+ return handleError(DataCloneError, "Couldn't serialize key data", next);
+ } else if (V8ImageData::hasInstance(value, isolate()))
writeImageData(value);
else if (value->IsRegExp())
writeRegExp(value);
- else if (V8ArrayBuffer::hasInstance(value, m_isolate, currentWorldType))
+ else if (V8ArrayBuffer::hasInstance(value, isolate()))
return writeArrayBuffer(value, next);
else if (value->IsObject()) {
if (isHostObject(jsObject) || jsObject->IsCallable() || value->IsNativeError())
- return handleError(DataCloneError, next);
+ return handleError(DataCloneError, "An object could not be cloned.", next);
return startObjectState(jsObject, next);
} else
- return handleError(DataCloneError, next);
+ return handleError(DataCloneError, "A value could not be cloned.", next);
}
return 0;
}
@@ -1319,12 +1613,13 @@ public:
// restoring information about saved objects of composite types.
class Reader {
public:
- Reader(const uint8_t* buffer, int length, v8::Isolate* isolate, const BlobDataHandleMap& blobDataHandles)
- : m_buffer(buffer)
+ Reader(const uint8_t* buffer, int length, const WebBlobInfoArray* blobInfo, BlobDataHandleMap& blobDataHandles, ScriptState* scriptState)
+ : m_scriptState(scriptState)
+ , m_buffer(buffer)
, m_length(length)
, m_position(0)
, m_version(0)
- , m_isolate(isolate)
+ , m_blobInfo(blobInfo)
, m_blobDataHandles(blobDataHandles)
{
ASSERT(!(reinterpret_cast<size_t>(buffer) & 1));
@@ -1333,8 +1628,12 @@ public:
bool isEof() const { return m_position >= m_length; }
- v8::Isolate* isolate() const { return m_isolate; }
+ ScriptState* scriptState() const { return m_scriptState.get(); }
+
+private:
+ v8::Isolate* isolate() const { return m_scriptState->isolate(); }
+public:
bool read(v8::Handle<v8::Value>* value, CompositeCreator& creator)
{
SerializationTag tag;
@@ -1342,7 +1641,7 @@ public:
return false;
switch (tag) {
case ReferenceCountTag: {
- if (m_version <= 0)
+ if (!m_version)
return false;
uint32_t referenceTableSize;
if (!doReadUint32(&referenceTableSize))
@@ -1359,16 +1658,16 @@ public:
case PaddingTag:
return true;
case UndefinedTag:
- *value = v8::Undefined(m_isolate);
+ *value = v8::Undefined(isolate());
break;
case NullTag:
- *value = v8::Null(m_isolate);
+ *value = v8::Null(isolate());
break;
case TrueTag:
- *value = v8BooleanWithCheck(true, m_isolate);
+ *value = v8Boolean(true, isolate());
break;
case FalseTag:
- *value = v8BooleanWithCheck(false, m_isolate);
+ *value = v8Boolean(false, isolate());
break;
case TrueObjectTag:
*value = v8::BooleanObject::New(true);
@@ -1414,12 +1713,14 @@ public:
creator.pushObjectReference(*value);
break;
case BlobTag:
- if (!readBlob(value))
+ case BlobIndexTag:
+ if (!readBlob(value, tag == BlobIndexTag))
return false;
creator.pushObjectReference(*value);
break;
case FileTag:
- if (!readFile(value))
+ case FileIndexTag:
+ if (!readFile(value, tag == FileIndexTag))
return false;
creator.pushObjectReference(*value);
break;
@@ -1429,7 +1730,13 @@ public:
creator.pushObjectReference(*value);
break;
case FileListTag:
- if (!readFileList(value))
+ case FileListIndexTag:
+ if (!readFileList(value, tag == FileListIndexTag))
+ return false;
+ creator.pushObjectReference(*value);
+ break;
+ case CryptoKeyTag:
+ if (!readCryptoKey(value))
return false;
creator.pushObjectReference(*value);
break;
@@ -1475,7 +1782,7 @@ public:
break;
}
case ArrayBufferViewTag: {
- if (m_version <= 0)
+ if (!m_version)
return false;
if (!readArrayBufferView(value, creator))
return false;
@@ -1483,7 +1790,7 @@ public:
break;
}
case ArrayBufferTag: {
- if (m_version <= 0)
+ if (!m_version)
return false;
if (!readArrayBuffer(value))
return false;
@@ -1491,14 +1798,14 @@ public:
break;
}
case GenerateFreshObjectTag: {
- if (m_version <= 0)
+ if (!m_version)
return false;
if (!creator.newObject())
return false;
return true;
}
case GenerateFreshSparseArrayTag: {
- if (m_version <= 0)
+ if (!m_version)
return false;
uint32_t length;
if (!doReadUint32(&length))
@@ -1508,7 +1815,7 @@ public:
return true;
}
case GenerateFreshDenseArrayTag: {
- if (m_version <= 0)
+ if (!m_version)
return false;
uint32_t length;
if (!doReadUint32(&length))
@@ -1518,7 +1825,7 @@ public:
return true;
}
case MessagePortTag: {
- if (m_version <= 0)
+ if (!m_version)
return false;
uint32_t index;
if (!doReadUint32(&index))
@@ -1528,7 +1835,7 @@ public:
break;
}
case ArrayBufferTransferTag: {
- if (m_version <= 0)
+ if (!m_version)
return false;
uint32_t index;
if (!doReadUint32(&index))
@@ -1538,7 +1845,7 @@ public:
break;
}
case ObjectReferenceTag: {
- if (m_version <= 0)
+ if (!m_version)
return false;
uint32_t reference;
if (!doReadUint32(&reference))
@@ -1577,8 +1884,6 @@ public:
m_version = version;
}
- v8::Isolate* getIsolate() { return m_isolate; }
-
private:
bool readTag(SerializationTag* tag)
{
@@ -1609,7 +1914,7 @@ private:
return false;
if (m_position + length > m_length)
return false;
- *value = v8::String::NewFromUtf8(m_isolate, reinterpret_cast<const char*>(m_buffer + m_position), v8::String::kNormalString, length);
+ *value = v8::String::NewFromUtf8(isolate(), reinterpret_cast<const char*>(m_buffer + m_position), v8::String::kNormalString, length);
m_position += length;
return true;
}
@@ -1622,7 +1927,7 @@ private:
if (m_position + length > m_length)
return false;
ASSERT(!(m_position & 1));
- *value = v8::String::NewFromTwoByte(m_isolate, reinterpret_cast<const uint16_t*>(m_buffer + m_position), v8::String::kNormalString, length / sizeof(UChar));
+ *value = v8::String::NewFromTwoByte(isolate(), reinterpret_cast<const uint16_t*>(m_buffer + m_position), v8::String::kNormalString, length / sizeof(UChar));
m_position += length;
return true;
}
@@ -1653,7 +1958,7 @@ private:
uint32_t rawValue;
if (!doReadUint32(&rawValue))
return false;
- *value = v8::Integer::New(static_cast<int32_t>(ZigZag::decode(rawValue)), m_isolate);
+ *value = v8::Integer::New(isolate(), static_cast<int32_t>(ZigZag::decode(rawValue)));
return true;
}
@@ -1662,7 +1967,7 @@ private:
uint32_t rawValue;
if (!doReadUint32(&rawValue))
return false;
- *value = v8::Integer::NewFromUnsigned(rawValue, m_isolate);
+ *value = v8::Integer::NewFromUnsigned(isolate(), rawValue);
return true;
}
@@ -1671,7 +1976,7 @@ private:
double numberValue;
if (!doReadNumber(&numberValue))
return false;
- *value = v8DateOrNull(numberValue, m_isolate);
+ *value = v8DateOrNaN(numberValue, isolate());
return true;
}
@@ -1680,7 +1985,7 @@ private:
double number;
if (!doReadNumber(&number))
return false;
- *value = v8::Number::New(m_isolate, number);
+ *value = v8::Number::New(isolate(), number);
return true;
}
@@ -1689,7 +1994,7 @@ private:
double number;
if (!doReadNumber(&number))
return false;
- *value = v8::NumberObject::New(m_isolate, number);
+ *value = v8::NumberObject::New(isolate(), number);
return true;
}
@@ -1706,13 +2011,13 @@ private:
return false;
if (m_position + pixelDataLength > m_length)
return false;
- RefPtr<ImageData> imageData = ImageData::create(IntSize(width, height));
+ RefPtrWillBeRawPtr<ImageData> imageData = ImageData::create(IntSize(width, height));
Uint8ClampedArray* pixelArray = imageData->data();
ASSERT(pixelArray);
ASSERT(pixelArray->length() >= pixelDataLength);
memcpy(pixelArray->data(), m_buffer + m_position, pixelDataLength);
m_position += pixelDataLength;
- *value = toV8(imageData.release(), v8::Handle<v8::Object>(), m_isolate);
+ *value = toV8(imageData.release(), m_scriptState->context()->Global(), isolate());
return true;
}
@@ -1720,9 +2025,9 @@ private:
{
uint32_t byteLength;
if (!doReadUint32(&byteLength))
- return 0;
+ return nullptr;
if (m_position + byteLength > m_length)
- return 0;
+ return nullptr;
const void* bufferStart = m_buffer + m_position;
RefPtr<ArrayBuffer> arrayBuffer = ArrayBuffer::create(bufferStart, byteLength);
arrayBuffer->setDeallocationObserver(V8ArrayBufferDeallocationObserver::instanceTemplate());
@@ -1735,7 +2040,7 @@ private:
RefPtr<ArrayBuffer> arrayBuffer = doReadArrayBuffer();
if (!arrayBuffer)
return false;
- *value = toV8(arrayBuffer.release(), v8::Handle<v8::Object>(), m_isolate);
+ *value = toV8(arrayBuffer.release(), m_scriptState->context()->Global(), isolate());
return true;
}
@@ -1759,60 +2064,62 @@ private:
arrayBuffer = V8ArrayBuffer::toNative(arrayBufferV8Value.As<v8::Object>());
if (!arrayBuffer)
return false;
+
+ v8::Handle<v8::Object> creationContext = m_scriptState->context()->Global();
switch (subTag) {
case ByteArrayTag:
- *value = toV8(Int8Array::create(arrayBuffer.release(), byteOffset, byteLength), v8::Handle<v8::Object>(), m_isolate);
+ *value = toV8(Int8Array::create(arrayBuffer.release(), byteOffset, byteLength), creationContext, isolate());
break;
case UnsignedByteArrayTag:
- *value = toV8(Uint8Array::create(arrayBuffer.release(), byteOffset, byteLength), v8::Handle<v8::Object>(), m_isolate);
+ *value = toV8(Uint8Array::create(arrayBuffer.release(), byteOffset, byteLength), creationContext, isolate());
break;
case UnsignedByteClampedArrayTag:
- *value = toV8(Uint8ClampedArray::create(arrayBuffer.release(), byteOffset, byteLength), v8::Handle<v8::Object>(), m_isolate);
+ *value = toV8(Uint8ClampedArray::create(arrayBuffer.release(), byteOffset, byteLength), creationContext, isolate());
break;
case ShortArrayTag: {
uint32_t shortLength = byteLength / sizeof(int16_t);
if (shortLength * sizeof(int16_t) != byteLength)
return false;
- *value = toV8(Int16Array::create(arrayBuffer.release(), byteOffset, shortLength), v8::Handle<v8::Object>(), m_isolate);
+ *value = toV8(Int16Array::create(arrayBuffer.release(), byteOffset, shortLength), creationContext, isolate());
break;
}
case UnsignedShortArrayTag: {
uint32_t shortLength = byteLength / sizeof(uint16_t);
if (shortLength * sizeof(uint16_t) != byteLength)
return false;
- *value = toV8(Uint16Array::create(arrayBuffer.release(), byteOffset, shortLength), v8::Handle<v8::Object>(), m_isolate);
+ *value = toV8(Uint16Array::create(arrayBuffer.release(), byteOffset, shortLength), creationContext, isolate());
break;
}
case IntArrayTag: {
uint32_t intLength = byteLength / sizeof(int32_t);
if (intLength * sizeof(int32_t) != byteLength)
return false;
- *value = toV8(Int32Array::create(arrayBuffer.release(), byteOffset, intLength), v8::Handle<v8::Object>(), m_isolate);
+ *value = toV8(Int32Array::create(arrayBuffer.release(), byteOffset, intLength), creationContext, isolate());
break;
}
case UnsignedIntArrayTag: {
uint32_t intLength = byteLength / sizeof(uint32_t);
if (intLength * sizeof(uint32_t) != byteLength)
return false;
- *value = toV8(Uint32Array::create(arrayBuffer.release(), byteOffset, intLength), v8::Handle<v8::Object>(), m_isolate);
+ *value = toV8(Uint32Array::create(arrayBuffer.release(), byteOffset, intLength), creationContext, isolate());
break;
}
case FloatArrayTag: {
uint32_t floatLength = byteLength / sizeof(float);
if (floatLength * sizeof(float) != byteLength)
return false;
- *value = toV8(Float32Array::create(arrayBuffer.release(), byteOffset, floatLength), v8::Handle<v8::Object>(), m_isolate);
+ *value = toV8(Float32Array::create(arrayBuffer.release(), byteOffset, floatLength), creationContext, isolate());
break;
}
case DoubleArrayTag: {
uint32_t floatLength = byteLength / sizeof(double);
if (floatLength * sizeof(double) != byteLength)
return false;
- *value = toV8(Float64Array::create(arrayBuffer.release(), byteOffset, floatLength), v8::Handle<v8::Object>(), m_isolate);
+ *value = toV8(Float64Array::create(arrayBuffer.release(), byteOffset, floatLength), creationContext, isolate());
break;
}
case DataViewTag:
- *value = toV8(DataView::create(arrayBuffer.release(), byteOffset, byteLength), v8::Handle<v8::Object>(), m_isolate);
+ *value = toV8(DataView::create(arrayBuffer.release(), byteOffset, byteLength), creationContext, isolate());
break;
default:
return false;
@@ -1835,21 +2142,35 @@ private:
return true;
}
- bool readBlob(v8::Handle<v8::Value>* value)
+ bool readBlob(v8::Handle<v8::Value>* value, bool isIndexed)
{
if (m_version < 3)
return false;
- String uuid;
- String type;
- uint64_t size;
- if (!readWebCoreString(&uuid))
- return false;
- if (!readWebCoreString(&type))
- return false;
- if (!doReadUint64(&size))
- return false;
- RefPtr<Blob> blob = Blob::create(getOrCreateBlobDataHandle(uuid, type, size));
- *value = toV8(blob.release(), v8::Handle<v8::Object>(), m_isolate);
+ RefPtrWillBeRawPtr<Blob> blob;
+ if (isIndexed) {
+ if (m_version < 6)
+ return false;
+ ASSERT(m_blobInfo);
+ uint32_t index;
+ if (!doReadUint32(&index) || index >= m_blobInfo->size())
+ return false;
+ const blink::WebBlobInfo& info = (*m_blobInfo)[index];
+ blob = Blob::create(getOrCreateBlobDataHandle(info.uuid(), info.type(), info.size()));
+ } else {
+ ASSERT(!m_blobInfo);
+ String uuid;
+ String type;
+ uint64_t size;
+ ASSERT(!m_blobInfo);
+ if (!readWebCoreString(&uuid))
+ return false;
+ if (!readWebCoreString(&type))
+ return false;
+ if (!doReadUint64(&size))
+ return false;
+ blob = Blob::create(getOrCreateBlobDataHandle(uuid, type, size));
+ }
+ *value = toV8(blob.release(), m_scriptState->context()->Global(), isolate());
return true;
}
@@ -1864,42 +2185,108 @@ private:
return false;
if (!readWebCoreString(&url))
return false;
- RefPtr<DOMFileSystem> fs = DOMFileSystem::create(getExecutionContext(), name, static_cast<WebCore::FileSystemType>(type), KURL(ParsedURLString, url));
- *value = toV8(fs.release(), v8::Handle<v8::Object>(), m_isolate);
+ DOMFileSystem* fs = DOMFileSystem::create(m_scriptState->executionContext(), name, static_cast<WebCore::FileSystemType>(type), KURL(ParsedURLString, url));
+ *value = toV8(fs, m_scriptState->context()->Global(), isolate());
return true;
}
- bool readFile(v8::Handle<v8::Value>* value)
+ bool readFile(v8::Handle<v8::Value>* value, bool isIndexed)
{
- RefPtr<File> file = doReadFileHelper();
+ RefPtrWillBeRawPtr<File> file;
+ if (isIndexed) {
+ if (m_version < 6)
+ return false;
+ file = readFileIndexHelper();
+ } else {
+ file = readFileHelper();
+ }
if (!file)
return false;
- *value = toV8(file.release(), v8::Handle<v8::Object>(), m_isolate);
+ *value = toV8(file.release(), m_scriptState->context()->Global(), isolate());
return true;
}
- bool readFileList(v8::Handle<v8::Value>* value)
+ bool readFileList(v8::Handle<v8::Value>* value, bool isIndexed)
{
if (m_version < 3)
return false;
uint32_t length;
if (!doReadUint32(&length))
return false;
- RefPtr<FileList> fileList = FileList::create();
+ RefPtrWillBeRawPtr<FileList> fileList = FileList::create();
for (unsigned i = 0; i < length; ++i) {
- RefPtr<File> file = doReadFileHelper();
+ RefPtrWillBeRawPtr<File> file;
+ if (isIndexed) {
+ if (m_version < 6)
+ return false;
+ file = readFileIndexHelper();
+ } else {
+ file = readFileHelper();
+ }
if (!file)
return false;
fileList->append(file.release());
}
- *value = toV8(fileList.release(), v8::Handle<v8::Object>(), m_isolate);
+ *value = toV8(fileList.release(), m_scriptState->context()->Global(), isolate());
return true;
}
- PassRefPtr<File> doReadFileHelper()
+ bool readCryptoKey(v8::Handle<v8::Value>* value)
+ {
+ uint32_t rawKeyType;
+ if (!doReadUint32(&rawKeyType))
+ return false;
+
+ blink::WebCryptoKeyAlgorithm algorithm;
+ blink::WebCryptoKeyType type = blink::WebCryptoKeyTypeSecret;
+
+ switch (static_cast<CryptoKeySubTag>(rawKeyType)) {
+ case AesKeyTag:
+ if (!doReadAesKey(algorithm, type))
+ return false;
+ break;
+ case HmacKeyTag:
+ if (!doReadHmacKey(algorithm, type))
+ return false;
+ break;
+ case RsaHashedKeyTag:
+ if (!doReadRsaHashedKey(algorithm, type))
+ return false;
+ break;
+ default:
+ return false;
+ }
+
+ blink::WebCryptoKeyUsageMask usages;
+ bool extractable;
+ if (!doReadKeyUsages(usages, extractable))
+ return false;
+
+ uint32_t keyDataLength;
+ if (!doReadUint32(&keyDataLength))
+ return false;
+
+ if (m_position + keyDataLength > m_length)
+ return false;
+
+ const uint8_t* keyData = m_buffer + m_position;
+ m_position += keyDataLength;
+
+ blink::WebCryptoKey key = blink::WebCryptoKey::createNull();
+ if (!blink::Platform::current()->crypto()->deserializeKeyForClone(
+ algorithm, type, extractable, usages, keyData, keyDataLength, key)) {
+ return false;
+ }
+
+ *value = toV8(Key::create(key), m_scriptState->context()->Global(), isolate());
+ return true;
+ }
+
+ PassRefPtrWillBeRawPtr<File> readFileHelper()
{
if (m_version < 3)
- return 0;
+ return nullptr;
+ ASSERT(!m_blobInfo);
String path;
String name;
String relativePath;
@@ -1909,26 +2296,38 @@ private:
uint64_t size = 0;
double lastModified = 0;
if (!readWebCoreString(&path))
- return 0;
+ return nullptr;
if (m_version >= 4 && !readWebCoreString(&name))
- return 0;
+ return nullptr;
if (m_version >= 4 && !readWebCoreString(&relativePath))
- return 0;
+ return nullptr;
if (!readWebCoreString(&uuid))
- return 0;
+ return nullptr;
if (!readWebCoreString(&type))
- return 0;
+ return nullptr;
if (m_version >= 4 && !doReadUint32(&hasSnapshot))
- return 0;
+ return nullptr;
if (hasSnapshot) {
if (!doReadUint64(&size))
- return 0;
+ return nullptr;
if (!doReadNumber(&lastModified))
- return 0;
+ return nullptr;
}
return File::create(path, name, relativePath, hasSnapshot > 0, size, lastModified, getOrCreateBlobDataHandle(uuid, type));
}
+ PassRefPtrWillBeRawPtr<File> readFileIndexHelper()
+ {
+ if (m_version < 3)
+ return nullptr;
+ ASSERT(m_blobInfo);
+ uint32_t index;
+ if (!doReadUint32(&index) || index >= m_blobInfo->size())
+ return nullptr;
+ const blink::WebBlobInfo& info = (*m_blobInfo)[index];
+ return File::create(info.filePath(), info.fileName(), info.size(), info.lastModified(), getOrCreateBlobDataHandle(info.uuid(), info.type(), info.size()));
+ }
+
template<class T>
bool doReadUintHelper(T* value)
{
@@ -1976,7 +2375,7 @@ private:
// the collection of BDH's for blobs to work, which would encourage lifetimes to be considered
// when passing ssv's around cross process. At present, we get 'lucky' in some cases because
// the blob in the src process happens to still exist at the time the dest process is deserializing.
- // For example in sharedWorker.postMesssage(...).
+ // For example in sharedWorker.postMessage(...).
BlobDataHandleMap::const_iterator it = m_blobDataHandles.find(uuid);
if (it != m_blobDataHandles.end()) {
// make assertions about type and size?
@@ -1985,18 +2384,171 @@ private:
return BlobDataHandle::create(uuid, type, size);
}
+ bool doReadHmacKey(blink::WebCryptoKeyAlgorithm& algorithm, blink::WebCryptoKeyType& type)
+ {
+ uint32_t lengthBytes;
+ if (!doReadUint32(&lengthBytes))
+ return false;
+ blink::WebCryptoAlgorithmId hash;
+ if (!doReadAlgorithmId(hash))
+ return false;
+ algorithm = blink::WebCryptoKeyAlgorithm::createHmac(hash, lengthBytes * 8);
+ type = blink::WebCryptoKeyTypeSecret;
+ return !algorithm.isNull();
+ }
+
+ bool doReadAesKey(blink::WebCryptoKeyAlgorithm& algorithm, blink::WebCryptoKeyType& type)
+ {
+ blink::WebCryptoAlgorithmId id;
+ if (!doReadAlgorithmId(id))
+ return false;
+ uint32_t lengthBytes;
+ if (!doReadUint32(&lengthBytes))
+ return false;
+ algorithm = blink::WebCryptoKeyAlgorithm::createAes(id, lengthBytes * 8);
+ type = blink::WebCryptoKeyTypeSecret;
+ return !algorithm.isNull();
+ }
+
+ bool doReadRsaHashedKey(blink::WebCryptoKeyAlgorithm& algorithm, blink::WebCryptoKeyType& type)
+ {
+ blink::WebCryptoAlgorithmId id;
+ if (!doReadAlgorithmId(id))
+ return false;
+
+ uint32_t rawType;
+ if (!doReadUint32(&rawType))
+ return false;
+
+ switch (static_cast<AssymetricCryptoKeyType>(rawType)) {
+ case PublicKeyType:
+ type = blink::WebCryptoKeyTypePublic;
+ break;
+ case PrivateKeyType:
+ type = blink::WebCryptoKeyTypePrivate;
+ break;
+ default:
+ return false;
+ }
+
+ uint32_t modulusLengthBits;
+ if (!doReadUint32(&modulusLengthBits))
+ return false;
+
+ uint32_t publicExponentSize;
+ if (!doReadUint32(&publicExponentSize))
+ return false;
+
+ if (m_position + publicExponentSize > m_length)
+ return false;
+
+ const uint8_t* publicExponent = m_buffer + m_position;
+ m_position += publicExponentSize;
+
+ blink::WebCryptoAlgorithmId hash;
+ if (!doReadAlgorithmId(hash))
+ return false;
+ algorithm = blink::WebCryptoKeyAlgorithm::createRsaHashed(id, modulusLengthBits, publicExponent, publicExponentSize, hash);
+
+ return !algorithm.isNull();
+ }
+
+ bool doReadAlgorithmId(blink::WebCryptoAlgorithmId& id)
+ {
+ uint32_t rawId;
+ if (!doReadUint32(&rawId))
+ return false;
+
+ switch (static_cast<CryptoKeyAlgorithmTag>(rawId)) {
+ case AesCbcTag:
+ id = blink::WebCryptoAlgorithmIdAesCbc;
+ return true;
+ case HmacTag:
+ id = blink::WebCryptoAlgorithmIdHmac;
+ return true;
+ case RsaSsaPkcs1v1_5Tag:
+ id = blink::WebCryptoAlgorithmIdRsaSsaPkcs1v1_5;
+ return true;
+ case Sha1Tag:
+ id = blink::WebCryptoAlgorithmIdSha1;
+ return true;
+ case Sha256Tag:
+ id = blink::WebCryptoAlgorithmIdSha256;
+ return true;
+ case Sha384Tag:
+ id = blink::WebCryptoAlgorithmIdSha384;
+ return true;
+ case Sha512Tag:
+ id = blink::WebCryptoAlgorithmIdSha512;
+ return true;
+ case AesGcmTag:
+ id = blink::WebCryptoAlgorithmIdAesGcm;
+ return true;
+ case RsaOaepTag:
+ id = blink::WebCryptoAlgorithmIdRsaOaep;
+ return true;
+ case AesCtrTag:
+ id = blink::WebCryptoAlgorithmIdAesCtr;
+ return true;
+ case AesKwTag:
+ id = blink::WebCryptoAlgorithmIdAesKw;
+ return true;
+ }
+
+ return false;
+ }
+
+ bool doReadKeyUsages(blink::WebCryptoKeyUsageMask& usages, bool& extractable)
+ {
+ // Reminder to update this when adding new key usages.
+ COMPILE_ASSERT(blink::EndOfWebCryptoKeyUsage == (1 << 7) + 1, UpdateMe);
+ const uint32_t allPossibleUsages = ExtractableUsage | EncryptUsage | DecryptUsage | SignUsage | VerifyUsage | DeriveKeyUsage | WrapKeyUsage | UnwrapKeyUsage | DeriveBitsUsage;
+
+ uint32_t rawUsages;
+ if (!doReadUint32(&rawUsages))
+ return false;
+
+ // Make sure it doesn't contain an unrecognized usage value.
+ if (rawUsages & ~allPossibleUsages)
+ return false;
+
+ usages = 0;
+
+ extractable = rawUsages & ExtractableUsage;
+
+ if (rawUsages & EncryptUsage)
+ usages |= blink::WebCryptoKeyUsageEncrypt;
+ if (rawUsages & DecryptUsage)
+ usages |= blink::WebCryptoKeyUsageDecrypt;
+ if (rawUsages & SignUsage)
+ usages |= blink::WebCryptoKeyUsageSign;
+ if (rawUsages & VerifyUsage)
+ usages |= blink::WebCryptoKeyUsageVerify;
+ if (rawUsages & DeriveKeyUsage)
+ usages |= blink::WebCryptoKeyUsageDeriveKey;
+ if (rawUsages & WrapKeyUsage)
+ usages |= blink::WebCryptoKeyUsageWrapKey;
+ if (rawUsages & UnwrapKeyUsage)
+ usages |= blink::WebCryptoKeyUsageUnwrapKey;
+ if (rawUsages & DeriveBitsUsage)
+ usages |= blink::WebCryptoKeyUsageDeriveBits;
+
+ return true;
+ }
+
+ RefPtr<ScriptState> m_scriptState;
const uint8_t* m_buffer;
const unsigned m_length;
unsigned m_position;
uint32_t m_version;
- v8::Isolate* m_isolate;
+ const WebBlobInfoArray* m_blobInfo;
const BlobDataHandleMap& m_blobDataHandles;
};
typedef Vector<WTF::ArrayBufferContents, 1> ArrayBufferContentsArray;
-class Deserializer : public CompositeCreator {
+class Deserializer FINAL : public CompositeCreator {
public:
Deserializer(Reader& reader, MessagePortArray* messagePorts, ArrayBufferContentsArray* arrayBufferContents)
: m_reader(reader)
@@ -2009,35 +2561,36 @@ public:
v8::Handle<v8::Value> deserialize()
{
+ v8::Isolate* isolate = m_reader.scriptState()->isolate();
if (!m_reader.readVersion(m_version) || m_version > SerializedScriptValue::wireFormatVersion)
- return v8::Null(m_reader.getIsolate());
+ return v8::Null(isolate);
m_reader.setVersion(m_version);
- v8::EscapableHandleScope scope(m_reader.getIsolate());
+ v8::EscapableHandleScope scope(isolate);
while (!m_reader.isEof()) {
if (!doDeserialize())
- return v8::Null(m_reader.getIsolate());
+ return v8::Null(isolate);
}
if (stackDepth() != 1 || m_openCompositeReferenceStack.size())
- return v8::Null(m_reader.getIsolate());
+ return v8::Null(isolate);
v8::Handle<v8::Value> result = scope.Escape(element(0));
return result;
}
- virtual bool newSparseArray(uint32_t)
+ virtual bool newSparseArray(uint32_t) OVERRIDE
{
- v8::Local<v8::Array> array = v8::Array::New(m_reader.isolate(), 0);
+ v8::Local<v8::Array> array = v8::Array::New(m_reader.scriptState()->isolate(), 0);
openComposite(array);
return true;
}
- virtual bool newDenseArray(uint32_t length)
+ virtual bool newDenseArray(uint32_t length) OVERRIDE
{
- v8::Local<v8::Array> array = v8::Array::New(m_reader.isolate(), length);
+ v8::Local<v8::Array> array = v8::Array::New(m_reader.scriptState()->isolate(), length);
openComposite(array);
return true;
}
- virtual bool consumeTopOfStack(v8::Handle<v8::Value>* object)
+ virtual bool consumeTopOfStack(v8::Handle<v8::Value>* object) OVERRIDE
{
if (stackDepth() < 1)
return false;
@@ -2046,40 +2599,16 @@ public:
return true;
}
- virtual bool completeArray(uint32_t length, v8::Handle<v8::Value>* value)
- {
- if (length > stackDepth())
- return false;
- v8::Local<v8::Array> array;
- if (m_version > 0) {
- v8::Local<v8::Value> composite;
- if (!closeComposite(&composite))
- return false;
- array = composite.As<v8::Array>();
- } else {
- array = v8::Array::New(m_reader.isolate(), length);
- }
- if (array.IsEmpty())
- return false;
- const int depth = stackDepth() - length;
- // The V8 API ensures space exists for any index argument to Set; it will (eg) resize arrays as necessary.
- for (unsigned i = 0; i < length; ++i)
- array->Set(i, element(depth + i));
- pop(length);
- *value = array;
- return true;
- }
-
- virtual bool newObject()
+ virtual bool newObject() OVERRIDE
{
- v8::Local<v8::Object> object = v8::Object::New();
+ v8::Local<v8::Object> object = v8::Object::New(m_reader.scriptState()->isolate());
if (object.IsEmpty())
return false;
openComposite(object);
return true;
}
- virtual bool completeObject(uint32_t numProperties, v8::Handle<v8::Value>* value)
+ virtual bool completeObject(uint32_t numProperties, v8::Handle<v8::Value>* value) OVERRIDE
{
v8::Local<v8::Object> object;
if (m_version > 0) {
@@ -2087,14 +2616,15 @@ public:
if (!closeComposite(&composite))
return false;
object = composite.As<v8::Object>();
- } else
- object = v8::Object::New();
+ } else {
+ object = v8::Object::New(m_reader.scriptState()->isolate());
+ }
if (object.IsEmpty())
return false;
return initializeObject(object, numProperties, value);
}
- virtual bool completeSparseArray(uint32_t numProperties, uint32_t length, v8::Handle<v8::Value>* value)
+ virtual bool completeSparseArray(uint32_t numProperties, uint32_t length, v8::Handle<v8::Value>* value) OVERRIDE
{
v8::Local<v8::Array> array;
if (m_version > 0) {
@@ -2103,14 +2633,14 @@ public:
return false;
array = composite.As<v8::Array>();
} else {
- array = v8::Array::New(m_reader.isolate());
+ array = v8::Array::New(m_reader.scriptState()->isolate());
}
if (array.IsEmpty())
return false;
return initializeObject(array, numProperties, value);
}
- virtual bool completeDenseArray(uint32_t numProperties, uint32_t length, v8::Handle<v8::Value>* value)
+ virtual bool completeDenseArray(uint32_t numProperties, uint32_t length, v8::Handle<v8::Value>* value) OVERRIDE
{
v8::Local<v8::Array> array;
if (m_version > 0) {
@@ -2134,22 +2664,23 @@ public:
return true;
}
- virtual void pushObjectReference(const v8::Handle<v8::Value>& object)
+ virtual void pushObjectReference(const v8::Handle<v8::Value>& object) OVERRIDE
{
m_objectPool.append(object);
}
- virtual bool tryGetTransferredMessagePort(uint32_t index, v8::Handle<v8::Value>* object)
+ virtual bool tryGetTransferredMessagePort(uint32_t index, v8::Handle<v8::Value>* object) OVERRIDE
{
if (!m_transferredMessagePorts)
return false;
if (index >= m_transferredMessagePorts->size())
return false;
- *object = toV8(m_transferredMessagePorts->at(index).get(), v8::Handle<v8::Object>(), m_reader.getIsolate());
+ v8::Handle<v8::Object> creationContext = m_reader.scriptState()->context()->Global();
+ *object = toV8(m_transferredMessagePorts->at(index).get(), creationContext, m_reader.scriptState()->isolate());
return true;
}
- virtual bool tryGetTransferredArrayBuffer(uint32_t index, v8::Handle<v8::Value>* object)
+ virtual bool tryGetTransferredArrayBuffer(uint32_t index, v8::Handle<v8::Value>* object) OVERRIDE
{
if (!m_arrayBufferContents)
return false;
@@ -2159,15 +2690,17 @@ public:
if (result.IsEmpty()) {
RefPtr<ArrayBuffer> buffer = ArrayBuffer::create(m_arrayBufferContents->at(index));
buffer->setDeallocationObserver(V8ArrayBufferDeallocationObserver::instanceTemplate());
- m_reader.isolate()->AdjustAmountOfExternalAllocatedMemory(buffer->byteLength());
- result = toV8Object(buffer.get(), m_reader.getIsolate());
+ v8::Isolate* isolate = m_reader.scriptState()->isolate();
+ v8::Handle<v8::Object> creationContext = m_reader.scriptState()->context()->Global();
+ isolate->AdjustAmountOfExternalAllocatedMemory(buffer->byteLength());
+ result = toV8Object(buffer.get(), creationContext, isolate);
m_arrayBuffers[index] = result;
}
*object = result;
return true;
}
- virtual bool tryGetObjectFromObjectReference(uint32_t reference, v8::Handle<v8::Value>* object)
+ virtual bool tryGetObjectFromObjectReference(uint32_t reference, v8::Handle<v8::Value>* object) OVERRIDE
{
if (reference >= m_objectPool.size())
return false;
@@ -2175,7 +2708,7 @@ public:
return object;
}
- virtual uint32_t objectReferenceCount()
+ virtual uint32_t objectReferenceCount() OVERRIDE
{
return m_objectPool.size();
}
@@ -2253,21 +2786,21 @@ private:
} // namespace
-PassRefPtr<SerializedScriptValue> SerializedScriptValue::create(v8::Handle<v8::Value> value, MessagePortArray* messagePorts, ArrayBufferArray* arrayBuffers, bool& didThrow, v8::Isolate* isolate)
+PassRefPtr<SerializedScriptValue> SerializedScriptValue::create(v8::Handle<v8::Value> value, MessagePortArray* messagePorts, ArrayBufferArray* arrayBuffers, ExceptionState& exceptionState, v8::Isolate* isolate)
{
- return adoptRef(new SerializedScriptValue(value, messagePorts, arrayBuffers, didThrow, isolate));
+ return adoptRef(new SerializedScriptValue(value, messagePorts, arrayBuffers, 0, exceptionState, isolate));
}
PassRefPtr<SerializedScriptValue> SerializedScriptValue::createAndSwallowExceptions(v8::Handle<v8::Value> value, v8::Isolate* isolate)
{
- bool didThrow;
- return adoptRef(new SerializedScriptValue(value, 0, 0, didThrow, isolate, DoNotThrowExceptions));
+ TrackExceptionState exceptionState;
+ return adoptRef(new SerializedScriptValue(value, 0, 0, 0, exceptionState, isolate));
}
-PassRefPtr<SerializedScriptValue> SerializedScriptValue::create(const ScriptValue& value, bool& didThrow, ScriptState* state)
+PassRefPtr<SerializedScriptValue> SerializedScriptValue::create(const ScriptValue& value, WebBlobInfoArray* blobInfo, ExceptionState& exceptionState, v8::Isolate* isolate)
{
- ScriptScope scope(state);
- return adoptRef(new SerializedScriptValue(value.v8Value(), 0, 0, didThrow, state->isolate()));
+ ASSERT(isolate->InContext());
+ return adoptRef(new SerializedScriptValue(value.v8Value(), 0, 0, blobInfo, exceptionState, isolate));
}
PassRefPtr<SerializedScriptValue> SerializedScriptValue::createFromWire(const String& data)
@@ -2296,7 +2829,7 @@ PassRefPtr<SerializedScriptValue> SerializedScriptValue::create(const String& da
PassRefPtr<SerializedScriptValue> SerializedScriptValue::create(const String& data, v8::Isolate* isolate)
{
- Writer writer(isolate);
+ Writer writer;
writer.writeWebCoreString(data);
String wireData = writer.takeWireString();
return adoptRef(new SerializedScriptValue(wireData));
@@ -2309,12 +2842,7 @@ PassRefPtr<SerializedScriptValue> SerializedScriptValue::create()
PassRefPtr<SerializedScriptValue> SerializedScriptValue::nullValue()
{
- return nullValue(v8::Isolate::GetCurrent());
-}
-
-PassRefPtr<SerializedScriptValue> SerializedScriptValue::nullValue(v8::Isolate* isolate)
-{
- Writer writer(isolate);
+ Writer writer;
writer.writeNull();
String wireData = writer.takeWireString();
return adoptRef(new SerializedScriptValue(wireData));
@@ -2344,12 +2872,21 @@ SerializedScriptValue::SerializedScriptValue()
{
}
-inline void neuterBinding(ArrayBuffer* object)
+static void neuterArrayBufferInAllWorlds(ArrayBuffer* object)
{
v8::Isolate* isolate = v8::Isolate::GetCurrent();
- Vector<DOMDataStore*>& allStores = V8PerIsolateData::from(isolate)->allStores();
- for (size_t i = 0; i < allStores.size(); i++) {
- v8::Handle<v8::Object> wrapper = allStores[i]->get<V8ArrayBuffer>(object, isolate);
+ if (isMainThread()) {
+ Vector<RefPtr<DOMWrapperWorld> > worlds;
+ DOMWrapperWorld::allWorldsInMainThread(worlds);
+ for (size_t i = 0; i < worlds.size(); i++) {
+ v8::Handle<v8::Object> wrapper = worlds[i]->domDataStore().get<V8ArrayBuffer>(object, isolate);
+ if (!wrapper.IsEmpty()) {
+ ASSERT(wrapper->IsArrayBuffer());
+ v8::Handle<v8::ArrayBuffer>::Cast(wrapper)->Neuter();
+ }
+ }
+ } else {
+ v8::Handle<v8::Object> wrapper = DOMWrapperWorld::current(isolate).domDataStore().get<V8ArrayBuffer>(object, isolate);
if (!wrapper.IsEmpty()) {
ASSERT(wrapper->IsArrayBuffer());
v8::Handle<v8::ArrayBuffer>::Cast(wrapper)->Neuter();
@@ -2357,25 +2894,13 @@ inline void neuterBinding(ArrayBuffer* object)
}
}
-inline void neuterBinding(ArrayBufferView* object)
-{
- v8::Isolate* isolate = v8::Isolate::GetCurrent();
- Vector<DOMDataStore*>& allStores = V8PerIsolateData::from(isolate)->allStores();
- for (size_t i = 0; i < allStores.size(); i++) {
- v8::Handle<v8::Object> wrapper = allStores[i]->get<V8ArrayBufferView>(object, isolate);
- if (!wrapper.IsEmpty())
- wrapper->SetIndexedPropertiesToExternalArrayData(0, v8::kExternalByteArray, 0);
- }
-}
-
-PassOwnPtr<SerializedScriptValue::ArrayBufferContentsArray> SerializedScriptValue::transferArrayBuffers(ArrayBufferArray& arrayBuffers, bool& didThrow, v8::Isolate* isolate)
+PassOwnPtr<SerializedScriptValue::ArrayBufferContentsArray> SerializedScriptValue::transferArrayBuffers(ArrayBufferArray& arrayBuffers, ExceptionState& exceptionState, v8::Isolate* isolate)
{
ASSERT(arrayBuffers.size());
for (size_t i = 0; i < arrayBuffers.size(); i++) {
if (arrayBuffers[i]->isNeutered()) {
- setDOMException(InvalidStateError, isolate);
- didThrow = true;
+ exceptionState.throwDOMException(DataCloneError, "ArrayBuffer at index " + String::number(i) + " is already neutered.");
return nullptr;
}
}
@@ -2384,72 +2909,51 @@ PassOwnPtr<SerializedScriptValue::ArrayBufferContentsArray> SerializedScriptValu
HashSet<ArrayBuffer*> visited;
for (size_t i = 0; i < arrayBuffers.size(); i++) {
- Vector<RefPtr<ArrayBufferView> > neuteredViews;
-
if (visited.contains(arrayBuffers[i].get()))
continue;
visited.add(arrayBuffers[i].get());
- bool result = arrayBuffers[i]->transfer(contents->at(i), neuteredViews);
+ bool result = arrayBuffers[i]->transfer(contents->at(i));
if (!result) {
- setDOMException(InvalidStateError, isolate);
- didThrow = true;
+ exceptionState.throwDOMException(DataCloneError, "ArrayBuffer at index " + String::number(i) + " could not be transferred.");
return nullptr;
}
- neuterBinding(arrayBuffers[i].get());
- for (size_t j = 0; j < neuteredViews.size(); j++)
- neuterBinding(neuteredViews[j].get());
+ neuterArrayBufferInAllWorlds(arrayBuffers[i].get());
}
return contents.release();
}
-SerializedScriptValue::SerializedScriptValue(v8::Handle<v8::Value> value, MessagePortArray* messagePorts, ArrayBufferArray* arrayBuffers, bool& didThrow, v8::Isolate* isolate, ExceptionPolicy policy)
+SerializedScriptValue::SerializedScriptValue(v8::Handle<v8::Value> value, MessagePortArray* messagePorts, ArrayBufferArray* arrayBuffers, WebBlobInfoArray* blobInfo, ExceptionState& exceptionState, v8::Isolate* isolate)
: m_externallyAllocatedMemory(0)
{
- didThrow = false;
- Writer writer(isolate);
+ Writer writer;
Serializer::Status status;
+ String errorMessage;
{
v8::TryCatch tryCatch;
- Serializer serializer(writer, messagePorts, arrayBuffers, m_blobDataHandles, tryCatch, isolate);
+ Serializer serializer(writer, messagePorts, arrayBuffers, blobInfo, m_blobDataHandles, tryCatch, ScriptState::current(isolate));
status = serializer.serialize(value);
if (status == Serializer::JSException) {
- didThrow = true;
// If there was a JS exception thrown, re-throw it.
- if (policy == ThrowExceptions)
- tryCatch.ReThrow();
+ exceptionState.rethrowV8Exception(tryCatch.Exception());
return;
}
+ errorMessage = serializer.errorMessage();
}
switch (status) {
case Serializer::InputError:
case Serializer::DataCloneError:
- // If there was an input error, throw a new exception outside
- // of the TryCatch scope.
- didThrow = true;
- if (policy == ThrowExceptions)
- setDOMException(DataCloneError, isolate);
- return;
- case Serializer::InvalidStateError:
- didThrow = true;
- if (policy == ThrowExceptions)
- setDOMException(InvalidStateError, isolate);
- return;
- case Serializer::JSFailure:
- // If there was a JS failure (but no exception), there's not
- // much we can do except for unwinding the C++ stack by
- // pretending there was a JS exception.
- didThrow = true;
+ exceptionState.throwDOMException(DataCloneError, errorMessage);
return;
case Serializer::Success:
m_data = writer.takeWireString();
ASSERT(m_data.impl()->hasOneRef());
if (arrayBuffers && arrayBuffers->size())
- m_arrayBufferContentsArray = transferArrayBuffers(*arrayBuffers, didThrow, isolate);
+ m_arrayBufferContentsArray = transferArrayBuffers(*arrayBuffers, exceptionState, isolate);
return;
case Serializer::JSException:
- // We should never get here because this case was handled above.
+ ASSERT_NOT_REACHED();
break;
}
ASSERT_NOT_REACHED();
@@ -2463,10 +2967,10 @@ SerializedScriptValue::SerializedScriptValue(const String& wireData)
v8::Handle<v8::Value> SerializedScriptValue::deserialize(MessagePortArray* messagePorts)
{
- return deserialize(v8::Isolate::GetCurrent(), messagePorts);
+ return deserialize(v8::Isolate::GetCurrent(), messagePorts, 0);
}
-v8::Handle<v8::Value> SerializedScriptValue::deserialize(v8::Isolate* isolate, MessagePortArray* messagePorts)
+v8::Handle<v8::Value> SerializedScriptValue::deserialize(v8::Isolate* isolate, MessagePortArray* messagePorts, const WebBlobInfoArray* blobInfo)
{
if (!m_data.impl())
return v8::Null(isolate);
@@ -2476,7 +2980,7 @@ v8::Handle<v8::Value> SerializedScriptValue::deserialize(v8::Isolate* isolate, M
// storage. Instead, it should use SharedBuffer or Vector<uint8_t>. The
// information stored in m_data isn't even encoded in UTF-16. Instead,
// unicode characters are encoded as UTF-8 with two code units per UChar.
- Reader reader(reinterpret_cast<const uint8_t*>(m_data.impl()->characters16()), 2 * m_data.length(), isolate, m_blobDataHandles);
+ Reader reader(reinterpret_cast<const uint8_t*>(m_data.impl()->characters16()), 2 * m_data.length(), blobInfo, m_blobDataHandles, ScriptState::current(isolate));
Deserializer deserializer(reader, messagePorts, m_arrayBufferContentsArray.get());
// deserialize() can run arbitrary script (e.g., setters), which could result in |this| being destroyed.
@@ -2485,6 +2989,57 @@ v8::Handle<v8::Value> SerializedScriptValue::deserialize(v8::Isolate* isolate, M
return deserializer.deserialize();
}
+bool SerializedScriptValue::extractTransferables(v8::Local<v8::Value> value, int argumentIndex, MessagePortArray& ports, ArrayBufferArray& arrayBuffers, ExceptionState& exceptionState, v8::Isolate* isolate)
+{
+ if (isUndefinedOrNull(value)) {
+ ports.resize(0);
+ arrayBuffers.resize(0);
+ return true;
+ }
+
+ uint32_t length = 0;
+ if (value->IsArray()) {
+ v8::Local<v8::Array> array = v8::Local<v8::Array>::Cast(value);
+ length = array->Length();
+ } else if (toV8Sequence(value, length, isolate).IsEmpty()) {
+ exceptionState.throwTypeError(ExceptionMessages::notAnArrayTypeArgumentOrValue(argumentIndex + 1));
+ return false;
+ }
+
+ v8::Local<v8::Object> transferrables = v8::Local<v8::Object>::Cast(value);
+
+ // Validate the passed array of transferrables.
+ for (unsigned i = 0; i < length; ++i) {
+ v8::Local<v8::Value> transferrable = transferrables->Get(i);
+ // Validation of non-null objects, per HTML5 spec 10.3.3.
+ if (isUndefinedOrNull(transferrable)) {
+ exceptionState.throwDOMException(DataCloneError, "Value at index " + String::number(i) + " is an untransferable " + (transferrable->IsUndefined() ? "'undefined'" : "'null'") + " value.");
+ return false;
+ }
+ // Validation of Objects implementing an interface, per WebIDL spec 4.1.15.
+ if (V8MessagePort::hasInstance(transferrable, isolate)) {
+ RefPtr<MessagePort> port = V8MessagePort::toNative(v8::Handle<v8::Object>::Cast(transferrable));
+ // Check for duplicate MessagePorts.
+ if (ports.contains(port)) {
+ exceptionState.throwDOMException(DataCloneError, "Message port at index " + String::number(i) + " is a duplicate of an earlier port.");
+ return false;
+ }
+ ports.append(port.release());
+ } else if (V8ArrayBuffer::hasInstance(transferrable, isolate)) {
+ RefPtr<ArrayBuffer> arrayBuffer = V8ArrayBuffer::toNative(v8::Handle<v8::Object>::Cast(transferrable));
+ if (arrayBuffers.contains(arrayBuffer)) {
+ exceptionState.throwDOMException(DataCloneError, "ArrayBuffer at index " + String::number(i) + " is a duplicate of an earlier ArrayBuffer.");
+ return false;
+ }
+ arrayBuffers.append(arrayBuffer.release());
+ } else {
+ exceptionState.throwDOMException(DataCloneError, "Value at index " + String::number(i) + " does not have a transferable type.");
+ return false;
+ }
+ }
+ return true;
+}
+
void SerializedScriptValue::registerMemoryAllocatedWithCurrentScriptContext()
{
if (m_externallyAllocatedMemory)
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/SerializedScriptValue.h b/chromium/third_party/WebKit/Source/bindings/v8/SerializedScriptValue.h
index 97a73aa04ab..b1064206698 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/SerializedScriptValue.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/SerializedScriptValue.h
@@ -32,11 +32,16 @@
#define SerializedScriptValue_h
#include "bindings/v8/ScriptValue.h"
-
#include "wtf/HashMap.h"
#include "wtf/ThreadSafeRefCounted.h"
#include <v8.h>
+namespace blink {
+
+class WebBlobInfo;
+
+}
+
namespace WTF {
class ArrayBuffer;
@@ -47,11 +52,13 @@ class ArrayBufferContents;
namespace WebCore {
class BlobDataHandle;
+class ExceptionState;
class MessagePort;
typedef Vector<RefPtr<MessagePort>, 1> MessagePortArray;
typedef Vector<RefPtr<WTF::ArrayBuffer>, 1> ArrayBufferArray;
typedef HashMap<String, RefPtr<BlobDataHandle> > BlobDataHandleMap;
+typedef Vector<blink::WebBlobInfo> WebBlobInfoArray;
class SerializedScriptValue FINAL : public ThreadSafeRefCounted<SerializedScriptValue> {
public:
@@ -59,7 +66,9 @@ public:
// Version 2: Added StringUCharTag for UChar v8 strings.
// Version 3: Switched to using uuids as blob data identifiers.
// Version 4: Extended File serialization to be complete.
- static const uint32_t wireFormatVersion = 4;
+ // Version 5: Added CryptoKeyTag for Key objects.
+ // Version 6: Added indexed serialization for File, Blob, and FileList.
+ static const uint32_t wireFormatVersion = 6;
~SerializedScriptValue();
@@ -68,20 +77,18 @@ public:
// be thrown using v8::ThrowException(), and sets |didThrow|. In this case
// the caller must not invoke any V8 operations until control returns to
// V8. When serialization is successful, |didThrow| is false.
- static PassRefPtr<SerializedScriptValue> create(v8::Handle<v8::Value>, MessagePortArray*, ArrayBufferArray*, bool& didThrow, v8::Isolate*);
+ static PassRefPtr<SerializedScriptValue> create(v8::Handle<v8::Value>, MessagePortArray*, ArrayBufferArray*, ExceptionState&, v8::Isolate*);
static PassRefPtr<SerializedScriptValue> createFromWire(const String&);
static PassRefPtr<SerializedScriptValue> createFromWireBytes(const Vector<uint8_t>&);
static PassRefPtr<SerializedScriptValue> create(const String&);
static PassRefPtr<SerializedScriptValue> create(const String&, v8::Isolate*);
static PassRefPtr<SerializedScriptValue> create();
-
- static PassRefPtr<SerializedScriptValue> create(const ScriptValue&, bool& didThrow, ScriptState*);
+ static PassRefPtr<SerializedScriptValue> create(const ScriptValue&, WebBlobInfoArray*, ExceptionState&, v8::Isolate*);
// Never throws exceptions.
static PassRefPtr<SerializedScriptValue> createAndSwallowExceptions(v8::Handle<v8::Value>, v8::Isolate*);
static PassRefPtr<SerializedScriptValue> nullValue();
- static PassRefPtr<SerializedScriptValue> nullValue(v8::Isolate*);
String toWireString() const { return m_data; }
void toWireBytes(Vector<char>&) const;
@@ -89,11 +96,13 @@ public:
// Deserializes the value (in the current context). Returns a null value in
// case of failure.
v8::Handle<v8::Value> deserialize(MessagePortArray* = 0);
- v8::Handle<v8::Value> deserialize(v8::Isolate*, MessagePortArray* = 0);
+ v8::Handle<v8::Value> deserialize(v8::Isolate*, MessagePortArray* = 0, const WebBlobInfoArray* = 0);
- // Only reflects the truth if the SSV was created by walking a v8 value, not reliable
- // if the SSV was created createdFromWire(data).
- bool containsBlobs() const { return !m_blobDataHandles.isEmpty(); }
+ // Helper function which pulls the values out of a JS sequence and into a MessagePortArray.
+ // Also validates the elements per sections 4.1.13 and 4.1.15 of the WebIDL spec and section 8.3.3
+ // of the HTML5 spec and generates exceptions as appropriate.
+ // Returns true if the array was filled, or false if the passed value was not of an appropriate type.
+ static bool extractTransferables(v8::Local<v8::Value>, int, MessagePortArray&, ArrayBufferArray&, ExceptionState&, v8::Isolate*);
// Informs the V8 about external memory allocated and owned by this object. Large values should contribute
// to GC counters to eventually trigger a GC, otherwise flood of postMessage() can cause OOM.
@@ -106,17 +115,13 @@ private:
StringValue,
WireData
};
- enum ExceptionPolicy {
- ThrowExceptions,
- DoNotThrowExceptions
- };
typedef Vector<WTF::ArrayBufferContents, 1> ArrayBufferContentsArray;
SerializedScriptValue();
- SerializedScriptValue(v8::Handle<v8::Value>, MessagePortArray*, ArrayBufferArray*, bool& didThrow, v8::Isolate*, ExceptionPolicy = ThrowExceptions);
+ SerializedScriptValue(v8::Handle<v8::Value>, MessagePortArray*, ArrayBufferArray*, WebBlobInfoArray*, ExceptionState&, v8::Isolate*);
explicit SerializedScriptValue(const String& wireData);
- static PassOwnPtr<ArrayBufferContentsArray> transferArrayBuffers(ArrayBufferArray&, bool& didThrow, v8::Isolate*);
+ static PassOwnPtr<ArrayBufferContentsArray> transferArrayBuffers(ArrayBufferArray&, ExceptionState&, v8::Isolate*);
String m_data;
OwnPtr<ArrayBufferContentsArray> m_arrayBufferContentsArray;
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/UnsafePersistent.h b/chromium/third_party/WebKit/Source/bindings/v8/UnsafePersistent.h
deleted file mode 100644
index 4a889c27430..00000000000
--- a/chromium/third_party/WebKit/Source/bindings/v8/UnsafePersistent.h
+++ /dev/null
@@ -1,129 +0,0 @@
-/*
- * Copyright (C) 2013 Google Inc. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions are
- * met:
- *
- * * Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * * Redistributions in binary form must reproduce the above
- * copyright notice, this list of conditions and the following disclaimer
- * in the documentation and/or other materials provided with the
- * distribution.
- * * Neither the name of Google Inc. nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
- * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
- * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
- * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
- * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
- * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
- * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
- * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
- * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-#ifndef UnsafePersistent_h
-#define UnsafePersistent_h
-
-#include "bindings/v8/WrapperTypeInfo.h"
-
-#include <v8.h>
-
-namespace WebCore {
-
-template<class KeyType> class DOMWrapperMap;
-
-// An unsafe way to pass Persistent handles around. Do not use unless you know
-// what you're doing. UnsafePersistent is only safe to use when we know that the
-// memory pointed by the it is not going away: 1) When GC cannot happen while
-// the UnsafePersistent is alive or 2) when there is a strong Persistent keeping
-// the memory alive while the UnsafePersistent is alive.
-template<typename T> class UnsafePersistent {
-public:
- UnsafePersistent() : m_value(0) { }
- explicit UnsafePersistent(T* value) : m_value(value) { }
- explicit UnsafePersistent(v8::Persistent<T>& handle)
- {
- m_value = handle.ClearAndLeak();
- }
-
- UnsafePersistent(v8::Isolate* isolate, v8::Handle<T>& handle)
- {
- v8::Persistent<T> persistent(isolate, handle);
- m_value = persistent.ClearAndLeak();
- }
-
- T* value() const
- {
- return m_value;
- }
-
- template<typename V8T, typename U>
- inline bool setReturnValueWithSecurityCheck(v8::ReturnValue<v8::Value> returnValue, U* object)
- {
- v8::Handle<v8::Object> result = deprecatedHandle();
- // Security: always guard against malicious tampering.
- RELEASE_ASSERT_WITH_SECURITY_IMPLICATION(result.IsEmpty() || result->GetAlignedPointerFromInternalField(v8DOMWrapperObjectIndex) == V8T::toInternalPointer(object));
- returnValue.Set(result);
- return !result.IsEmpty();
- }
-
- inline bool setReturnValue(v8::ReturnValue<v8::Value> returnValue)
- {
- returnValue.Set(deprecatedHandle());
- return !isEmpty();
- }
-
- // This is incredibly unsafe: the handle is valid only when this
- // UnsafePersistent is alive and valid (see class level comment).
- v8::Persistent<T>* persistent()
- {
- v8::Persistent<T>* handle = reinterpret_cast<v8::Persistent<T>*>(&m_value);
- return handle;
- }
-
- void setReferenceFrom(const v8::Persistent<v8::Object>& parent, v8::Isolate* isolate)
- {
- isolate->SetReference(parent, *persistent());
- }
-
- void dispose()
- {
- persistent()->Reset();
- m_value = 0;
- }
-
- void clear()
- {
- m_value = 0;
- }
-
- v8::Local<T> newLocal(v8::Isolate* isolate)
- {
- return v8::Local<T>::New(isolate, *persistent());
- }
-
- bool isEmpty() const
- {
- return !m_value;
- }
-
-private:
- v8::Handle<T> deprecatedHandle()
- {
- v8::Handle<T>* handle = reinterpret_cast<v8::Handle<T>*>(&m_value);
- return *handle;
- }
-
- T* m_value;
-};
-
-} // namespace WebCore
-
-#endif // UnsafePersistent_h
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8AbstractEventListener.cpp b/chromium/third_party/WebKit/Source/bindings/v8/V8AbstractEventListener.cpp
index 5324a0d59c2..12f78db5563 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8AbstractEventListener.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8AbstractEventListener.cpp
@@ -31,23 +31,32 @@
#include "config.h"
#include "bindings/v8/V8AbstractEventListener.h"
-#include "V8Event.h"
-#include "V8EventTarget.h"
+#include "bindings/core/v8/V8Event.h"
+#include "bindings/core/v8/V8EventTarget.h"
#include "bindings/v8/V8Binding.h"
#include "bindings/v8/V8EventListenerList.h"
-#include "bindings/v8/V8HiddenPropertyName.h"
+#include "bindings/v8/V8HiddenValue.h"
#include "core/events/BeforeUnloadEvent.h"
#include "core/events/Event.h"
-#include "core/events/ThreadLocalEventNames.h"
#include "core/inspector/InspectorCounters.h"
#include "core/workers/WorkerGlobalScope.h"
namespace WebCore {
-V8AbstractEventListener::V8AbstractEventListener(bool isAttribute, PassRefPtr<DOMWrapperWorld> world, v8::Isolate* isolate)
+V8AbstractEventListener::V8AbstractEventListener(bool isAttribute, ScriptState* scriptState)
: EventListener(JSEventListenerType)
, m_isAttribute(isAttribute)
- , m_world(world)
+ , m_scriptState(scriptState)
+ , m_isolate(scriptState->isolate())
+{
+ if (isMainThread())
+ InspectorCounters::incrementCounter(InspectorCounters::JSEventListenerCounter);
+}
+
+V8AbstractEventListener::V8AbstractEventListener(bool isAttribute, v8::Isolate* isolate)
+ : EventListener(JSEventListenerType)
+ , m_isAttribute(isAttribute)
+ , m_scriptState(nullptr)
, m_isolate(isolate)
{
if (isMainThread())
@@ -58,16 +67,16 @@ V8AbstractEventListener::~V8AbstractEventListener()
{
if (!m_listener.isEmpty()) {
v8::HandleScope scope(m_isolate);
- V8EventListenerList::clearWrapper(m_listener.newLocal(m_isolate), m_isAttribute, m_isolate);
+ V8EventListenerList::clearWrapper(m_listener.newLocal(isolate()), m_isAttribute, isolate());
}
if (isMainThread())
InspectorCounters::decrementCounter(InspectorCounters::JSEventListenerCounter);
}
-void V8AbstractEventListener::handleEvent(ExecutionContext* context, Event* event)
+void V8AbstractEventListener::handleEvent(ExecutionContext*, Event* event)
{
// Don't reenter V8 if execution was terminated in this instance of V8.
- if (context->isJSExecutionForbidden())
+ if (scriptState()->executionContext()->isJSExecutionForbidden())
return;
ASSERT(event);
@@ -76,82 +85,68 @@ void V8AbstractEventListener::handleEvent(ExecutionContext* context, Event* even
// See issue 889829.
RefPtr<V8AbstractEventListener> protect(this);
- v8::HandleScope handleScope(m_isolate);
-
- v8::Local<v8::Context> v8Context = toV8Context(context, world());
- if (v8Context.IsEmpty())
+ if (scriptState()->contextIsEmpty())
return;
-
- // Enter the V8 context in which to perform the event handling.
- v8::Context::Scope scope(v8Context);
+ ScriptState::Scope scope(scriptState());
// Get the V8 wrapper for the event object.
- v8::Isolate* isolate = v8Context->GetIsolate();
- v8::Handle<v8::Value> jsEvent = toV8(event, v8::Handle<v8::Object>(), isolate);
+ v8::Handle<v8::Value> jsEvent = toV8(event, scriptState()->context()->Global(), isolate());
if (jsEvent.IsEmpty())
return;
- invokeEventHandler(context, event, v8::Local<v8::Value>::New(isolate, jsEvent));
+ invokeEventHandler(event, v8::Local<v8::Value>::New(isolate(), jsEvent));
}
void V8AbstractEventListener::setListenerObject(v8::Handle<v8::Object> listener)
{
- m_listener.set(m_isolate, listener);
+ m_listener.set(isolate(), listener);
m_listener.setWeak(this, &setWeakCallback);
}
-void V8AbstractEventListener::invokeEventHandler(ExecutionContext* context, Event* event, v8::Local<v8::Value> jsEvent)
+void V8AbstractEventListener::invokeEventHandler(Event* event, v8::Local<v8::Value> jsEvent)
{
// If jsEvent is empty, attempt to set it as a hidden value would crash v8.
if (jsEvent.IsEmpty())
return;
- v8::Local<v8::Context> v8Context = toV8Context(context, world());
- if (v8Context.IsEmpty())
- return;
-
- // We push the event being processed into the global object, so that it can be exposed by DOMWindow's bindings.
- v8::Handle<v8::String> eventSymbol = V8HiddenPropertyName::event(v8Context->GetIsolate());
+ ASSERT(!scriptState()->contextIsEmpty());
v8::Local<v8::Value> returnValue;
-
{
// Catch exceptions thrown in the event handler so they do not propagate to javascript code that caused the event to fire.
v8::TryCatch tryCatch;
tryCatch.SetVerbose(true);
// Save the old 'event' property so we can restore it later.
- v8::Local<v8::Value> savedEvent = v8Context->Global()->GetHiddenValue(eventSymbol);
+ v8::Local<v8::Value> savedEvent = V8HiddenValue::getHiddenValue(isolate(), scriptState()->context()->Global(), V8HiddenValue::event(isolate()));
tryCatch.Reset();
- // Make the event available in the global object, so DOMWindow can expose it.
- v8Context->Global()->SetHiddenValue(eventSymbol, jsEvent);
+ // Make the event available in the global object, so LocalDOMWindow can expose it.
+ V8HiddenValue::setHiddenValue(isolate(), scriptState()->context()->Global(), V8HiddenValue::event(isolate()), jsEvent);
tryCatch.Reset();
- returnValue = callListenerFunction(context, jsEvent, event);
+ returnValue = callListenerFunction(jsEvent, event);
if (tryCatch.HasCaught())
event->target()->uncaughtExceptionInEventHandler();
if (!tryCatch.CanContinue()) { // Result of TerminateExecution().
- if (context->isWorkerGlobalScope())
- toWorkerGlobalScope(context)->script()->forbidExecution();
+ if (scriptState()->executionContext()->isWorkerGlobalScope())
+ toWorkerGlobalScope(scriptState()->executionContext())->script()->forbidExecution();
return;
}
tryCatch.Reset();
// Restore the old event. This must be done for all exit paths through this method.
if (savedEvent.IsEmpty())
- v8Context->Global()->SetHiddenValue(eventSymbol, v8::Undefined(v8Context->GetIsolate()));
+ V8HiddenValue::setHiddenValue(isolate(), scriptState()->context()->Global(), V8HiddenValue::event(isolate()), v8::Undefined(isolate()));
else
- v8Context->Global()->SetHiddenValue(eventSymbol, savedEvent);
+ V8HiddenValue::setHiddenValue(isolate(), scriptState()->context()->Global(), V8HiddenValue::event(isolate()), savedEvent);
tryCatch.Reset();
}
- ASSERT(!handleOutOfMemory() || returnValue.IsEmpty());
-
if (returnValue.IsEmpty())
return;
- if (!returnValue->IsNull() && !returnValue->IsUndefined() && event->isBeforeUnloadEvent()) {
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<>, stringReturnValue, returnValue);
+ if (m_isAttribute && !returnValue->IsNull() && !returnValue->IsUndefined() && event->isBeforeUnloadEvent()) {
+ TOSTRING_VOID(V8StringResource<>, stringReturnValue, returnValue);
toBeforeUnloadEvent(event)->setReturnValue(stringReturnValue);
}
@@ -166,18 +161,22 @@ bool V8AbstractEventListener::shouldPreventDefault(v8::Local<v8::Value> returnVa
return returnValue->IsBoolean() && !returnValue->BooleanValue();
}
-v8::Local<v8::Object> V8AbstractEventListener::getReceiverObject(ExecutionContext* context, Event* event)
+v8::Local<v8::Object> V8AbstractEventListener::getReceiverObject(Event* event)
{
- v8::Isolate* isolate = toV8Context(context, world())->GetIsolate();
- v8::Local<v8::Object> listener = m_listener.newLocal(isolate);
+ v8::Local<v8::Object> listener = m_listener.newLocal(isolate());
if (!m_listener.isEmpty() && !listener->IsFunction())
return listener;
EventTarget* target = event->currentTarget();
- v8::Handle<v8::Value> value = toV8(target, v8::Handle<v8::Object>(), isolate);
+ v8::Handle<v8::Value> value = toV8(target, scriptState()->context()->Global(), isolate());
if (value.IsEmpty())
return v8::Local<v8::Object>();
- return v8::Local<v8::Object>::New(isolate, v8::Handle<v8::Object>::Cast(value));
+ return v8::Local<v8::Object>::New(isolate(), v8::Handle<v8::Object>::Cast(value));
+}
+
+bool V8AbstractEventListener::belongsToTheCurrentWorld() const
+{
+ return isolate()->InContext() && &world() == &DOMWrapperWorld::current(isolate());
}
void V8AbstractEventListener::setWeakCallback(const v8::WeakCallbackData<v8::Object, V8AbstractEventListener> &data)
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8AbstractEventListener.h b/chromium/third_party/WebKit/Source/bindings/v8/V8AbstractEventListener.h
index c605821ea67..469050c4207 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8AbstractEventListener.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8AbstractEventListener.h
@@ -33,7 +33,6 @@
#include "bindings/v8/DOMWrapperWorld.h"
#include "bindings/v8/ScopedPersistent.h"
-#include "bindings/v8/V8Utilities.h"
#include "core/events/EventListener.h"
#include <v8.h>
#include "wtf/PassRefPtr.h"
@@ -69,9 +68,9 @@ namespace WebCore {
// Implementation of EventListener interface.
- virtual bool operator==(const EventListener& other) { return this == &other; }
+ virtual bool operator==(const EventListener& other) OVERRIDE { return this == &other; }
- virtual void handleEvent(ExecutionContext*, Event*);
+ virtual void handleEvent(ExecutionContext*, Event*) OVERRIDE;
virtual bool isLazy() const { return false; }
@@ -109,26 +108,34 @@ namespace WebCore {
m_listener.clear();
}
- virtual DOMWrapperWorld* world() const OVERRIDE FINAL { return m_world.get(); }
+ virtual bool belongsToTheCurrentWorld() const OVERRIDE FINAL;
v8::Isolate* isolate() const { return m_isolate; }
+ virtual DOMWrapperWorld& world() const { return scriptState()->world(); }
+ ScriptState* scriptState() const
+ {
+ ASSERT(m_scriptState);
+ return m_scriptState.get();
+ }
+ void setScriptState(ScriptState* scriptState) { m_scriptState = scriptState; }
protected:
- V8AbstractEventListener(bool isAttribute, PassRefPtr<DOMWrapperWorld>, v8::Isolate*);
+ V8AbstractEventListener(bool isAttribute, ScriptState*);
+ V8AbstractEventListener(bool isAttribute, v8::Isolate*);
virtual void prepareListenerObject(ExecutionContext*) { }
void setListenerObject(v8::Handle<v8::Object> listener);
- void invokeEventHandler(ExecutionContext*, Event*, v8::Local<v8::Value> jsEvent);
+ void invokeEventHandler(Event*, v8::Local<v8::Value> jsEvent);
// Get the receiver object to use for event listener call.
- v8::Local<v8::Object> getReceiverObject(ExecutionContext*, Event*);
+ v8::Local<v8::Object> getReceiverObject(Event*);
private:
// Implementation of EventListener function.
- virtual bool virtualisAttribute() const { return m_isAttribute; }
+ virtual bool virtualisAttribute() const OVERRIDE { return m_isAttribute; }
- virtual v8::Local<v8::Value> callListenerFunction(ExecutionContext*, v8::Handle<v8::Value> jsevent, Event*) = 0;
+ virtual v8::Local<v8::Value> callListenerFunction(v8::Handle<v8::Value> jsevent, Event*) = 0;
virtual bool shouldPreventDefault(v8::Local<v8::Value> returnValue);
@@ -139,7 +146,10 @@ namespace WebCore {
// Indicates if this is an HTML type listener.
bool m_isAttribute;
- RefPtr<DOMWrapperWorld> m_world;
+ // For V8LazyEventListener, m_scriptState can be 0 until V8LazyEventListener is actually used.
+ // m_scriptState is set lazily because V8LazyEventListener doesn't know the associated frame
+ // until the listener is actually used.
+ RefPtr<ScriptState> m_scriptState;
v8::Isolate* m_isolate;
};
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8Binding.cpp b/chromium/third_party/WebKit/Source/bindings/v8/V8Binding.cpp
index 2d8da03d149..639784e3f56 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8Binding.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8Binding.cpp
@@ -31,12 +31,14 @@
#include "config.h"
#include "bindings/v8/V8Binding.h"
-#include "V8Element.h"
-#include "V8NodeFilter.h"
-#include "V8Window.h"
-#include "V8WorkerGlobalScope.h"
-#include "V8XPathNSResolver.h"
+#include "bindings/core/v8/V8Element.h"
+#include "bindings/core/v8/V8NodeFilter.h"
+#include "bindings/core/v8/V8Window.h"
+#include "bindings/core/v8/V8WorkerGlobalScope.h"
+#include "bindings/core/v8/V8XPathNSResolver.h"
#include "bindings/v8/ScriptController.h"
+#include "bindings/v8/V8AbstractEventListener.h"
+#include "bindings/v8/V8BindingMacros.h"
#include "bindings/v8/V8NodeFilterCondition.h"
#include "bindings/v8/V8ObjectConstructor.h"
#include "bindings/v8/V8WindowShell.h"
@@ -45,14 +47,16 @@
#include "core/dom/Element.h"
#include "core/dom/NodeFilter.h"
#include "core/dom/QualifiedName.h"
+#include "core/frame/LocalFrame.h"
+#include "core/frame/Settings.h"
#include "core/inspector/BindingVisitors.h"
+#include "core/inspector/InspectorTraceEvents.h"
#include "core/loader/FrameLoader.h"
#include "core/loader/FrameLoaderClient.h"
-#include "core/frame/Frame.h"
-#include "core/frame/Settings.h"
#include "core/workers/WorkerGlobalScope.h"
#include "core/xml/XPathNSResolver.h"
-#include "gin/public/isolate_holder.h"
+#include "platform/EventTracer.h"
+#include "platform/JSONValues.h"
#include "wtf/ArrayBufferContents.h"
#include "wtf/MainThread.h"
#include "wtf/MathExtras.h"
@@ -63,38 +67,56 @@
#include "wtf/text/StringBuffer.h"
#include "wtf/text/StringHash.h"
#include "wtf/text/WTFString.h"
+#include "wtf/unicode/CharacterNames.h"
+#include "wtf/unicode/Unicode.h"
namespace WebCore {
-v8::Handle<v8::Value> setDOMException(int exceptionCode, v8::Isolate* isolate)
+v8::Handle<v8::Value> throwError(V8ErrorType errorType, const String& message, v8::Isolate* isolate)
{
- // FIXME: pass in an ExceptionState instead for better creationContext.
- return V8ThrowException::throwDOMException(exceptionCode, v8::Handle<v8::Object>(), isolate);
+ return V8ThrowException::throwError(errorType, message, isolate);
}
-v8::Handle<v8::Value> setDOMException(int exceptionCode, const String& message, v8::Isolate* isolate)
+v8::Handle<v8::Value> throwError(v8::Handle<v8::Value> exception, v8::Isolate* isolate)
{
- return V8ThrowException::throwDOMException(exceptionCode, message, v8::Handle<v8::Object>(), isolate);
+ return V8ThrowException::throwError(exception, isolate);
}
-v8::Handle<v8::Value> throwError(V8ErrorType errorType, const String& message, v8::Isolate* isolate)
+v8::Handle<v8::Value> throwTypeError(const String& message, v8::Isolate* isolate)
{
- return V8ThrowException::throwError(errorType, message, isolate);
+ return V8ThrowException::throwTypeError(message, isolate);
}
-v8::Handle<v8::Value> throwError(v8::Handle<v8::Value> exception, v8::Isolate* isolate)
+void throwArityTypeErrorForMethod(const char* method, const char* type, const char* valid, unsigned provided, v8::Isolate* isolate)
{
- return V8ThrowException::throwError(exception, isolate);
+ throwTypeError(ExceptionMessages::failedToExecute(method, type, ExceptionMessages::invalidArity(valid, provided)), isolate);
}
-v8::Handle<v8::Value> throwUninformativeAndGenericTypeError(v8::Isolate* isolate)
+void throwArityTypeErrorForConstructor(const char* type, const char* valid, unsigned provided, v8::Isolate* isolate)
{
- return V8ThrowException::throwTypeError(String(), isolate);
+ throwTypeError(ExceptionMessages::failedToConstruct(type, ExceptionMessages::invalidArity(valid, provided)), isolate);
}
-v8::Handle<v8::Value> throwTypeError(const String& message, v8::Isolate* isolate)
+void throwArityTypeError(ExceptionState& exceptionState, const char* valid, unsigned provided)
{
- return V8ThrowException::throwTypeError(message, isolate);
+ exceptionState.throwTypeError(ExceptionMessages::invalidArity(valid, provided));
+ exceptionState.throwIfNeeded();
+}
+
+void throwMinimumArityTypeErrorForMethod(const char* method, const char* type, unsigned expected, unsigned providedLeastNumMandatoryParams, v8::Isolate* isolate)
+{
+ throwTypeError(ExceptionMessages::failedToExecute(method, type, ExceptionMessages::notEnoughArguments(expected, providedLeastNumMandatoryParams)), isolate);
+}
+
+void throwMinimumArityTypeErrorForConstructor(const char* type, unsigned expected, unsigned providedLeastNumMandatoryParams, v8::Isolate* isolate)
+{
+ throwTypeError(ExceptionMessages::failedToConstruct(type, ExceptionMessages::notEnoughArguments(expected, providedLeastNumMandatoryParams)), isolate);
+}
+
+void throwMinimumArityTypeError(ExceptionState& exceptionState, unsigned expected, unsigned providedLeastNumMandatoryParams)
+{
+ exceptionState.throwTypeError(ExceptionMessages::notEnoughArguments(expected, providedLeastNumMandatoryParams));
+ exceptionState.throwIfNeeded();
}
class ArrayBufferAllocator : public v8::ArrayBuffer::Allocator {
@@ -124,14 +146,13 @@ v8::ArrayBuffer::Allocator* v8ArrayBufferAllocator()
return &arrayBufferAllocator;
}
-PassRefPtr<NodeFilter> toNodeFilter(v8::Handle<v8::Value> callback, v8::Isolate* isolate)
+PassRefPtrWillBeRawPtr<NodeFilter> toNodeFilter(v8::Handle<v8::Value> callback, v8::Handle<v8::Object> creationContext, ScriptState* scriptState)
{
- RefPtr<NodeFilter> filter = NodeFilter::create();
+ RefPtrWillBeRawPtr<NodeFilter> filter = NodeFilter::create();
- // FIXME: Should pass in appropriate creationContext
- v8::Handle<v8::Object> filterWrapper = toV8(filter, v8::Handle<v8::Object>(), isolate).As<v8::Object>();
+ v8::Handle<v8::Object> filterWrapper = toV8(filter, creationContext, scriptState->isolate()).As<v8::Object>();
- RefPtr<NodeFilterCondition> condition = V8NodeFilterCondition::create(callback, filterWrapper, isolate);
+ RefPtrWillBeRawPtr<NodeFilterCondition> condition = V8NodeFilterCondition::create(callback, filterWrapper, scriptState);
filter->setCondition(condition.release());
return filter.release();
@@ -140,17 +161,17 @@ PassRefPtr<NodeFilter> toNodeFilter(v8::Handle<v8::Value> callback, v8::Isolate*
const int32_t kMaxInt32 = 0x7fffffff;
const int32_t kMinInt32 = -kMaxInt32 - 1;
const uint32_t kMaxUInt32 = 0xffffffff;
-const int64_t kJSMaxInteger = 0x20000000000000LL - 1; // 2^53 - 1, maximum integer exactly representable in ECMAScript.
+const int64_t kJSMaxInteger = 0x20000000000000LL - 1; // 2^53 - 1, maximum uniquely representable integer in ECMAScript.
-static double enforceRange(double x, double minimum, double maximum, bool& ok)
+static double enforceRange(double x, double minimum, double maximum, const char* typeName, ExceptionState& exceptionState)
{
if (std::isnan(x) || std::isinf(x)) {
- ok = false;
+ exceptionState.throwTypeError("Value is" + String(std::isinf(x) ? " infinite and" : "") + " not of type '" + String(typeName) + "'.");
return 0;
}
x = trunc(x);
if (x < minimum || x > maximum) {
- ok = false;
+ exceptionState.throwTypeError("Value is outside the '" + String(typeName) + "' value range.");
return 0;
}
return x;
@@ -187,10 +208,9 @@ struct IntTypeLimits<uint16_t> {
};
template <typename T>
-static inline T toSmallerInt(v8::Handle<v8::Value> value, IntegerConversionConfiguration configuration, bool& ok)
+static inline T toSmallerInt(v8::Handle<v8::Value> value, IntegerConversionConfiguration configuration, const char* typeName, ExceptionState& exceptionState)
{
typedef IntTypeLimits<T> LimitsTrait;
- ok = true;
// Fast case. The value is already a 32-bit integer in the right range.
if (value->IsInt32()) {
@@ -198,7 +218,7 @@ static inline T toSmallerInt(v8::Handle<v8::Value> value, IntegerConversionConfi
if (result >= LimitsTrait::minValue && result <= LimitsTrait::maxValue)
return static_cast<T>(result);
if (configuration == EnforceRange) {
- ok = false;
+ exceptionState.throwTypeError("Value is outside the '" + String(typeName) + "' value range.");
return 0;
}
result %= LimitsTrait::numberOfValues;
@@ -206,14 +226,14 @@ static inline T toSmallerInt(v8::Handle<v8::Value> value, IntegerConversionConfi
}
// Can the value be converted to a number?
- v8::Local<v8::Number> numberObject = value->ToNumber();
+ TONATIVE_DEFAULT_EXCEPTIONSTATE(v8::Local<v8::Number>, numberObject, value->ToNumber(), exceptionState, 0);
if (numberObject.IsEmpty()) {
- ok = false;
+ exceptionState.throwTypeError("Not convertible to a number value (of type '" + String(typeName) + "'.");
return 0;
}
if (configuration == EnforceRange)
- return enforceRange(numberObject->Value(), LimitsTrait::minValue, LimitsTrait::maxValue, ok);
+ return enforceRange(numberObject->Value(), LimitsTrait::minValue, LimitsTrait::maxValue, typeName, exceptionState);
double numberValue = numberObject->Value();
if (std::isnan(numberValue) || std::isinf(numberValue) || !numberValue)
@@ -226,10 +246,9 @@ static inline T toSmallerInt(v8::Handle<v8::Value> value, IntegerConversionConfi
}
template <typename T>
-static inline T toSmallerUInt(v8::Handle<v8::Value> value, IntegerConversionConfiguration configuration, bool& ok)
+static inline T toSmallerUInt(v8::Handle<v8::Value> value, IntegerConversionConfiguration configuration, const char* typeName, ExceptionState& exceptionState)
{
typedef IntTypeLimits<T> LimitsTrait;
- ok = true;
// Fast case. The value is a 32-bit signed integer - possibly positive?
if (value->IsInt32()) {
@@ -237,21 +256,21 @@ static inline T toSmallerUInt(v8::Handle<v8::Value> value, IntegerConversionConf
if (result >= 0 && result <= LimitsTrait::maxValue)
return static_cast<T>(result);
if (configuration == EnforceRange) {
- ok = false;
+ exceptionState.throwTypeError("Value is outside the '" + String(typeName) + "' value range.");
return 0;
}
return static_cast<T>(result);
}
// Can the value be converted to a number?
- v8::Local<v8::Number> numberObject = value->ToNumber();
+ TONATIVE_DEFAULT_EXCEPTIONSTATE(v8::Local<v8::Number>, numberObject, value->ToNumber(), exceptionState, 0);
if (numberObject.IsEmpty()) {
- ok = false;
+ exceptionState.throwTypeError("Not convertible to a number value (of type '" + String(typeName) + "'.");
return 0;
}
if (configuration == EnforceRange)
- return enforceRange(numberObject->Value(), 0, LimitsTrait::maxValue, ok);
+ return enforceRange(numberObject->Value(), 0, LimitsTrait::maxValue, typeName, exceptionState);
// Does the value convert to nan or to an infinity?
double numberValue = numberObject->Value();
@@ -265,44 +284,65 @@ static inline T toSmallerUInt(v8::Handle<v8::Value> value, IntegerConversionConf
return static_cast<T>(fmod(numberValue, LimitsTrait::numberOfValues));
}
-int8_t toInt8(v8::Handle<v8::Value> value, IntegerConversionConfiguration configuration, bool& ok)
+int8_t toInt8(v8::Handle<v8::Value> value, IntegerConversionConfiguration configuration, ExceptionState& exceptionState)
+{
+ return toSmallerInt<int8_t>(value, configuration, "byte", exceptionState);
+}
+
+int8_t toInt8(v8::Handle<v8::Value> value)
+{
+ NonThrowableExceptionState exceptionState;
+ return toInt8(value, NormalConversion, exceptionState);
+}
+
+uint8_t toUInt8(v8::Handle<v8::Value> value, IntegerConversionConfiguration configuration, ExceptionState& exceptionState)
{
- return toSmallerInt<int8_t>(value, configuration, ok);
+ return toSmallerUInt<uint8_t>(value, configuration, "octet", exceptionState);
}
-uint8_t toUInt8(v8::Handle<v8::Value> value, IntegerConversionConfiguration configuration, bool& ok)
+uint8_t toUInt8(v8::Handle<v8::Value> value)
{
- return toSmallerUInt<uint8_t>(value, configuration, ok);
+ NonThrowableExceptionState exceptionState;
+ return toUInt8(value, NormalConversion, exceptionState);
}
-int16_t toInt16(v8::Handle<v8::Value> value, IntegerConversionConfiguration configuration, bool& ok)
+int16_t toInt16(v8::Handle<v8::Value> value, IntegerConversionConfiguration configuration, ExceptionState& exceptionState)
{
- return toSmallerInt<int16_t>(value, configuration, ok);
+ return toSmallerInt<int16_t>(value, configuration, "short", exceptionState);
}
-uint16_t toUInt16(v8::Handle<v8::Value> value, IntegerConversionConfiguration configuration, bool& ok)
+int16_t toInt16(v8::Handle<v8::Value> value)
{
- return toSmallerUInt<uint16_t>(value, configuration, ok);
+ NonThrowableExceptionState exceptionState;
+ return toInt16(value, NormalConversion, exceptionState);
}
-int32_t toInt32(v8::Handle<v8::Value> value, IntegerConversionConfiguration configuration, bool& ok)
+uint16_t toUInt16(v8::Handle<v8::Value> value, IntegerConversionConfiguration configuration, ExceptionState& exceptionState)
{
- ok = true;
+ return toSmallerUInt<uint16_t>(value, configuration, "unsigned short", exceptionState);
+}
+uint16_t toUInt16(v8::Handle<v8::Value> value)
+{
+ NonThrowableExceptionState exceptionState;
+ return toUInt16(value, NormalConversion, exceptionState);
+}
+
+int32_t toInt32(v8::Handle<v8::Value> value, IntegerConversionConfiguration configuration, ExceptionState& exceptionState)
+{
// Fast case. The value is already a 32-bit integer.
if (value->IsInt32())
return value->Int32Value();
// Can the value be converted to a number?
- ok = false;
- V8TRYCATCH_RETURN(v8::Local<v8::Number>, numberObject, value->ToNumber(), 0);
+ TONATIVE_DEFAULT_EXCEPTIONSTATE(v8::Local<v8::Number>, numberObject, value->ToNumber(), exceptionState, 0);
if (numberObject.IsEmpty()) {
+ exceptionState.throwTypeError("Not convertible to a number value (of type 'long'.)");
return 0;
}
- ok = true;
if (configuration == EnforceRange)
- return enforceRange(numberObject->Value(), kMinInt32, kMaxInt32, ok);
+ return enforceRange(numberObject->Value(), kMinInt32, kMaxInt32, "long", exceptionState);
// Does the value convert to nan or to an infinity?
double numberValue = numberObject->Value();
@@ -312,14 +352,18 @@ int32_t toInt32(v8::Handle<v8::Value> value, IntegerConversionConfiguration conf
if (configuration == Clamp)
return clampTo<int32_t>(numberObject->Value());
- V8TRYCATCH_RETURN(int32_t, result, numberObject->Int32Value(), 0);
+ TONATIVE_DEFAULT_EXCEPTIONSTATE(int32_t, result, numberObject->Int32Value(), exceptionState, 0);
return result;
}
-uint32_t toUInt32(v8::Handle<v8::Value> value, IntegerConversionConfiguration configuration, bool& ok)
+int32_t toInt32(v8::Handle<v8::Value> value)
{
- ok = true;
+ NonThrowableExceptionState exceptionState;
+ return toInt32(value, NormalConversion, exceptionState);
+}
+uint32_t toUInt32(v8::Handle<v8::Value> value, IntegerConversionConfiguration configuration, ExceptionState& exceptionState)
+{
// Fast case. The value is already a 32-bit unsigned integer.
if (value->IsUint32())
return value->Uint32Value();
@@ -330,22 +374,21 @@ uint32_t toUInt32(v8::Handle<v8::Value> value, IntegerConversionConfiguration co
if (result >= 0)
return result;
if (configuration == EnforceRange) {
- ok = false;
+ exceptionState.throwTypeError("Value is outside the 'unsigned long' value range.");
return 0;
}
return result;
}
// Can the value be converted to a number?
- ok = false;
- V8TRYCATCH_RETURN(v8::Local<v8::Number>, numberObject, value->ToNumber(), 0);
+ TONATIVE_DEFAULT_EXCEPTIONSTATE(v8::Local<v8::Number>, numberObject, value->ToNumber(), exceptionState, 0);
if (numberObject.IsEmpty()) {
+ exceptionState.throwTypeError("Not convertible to a number value (of type 'unsigned long'.)");
return 0;
}
- ok = true;
if (configuration == EnforceRange)
- return enforceRange(numberObject->Value(), 0, kMaxUInt32, ok);
+ return enforceRange(numberObject->Value(), 0, kMaxUInt32, "unsigned long", exceptionState);
// Does the value convert to nan or to an infinity?
double numberValue = numberObject->Value();
@@ -355,29 +398,33 @@ uint32_t toUInt32(v8::Handle<v8::Value> value, IntegerConversionConfiguration co
if (configuration == Clamp)
return clampTo<uint32_t>(numberObject->Value());
- V8TRYCATCH_RETURN(uint32_t, result, numberObject->Uint32Value(), 0);
+ TONATIVE_DEFAULT(uint32_t, result, numberObject->Uint32Value(), 0);
return result;
}
-int64_t toInt64(v8::Handle<v8::Value> value, IntegerConversionConfiguration configuration, bool& ok)
+uint32_t toUInt32(v8::Handle<v8::Value> value)
{
- ok = true;
+ NonThrowableExceptionState exceptionState;
+ return toUInt32(value, NormalConversion, exceptionState);
+}
+int64_t toInt64(v8::Handle<v8::Value> value, IntegerConversionConfiguration configuration, ExceptionState& exceptionState)
+{
// Fast case. The value is a 32-bit integer.
if (value->IsInt32())
return value->Int32Value();
// Can the value be converted to a number?
- v8::Local<v8::Number> numberObject = value->ToNumber();
+ TONATIVE_DEFAULT_EXCEPTIONSTATE(v8::Local<v8::Number>, numberObject, value->ToNumber(), exceptionState, 0);
if (numberObject.IsEmpty()) {
- ok = false;
+ exceptionState.throwTypeError("Not convertible to a number value (of type 'long long'.)");
return 0;
}
double x = numberObject->Value();
if (configuration == EnforceRange)
- return enforceRange(x, -kJSMaxInteger, kJSMaxInteger, ok);
+ return enforceRange(x, -kJSMaxInteger, kJSMaxInteger, "long long", exceptionState);
// Does the value convert to nan or to an infinity?
if (std::isnan(x) || std::isinf(x))
@@ -389,10 +436,14 @@ int64_t toInt64(v8::Handle<v8::Value> value, IntegerConversionConfiguration conf
return integer;
}
-uint64_t toUInt64(v8::Handle<v8::Value> value, IntegerConversionConfiguration configuration, bool& ok)
+int64_t toInt64(v8::Handle<v8::Value> value)
{
- ok = true;
+ NonThrowableExceptionState exceptionState;
+ return toInt64(value, NormalConversion, exceptionState);
+}
+uint64_t toUInt64(v8::Handle<v8::Value> value, IntegerConversionConfiguration configuration, ExceptionState& exceptionState)
+{
// Fast case. The value is a 32-bit unsigned integer.
if (value->IsUint32())
return value->Uint32Value();
@@ -403,23 +454,23 @@ uint64_t toUInt64(v8::Handle<v8::Value> value, IntegerConversionConfiguration co
if (result >= 0)
return result;
if (configuration == EnforceRange) {
- ok = false;
+ exceptionState.throwTypeError("Value is outside the 'unsigned long long' value range.");
return 0;
}
return result;
}
// Can the value be converted to a number?
- v8::Local<v8::Number> numberObject = value->ToNumber();
+ TONATIVE_DEFAULT_EXCEPTIONSTATE(v8::Local<v8::Number>, numberObject, value->ToNumber(), exceptionState, 0);
if (numberObject.IsEmpty()) {
- ok = false;
+ exceptionState.throwTypeError("Not convertible to a number value (of type 'unsigned long long'.)");
return 0;
}
double x = numberObject->Value();
if (configuration == EnforceRange)
- return enforceRange(x, 0, kJSMaxInteger, ok);
+ return enforceRange(x, 0, kJSMaxInteger, "unsigned long long", exceptionState);
// Does the value convert to nan or to an infinity?
if (std::isnan(x) || std::isinf(x))
@@ -431,134 +482,283 @@ uint64_t toUInt64(v8::Handle<v8::Value> value, IntegerConversionConfiguration co
return integer;
}
-v8::Handle<v8::FunctionTemplate> createRawTemplate(v8::Isolate* isolate)
+uint64_t toUInt64(v8::Handle<v8::Value> value)
+{
+ NonThrowableExceptionState exceptionState;
+ return toUInt64(value, NormalConversion, exceptionState);
+}
+
+float toFloat(v8::Handle<v8::Value> value, ExceptionState& exceptionState)
+{
+ TONATIVE_DEFAULT_EXCEPTIONSTATE(v8::Local<v8::Number>, numberObject, value->ToNumber(), exceptionState, 0);
+ return numberObject->NumberValue();
+}
+
+String toByteString(v8::Handle<v8::Value> value, ExceptionState& exceptionState)
+{
+ // Handle null default value.
+ if (value.IsEmpty())
+ return String();
+
+ // From the Web IDL spec: http://heycam.github.io/webidl/#es-ByteString
+ if (value.IsEmpty())
+ return String();
+
+ // 1. Let x be ToString(v)
+ TONATIVE_DEFAULT_EXCEPTIONSTATE(v8::Local<v8::String>, stringObject, value->ToString(), exceptionState, String());
+ String x = toCoreString(stringObject);
+
+ // 2. If the value of any element of x is greater than 255, then throw a TypeError.
+ if (!x.containsOnlyLatin1()) {
+ exceptionState.throwTypeError("Value is not a valid ByteString.");
+ return String();
+ }
+
+ // 3. Return an IDL ByteString value whose length is the length of x, and where the
+ // value of each element is the value of the corresponding element of x.
+ // Blink: A ByteString is simply a String with a range constrained per the above, so
+ // this is the identity operation.
+ return x;
+}
+
+static bool hasUnmatchedSurrogates(const String& string)
+{
+ // By definition, 8-bit strings are confined to the Latin-1 code page and
+ // have no surrogates, matched or otherwise.
+ if (string.is8Bit())
+ return false;
+
+ const UChar* characters = string.characters16();
+ const unsigned length = string.length();
+
+ for (unsigned i = 0; i < length; ++i) {
+ UChar c = characters[i];
+ if (U16_IS_SINGLE(c))
+ continue;
+ if (U16_IS_TRAIL(c))
+ return true;
+ ASSERT(U16_IS_LEAD(c));
+ if (i == length - 1)
+ return true;
+ UChar d = characters[i + 1];
+ if (!U16_IS_TRAIL(d))
+ return true;
+ ++i;
+ }
+ return false;
+}
+
+// Replace unmatched surrogates with REPLACEMENT CHARACTER U+FFFD.
+static String replaceUnmatchedSurrogates(const String& string)
+{
+ // This roughly implements http://heycam.github.io/webidl/#dfn-obtain-unicode
+ // but since Blink strings are 16-bits internally, the output is simply
+ // re-encoded to UTF-16.
+
+ // The concept of surrogate pairs is explained at:
+ // http://www.unicode.org/versions/Unicode6.2.0/ch03.pdf#G2630
+
+ // Blink-specific optimization to avoid making an unnecessary copy.
+ if (!hasUnmatchedSurrogates(string))
+ return string;
+ ASSERT(!string.is8Bit());
+
+ // 1. Let S be the DOMString value.
+ const UChar* s = string.characters16();
+
+ // 2. Let n be the length of S.
+ const unsigned n = string.length();
+
+ // 3. Initialize i to 0.
+ unsigned i = 0;
+
+ // 4. Initialize U to be an empty sequence of Unicode characters.
+ StringBuilder u;
+ u.reserveCapacity(n);
+
+ // 5. While i < n:
+ while (i < n) {
+ // 1. Let c be the code unit in S at index i.
+ UChar c = s[i];
+ // 2. Depending on the value of c:
+ if (U16_IS_SINGLE(c)) {
+ // c < 0xD800 or c > 0xDFFF
+ // Append to U the Unicode character with code point c.
+ u.append(c);
+ } else if (U16_IS_TRAIL(c)) {
+ // 0xDC00 <= c <= 0xDFFF
+ // Append to U a U+FFFD REPLACEMENT CHARACTER.
+ u.append(WTF::Unicode::replacementCharacter);
+ } else {
+ // 0xD800 <= c <= 0xDBFF
+ ASSERT(U16_IS_LEAD(c));
+ if (i == n - 1) {
+ // 1. If i = n−1, then append to U a U+FFFD REPLACEMENT CHARACTER.
+ u.append(WTF::Unicode::replacementCharacter);
+ } else {
+ // 2. Otherwise, i < n−1:
+ ASSERT(i < n - 1);
+ // ....1. Let d be the code unit in S at index i+1.
+ UChar d = s[i + 1];
+ if (U16_IS_TRAIL(d)) {
+ // 2. If 0xDC00 <= d <= 0xDFFF, then:
+ // ..1. Let a be c & 0x3FF.
+ // ..2. Let b be d & 0x3FF.
+ // ..3. Append to U the Unicode character with code point 2^16+2^10*a+b.
+ u.append(U16_GET_SUPPLEMENTARY(c, d));
+ // Blink: This is equivalent to u.append(c); u.append(d);
+ ++i;
+ } else {
+ // 3. Otherwise, d < 0xDC00 or d > 0xDFFF. Append to U a U+FFFD REPLACEMENT CHARACTER.
+ u.append(WTF::Unicode::replacementCharacter);
+ }
+ }
+ }
+ // 3. Set i to i+1.
+ ++i;
+ }
+
+ // 6. Return U.
+ ASSERT(u.length() == string.length());
+ return u.toString();
+}
+
+String toScalarValueString(v8::Handle<v8::Value> value, ExceptionState& exceptionState)
{
- v8::EscapableHandleScope scope(isolate);
- v8::Local<v8::FunctionTemplate> result = v8::FunctionTemplate::New(isolate, V8ObjectConstructor::isValidConstructorMode);
- return scope.Escape(result);
+ // From the Encoding standard (with a TODO to move to Web IDL):
+ // http://encoding.spec.whatwg.org/#type-scalarvaluestring
+ if (value.IsEmpty())
+ return String();
+ TONATIVE_DEFAULT_EXCEPTIONSTATE(v8::Local<v8::String>, stringObject, value->ToString(), exceptionState, String());
+
+ // ScalarValueString is identical to DOMString except that "convert a
+ // DOMString to a sequence of Unicode characters" is used subsequently
+ // when converting to an IDL value
+ String x = toCoreString(stringObject);
+ return replaceUnmatchedSurrogates(x);
}
-PassRefPtr<XPathNSResolver> toXPathNSResolver(v8::Handle<v8::Value> value, v8::Isolate* isolate)
+PassRefPtrWillBeRawPtr<XPathNSResolver> toXPathNSResolver(v8::Handle<v8::Value> value, v8::Isolate* isolate)
{
- RefPtr<XPathNSResolver> resolver;
- if (V8XPathNSResolver::hasInstance(value, isolate, worldType(isolate)))
+ RefPtrWillBeRawPtr<XPathNSResolver> resolver = nullptr;
+ if (V8XPathNSResolver::hasInstance(value, isolate))
resolver = V8XPathNSResolver::toNative(v8::Handle<v8::Object>::Cast(value));
else if (value->IsObject())
resolver = V8CustomXPathNSResolver::create(value->ToObject(), isolate);
return resolver;
}
-v8::Handle<v8::Object> toInnerGlobalObject(v8::Handle<v8::Context> context)
+LocalDOMWindow* toDOMWindow(v8::Handle<v8::Value> value, v8::Isolate* isolate)
{
- return v8::Handle<v8::Object>::Cast(context->Global()->GetPrototype());
+ if (value.IsEmpty() || !value->IsObject())
+ return 0;
+
+ v8::Handle<v8::Object> windowWrapper = V8Window::findInstanceInPrototypeChain(v8::Handle<v8::Object>::Cast(value), isolate);
+ if (!windowWrapper.IsEmpty())
+ return V8Window::toNative(windowWrapper);
+ return 0;
}
-DOMWindow* toDOMWindow(v8::Handle<v8::Context> context)
+LocalDOMWindow* toDOMWindow(v8::Handle<v8::Context> context)
{
- v8::Handle<v8::Object> global = context->Global();
- ASSERT(!global.IsEmpty());
- v8::Handle<v8::Object> window = global->FindInstanceInPrototypeChain(V8Window::domTemplate(context->GetIsolate(), MainWorld));
- if (!window.IsEmpty())
- return V8Window::toNative(window);
- window = global->FindInstanceInPrototypeChain(V8Window::domTemplate(context->GetIsolate(), IsolatedWorld));
- ASSERT(!window.IsEmpty());
- return V8Window::toNative(window);
+ if (context.IsEmpty())
+ return 0;
+ return toDOMWindow(context->Global(), context->GetIsolate());
+}
+
+LocalDOMWindow* enteredDOMWindow(v8::Isolate* isolate)
+{
+ LocalDOMWindow* window = toDOMWindow(isolate->GetEnteredContext());
+ if (!window) {
+ // We don't always have an entered DOM window, for example during microtask callbacks from V8
+ // (where the entered context may be the DOM-in-JS context). In that case, we fall back
+ // to the current context.
+ window = currentDOMWindow(isolate);
+ ASSERT(window);
+ }
+ return window;
+}
+
+LocalDOMWindow* currentDOMWindow(v8::Isolate* isolate)
+{
+ return toDOMWindow(isolate->GetCurrentContext());
+}
+
+LocalDOMWindow* callingDOMWindow(v8::Isolate* isolate)
+{
+ v8::Handle<v8::Context> context = isolate->GetCallingContext();
+ if (context.IsEmpty()) {
+ // Unfortunately, when processing script from a plug-in, we might not
+ // have a calling context. In those cases, we fall back to the
+ // entered context.
+ context = isolate->GetEnteredContext();
+ }
+ return toDOMWindow(context);
}
ExecutionContext* toExecutionContext(v8::Handle<v8::Context> context)
{
v8::Handle<v8::Object> global = context->Global();
- v8::Handle<v8::Object> windowWrapper = global->FindInstanceInPrototypeChain(V8Window::domTemplate(context->GetIsolate(), MainWorld));
- if (!windowWrapper.IsEmpty())
- return V8Window::toNative(windowWrapper)->executionContext();
- windowWrapper = global->FindInstanceInPrototypeChain(V8Window::domTemplate(context->GetIsolate(), IsolatedWorld));
+ v8::Handle<v8::Object> windowWrapper = V8Window::findInstanceInPrototypeChain(global, context->GetIsolate());
if (!windowWrapper.IsEmpty())
return V8Window::toNative(windowWrapper)->executionContext();
- v8::Handle<v8::Object> workerWrapper = global->FindInstanceInPrototypeChain(V8WorkerGlobalScope::domTemplate(context->GetIsolate(), WorkerWorld));
+ v8::Handle<v8::Object> workerWrapper = V8WorkerGlobalScope::findInstanceInPrototypeChain(global, context->GetIsolate());
if (!workerWrapper.IsEmpty())
return V8WorkerGlobalScope::toNative(workerWrapper)->executionContext();
// FIXME: Is this line of code reachable?
return 0;
}
-DOMWindow* activeDOMWindow()
+ExecutionContext* currentExecutionContext(v8::Isolate* isolate)
{
- v8::Handle<v8::Context> context = v8::Isolate::GetCurrent()->GetCallingContext();
- if (context.IsEmpty()) {
- // Unfortunately, when processing script from a plug-in, we might not
- // have a calling context. In those cases, we fall back to the
- // entered context.
- context = v8::Isolate::GetCurrent()->GetEnteredContext();
- }
- return toDOMWindow(context);
+ return toExecutionContext(isolate->GetCurrentContext());
}
-ExecutionContext* activeExecutionContext()
+ExecutionContext* callingExecutionContext(v8::Isolate* isolate)
{
- v8::Handle<v8::Context> context = v8::Isolate::GetCurrent()->GetCallingContext();
+ v8::Handle<v8::Context> context = isolate->GetCallingContext();
if (context.IsEmpty()) {
// Unfortunately, when processing script from a plug-in, we might not
// have a calling context. In those cases, we fall back to the
// entered context.
- context = v8::Isolate::GetCurrent()->GetEnteredContext();
+ context = isolate->GetEnteredContext();
}
return toExecutionContext(context);
}
-DOMWindow* firstDOMWindow()
-{
- return toDOMWindow(v8::Isolate::GetCurrent()->GetEnteredContext());
-}
-
-Document* currentDocument()
-{
- return toDOMWindow(v8::Isolate::GetCurrent()->GetCurrentContext())->document();
-}
-
-Frame* toFrameIfNotDetached(v8::Handle<v8::Context> context)
+LocalFrame* toFrameIfNotDetached(v8::Handle<v8::Context> context)
{
- DOMWindow* window = toDOMWindow(context);
- if (window->isCurrentlyDisplayedInFrame())
+ LocalDOMWindow* window = toDOMWindow(context);
+ if (window && window->isCurrentlyDisplayedInFrame())
return window->frame();
- // We return 0 here because |context| is detached from the Frame. If we
+ // We return 0 here because |context| is detached from the LocalFrame. If we
// did return |frame| we could get in trouble because the frame could be
// navigated to another security origin.
return 0;
}
-v8::Local<v8::Context> toV8Context(ExecutionContext* context, DOMWrapperWorld* world)
+v8::Local<v8::Context> toV8Context(ExecutionContext* context, DOMWrapperWorld& world)
{
+ ASSERT(context);
if (context->isDocument()) {
- ASSERT(world);
- if (Frame* frame = toDocument(context)->frame())
+ if (LocalFrame* frame = toDocument(context)->frame())
return frame->script().windowShell(world)->context();
} else if (context->isWorkerGlobalScope()) {
- ASSERT(!world);
if (WorkerScriptController* script = toWorkerGlobalScope(context)->script())
return script->context();
}
return v8::Local<v8::Context>();
}
-bool handleOutOfMemory()
+v8::Local<v8::Context> toV8Context(LocalFrame* frame, DOMWrapperWorld& world)
{
- v8::Local<v8::Context> context = v8::Isolate::GetCurrent()->GetCurrentContext();
-
- if (!context->HasOutOfMemoryException())
- return false;
-
- // Warning, error, disable JS for this frame?
- Frame* frame = toFrameIfNotDetached(context);
if (!frame)
- return true;
-
- frame->script().clearForOutOfMemory();
- frame->loader().client()->didExhaustMemoryAvailableForScript();
-
- if (Settings* settings = frame->settings())
- settings->setScriptEnabled(false);
-
- return true;
+ return v8::Local<v8::Context>();
+ v8::Local<v8::Context> context = frame->script().windowShell(world)->context();
+ if (context.IsEmpty())
+ return v8::Local<v8::Context>();
+ LocalFrame* attachedFrame= toFrameIfNotDetached(context);
+ return frame == attachedFrame ? context : v8::Local<v8::Context>();
}
v8::Local<v8::Value> handleMaxRecursionDepthExceeded(v8::Isolate* isolate)
@@ -576,73 +776,165 @@ void crashIfV8IsDead()
}
}
-WrapperWorldType worldType(v8::Isolate* isolate)
+v8::Handle<v8::Function> getBoundFunction(v8::Handle<v8::Function> function)
{
- V8PerIsolateData* data = V8PerIsolateData::from(isolate);
- if (!data->workerDOMDataStore())
- return worldTypeInMainThread(isolate);
- return WorkerWorld;
+ v8::Handle<v8::Value> boundFunction = function->GetBoundFunction();
+ return boundFunction->IsFunction() ? v8::Handle<v8::Function>::Cast(boundFunction) : function;
}
-WrapperWorldType worldTypeInMainThread(v8::Isolate* isolate)
+void addHiddenValueToArray(v8::Handle<v8::Object> object, v8::Local<v8::Value> value, int arrayIndex, v8::Isolate* isolate)
{
- if (!DOMWrapperWorld::isolatedWorldsExist())
- return MainWorld;
- ASSERT(!isolate->GetEnteredContext().IsEmpty());
- DOMWrapperWorld* isolatedWorld = DOMWrapperWorld::isolatedWorld(isolate->GetEnteredContext());
- if (isolatedWorld)
- return IsolatedWorld;
- return MainWorld;
+ v8::Local<v8::Value> arrayValue = object->GetInternalField(arrayIndex);
+ if (arrayValue->IsNull() || arrayValue->IsUndefined()) {
+ arrayValue = v8::Array::New(isolate);
+ object->SetInternalField(arrayIndex, arrayValue);
+ }
+
+ v8::Local<v8::Array> array = v8::Local<v8::Array>::Cast(arrayValue);
+ array->Set(v8::Integer::New(isolate, array->Length()), value);
}
-DOMWrapperWorld* isolatedWorldForIsolate(v8::Isolate* isolate)
+void removeHiddenValueFromArray(v8::Handle<v8::Object> object, v8::Local<v8::Value> value, int arrayIndex, v8::Isolate* isolate)
{
- V8PerIsolateData* data = V8PerIsolateData::from(isolate);
- if (data->workerDOMDataStore())
- return 0;
- if (!DOMWrapperWorld::isolatedWorldsExist())
- return 0;
- ASSERT(isolate->InContext());
- return DOMWrapperWorld::isolatedWorld(isolate->GetCurrentContext());
+ v8::Local<v8::Value> arrayValue = object->GetInternalField(arrayIndex);
+ if (!arrayValue->IsArray())
+ return;
+ v8::Local<v8::Array> array = v8::Local<v8::Array>::Cast(arrayValue);
+ for (int i = array->Length() - 1; i >= 0; --i) {
+ v8::Local<v8::Value> item = array->Get(v8::Integer::New(isolate, i));
+ if (item->StrictEquals(value)) {
+ array->Delete(i);
+ return;
+ }
+ }
}
-v8::Local<v8::Value> getHiddenValueFromMainWorldWrapper(v8::Isolate* isolate, ScriptWrappable* wrappable, v8::Handle<v8::String> key)
+void moveEventListenerToNewWrapper(v8::Handle<v8::Object> object, EventListener* oldValue, v8::Local<v8::Value> newValue, int arrayIndex, v8::Isolate* isolate)
{
- v8::Local<v8::Object> wrapper = wrappable->newLocalWrapper(isolate);
- return wrapper.IsEmpty() ? v8::Local<v8::Value>() : wrapper->GetHiddenValue(key);
+ if (oldValue) {
+ V8AbstractEventListener* oldListener = V8AbstractEventListener::cast(oldValue);
+ if (oldListener) {
+ v8::Local<v8::Object> oldListenerObject = oldListener->getExistingListenerObject();
+ if (!oldListenerObject.IsEmpty())
+ removeHiddenValueFromArray(object, oldListenerObject, arrayIndex, isolate);
+ }
+ }
+ // Non-callable input is treated as null and ignored
+ if (newValue->IsFunction())
+ addHiddenValueToArray(object, newValue, arrayIndex, isolate);
}
-static gin::IsolateHolder* mainIsolateHolder = 0;
+v8::Isolate* toIsolate(ExecutionContext* context)
+{
+ if (context && context->isDocument())
+ return V8PerIsolateData::mainThreadIsolate();
+ return v8::Isolate::GetCurrent();
+}
-v8::Isolate* mainThreadIsolate()
+v8::Isolate* toIsolate(LocalFrame* frame)
{
- ASSERT(mainIsolateHolder);
- ASSERT(isMainThread());
- return mainIsolateHolder->isolate();
+ ASSERT(frame);
+ return frame->script().isolate();
}
-void setMainThreadIsolate(v8::Isolate* isolate)
+PassRefPtr<JSONValue> v8ToJSONValue(v8::Isolate* isolate, v8::Handle<v8::Value> value, int maxDepth)
{
- ASSERT(!mainIsolateHolder || !isolate);
- ASSERT(isMainThread());
- if (isolate) {
- mainIsolateHolder = new gin::IsolateHolder(isolate);
- } else {
- delete mainIsolateHolder;
- mainIsolateHolder = 0;
+ if (value.IsEmpty()) {
+ ASSERT_NOT_REACHED();
+ return nullptr;
+ }
+
+ if (!maxDepth)
+ return nullptr;
+ maxDepth--;
+
+ if (value->IsNull() || value->IsUndefined())
+ return JSONValue::null();
+ if (value->IsBoolean())
+ return JSONBasicValue::create(value->BooleanValue());
+ if (value->IsNumber())
+ return JSONBasicValue::create(value->NumberValue());
+ if (value->IsString())
+ return JSONString::create(toCoreString(value.As<v8::String>()));
+ if (value->IsArray()) {
+ v8::Handle<v8::Array> array = v8::Handle<v8::Array>::Cast(value);
+ RefPtr<JSONArray> inspectorArray = JSONArray::create();
+ uint32_t length = array->Length();
+ for (uint32_t i = 0; i < length; i++) {
+ v8::Local<v8::Value> value = array->Get(v8::Int32::New(isolate, i));
+ RefPtr<JSONValue> element = v8ToJSONValue(isolate, value, maxDepth);
+ if (!element)
+ return nullptr;
+ inspectorArray->pushValue(element);
+ }
+ return inspectorArray;
+ }
+ if (value->IsObject()) {
+ RefPtr<JSONObject> jsonObject = JSONObject::create();
+ v8::Handle<v8::Object> object = v8::Handle<v8::Object>::Cast(value);
+ v8::Local<v8::Array> propertyNames = object->GetPropertyNames();
+ uint32_t length = propertyNames->Length();
+ for (uint32_t i = 0; i < length; i++) {
+ v8::Local<v8::Value> name = propertyNames->Get(v8::Int32::New(isolate, i));
+ // FIXME(yurys): v8::Object should support GetOwnPropertyNames
+ if (name->IsString() && !object->HasRealNamedProperty(v8::Handle<v8::String>::Cast(name)))
+ continue;
+ RefPtr<JSONValue> propertyValue = v8ToJSONValue(isolate, object->Get(name), maxDepth);
+ if (!propertyValue)
+ return nullptr;
+ TOSTRING_DEFAULT(V8StringResource<WithNullCheck>, nameString, name, nullptr);
+ jsonObject->setValue(nameString, propertyValue);
+ }
+ return jsonObject;
}
+ ASSERT_NOT_REACHED();
+ return nullptr;
}
-v8::Isolate* toIsolate(ExecutionContext* context)
+V8TestingScope::V8TestingScope(v8::Isolate* isolate)
+ : m_handleScope(isolate)
+ , m_contextScope(v8::Context::New(isolate))
+ , m_scriptState(ScriptStateForTesting::create(isolate->GetCurrentContext(), DOMWrapperWorld::create()))
{
- if (context && context->isDocument())
- return mainThreadIsolate();
- return v8::Isolate::GetCurrent();
}
-v8::Isolate* toIsolate(Frame* frame)
+V8TestingScope::~V8TestingScope()
{
- return frame->script().isolate();
+ m_scriptState->disposePerContextData();
+}
+
+ScriptState* V8TestingScope::scriptState() const
+{
+ return m_scriptState.get();
+}
+
+v8::Isolate* V8TestingScope::isolate() const
+{
+ return m_scriptState->isolate();
+}
+
+void GetDevToolsFunctionInfo(v8::Handle<v8::Function> function, v8::Isolate* isolate, int& scriptId, String& resourceName, int& lineNumber)
+{
+ v8::Handle<v8::Function> originalFunction = getBoundFunction(function);
+ scriptId = originalFunction->ScriptId();
+ v8::ScriptOrigin origin = originalFunction->GetScriptOrigin();
+ if (!origin.ResourceName().IsEmpty()) {
+ resourceName = NativeValueTraits<String>::nativeValue(origin.ResourceName(), isolate);
+ lineNumber = originalFunction->GetScriptLineNumber() + 1;
+ }
+ if (resourceName.isEmpty()) {
+ resourceName = "undefined";
+ lineNumber = 1;
+ }
+}
+
+PassRefPtr<TraceEvent::ConvertableToTraceFormat> devToolsTraceEventData(ExecutionContext* context, v8::Handle<v8::Function> function, v8::Isolate* isolate)
+{
+ int scriptId = 0;
+ String resourceName;
+ int lineNumber = 1;
+ GetDevToolsFunctionInfo(function, isolate, scriptId, resourceName, lineNumber);
+ return InspectorFunctionCallEvent::data(context, scriptId, resourceName, lineNumber);
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8Binding.h b/chromium/third_party/WebKit/Source/bindings/v8/V8Binding.h
index 48200a2fdd0..7fb8e727b57 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8Binding.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8Binding.h
@@ -34,668 +34,942 @@
#include "bindings/v8/DOMWrapperWorld.h"
#include "bindings/v8/ExceptionMessages.h"
+#include "bindings/v8/ScriptValue.h"
#include "bindings/v8/V8BindingMacros.h"
#include "bindings/v8/V8PerIsolateData.h"
#include "bindings/v8/V8StringResource.h"
#include "bindings/v8/V8ThrowException.h"
#include "bindings/v8/V8ValueCache.h"
+#include "platform/heap/Heap.h"
#include "wtf/MathExtras.h"
#include "wtf/text/AtomicString.h"
#include <v8.h>
namespace WebCore {
- class DOMWindow;
- class Document;
- class Frame;
- class NodeFilter;
- class ExecutionContext;
- class ScriptWrappable;
- class XPathNSResolver;
+class LocalDOMWindow;
+class Document;
+class EventListener;
+class ExecutionContext;
+class ExceptionState;
+class LocalFrame;
+class NodeFilter;
+class ScriptWrappable;
+class XPathNSResolver;
+
+namespace TraceEvent {
+class ConvertableToTraceFormat;
+}
+
+const int kMaxRecursionDepth = 22;
+
+// Schedule a JavaScript error to be thrown.
+v8::Handle<v8::Value> throwError(V8ErrorType, const String&, v8::Isolate*);
+
+// Schedule a JavaScript error to be thrown.
+v8::Handle<v8::Value> throwError(v8::Handle<v8::Value>, v8::Isolate*);
+
+// A helper for throwing JavaScript TypeError.
+v8::Handle<v8::Value> throwTypeError(const String&, v8::Isolate*);
+
+// Helpers for throwing JavaScript TypeErrors for arity mismatches.
+void throwArityTypeErrorForMethod(const char* method, const char* type, const char* valid, unsigned provided, v8::Isolate*);
+void throwArityTypeErrorForConstructor(const char* type, const char* valid, unsigned provided, v8::Isolate*);
+void throwArityTypeError(ExceptionState&, const char* valid, unsigned provided);
+void throwMinimumArityTypeErrorForMethod(const char* method, const char* type, unsigned expected, unsigned providedLeastNumMandatoryParams, v8::Isolate*);
+void throwMinimumArityTypeErrorForConstructor(const char* type, unsigned expected, unsigned providedLeastNumMandatoryParams, v8::Isolate*);
+void throwMinimumArityTypeError(ExceptionState&, unsigned expected, unsigned providedLeastNumMandatoryParams);
+
+v8::ArrayBuffer::Allocator* v8ArrayBufferAllocator();
+
+inline v8::Handle<v8::Value> argumentOrNull(const v8::FunctionCallbackInfo<v8::Value>& info, int index)
+{
+ return index >= info.Length() ? v8::Local<v8::Value>() : info[index];
+}
+
+template<typename CallbackInfo, typename V>
+inline void v8SetReturnValue(const CallbackInfo& info, V v)
+{
+ info.GetReturnValue().Set(v);
+}
+
+template<typename CallbackInfo>
+inline void v8SetReturnValueBool(const CallbackInfo& info, bool v)
+{
+ info.GetReturnValue().Set(v);
+}
+
+template<typename CallbackInfo>
+inline void v8SetReturnValueInt(const CallbackInfo& info, int v)
+{
+ info.GetReturnValue().Set(v);
+}
+
+template<typename CallbackInfo>
+inline void v8SetReturnValueUnsigned(const CallbackInfo& info, unsigned v)
+{
+ info.GetReturnValue().Set(v);
+}
+
+template<typename CallbackInfo>
+inline void v8SetReturnValueNull(const CallbackInfo& info)
+{
+ info.GetReturnValue().SetNull();
+}
+
+template<typename CallbackInfo>
+inline void v8SetReturnValueUndefined(const CallbackInfo& info)
+{
+ info.GetReturnValue().SetUndefined();
+}
+
+template<typename CallbackInfo>
+inline void v8SetReturnValueEmptyString(const CallbackInfo& info)
+{
+ info.GetReturnValue().SetEmptyString();
+}
+
+template <class CallbackInfo>
+inline void v8SetReturnValueString(const CallbackInfo& info, const String& string, v8::Isolate* isolate)
+{
+ if (string.isNull()) {
+ v8SetReturnValueEmptyString(info);
+ return;
+ }
+ V8PerIsolateData::from(isolate)->stringCache()->setReturnValueFromString(info.GetReturnValue(), string.impl());
+}
+
+template <class CallbackInfo>
+inline void v8SetReturnValueStringOrNull(const CallbackInfo& info, const String& string, v8::Isolate* isolate)
+{
+ if (string.isNull()) {
+ v8SetReturnValueNull(info);
+ return;
+ }
+ V8PerIsolateData::from(isolate)->stringCache()->setReturnValueFromString(info.GetReturnValue(), string.impl());
+}
+
+template <class CallbackInfo>
+inline void v8SetReturnValueStringOrUndefined(const CallbackInfo& info, const String& string, v8::Isolate* isolate)
+{
+ if (string.isNull()) {
+ v8SetReturnValueUndefined(info);
+ return;
+ }
+ V8PerIsolateData::from(isolate)->stringCache()->setReturnValueFromString(info.GetReturnValue(), string.impl());
+}
+
+// Convert v8::String to a WTF::String. If the V8 string is not already
+// an external string then it is transformed into an external string at this
+// point to avoid repeated conversions.
+inline String toCoreString(v8::Handle<v8::String> value)
+{
+ return v8StringToWebCoreString<String>(value, Externalize);
+}
+
+inline String toCoreStringWithNullCheck(v8::Handle<v8::String> value)
+{
+ if (value.IsEmpty() || value->IsNull())
+ return String();
+ return toCoreString(value);
+}
+
+inline String toCoreStringWithUndefinedOrNullCheck(v8::Handle<v8::String> value)
+{
+ if (value.IsEmpty() || value->IsNull() || value->IsUndefined())
+ return String();
+ return toCoreString(value);
+}
+
+inline AtomicString toCoreAtomicString(v8::Handle<v8::String> value)
+{
+ return v8StringToWebCoreString<AtomicString>(value, Externalize);
+}
+
+// This method will return a null String if the v8::Value does not contain a v8::String.
+// It will not call ToString() on the v8::Value. If you want ToString() to be called,
+// please use the TONATIVE_FOR_V8STRINGRESOURCE_*() macros instead.
+inline String toCoreStringWithUndefinedOrNullCheck(v8::Handle<v8::Value> value)
+{
+ if (value.IsEmpty() || !value->IsString())
+ return String();
+ return toCoreString(value.As<v8::String>());
+}
+
+// Convert a string to a V8 string.
+// Return a V8 external string that shares the underlying buffer with the given
+// WebCore string. The reference counting mechanism is used to keep the
+// underlying buffer alive while the string is still live in the V8 engine.
+inline v8::Handle<v8::String> v8String(v8::Isolate* isolate, const String& string)
+{
+ if (string.isNull())
+ return v8::String::Empty(isolate);
+ return V8PerIsolateData::from(isolate)->stringCache()->v8ExternalString(string.impl(), isolate);
+}
+
+inline v8::Handle<v8::String> v8AtomicString(v8::Isolate* isolate, const char* str)
+{
+ ASSERT(isolate);
+ return v8::String::NewFromUtf8(isolate, str, v8::String::kInternalizedString, strlen(str));
+}
- const int kMaxRecursionDepth = 22;
+inline v8::Handle<v8::String> v8AtomicString(v8::Isolate* isolate, const char* str, size_t length)
+{
+ ASSERT(isolate);
+ return v8::String::NewFromUtf8(isolate, str, v8::String::kInternalizedString, length);
+}
- // Schedule a DOM exception to be thrown, if the exception code is different
- // from zero.
- v8::Handle<v8::Value> setDOMException(int, v8::Isolate*);
- v8::Handle<v8::Value> setDOMException(int, const String&, v8::Isolate*);
+inline v8::Handle<v8::Value> v8Undefined()
+{
+ return v8::Handle<v8::Value>();
+}
- // Schedule a JavaScript error to be thrown.
- v8::Handle<v8::Value> throwError(V8ErrorType, const String&, v8::Isolate*);
-
- // Schedule a JavaScript error to be thrown.
- v8::Handle<v8::Value> throwError(v8::Handle<v8::Value>, v8::Isolate*);
-
- // A helper for throwing JavaScript TypeError.
- v8::Handle<v8::Value> throwTypeError(const String&, v8::Isolate*);
-
- // FIXME: Remove this once we kill its callers.
- v8::Handle<v8::Value> throwUninformativeAndGenericTypeError(v8::Isolate*);
-
- v8::ArrayBuffer::Allocator* v8ArrayBufferAllocator();
-
- v8::Handle<v8::Value> toV8Sequence(v8::Handle<v8::Value>, uint32_t& length, v8::Isolate*);
-
- inline v8::Handle<v8::Value> argumentOrNull(const v8::FunctionCallbackInfo<v8::Value>& info, int index)
+template <class T>
+struct V8ValueTraits {
+ // FIXME: This function requires the associated generated header to be
+ // included. Also, this function does not match with other V8ValueTraits
+ // classes. Remove this V8ValueTraits if possible.
+ static inline v8::Handle<v8::Value> toV8Value(const T& value, v8::Handle<v8::Object> creationContext, v8::Isolate* isolate)
{
- return index >= info.Length() ? v8::Local<v8::Value>() : info[index];
+ return toV8(WTF::getPtr(value), creationContext, isolate);
}
+};
- template<typename CallbackInfo, typename V>
- inline void v8SetReturnValue(const CallbackInfo& info, V v)
+template<>
+struct V8ValueTraits<String> {
+ static inline v8::Handle<v8::Value> toV8Value(const String& value, v8::Handle<v8::Object>, v8::Isolate* isolate)
{
- info.GetReturnValue().Set(v);
+ return v8String(isolate, value);
}
+};
- template<typename CallbackInfo>
- inline void v8SetReturnValueBool(const CallbackInfo& info, bool v)
+template<>
+struct V8ValueTraits<AtomicString> {
+ static inline v8::Handle<v8::Value> toV8Value(const AtomicString& value, v8::Handle<v8::Object>, v8::Isolate* isolate)
{
- info.GetReturnValue().Set(v);
+ return v8String(isolate, value);
}
+};
- template<typename CallbackInfo>
- inline void v8SetReturnValueInt(const CallbackInfo& info, int v)
+template<size_t n>
+struct V8ValueTraits<char[n]> {
+ static inline v8::Handle<v8::Value> toV8Value(char const (&value)[n], v8::Handle<v8::Object>, v8::Isolate* isolate)
{
- info.GetReturnValue().Set(v);
+ return v8String(isolate, value);
}
+};
- template<typename CallbackInfo>
- inline void v8SetReturnValueUnsigned(const CallbackInfo& info, unsigned v)
+template<>
+struct V8ValueTraits<const char*> {
+ static inline v8::Handle<v8::Value> toV8Value(const char* const& value, v8::Handle<v8::Object>, v8::Isolate* isolate)
{
- info.GetReturnValue().Set(v);
+ return v8String(isolate, value);
}
+};
- template<typename CallbackInfo>
- inline void v8SetReturnValueNull(const CallbackInfo& info)
+template<>
+struct V8ValueTraits<int> {
+ static inline v8::Handle<v8::Value> toV8Value(const int& value, v8::Handle<v8::Object>, v8::Isolate* isolate)
{
- info.GetReturnValue().SetNull();
+ return v8::Integer::New(isolate, value);
}
+};
- template<typename CallbackInfo>
- inline void v8SetReturnValueUndefined(const CallbackInfo& info)
+template<>
+struct V8ValueTraits<long> {
+ static inline v8::Handle<v8::Value> toV8Value(const long& value, v8::Handle<v8::Object>, v8::Isolate* isolate)
{
- info.GetReturnValue().SetUndefined();
+ return v8::Integer::New(isolate, value);
}
+};
- template<typename CallbackInfo>
- inline void v8SetReturnValueEmptyString(const CallbackInfo& info)
+template<>
+struct V8ValueTraits<unsigned> {
+ static inline v8::Handle<v8::Value> toV8Value(const unsigned& value, v8::Handle<v8::Object>, v8::Isolate* isolate)
{
- info.GetReturnValue().SetEmptyString();
+ return v8::Integer::NewFromUnsigned(isolate, value);
}
+};
- template <class CallbackInfo>
- inline void v8SetReturnValueString(const CallbackInfo& info, const String& string, v8::Isolate* isolate)
+template<>
+struct V8ValueTraits<unsigned long> {
+ static inline v8::Handle<v8::Value> toV8Value(const unsigned long& value, v8::Handle<v8::Object>, v8::Isolate* isolate)
{
- if (string.isNull()) {
- v8SetReturnValueEmptyString(info);
- return;
- }
- V8PerIsolateData::from(isolate)->stringCache()->setReturnValueFromString(info.GetReturnValue(), string.impl());
+ return v8::Integer::NewFromUnsigned(isolate, value);
}
+};
- template <class CallbackInfo>
- inline void v8SetReturnValueStringOrNull(const CallbackInfo& info, const String& string, v8::Isolate* isolate)
+template<>
+struct V8ValueTraits<float> {
+ static inline v8::Handle<v8::Value> toV8Value(const float& value, v8::Handle<v8::Object>, v8::Isolate* isolate)
{
- if (string.isNull()) {
- v8SetReturnValueNull(info);
- return;
- }
- V8PerIsolateData::from(isolate)->stringCache()->setReturnValueFromString(info.GetReturnValue(), string.impl());
+ return v8::Number::New(isolate, value);
}
+};
- template <class CallbackInfo>
- inline void v8SetReturnValueStringOrUndefined(const CallbackInfo& info, const String& string, v8::Isolate* isolate)
+template<>
+struct V8ValueTraits<double> {
+ static inline v8::Handle<v8::Value> toV8Value(const double& value, v8::Handle<v8::Object>, v8::Isolate* isolate)
{
- if (string.isNull()) {
- v8SetReturnValueUndefined(info);
- return;
- }
- V8PerIsolateData::from(isolate)->stringCache()->setReturnValueFromString(info.GetReturnValue(), string.impl());
+ return v8::Number::New(isolate, value);
}
+};
- // Convert v8::String to a WTF::String. If the V8 string is not already
- // an external string then it is transformed into an external string at this
- // point to avoid repeated conversions.
- inline String toCoreString(v8::Handle<v8::String> value)
+template<>
+struct V8ValueTraits<bool> {
+ static inline v8::Handle<v8::Value> toV8Value(const bool& value, v8::Handle<v8::Object>, v8::Isolate* isolate)
{
- return v8StringToWebCoreString<String>(value, Externalize);
+ return v8::Boolean::New(isolate, value);
}
+};
- inline String toCoreStringWithNullCheck(v8::Handle<v8::String> value)
- {
- if (value.IsEmpty() || value->IsNull())
- return String();
- return toCoreString(value);
- }
+// V8NullType and V8UndefinedType are used only for the value conversion.
+class V8NullType { };
+class V8UndefinedType { };
- inline String toCoreStringWithUndefinedOrNullCheck(v8::Handle<v8::String> value)
+template<>
+struct V8ValueTraits<V8NullType> {
+ static inline v8::Handle<v8::Value> toV8Value(const V8NullType&, v8::Handle<v8::Object>, v8::Isolate* isolate)
{
- if (value.IsEmpty() || value->IsNull() || value->IsUndefined())
- return String();
- return toCoreString(value);
+ return v8::Null(isolate);
}
+};
- inline AtomicString toCoreAtomicString(v8::Handle<v8::String> value)
+template<>
+struct V8ValueTraits<V8UndefinedType> {
+ static inline v8::Handle<v8::Value> toV8Value(const V8UndefinedType&, v8::Handle<v8::Object>, v8::Isolate* isolate)
{
- return v8StringToWebCoreString<AtomicString>(value, Externalize);
+ return v8::Undefined(isolate);
}
+};
- // This method will return a null String if the v8::Value does not contain a v8::String.
- // It will not call ToString() on the v8::Value. If you want ToString() to be called,
- // please use the V8TRYCATCH_FOR_V8STRINGRESOURCE_*() macros instead.
- inline String toCoreStringWithUndefinedOrNullCheck(v8::Handle<v8::Value> value)
+template<>
+struct V8ValueTraits<ScriptValue> {
+ static inline v8::Handle<v8::Value> toV8Value(const ScriptValue& value, v8::Handle<v8::Object>, v8::Isolate*)
{
- if (value.IsEmpty() || !value->IsString())
- return String();
-
- return toCoreString(value.As<v8::String>());
+ return value.v8Value();
}
+};
- // Convert a string to a V8 string.
- // Return a V8 external string that shares the underlying buffer with the given
- // WebCore string. The reference counting mechanism is used to keep the
- // underlying buffer alive while the string is still live in the V8 engine.
- inline v8::Handle<v8::String> v8String(v8::Isolate* isolate, const String& string)
+template<>
+struct V8ValueTraits<v8::Handle<v8::Value> > {
+ static inline v8::Handle<v8::Value> toV8Value(const v8::Handle<v8::Value>& value, v8::Handle<v8::Object>, v8::Isolate*)
{
- if (string.isNull())
- return v8::String::Empty(isolate);
- return V8PerIsolateData::from(isolate)->stringCache()->v8ExternalString(string.impl(), isolate);
+ return value;
}
+};
- inline v8::Handle<v8::Value> v8Undefined()
+template<>
+struct V8ValueTraits<v8::Local<v8::Value> > {
+ static inline v8::Handle<v8::Value> toV8Value(const v8::Local<v8::Value>& value, v8::Handle<v8::Object>, v8::Isolate*)
{
- return v8::Handle<v8::Value>();
+ return value;
}
+};
- template <class T>
- struct V8ValueTraits {
- static inline v8::Handle<v8::Value> arrayV8Value(const T& value, v8::Isolate* isolate)
- {
- return toV8(WTF::getPtr(value), v8::Handle<v8::Object>(), isolate);
- }
- };
-
- template<>
- struct V8ValueTraits<String> {
- static inline v8::Handle<v8::Value> arrayV8Value(const String& value, v8::Isolate* isolate)
- {
- return v8String(isolate, value);
- }
- };
-
- template<>
- struct V8ValueTraits<unsigned> {
- static inline v8::Handle<v8::Value> arrayV8Value(const unsigned& value, v8::Isolate* isolate)
- {
- return v8::Integer::NewFromUnsigned(value, isolate);
- }
- };
-
- template<>
- struct V8ValueTraits<unsigned long> {
- static inline v8::Handle<v8::Value> arrayV8Value(const unsigned long& value, v8::Isolate* isolate)
- {
- return v8::Integer::NewFromUnsigned(value, isolate);
- }
- };
-
- template<>
- struct V8ValueTraits<float> {
- static inline v8::Handle<v8::Value> arrayV8Value(const float& value, v8::Isolate* isolate)
- {
- return v8::Number::New(isolate, value);
- }
- };
-
- template<>
- struct V8ValueTraits<double> {
- static inline v8::Handle<v8::Value> arrayV8Value(const double& value, v8::Isolate* isolate)
- {
- return v8::Number::New(isolate, value);
- }
- };
-
- template<typename T, size_t inlineCapacity>
- v8::Handle<v8::Value> v8Array(const Vector<T, inlineCapacity>& iterator, v8::Isolate* isolate)
+template<typename T, size_t inlineCapacity>
+v8::Handle<v8::Value> v8Array(const Vector<T, inlineCapacity>& iterator, v8::Handle<v8::Object> creationContext, v8::Isolate* isolate)
+{
+ v8::Local<v8::Array> result = v8::Array::New(isolate, iterator.size());
+ int index = 0;
+ typename Vector<T, inlineCapacity>::const_iterator end = iterator.end();
+ typedef V8ValueTraits<T> TraitsType;
+ for (typename Vector<T, inlineCapacity>::const_iterator iter = iterator.begin(); iter != end; ++iter)
+ result->Set(v8::Integer::New(isolate, index++), TraitsType::toV8Value(*iter, creationContext, isolate));
+ return result;
+}
+
+template<typename T, size_t inlineCapacity>
+v8::Handle<v8::Value> v8Array(const HeapVector<T, inlineCapacity>& iterator, v8::Handle<v8::Object> creationContext, v8::Isolate* isolate)
+{
+ v8::Local<v8::Array> result = v8::Array::New(isolate, iterator.size());
+ int index = 0;
+ typename HeapVector<T, inlineCapacity>::const_iterator end = iterator.end();
+ typedef V8ValueTraits<T> TraitsType;
+ for (typename HeapVector<T, inlineCapacity>::const_iterator iter = iterator.begin(); iter != end; ++iter)
+ result->Set(v8::Integer::New(isolate, index++), TraitsType::toV8Value(*iter, creationContext, isolate));
+ return result;
+}
+
+template<typename T, size_t inlineCapacity>
+v8::Handle<v8::Value> v8ArrayNoInline(const Vector<T, inlineCapacity>& iterator, v8::Handle<v8::Object> creationContext, v8::Isolate* isolate)
+{
+ v8::Local<v8::Array> result = v8::Array::New(isolate, iterator.size());
+ int index = 0;
+ typename Vector<T, inlineCapacity>::const_iterator end = iterator.end();
+ for (typename Vector<T, inlineCapacity>::const_iterator iter = iterator.begin(); iter != end; ++iter)
+ result->Set(v8::Integer::New(isolate, index++), toV8NoInline(WTF::getPtr(*iter), creationContext, isolate));
+ return result;
+}
+
+template<typename T, size_t inlineCapacity>
+v8::Handle<v8::Value> v8ArrayNoInline(const HeapVector<T, inlineCapacity>& iterator, v8::Handle<v8::Object> creationContext, v8::Isolate* isolate)
+{
+ v8::Local<v8::Array> result = v8::Array::New(isolate, iterator.size());
+ int index = 0;
+ typename HeapVector<T, inlineCapacity>::const_iterator end = iterator.end();
+ for (typename HeapVector<T, inlineCapacity>::const_iterator iter = iterator.begin(); iter != end; ++iter)
+ result->Set(v8::Integer::New(isolate, index++), toV8NoInline(WTF::getPtr(*iter), creationContext, isolate));
+ return result;
+}
+
+// Conversion flags, used in toIntXX/toUIntXX.
+enum IntegerConversionConfiguration {
+ NormalConversion,
+ EnforceRange,
+ Clamp
+};
+
+// Convert a value to a 8-bit signed integer. The conversion fails if the
+// value cannot be converted to a number or the range violated per WebIDL:
+// http://www.w3.org/TR/WebIDL/#es-byte
+int8_t toInt8(v8::Handle<v8::Value>, IntegerConversionConfiguration, ExceptionState&);
+inline int8_t toInt8(v8::Handle<v8::Value> value, ExceptionState& exceptionState)
+{
+ return toInt8(value, NormalConversion, exceptionState);
+}
+
+// Convert a value to a 8-bit integer assuming the conversion cannot fail.
+int8_t toInt8(v8::Handle<v8::Value>);
+
+// Convert a value to a 8-bit unsigned integer. The conversion fails if the
+// value cannot be converted to a number or the range violated per WebIDL:
+// http://www.w3.org/TR/WebIDL/#es-octet
+uint8_t toUInt8(v8::Handle<v8::Value>, IntegerConversionConfiguration, ExceptionState&);
+inline uint8_t toUInt8(v8::Handle<v8::Value> value, ExceptionState& exceptionState)
+{
+ return toUInt8(value, NormalConversion, exceptionState);
+}
+
+// Convert a value to a 8-bit unsigned integer assuming the conversion cannot fail.
+uint8_t toUInt8(v8::Handle<v8::Value>);
+
+// Convert a value to a 16-bit signed integer. The conversion fails if the
+// value cannot be converted to a number or the range violated per WebIDL:
+// http://www.w3.org/TR/WebIDL/#es-short
+int16_t toInt16(v8::Handle<v8::Value>, IntegerConversionConfiguration, ExceptionState&);
+inline int16_t toInt16(v8::Handle<v8::Value> value, ExceptionState& exceptionState)
+{
+ return toInt16(value, NormalConversion, exceptionState);
+}
+
+// Convert a value to a 16-bit integer assuming the conversion cannot fail.
+int16_t toInt16(v8::Handle<v8::Value>);
+
+// Convert a value to a 16-bit unsigned integer. The conversion fails if the
+// value cannot be converted to a number or the range violated per WebIDL:
+// http://www.w3.org/TR/WebIDL/#es-unsigned-short
+uint16_t toUInt16(v8::Handle<v8::Value>, IntegerConversionConfiguration, ExceptionState&);
+inline uint16_t toUInt16(v8::Handle<v8::Value> value, ExceptionState& exceptionState)
+{
+ return toUInt16(value, NormalConversion, exceptionState);
+}
+
+// Convert a value to a 16-bit unsigned integer assuming the conversion cannot fail.
+uint16_t toUInt16(v8::Handle<v8::Value>);
+
+// Convert a value to a 32-bit signed integer. The conversion fails if the
+// value cannot be converted to a number or the range violated per WebIDL:
+// http://www.w3.org/TR/WebIDL/#es-long
+int32_t toInt32(v8::Handle<v8::Value>, IntegerConversionConfiguration, ExceptionState&);
+inline int32_t toInt32(v8::Handle<v8::Value> value, ExceptionState& exceptionState)
+{
+ return toInt32(value, NormalConversion, exceptionState);
+}
+
+// Convert a value to a 32-bit integer assuming the conversion cannot fail.
+int32_t toInt32(v8::Handle<v8::Value>);
+
+// Convert a value to a 32-bit unsigned integer. The conversion fails if the
+// value cannot be converted to a number or the range violated per WebIDL:
+// http://www.w3.org/TR/WebIDL/#es-unsigned-long
+uint32_t toUInt32(v8::Handle<v8::Value>, IntegerConversionConfiguration, ExceptionState&);
+inline uint32_t toUInt32(v8::Handle<v8::Value> value, ExceptionState& exceptionState)
+{
+ return toUInt32(value, NormalConversion, exceptionState);
+}
+
+// Convert a value to a 32-bit unsigned integer assuming the conversion cannot fail.
+uint32_t toUInt32(v8::Handle<v8::Value>);
+
+// Convert a value to a 64-bit signed integer. The conversion fails if the
+// value cannot be converted to a number or the range violated per WebIDL:
+// http://www.w3.org/TR/WebIDL/#es-long-long
+int64_t toInt64(v8::Handle<v8::Value>, IntegerConversionConfiguration, ExceptionState&);
+inline int64_t toInt64(v8::Handle<v8::Value> value, ExceptionState& exceptionState)
+{
+ return toInt64(value, NormalConversion, exceptionState);
+}
+
+// Convert a value to a 64-bit integer assuming the conversion cannot fail.
+int64_t toInt64(v8::Handle<v8::Value>);
+
+// Convert a value to a 64-bit unsigned integer. The conversion fails if the
+// value cannot be converted to a number or the range violated per WebIDL:
+// http://www.w3.org/TR/WebIDL/#es-unsigned-long-long
+uint64_t toUInt64(v8::Handle<v8::Value>, IntegerConversionConfiguration, ExceptionState&);
+inline uint64_t toUInt64(v8::Handle<v8::Value> value, ExceptionState& exceptionState)
+{
+ return toUInt64(value, NormalConversion, exceptionState);
+}
+
+// Convert a value to a 64-bit unsigned integer assuming the conversion cannot fail.
+uint64_t toUInt64(v8::Handle<v8::Value>);
+
+// Convert a value to a single precision float, which might fail.
+float toFloat(v8::Handle<v8::Value>, ExceptionState&);
+
+// Convert a value to a single precision float assuming the conversion cannot fail.
+inline float toFloat(v8::Local<v8::Value> value)
+{
+ return static_cast<float>(value->NumberValue());
+}
+
+// Converts a value to a String, throwing if any code unit is outside 0-255.
+String toByteString(v8::Handle<v8::Value>, ExceptionState&);
+
+// Converts a value to a String, replacing unmatched UTF-16 surrogates with replacement characters.
+String toScalarValueString(v8::Handle<v8::Value>, ExceptionState&);
+
+inline v8::Handle<v8::Boolean> v8Boolean(bool value, v8::Isolate* isolate)
+{
+ return value ? v8::True(isolate) : v8::False(isolate);
+}
+
+inline double toCoreDate(v8::Handle<v8::Value> object)
+{
+ if (object->IsDate())
+ return v8::Handle<v8::Date>::Cast(object)->ValueOf();
+ if (object->IsNumber())
+ return object->NumberValue();
+ return std::numeric_limits<double>::quiet_NaN();
+}
+
+inline v8::Handle<v8::Value> v8DateOrNaN(double value, v8::Isolate* isolate)
+{
+ ASSERT(isolate);
+ return v8::Date::New(isolate, std::isfinite(value) ? value : std::numeric_limits<double>::quiet_NaN());
+}
+
+// FIXME: Remove the special casing for NodeFilter and XPathNSResolver.
+PassRefPtrWillBeRawPtr<NodeFilter> toNodeFilter(v8::Handle<v8::Value>, v8::Handle<v8::Object>, ScriptState*);
+PassRefPtrWillBeRawPtr<XPathNSResolver> toXPathNSResolver(v8::Handle<v8::Value>, v8::Isolate*);
+
+template<class T> struct NativeValueTraits;
+
+template<>
+struct NativeValueTraits<String> {
+ static inline String nativeValue(const v8::Handle<v8::Value>& value, v8::Isolate* isolate)
+ {
+ TOSTRING_DEFAULT(V8StringResource<>, stringValue, value, String());
+ return stringValue;
+ }
+};
+
+template<>
+struct NativeValueTraits<unsigned> {
+ static inline unsigned nativeValue(const v8::Handle<v8::Value>& value, v8::Isolate* isolate)
+ {
+ return toUInt32(value);
+ }
+};
+
+template<>
+struct NativeValueTraits<float> {
+ static inline float nativeValue(const v8::Handle<v8::Value>& value, v8::Isolate* isolate)
{
- v8::Local<v8::Array> result = v8::Array::New(isolate, iterator.size());
- int index = 0;
- typename Vector<T, inlineCapacity>::const_iterator end = iterator.end();
- typedef V8ValueTraits<T> TraitsType;
- for (typename Vector<T, inlineCapacity>::const_iterator iter = iterator.begin(); iter != end; ++iter)
- result->Set(v8::Integer::New(index++, isolate), TraitsType::arrayV8Value(*iter, isolate));
- return result;
+ return static_cast<float>(value->NumberValue());
}
+};
- // Conversion flags, used in toIntXX/toUIntXX.
- enum IntegerConversionConfiguration {
- NormalConversion,
- EnforceRange,
- Clamp
- };
-
- // Convert a value to a 8-bit signed integer. The conversion fails if the
- // value cannot be converted to a number or the range violated per WebIDL:
- // http://www.w3.org/TR/WebIDL/#es-byte
- int8_t toInt8(v8::Handle<v8::Value>, IntegerConversionConfiguration, bool& ok);
- inline int8_t toInt8(v8::Handle<v8::Value> value, bool& ok) { return toInt8(value, NormalConversion, ok); }
-
- // Convert a value to a 8-bit integer assuming the conversion cannot fail.
- inline int8_t toInt8(v8::Handle<v8::Value> value)
+template<>
+struct NativeValueTraits<double> {
+ static inline double nativeValue(const v8::Handle<v8::Value>& value, v8::Isolate* isolate)
{
- bool ok;
- return toInt8(value, NormalConversion, ok);
+ return static_cast<double>(value->NumberValue());
}
+};
- // Convert a value to a 8-bit unsigned integer. The conversion fails if the
- // value cannot be converted to a number or the range violated per WebIDL:
- // http://www.w3.org/TR/WebIDL/#es-octet
- uint8_t toUInt8(v8::Handle<v8::Value>, IntegerConversionConfiguration, bool& ok);
- inline uint8_t toUInt8(v8::Handle<v8::Value> value, bool& ok) { return toUInt8(value, NormalConversion, ok); }
-
- // Convert a value to a 8-bit unsigned integer assuming the conversion cannot fail.
- inline uint8_t toUInt8(v8::Handle<v8::Value> value)
+template<>
+struct NativeValueTraits<v8::Handle<v8::Value> > {
+ static inline v8::Handle<v8::Value> nativeValue(const v8::Handle<v8::Value>& value, v8::Isolate* isolate)
{
- bool ok;
- return toUInt8(value, NormalConversion, ok);
+ return value;
}
+};
- // Convert a value to a 16-bit signed integer. The conversion fails if the
- // value cannot be converted to a number or the range violated per WebIDL:
- // http://www.w3.org/TR/WebIDL/#es-short
- int16_t toInt16(v8::Handle<v8::Value>, IntegerConversionConfiguration, bool& ok);
- inline int16_t toInt16(v8::Handle<v8::Value> value, bool& ok) { return toInt16(value, NormalConversion, ok); }
+v8::Handle<v8::Value> toV8Sequence(v8::Handle<v8::Value>, uint32_t& length, v8::Isolate*);
- // Convert a value to a 16-bit integer assuming the conversion cannot fail.
- inline int16_t toInt16(v8::Handle<v8::Value> value)
- {
- bool ok;
- return toInt16(value, NormalConversion, ok);
+// Converts a JavaScript value to an array as per the Web IDL specification:
+// http://www.w3.org/TR/2012/CR-WebIDL-20120419/#es-array
+template <class T, class V8T>
+Vector<RefPtr<T> > toRefPtrNativeArrayUnchecked(v8::Local<v8::Value> v8Value, uint32_t length, v8::Isolate* isolate, bool* success = 0)
+{
+ Vector<RefPtr<T> > result;
+ result.reserveInitialCapacity(length);
+ v8::Local<v8::Object> object = v8::Local<v8::Object>::Cast(v8Value);
+ for (uint32_t i = 0; i < length; ++i) {
+ v8::Handle<v8::Value> element = object->Get(i);
+ if (V8T::hasInstance(element, isolate)) {
+ v8::Handle<v8::Object> elementObject = v8::Handle<v8::Object>::Cast(element);
+ result.uncheckedAppend(V8T::toNative(elementObject));
+ } else {
+ if (success)
+ *success = false;
+ throwTypeError("Invalid Array element type", isolate);
+ return Vector<RefPtr<T> >();
+ }
}
-
- // Convert a value to a 16-bit unsigned integer. The conversion fails if the
- // value cannot be converted to a number or the range violated per WebIDL:
- // http://www.w3.org/TR/WebIDL/#es-unsigned-short
- uint16_t toUInt16(v8::Handle<v8::Value>, IntegerConversionConfiguration, bool& ok);
- inline uint16_t toUInt16(v8::Handle<v8::Value> value, bool& ok) { return toUInt16(value, NormalConversion, ok); }
-
- // Convert a value to a 16-bit unsigned integer assuming the conversion cannot fail.
- inline uint16_t toUInt16(v8::Handle<v8::Value> value)
- {
- bool ok;
- return toUInt16(value, NormalConversion, ok);
+ return result;
+}
+
+template <class T, class V8T>
+Vector<RefPtr<T> > toRefPtrNativeArray(v8::Handle<v8::Value> value, int argumentIndex, v8::Isolate* isolate, bool* success = 0)
+{
+ if (success)
+ *success = true;
+
+ v8::Local<v8::Value> v8Value(v8::Local<v8::Value>::New(isolate, value));
+ uint32_t length = 0;
+ if (value->IsArray()) {
+ length = v8::Local<v8::Array>::Cast(v8Value)->Length();
+ } else if (toV8Sequence(value, length, isolate).IsEmpty()) {
+ throwTypeError(ExceptionMessages::notAnArrayTypeArgumentOrValue(argumentIndex), isolate);
+ return Vector<RefPtr<T> >();
+ }
+ return toRefPtrNativeArrayUnchecked<T, V8T>(v8Value, length, isolate, success);
+}
+
+template <class T, class V8T>
+Vector<RefPtr<T> > toRefPtrNativeArray(v8::Handle<v8::Value> value, const String& propertyName, v8::Isolate* isolate, bool* success = 0)
+{
+ if (success)
+ *success = true;
+
+ v8::Local<v8::Value> v8Value(v8::Local<v8::Value>::New(isolate, value));
+ uint32_t length = 0;
+ if (value->IsArray()) {
+ length = v8::Local<v8::Array>::Cast(v8Value)->Length();
+ } else if (toV8Sequence(value, length, isolate).IsEmpty()) {
+ throwTypeError(ExceptionMessages::notASequenceTypeProperty(propertyName), isolate);
+ return Vector<RefPtr<T> >();
+ }
+ return toRefPtrNativeArrayUnchecked<T, V8T>(v8Value, length, isolate, success);
+}
+
+template <class T, class V8T>
+WillBeHeapVector<RefPtrWillBeMember<T> > toRefPtrWillBeMemberNativeArray(v8::Handle<v8::Value> value, int argumentIndex, v8::Isolate* isolate, bool* success = 0)
+{
+ if (success)
+ *success = true;
+
+ v8::Local<v8::Value> v8Value(v8::Local<v8::Value>::New(isolate, value));
+ uint32_t length = 0;
+ if (value->IsArray()) {
+ length = v8::Local<v8::Array>::Cast(v8Value)->Length();
+ } else if (toV8Sequence(value, length, isolate).IsEmpty()) {
+ throwTypeError(ExceptionMessages::notAnArrayTypeArgumentOrValue(argumentIndex), isolate);
+ return WillBeHeapVector<RefPtrWillBeMember<T> >();
+ }
+
+ WillBeHeapVector<RefPtrWillBeMember<T> > result;
+ result.reserveInitialCapacity(length);
+ v8::Local<v8::Object> object = v8::Local<v8::Object>::Cast(v8Value);
+ for (uint32_t i = 0; i < length; ++i) {
+ v8::Handle<v8::Value> element = object->Get(i);
+ if (V8T::hasInstance(element, isolate)) {
+ v8::Handle<v8::Object> elementObject = v8::Handle<v8::Object>::Cast(element);
+ result.uncheckedAppend(V8T::toNative(elementObject));
+ } else {
+ if (success)
+ *success = false;
+ throwTypeError("Invalid Array element type", isolate);
+ return WillBeHeapVector<RefPtrWillBeMember<T> >();
+ }
}
-
- // Convert a value to a 32-bit signed integer. The conversion fails if the
- // value cannot be converted to a number or the range violated per WebIDL:
- // http://www.w3.org/TR/WebIDL/#es-long
- int32_t toInt32(v8::Handle<v8::Value>, IntegerConversionConfiguration, bool& ok);
- inline int32_t toInt32(v8::Handle<v8::Value> value, bool& ok) { return toInt32(value, NormalConversion, ok); }
-
- // Convert a value to a 32-bit integer assuming the conversion cannot fail.
- inline int32_t toInt32(v8::Handle<v8::Value> value)
+ return result;
+}
+
+// Converts a JavaScript value to an array as per the Web IDL specification:
+// http://www.w3.org/TR/2012/CR-WebIDL-20120419/#es-array
+template <class T>
+Vector<T> toNativeArray(v8::Handle<v8::Value> value, int argumentIndex, v8::Isolate* isolate)
+{
+ v8::Local<v8::Value> v8Value(v8::Local<v8::Value>::New(isolate, value));
+ uint32_t length = 0;
+ if (value->IsArray()) {
+ length = v8::Local<v8::Array>::Cast(v8Value)->Length();
+ } else if (toV8Sequence(value, length, isolate).IsEmpty()) {
+ throwTypeError(ExceptionMessages::notAnArrayTypeArgumentOrValue(argumentIndex), isolate);
+ return Vector<T>();
+ }
+
+ Vector<T> result;
+ result.reserveInitialCapacity(length);
+ typedef NativeValueTraits<T> TraitsType;
+ v8::Local<v8::Object> object = v8::Local<v8::Object>::Cast(v8Value);
+ for (uint32_t i = 0; i < length; ++i)
+ result.uncheckedAppend(TraitsType::nativeValue(object->Get(i), isolate));
+ return result;
+}
+
+template <class T>
+Vector<T> toNativeArguments(const v8::FunctionCallbackInfo<v8::Value>& info, int startIndex)
+{
+ ASSERT(startIndex <= info.Length());
+ Vector<T> result;
+ typedef NativeValueTraits<T> TraitsType;
+ int length = info.Length();
+ result.reserveInitialCapacity(length);
+ for (int i = startIndex; i < length; ++i)
+ result.uncheckedAppend(TraitsType::nativeValue(info[i], info.GetIsolate()));
+ return result;
+}
+
+// Validates that the passed object is a sequence type per WebIDL spec
+// http://www.w3.org/TR/2012/CR-WebIDL-20120419/#es-sequence
+inline v8::Handle<v8::Value> toV8Sequence(v8::Handle<v8::Value> value, uint32_t& length, v8::Isolate* isolate)
+{
+ // Attempt converting to a sequence if the value is not already an array but is
+ // any kind of object except for a native Date object or a native RegExp object.
+ ASSERT(!value->IsArray());
+ // FIXME: Do we really need to special case Date and RegExp object?
+ // https://www.w3.org/Bugs/Public/show_bug.cgi?id=22806
+ if (!value->IsObject() || value->IsDate() || value->IsRegExp()) {
+ // The caller is responsible for reporting a TypeError.
+ return v8Undefined();
+ }
+
+ v8::Local<v8::Value> v8Value(v8::Local<v8::Value>::New(isolate, value));
+ v8::Local<v8::Object> object = v8::Local<v8::Object>::Cast(v8Value);
+ v8::Local<v8::String> lengthSymbol = v8AtomicString(isolate, "length");
+
+ // FIXME: The specification states that the length property should be used as fallback, if value
+ // is not a platform object that supports indexed properties. If it supports indexed properties,
+ // length should actually be one greater than value’s maximum indexed property index.
+ TONATIVE_EXCEPTION(v8::Local<v8::Value>, lengthValue, object->Get(lengthSymbol));
+
+ if (lengthValue->IsUndefined() || lengthValue->IsNull()) {
+ // The caller is responsible for reporting a TypeError.
+ return v8Undefined();
+ }
+
+ TONATIVE_EXCEPTION(uint32_t, sequenceLength, lengthValue->Int32Value());
+ length = sequenceLength;
+ return v8Value;
+}
+
+v8::Isolate* toIsolate(ExecutionContext*);
+v8::Isolate* toIsolate(LocalFrame*);
+
+LocalDOMWindow* toDOMWindow(v8::Handle<v8::Value>, v8::Isolate*);
+LocalDOMWindow* toDOMWindow(v8::Handle<v8::Context>);
+LocalDOMWindow* enteredDOMWindow(v8::Isolate*);
+LocalDOMWindow* currentDOMWindow(v8::Isolate*);
+LocalDOMWindow* callingDOMWindow(v8::Isolate*);
+ExecutionContext* toExecutionContext(v8::Handle<v8::Context>);
+ExecutionContext* currentExecutionContext(v8::Isolate*);
+ExecutionContext* callingExecutionContext(v8::Isolate*);
+
+// Returns a V8 context associated with a ExecutionContext and a DOMWrapperWorld.
+// This method returns an empty context if there is no frame or the frame is already detached.
+v8::Local<v8::Context> toV8Context(ExecutionContext*, DOMWrapperWorld&);
+// Returns a V8 context associated with a LocalFrame and a DOMWrapperWorld.
+// This method returns an empty context if the frame is already detached.
+v8::Local<v8::Context> toV8Context(LocalFrame*, DOMWrapperWorld&);
+
+// Returns the frame object of the window object associated with
+// a context, if the window is currently being displayed in the LocalFrame.
+LocalFrame* toFrameIfNotDetached(v8::Handle<v8::Context>);
+
+// If the current context causes out of memory, JavaScript setting
+// is disabled and it returns true.
+bool handleOutOfMemory();
+v8::Local<v8::Value> handleMaxRecursionDepthExceeded(v8::Isolate*);
+void crashIfV8IsDead();
+
+inline bool isUndefinedOrNull(v8::Handle<v8::Value> value)
+{
+ return value->IsNull() || value->IsUndefined();
+}
+v8::Handle<v8::Function> getBoundFunction(v8::Handle<v8::Function>);
+
+// Attaches |environment| to |function| and returns it.
+inline v8::Local<v8::Function> createClosure(v8::FunctionCallback function, v8::Handle<v8::Value> environment, v8::Isolate* isolate)
+{
+ return v8::Function::New(isolate, function, environment);
+}
+
+// FIXME: This will be soon embedded in the generated code.
+template<class Collection> static void indexedPropertyEnumerator(const v8::PropertyCallbackInfo<v8::Array>& info)
+{
+ Collection* collection = reinterpret_cast<Collection*>(info.Holder()->GetAlignedPointerFromInternalField(v8DOMWrapperObjectIndex));
+ int length = collection->length();
+ v8::Handle<v8::Array> properties = v8::Array::New(info.GetIsolate(), length);
+ for (int i = 0; i < length; ++i) {
+ // FIXME: Do we need to check that the item function returns a non-null value for this index?
+ v8::Handle<v8::Integer> integer = v8::Integer::New(info.GetIsolate(), i);
+ properties->Set(integer, integer);
+ }
+ v8SetReturnValue(info, properties);
+}
+
+// These methods store hidden values into an array that is stored in the internal field of a DOM wrapper.
+void addHiddenValueToArray(v8::Handle<v8::Object>, v8::Local<v8::Value>, int cacheIndex, v8::Isolate*);
+void removeHiddenValueFromArray(v8::Handle<v8::Object>, v8::Local<v8::Value>, int cacheIndex, v8::Isolate*);
+void moveEventListenerToNewWrapper(v8::Handle<v8::Object>, EventListener* oldValue, v8::Local<v8::Value> newValue, int cacheIndex, v8::Isolate*);
+
+PassRefPtr<JSONValue> v8ToJSONValue(v8::Isolate*, v8::Handle<v8::Value>, int);
+
+// Converts a DOM object to a v8 value.
+// This is a no-inline version of toV8(). If you want to call toV8()
+// without creating #include cycles, you can use this function instead.
+// Each specialized implementation will be generated.
+template<typename T>
+v8::Handle<v8::Value> toV8NoInline(T* impl, v8::Handle<v8::Object> creationContext, v8::Isolate*);
+
+// ToV8Value<U, Context> is a class that converts a C++ object to a
+// v8 value. U has to be a class having a static method getCreationContext
+// which returns an object created from a target context.
+template<typename U, typename Context>
+class ToV8Value {
+public:
+ template<typename T>
+ static v8::Handle<v8::Value> toV8Value(const T& value, Context context, v8::Isolate* isolate)
{
- bool ok;
- return toInt32(value, NormalConversion, ok);
+ // Default implementaion: for types that don't need the context.
+ return V8ValueTraits<T>::toV8Value(value, context, isolate);
}
- // Convert a value to a 32-bit unsigned integer. The conversion fails if the
- // value cannot be converted to a number or the range violated per WebIDL:
- // http://www.w3.org/TR/WebIDL/#es-unsigned-long
- uint32_t toUInt32(v8::Handle<v8::Value>, IntegerConversionConfiguration, bool& ok);
- inline uint32_t toUInt32(v8::Handle<v8::Value> value, bool& ok) { return toUInt32(value, NormalConversion, ok); }
-
- // Convert a value to a 32-bit unsigned integer assuming the conversion cannot fail.
- inline uint32_t toUInt32(v8::Handle<v8::Value> value)
+ // Pointer specializations.
+ template<typename T>
+ static v8::Handle<v8::Value> toV8Value(T* const& value, Context context, v8::Isolate* isolate)
{
- bool ok;
- return toUInt32(value, NormalConversion, ok);
+ return toV8NoInline(value, context, isolate);
}
-
- // Convert a value to a 64-bit signed integer. The conversion fails if the
- // value cannot be converted to a number or the range violated per WebIDL:
- // http://www.w3.org/TR/WebIDL/#es-long-long
- int64_t toInt64(v8::Handle<v8::Value>, IntegerConversionConfiguration, bool& ok);
-
- // Convert a value to a 64-bit integer assuming the conversion cannot fail.
- inline int64_t toInt64(v8::Handle<v8::Value> value)
+ template<typename T>
+ static v8::Handle<v8::Value> toV8Value(const RefPtr<T>& value, Context context, v8::Isolate* isolate)
{
- bool ok;
- return toInt64(value, NormalConversion, ok);
+ return toV8Value(value.get(), context, isolate);
}
-
- // Convert a value to a 64-bit unsigned integer. The conversion fails if the
- // value cannot be converted to a number or the range violated per WebIDL:
- // http://www.w3.org/TR/WebIDL/#es-unsigned-long-long
- uint64_t toUInt64(v8::Handle<v8::Value>, IntegerConversionConfiguration, bool& ok);
-
- // Convert a value to a 64-bit unsigned integer assuming the conversion cannot fail.
- inline uint64_t toUInt64(v8::Handle<v8::Value> value)
+ template<typename T>
+ static v8::Handle<v8::Value> toV8Value(const PassRefPtr<T>& value, Context context, v8::Isolate* isolate)
{
- bool ok;
- return toUInt64(value, NormalConversion, ok);
+ return toV8Value(value.get(), context, isolate);
}
-
- inline float toFloat(v8::Local<v8::Value> value)
+ template<typename T>
+ static v8::Handle<v8::Value> toV8Value(const OwnPtr<T>& value, Context context, v8::Isolate* isolate)
{
- return static_cast<float>(value->NumberValue());
- }
-
- WrapperWorldType worldType(v8::Isolate*);
- WrapperWorldType worldTypeInMainThread(v8::Isolate*);
-
- DOMWrapperWorld* isolatedWorldForIsolate(v8::Isolate*);
-
- template<class T> struct NativeValueTraits;
-
- template<>
- struct NativeValueTraits<String> {
- static inline String nativeValue(const v8::Handle<v8::Value>& value, v8::Isolate* isolate)
- {
- V8TRYCATCH_FOR_V8STRINGRESOURCE_RETURN(V8StringResource<>, stringValue, value, String());
- return stringValue;
- }
- };
-
- template<>
- struct NativeValueTraits<unsigned> {
- static inline unsigned nativeValue(const v8::Handle<v8::Value>& value, v8::Isolate* isolate)
- {
- return toUInt32(value);
- }
- };
-
- template<>
- struct NativeValueTraits<float> {
- static inline float nativeValue(const v8::Handle<v8::Value>& value, v8::Isolate* isolate)
- {
- return static_cast<float>(value->NumberValue());
- }
- };
-
- template<>
- struct NativeValueTraits<double> {
- static inline double nativeValue(const v8::Handle<v8::Value>& value, v8::Isolate* isolate)
- {
- return static_cast<double>(value->NumberValue());
- }
- };
-
- template<>
- struct NativeValueTraits<v8::Handle<v8::Value> > {
- static inline v8::Handle<v8::Value> nativeValue(const v8::Handle<v8::Value>& value, v8::Isolate* isolate)
- {
- return value;
- }
- };
-
- // Converts a JavaScript value to an array as per the Web IDL specification:
- // http://www.w3.org/TR/2012/CR-WebIDL-20120419/#es-array
- template <class T, class V8T>
- Vector<RefPtr<T> > toRefPtrNativeArrayUnchecked(v8::Local<v8::Value> v8Value, uint32_t length, v8::Isolate* isolate, bool* success = 0)
- {
- Vector<RefPtr<T> > result;
- result.reserveInitialCapacity(length);
- v8::Local<v8::Object> object = v8::Local<v8::Object>::Cast(v8Value);
- for (uint32_t i = 0; i < length; ++i) {
- v8::Handle<v8::Value> element = object->Get(i);
-
- if (V8T::hasInstance(element, isolate, worldType(isolate))) {
- v8::Handle<v8::Object> elementObject = v8::Handle<v8::Object>::Cast(element);
- result.uncheckedAppend(V8T::toNative(elementObject));
- } else {
- if (success)
- *success = false;
- throwTypeError("Invalid Array element type", isolate);
- return Vector<RefPtr<T> >();
- }
- }
- return result;
+ return toV8Value(value.get(), context, isolate);
}
-
- template <class T, class V8T>
- Vector<RefPtr<T> > toRefPtrNativeArray(v8::Handle<v8::Value> value, int argumentIndex, v8::Isolate* isolate, bool* success = 0)
+ template<typename T>
+ static v8::Handle<v8::Value> toV8Value(const PassOwnPtr<T>& value, Context context, v8::Isolate* isolate)
{
- if (success)
- *success = true;
-
- v8::Local<v8::Value> v8Value(v8::Local<v8::Value>::New(isolate, value));
- uint32_t length = 0;
- if (value->IsArray()) {
- length = v8::Local<v8::Array>::Cast(v8Value)->Length();
- } else if (toV8Sequence(value, length, isolate).IsEmpty()) {
- throwTypeError(ExceptionMessages::notAnArrayTypeArgumentOrValue(argumentIndex), isolate);
- return Vector<RefPtr<T> >();
- }
-
- return toRefPtrNativeArrayUnchecked<T, V8T>(v8Value, length, isolate, success);
+ return toV8Value(value.get(), context, isolate);
}
-
- template <class T, class V8T>
- Vector<RefPtr<T> > toRefPtrNativeArray(v8::Handle<v8::Value> value, const String& propertyName, v8::Isolate* isolate, bool* success = 0)
+ template<typename T>
+ static v8::Handle<v8::Value> toV8Value(const RawPtr<T>& value, Context context, v8::Isolate* isolate)
{
- if (success)
- *success = true;
-
- v8::Local<v8::Value> v8Value(v8::Local<v8::Value>::New(isolate, value));
- uint32_t length = 0;
- if (value->IsArray()) {
- length = v8::Local<v8::Array>::Cast(v8Value)->Length();
- } else if (toV8Sequence(value, length, isolate).IsEmpty()) {
- throwTypeError(ExceptionMessages::notASequenceTypeProperty(propertyName), isolate);
- return Vector<RefPtr<T> >();
- }
-
- return toRefPtrNativeArrayUnchecked<T, V8T>(v8Value, length, isolate, success);
+ return toV8Value(value.get(), context, isolate);
}
- // Converts a JavaScript value to an array as per the Web IDL specification:
- // http://www.w3.org/TR/2012/CR-WebIDL-20120419/#es-array
- template <class T>
- Vector<T> toNativeArray(v8::Handle<v8::Value> value, int argumentIndex, v8::Isolate* isolate)
+ // const char* should use V8ValueTraits.
+ static v8::Handle<v8::Value> toV8Value(const char* const& value, Context context, v8::Isolate* isolate)
{
- v8::Local<v8::Value> v8Value(v8::Local<v8::Value>::New(isolate, value));
- uint32_t length = 0;
- if (value->IsArray()) {
- length = v8::Local<v8::Array>::Cast(v8Value)->Length();
- } else if (toV8Sequence(value, length, isolate).IsEmpty()) {
- throwTypeError(ExceptionMessages::notAnArrayTypeArgumentOrValue(argumentIndex), isolate);
- return Vector<T>();
- }
-
- Vector<T> result;
- result.reserveInitialCapacity(length);
- typedef NativeValueTraits<T> TraitsType;
- v8::Local<v8::Object> object = v8::Local<v8::Object>::Cast(v8Value);
- for (uint32_t i = 0; i < length; ++i)
- result.uncheckedAppend(TraitsType::nativeValue(object->Get(i), isolate));
- return result;
- }
-
- template <class T>
- Vector<T> toNativeArguments(const v8::FunctionCallbackInfo<v8::Value>& info, int startIndex)
- {
- ASSERT(startIndex <= info.Length());
- Vector<T> result;
- typedef NativeValueTraits<T> TraitsType;
- int length = info.Length();
- result.reserveInitialCapacity(length);
- for (int i = startIndex; i < length; ++i)
- result.uncheckedAppend(TraitsType::nativeValue(info[i], info.GetIsolate()));
- return result;
- }
-
- // Validates that the passed object is a sequence type per WebIDL spec
- // http://www.w3.org/TR/2012/CR-WebIDL-20120419/#es-sequence
- inline v8::Handle<v8::Value> toV8Sequence(v8::Handle<v8::Value> value, uint32_t& length, v8::Isolate* isolate)
- {
- // Attempt converting to a sequence if the value is not already an array but is
- // any kind of object except for a native Date object or a native RegExp object.
- ASSERT(!value->IsArray());
- // FIXME: Do we really need to special case Date and RegExp object?
- // https://www.w3.org/Bugs/Public/show_bug.cgi?id=22806
- if (!value->IsObject() || value->IsDate() || value->IsRegExp()) {
- // The caller is responsible for reporting a TypeError.
- return v8Undefined();
- }
-
- v8::Local<v8::Value> v8Value(v8::Local<v8::Value>::New(isolate, value));
- v8::Local<v8::Object> object = v8::Local<v8::Object>::Cast(v8Value);
- v8::Local<v8::String> lengthSymbol = v8::String::NewFromUtf8(isolate, "length", v8::String::kInternalizedString, 6);
-
- // FIXME: The specification states that the length property should be used as fallback, if value
- // is not a platform object that supports indexed properties. If it supports indexed properties,
- // length should actually be one greater than value’s maximum indexed property index.
- V8TRYCATCH(v8::Local<v8::Value>, lengthValue, object->Get(lengthSymbol));
-
- if (lengthValue->IsUndefined() || lengthValue->IsNull()) {
- // The caller is responsible for reporting a TypeError.
- return v8Undefined();
- }
-
- V8TRYCATCH(uint32_t, sequenceLength, lengthValue->Int32Value());
- length = sequenceLength;
-
- return v8Value;
+ return V8ValueTraits<const char*>::toV8Value(value, context, isolate);
}
- PassRefPtr<NodeFilter> toNodeFilter(v8::Handle<v8::Value>, v8::Isolate*);
-
- inline bool isUndefinedOrNull(v8::Handle<v8::Value> value)
+ template<typename T, size_t inlineCapacity>
+ static v8::Handle<v8::Value> toV8Value(const Vector<T, inlineCapacity>& value, Context context, v8::Isolate* isolate)
{
- return value->IsNull() || value->IsUndefined();
+ return v8ArrayNoInline(value, context, isolate);
}
- // Returns true if the provided object is to be considered a 'host object', as used in the
- // HTML5 structured clone algorithm.
- inline bool isHostObject(v8::Handle<v8::Object> object)
+ template<typename T, size_t inlineCapacity>
+ static v8::Handle<v8::Value> toV8Value(const HeapVector<T, inlineCapacity>& value, Context context, v8::Isolate* isolate)
{
- // If the object has any internal fields, then we won't be able to serialize or deserialize
- // them; conveniently, this is also a quick way to detect DOM wrapper objects, because
- // the mechanism for these relies on data stored in these fields. We should
- // catch external array data as a special case.
- return object->InternalFieldCount() || object->HasIndexedPropertiesInExternalArrayData();
+ return v8ArrayNoInline(value, context, isolate);
}
- inline v8::Handle<v8::Boolean> v8Boolean(bool value, v8::Isolate* isolate)
+ template<typename T, size_t inlineCapacity>
+ static v8::Handle<v8::Value> toV8Value(const PersistentHeapVector<T, inlineCapacity>& value, Context context, v8::Isolate* isolate)
{
- return value ? v8::True(isolate) : v8::False(isolate);
+ return v8ArrayNoInline(static_cast<HeapVector<T, inlineCapacity> >(value), context, isolate);
}
+};
- // Since v8Boolean(value, isolate) crashes if we pass a null isolate,
- // we need to use v8BooleanWithCheck(value, isolate) if an isolate can be null.
- //
- // FIXME: Remove all null isolates from V8 bindings, and remove v8BooleanWithCheck(value, isolate).
- inline v8::Handle<v8::Boolean> v8BooleanWithCheck(bool value, v8::Isolate* isolate)
- {
- return isolate ? v8Boolean(value, isolate) : v8Boolean(value, v8::Isolate::GetCurrent());
- }
+// Result values for platform object 'deleter' methods,
+// http://www.w3.org/TR/WebIDL/#delete
+enum DeleteResult {
+ DeleteSuccess,
+ DeleteReject,
+ DeleteUnknownProperty
+};
- inline double toWebCoreDate(v8::Handle<v8::Value> object)
- {
- if (object->IsDate())
- return v8::Handle<v8::Date>::Cast(object)->ValueOf();
- if (object->IsNumber())
- return object->NumberValue();
- return std::numeric_limits<double>::quiet_NaN();
- }
+class V8IsolateInterruptor : public ThreadState::Interruptor {
+public:
+ explicit V8IsolateInterruptor(v8::Isolate* isolate) : m_isolate(isolate) { }
- inline v8::Handle<v8::Value> v8DateOrNull(double value, v8::Isolate* isolate)
+ static void onInterruptCallback(v8::Isolate* isolate, void* data)
{
- ASSERT(isolate);
- return std::isfinite(value) ? v8::Date::New(isolate, value) : v8::Handle<v8::Value>::Cast(v8::Null(isolate));
+ reinterpret_cast<V8IsolateInterruptor*>(data)->onInterrupted();
}
- inline v8::Handle<v8::String> v8AtomicString(v8::Isolate* isolate, const char* str)
+ virtual void requestInterrupt() OVERRIDE
{
- ASSERT(isolate);
- return v8::String::NewFromUtf8(isolate, str, v8::String::kInternalizedString, strlen(str));
+ m_isolate->RequestInterrupt(&onInterruptCallback, this);
}
- inline v8::Handle<v8::String> v8AtomicString(v8::Isolate* isolate, const char* str, size_t length)
+ virtual void clearInterrupt() OVERRIDE
{
- ASSERT(isolate);
- return v8::String::NewFromUtf8(isolate, str, v8::String::kInternalizedString, length);
+ m_isolate->ClearInterrupt();
}
+private:
+ v8::Isolate* m_isolate;
+};
- v8::Handle<v8::FunctionTemplate> createRawTemplate(v8::Isolate*);
-
- PassRefPtr<XPathNSResolver> toXPathNSResolver(v8::Handle<v8::Value>, v8::Isolate*);
+class V8TestingScope {
+public:
+ explicit V8TestingScope(v8::Isolate*);
+ ScriptState* scriptState() const;
+ v8::Isolate* isolate() const;
+ ~V8TestingScope();
- v8::Handle<v8::Object> toInnerGlobalObject(v8::Handle<v8::Context>);
- DOMWindow* toDOMWindow(v8::Handle<v8::Context>);
- ExecutionContext* toExecutionContext(v8::Handle<v8::Context>);
+private:
+ v8::HandleScope m_handleScope;
+ v8::Context::Scope m_contextScope;
+ RefPtr<ScriptState> m_scriptState;
+};
- DOMWindow* activeDOMWindow();
- ExecutionContext* activeExecutionContext();
- DOMWindow* firstDOMWindow();
- Document* currentDocument();
+void GetDevToolsFunctionInfo(v8::Handle<v8::Function>, v8::Isolate*, int& scriptId, String& resourceName, int& lineNumber);
+PassRefPtr<TraceEvent::ConvertableToTraceFormat> devToolsTraceEventData(ExecutionContext*, v8::Handle<v8::Function>, v8::Isolate*);
- // Returns the context associated with a ExecutionContext.
- v8::Local<v8::Context> toV8Context(ExecutionContext*, DOMWrapperWorld*);
-
- // Returns the frame object of the window object associated with
- // a context, if the window is currently being displayed in the Frame.
- Frame* toFrameIfNotDetached(v8::Handle<v8::Context>);
-
- inline DOMWrapperWorld* isolatedWorldForEnteredContext(v8::Isolate* isolate)
+class V8RethrowTryCatchScope FINAL {
+public:
+ explicit V8RethrowTryCatchScope(v8::TryCatch& block) : m_block(block) { }
+ ~V8RethrowTryCatchScope()
{
- v8::Handle<v8::Context> context = isolate->GetEnteredContext();
- if (context.IsEmpty())
- return 0;
- return DOMWrapperWorld::isolatedWorld(context);
+ // ReThrow() is a no-op if no exception has been caught, so always call.
+ m_block.ReThrow();
}
- // FIXME: This will be soon embedded in the generated code.
- template<class Collection> static void indexedPropertyEnumerator(const v8::PropertyCallbackInfo<v8::Array>& info)
- {
- Collection* collection = reinterpret_cast<Collection*>(info.Holder()->GetAlignedPointerFromInternalField(v8DOMWrapperObjectIndex));
- int length = collection->length();
- v8::Handle<v8::Array> properties = v8::Array::New(info.GetIsolate(), length);
- for (int i = 0; i < length; ++i) {
- // FIXME: Do we need to check that the item function returns a non-null value for this index?
- v8::Handle<v8::Integer> integer = v8::Integer::New(i, info.GetIsolate());
- properties->Set(integer, integer);
- }
- v8SetReturnValue(info, properties);
- }
-
- // If the current context causes out of memory, JavaScript setting
- // is disabled and it returns true.
- bool handleOutOfMemory();
- v8::Local<v8::Value> handleMaxRecursionDepthExceeded(v8::Isolate*);
-
- void crashIfV8IsDead();
+private:
+ v8::TryCatch& m_block;
+};
- template <class T>
- v8::Handle<T> unsafeHandleFromRawValue(const T* value)
+class V8ResetTryCatchScope FINAL {
+public:
+ explicit V8ResetTryCatchScope(v8::TryCatch& block) : m_block(block) { }
+ ~V8ResetTryCatchScope()
{
- const v8::Handle<T>* handle = reinterpret_cast<const v8::Handle<T>*>(&value);
- return *handle;
+ m_block.Reset();
}
- // Attaches |environment| to |function| and returns it.
- inline v8::Local<v8::Function> createClosure(v8::FunctionCallback function, v8::Handle<v8::Value> environment, v8::Isolate* isolate)
- {
- return v8::Function::New(isolate, function, environment);
- }
-
- v8::Local<v8::Value> getHiddenValueFromMainWorldWrapper(v8::Isolate*, ScriptWrappable*, v8::Handle<v8::String> key);
+private:
+ v8::TryCatch& m_block;
+};
- v8::Isolate* mainThreadIsolate();
- v8::Isolate* toIsolate(ExecutionContext*);
- v8::Isolate* toIsolate(Frame*);
-
- // Can only be called by blink::initialize
- void setMainThreadIsolate(v8::Isolate*);
-
- // Converts a DOM object to a v8 value.
- // This is a no-inline version of toV8(). If you want to call toV8()
- // without creating #include cycles, you can use this function instead.
- // Each specialized implementation will be generated.
- template<typename T>
- v8::Handle<v8::Value> toV8NoInline(T* impl, v8::Handle<v8::Object> creationContext, v8::Isolate*);
} // namespace WebCore
#endif // V8Binding_h
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8BindingMacros.h b/chromium/third_party/WebKit/Source/bindings/v8/V8BindingMacros.h
index 8098652e209..1abb3233b80 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8BindingMacros.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8BindingMacros.h
@@ -33,65 +33,84 @@
namespace WebCore {
-#define V8TRYCATCH(type, var, value) \
- type var; \
- { \
- v8::TryCatch block; \
- var = (value); \
- if (block.HasCaught()) \
- return block.ReThrow(); \
+// Naming scheme:
+// TO*_RETURNTYPE[_ARGTYPE]...
+// ...using _DEFAULT instead of _ANY..._ANY when returing a default value.
+
+#define TONATIVE_EXCEPTION(type, var, value) \
+ type var; \
+ { \
+ v8::TryCatch block; \
+ var = (value); \
+ if (UNLIKELY(block.HasCaught())) \
+ return block.ReThrow(); \
}
-#define V8TRYCATCH_RETURN(type, var, value, retVal) \
- type var; \
- { \
- v8::TryCatch block; \
- var = (value); \
- if (block.HasCaught()) { \
- block.ReThrow(); \
- return retVal; \
- } \
+#define TONATIVE_VOID_INTERNAL(var, value) \
+ var = (value); \
+ if (UNLIKELY(block.HasCaught())) \
+ return;
+
+#define TONATIVE_VOID(type, var, value) \
+ type var; \
+ { \
+ v8::TryCatch block; \
+ V8RethrowTryCatchScope rethrow(block); \
+ TONATIVE_VOID_INTERNAL(var, value); \
}
-#define V8TRYCATCH_VOID(type, var, value) \
- type var; \
- { \
- v8::TryCatch block; \
- var = (value); \
- if (block.HasCaught()) { \
- block.ReThrow(); \
- return; \
- } \
+#define TONATIVE_DEFAULT(type, var, value, retVal) \
+ type var; \
+ { \
+ v8::TryCatch block; \
+ var = (value); \
+ if (UNLIKELY(block.HasCaught())) { \
+ block.ReThrow(); \
+ return retVal; \
+ } \
}
-#define V8TRYCATCH_WITH_TYPECHECK_VOID(type, var, value, isolate) \
- type var; \
- { \
- bool ok = true; \
- { \
- v8::TryCatch block; \
- var = (value); \
- if (block.HasCaught()) { \
- block.ReThrow(); \
- return; \
- } \
- } \
- if (UNLIKELY(!ok)) { \
- throwUninformativeAndGenericTypeError(isolate); \
- return; \
- } \
+#define TONATIVE_VOID_EXCEPTIONSTATE_INTERNAL(var, value, exceptionState) \
+ var = (value); \
+ if (UNLIKELY(block.HasCaught() || exceptionState.throwIfNeeded())) \
+ return; \
+
+#define TONATIVE_VOID_EXCEPTIONSTATE(type, var, value, exceptionState) \
+ type var; \
+ { \
+ v8::TryCatch block; \
+ V8RethrowTryCatchScope rethrow(block); \
+ TONATIVE_VOID_EXCEPTIONSTATE_INTERNAL(var, value, exceptionState); \
}
-#define V8TRYCATCH_FOR_V8STRINGRESOURCE_RETURN(type, var, value, retVal) \
- type var(value); \
- if (!var.prepare()) \
- return retVal;
+#define TONATIVE_DEFAULT_EXCEPTIONSTATE(type, var, value, exceptionState, retVal) \
+ type var; \
+ { \
+ v8::TryCatch block; \
+ V8RethrowTryCatchScope rethrow(block); \
+ var = (value); \
+ if (UNLIKELY(block.HasCaught() || exceptionState.throwIfNeeded())) \
+ return retVal; \
+ }
+
+// type is an instance of class template V8StringResource<>,
+// but Mode argument varies; using type (not Mode) for consistency
+// with other macros and ease of code generation
+#define TOSTRING_VOID(type, var, value) \
+ type var(value); \
+ if (UNLIKELY(!var.prepare())) \
+ return;
-#define V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(type, var, value) \
- type var(value); \
- if (!var.prepare()) \
+#define TOSTRING_VOID_INTERNAL(var, value) \
+ var = (value); \
+ if (UNLIKELY(!var.prepare())) \
return;
+#define TOSTRING_DEFAULT(type, var, value, retVal) \
+ type var(value); \
+ if (UNLIKELY(!var.prepare())) \
+ return retVal;
+
} // namespace WebCore
#endif // V8BindingMacros_h
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8Callback.cpp b/chromium/third_party/WebKit/Source/bindings/v8/V8Callback.cpp
index ef56f45fcbc..b47b3daf58a 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8Callback.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8Callback.cpp
@@ -36,16 +36,16 @@
namespace WebCore {
-bool invokeCallback(v8::Local<v8::Function> callback, int argc, v8::Handle<v8::Value> argv[], ExecutionContext* executionContext, v8::Isolate* isolate)
+bool invokeCallback(ScriptState* scriptState, v8::Local<v8::Function> callback, int argc, v8::Handle<v8::Value> argv[])
{
- return invokeCallback(callback, isolate->GetCurrentContext()->Global(), argc, argv, executionContext, isolate);
+ return invokeCallback(scriptState, callback, scriptState->context()->Global(), argc, argv);
}
-bool invokeCallback(v8::Local<v8::Function> callback, v8::Handle<v8::Object> thisObject, int argc, v8::Handle<v8::Value> argv[], ExecutionContext* executionContext, v8::Isolate* isolate)
+bool invokeCallback(ScriptState* scriptState, v8::Local<v8::Function> callback, v8::Handle<v8::Value> thisValue, int argc, v8::Handle<v8::Value> argv[])
{
v8::TryCatch exceptionCatcher;
exceptionCatcher.SetVerbose(true);
- ScriptController::callFunction(executionContext, callback, thisObject, argc, argv, isolate);
+ ScriptController::callFunction(scriptState->executionContext(), callback, thisValue, argc, argv, scriptState->isolate());
return !exceptionCatcher.HasCaught();
}
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8Callback.h b/chromium/third_party/WebKit/Source/bindings/v8/V8Callback.h
index 6fad1b5c503..f6126243f27 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8Callback.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8Callback.h
@@ -31,8 +31,8 @@
#ifndef V8Callback_h
#define V8Callback_h
+#include "bindings/v8/ExceptionState.h"
#include "bindings/v8/V8Binding.h"
-#include "bindings/v8/V8Utilities.h"
#include "core/dom/ExceptionCode.h"
#include <v8.h>
@@ -41,9 +41,10 @@ namespace WebCore {
class ExecutionContext;
// Returns false if the callback threw an exception, true otherwise.
-bool invokeCallback(v8::Local<v8::Function> callback, int argc, v8::Handle<v8::Value> argv[], ExecutionContext*, v8::Isolate*);
-bool invokeCallback(v8::Local<v8::Function> callback, v8::Handle<v8::Object> thisObject, int argc, v8::Handle<v8::Value> argv[], ExecutionContext*, v8::Isolate*);
+bool invokeCallback(ScriptState*, v8::Local<v8::Function> callback, int argc, v8::Handle<v8::Value> argv[]);
+bool invokeCallback(ScriptState*, v8::Local<v8::Function> callback, v8::Handle<v8::Value> thisValue, int argc, v8::Handle<v8::Value> argv[]);
+// FIXME: This file is used only by V8GeolocationCustom.cpp. Remove the custom binding and this file.
enum CallbackAllowedValueFlag {
CallbackAllowUndefined = 1,
CallbackAllowNull = 1 << 1
@@ -53,7 +54,7 @@ typedef unsigned CallbackAllowedValueFlags;
// 'FunctionOnly' is assumed for the created callback.
template <typename V8CallbackType>
-PassOwnPtr<V8CallbackType> createFunctionOnlyCallback(v8::Local<v8::Value> value, bool& succeeded, v8::Isolate* isolate, CallbackAllowedValueFlags acceptedValues = 0)
+PassOwnPtr<V8CallbackType> createFunctionOnlyCallback(v8::Local<v8::Value> value, unsigned index, bool& succeeded, v8::Isolate* isolate, ExceptionState& exceptionState, CallbackAllowedValueFlags acceptedValues = 0)
{
succeeded = true;
@@ -65,11 +66,12 @@ PassOwnPtr<V8CallbackType> createFunctionOnlyCallback(v8::Local<v8::Value> value
if (!value->IsFunction()) {
succeeded = false;
- setDOMException(TypeMismatchError, isolate);
+ exceptionState.throwDOMException(TypeMismatchError, ExceptionMessages::argumentNullOrIncorrectType(index, "Function"));
+ exceptionState.throwIfNeeded();
return nullptr;
}
- return V8CallbackType::create(v8::Handle<v8::Function>::Cast(value), getExecutionContext());
+ return V8CallbackType::create(v8::Handle<v8::Function>::Cast(value), ScriptState::current(isolate));
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8CustomElementLifecycleCallbacks.cpp b/chromium/third_party/WebKit/Source/bindings/v8/V8CustomElementLifecycleCallbacks.cpp
index 29e1bc093de..aa03363d7d9 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8CustomElementLifecycleCallbacks.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8CustomElementLifecycleCallbacks.cpp
@@ -31,14 +31,15 @@
#include "config.h"
#include "bindings/v8/V8CustomElementLifecycleCallbacks.h"
-#include "V8Element.h"
+#include "bindings/core/v8/V8Element.h"
#include "bindings/v8/CustomElementBinding.h"
#include "bindings/v8/DOMDataStore.h"
#include "bindings/v8/ScriptController.h"
#include "bindings/v8/V8Binding.h"
-#include "bindings/v8/V8HiddenPropertyName.h"
+#include "bindings/v8/V8HiddenValue.h"
#include "bindings/v8/V8PerContextData.h"
#include "core/dom/ExecutionContext.h"
+#include "core/inspector/InspectorInstrumentation.h"
#include "wtf/PassOwnPtr.h"
namespace WebCore {
@@ -49,20 +50,20 @@ namespace WebCore {
V(detached, Detached) \
V(attributeChanged, AttributeChanged)
-PassRefPtr<V8CustomElementLifecycleCallbacks> V8CustomElementLifecycleCallbacks::create(ExecutionContext* executionContext, v8::Handle<v8::Object> prototype, v8::Handle<v8::Function> created, v8::Handle<v8::Function> attached, v8::Handle<v8::Function> detached, v8::Handle<v8::Function> attributeChanged)
+PassRefPtr<V8CustomElementLifecycleCallbacks> V8CustomElementLifecycleCallbacks::create(ScriptState* scriptState, v8::Handle<v8::Object> prototype, v8::Handle<v8::Function> created, v8::Handle<v8::Function> attached, v8::Handle<v8::Function> detached, v8::Handle<v8::Function> attributeChanged)
{
- v8::Isolate* isolate = toIsolate(executionContext);
+ v8::Isolate* isolate = scriptState->isolate();
// A given object can only be used as a Custom Element prototype
// once; see customElementIsInterfacePrototypeObject
-#define SET_HIDDEN_PROPERTY(Value, Name) \
- ASSERT(prototype->GetHiddenValue(V8HiddenPropertyName::customElement##Name(isolate)).IsEmpty()); \
+#define SET_HIDDEN_VALUE(Value, Name) \
+ ASSERT(V8HiddenValue::getHiddenValue(isolate, prototype, V8HiddenValue::customElement##Name(isolate)).IsEmpty()); \
if (!Value.IsEmpty()) \
- prototype->SetHiddenValue(V8HiddenPropertyName::customElement##Name(isolate), Value);
+ V8HiddenValue::setHiddenValue(isolate, prototype, V8HiddenValue::customElement##Name(isolate), Value);
- CALLBACK_LIST(SET_HIDDEN_PROPERTY)
-#undef SET_HIDDEN_PROPERTY
+ CALLBACK_LIST(SET_HIDDEN_VALUE)
+#undef SET_HIDDEN_VALUE
- return adoptRef(new V8CustomElementLifecycleCallbacks(executionContext, prototype, created, attached, detached, attributeChanged));
+ return adoptRef(new V8CustomElementLifecycleCallbacks(scriptState, prototype, created, attached, detached, attributeChanged));
}
static CustomElementLifecycleCallbacks::CallbackType flagSet(v8::Handle<v8::Function> attached, v8::Handle<v8::Function> detached, v8::Handle<v8::Function> attributeChanged)
@@ -88,16 +89,16 @@ static void weakCallback(const v8::WeakCallbackData<T, ScopedPersistent<T> >& da
data.GetParameter()->clear();
}
-V8CustomElementLifecycleCallbacks::V8CustomElementLifecycleCallbacks(ExecutionContext* executionContext, v8::Handle<v8::Object> prototype, v8::Handle<v8::Function> created, v8::Handle<v8::Function> attached, v8::Handle<v8::Function> detached, v8::Handle<v8::Function> attributeChanged)
+V8CustomElementLifecycleCallbacks::V8CustomElementLifecycleCallbacks(ScriptState* scriptState, v8::Handle<v8::Object> prototype, v8::Handle<v8::Function> created, v8::Handle<v8::Function> attached, v8::Handle<v8::Function> detached, v8::Handle<v8::Function> attributeChanged)
: CustomElementLifecycleCallbacks(flagSet(attached, detached, attributeChanged))
- , ActiveDOMCallback(executionContext)
+ , ContextLifecycleObserver(scriptState->executionContext())
, m_owner(0)
- , m_world(DOMWrapperWorld::current())
- , m_prototype(toIsolate(executionContext), prototype)
- , m_created(toIsolate(executionContext), created)
- , m_attached(toIsolate(executionContext), attached)
- , m_detached(toIsolate(executionContext), detached)
- , m_attributeChanged(toIsolate(executionContext), attributeChanged)
+ , m_scriptState(scriptState)
+ , m_prototype(scriptState->isolate(), prototype)
+ , m_created(scriptState->isolate(), created)
+ , m_attached(scriptState->isolate(), attached)
+ , m_detached(scriptState->isolate(), detached)
+ , m_attributeChanged(scriptState->isolate(), attributeChanged)
{
m_prototype.setWeak(&m_prototype, weakCallback<v8::Object>);
@@ -114,7 +115,7 @@ V8PerContextData* V8CustomElementLifecycleCallbacks::creationContextData()
if (!executionContext())
return 0;
- v8::Handle<v8::Context> context = toV8Context(executionContext(), m_world.get());
+ v8::Handle<v8::Context> context = m_scriptState->context();
if (context.IsEmpty())
return 0;
@@ -126,7 +127,7 @@ V8CustomElementLifecycleCallbacks::~V8CustomElementLifecycleCallbacks()
if (!m_owner)
return;
- v8::HandleScope handleScope(toIsolate(executionContext()));
+ v8::HandleScope handleScope(m_scriptState->isolate());
if (V8PerContextData* perContextData = creationContextData())
perContextData->clearCustomElementBinding(m_owner);
}
@@ -149,20 +150,20 @@ bool V8CustomElementLifecycleCallbacks::setBinding(CustomElementDefinition* owne
void V8CustomElementLifecycleCallbacks::created(Element* element)
{
- if (!canInvokeCallback())
+ // FIXME: callbacks while paused should be queued up for execution to
+ // continue then be delivered in order rather than delivered immediately.
+ // Bug 329665 tracks similar behavior for other synchronous events.
+ if (!executionContext() || executionContext()->activeDOMObjectsAreStopped())
return;
element->setCustomElementState(Element::Upgraded);
- v8::Isolate* isolate = toIsolate(executionContext());
- v8::HandleScope handleScope(isolate);
- v8::Handle<v8::Context> context = toV8Context(executionContext(), m_world.get());
- if (context.IsEmpty())
+ if (m_scriptState->contextIsEmpty())
return;
-
- v8::Context::Scope scope(context);
-
- v8::Handle<v8::Object> receiver = DOMDataStore::current(isolate).get<V8Element>(element, isolate);
+ ScriptState::Scope scope(m_scriptState.get());
+ v8::Isolate* isolate = m_scriptState->isolate();
+ v8::Handle<v8::Context> context = m_scriptState->context();
+ v8::Handle<v8::Object> receiver = m_scriptState->world().domDataStore().get<V8Element>(element, isolate);
if (!receiver.IsEmpty()) {
// Swizzle the prototype of the existing wrapper. We don't need to
// worry about non-existent wrappers; they will get the right
@@ -182,6 +183,8 @@ void V8CustomElementLifecycleCallbacks::created(Element* element)
ASSERT(!receiver.IsEmpty());
+ InspectorInstrumentation::willExecuteCustomElementCallback(element);
+
v8::TryCatch exceptionCatcher;
exceptionCatcher.SetVerbose(true);
ScriptController::callFunction(executionContext(), callback, receiver, 0, 0, isolate);
@@ -199,17 +202,17 @@ void V8CustomElementLifecycleCallbacks::detached(Element* element)
void V8CustomElementLifecycleCallbacks::attributeChanged(Element* element, const AtomicString& name, const AtomicString& oldValue, const AtomicString& newValue)
{
- if (!canInvokeCallback())
+ // FIXME: callbacks while paused should be queued up for execution to
+ // continue then be delivered in order rather than delivered immediately.
+ // Bug 329665 tracks similar behavior for other synchronous events.
+ if (!executionContext() || executionContext()->activeDOMObjectsAreStopped())
return;
- v8::Isolate* isolate = toIsolate(executionContext());
- v8::HandleScope handleScope(isolate);
- v8::Handle<v8::Context> context = toV8Context(executionContext(), m_world.get());
- if (context.IsEmpty())
+ if (m_scriptState->contextIsEmpty())
return;
-
- v8::Context::Scope scope(context);
-
+ ScriptState::Scope scope(m_scriptState.get());
+ v8::Isolate* isolate = m_scriptState->isolate();
+ v8::Handle<v8::Context> context = m_scriptState->context();
v8::Handle<v8::Object> receiver = toV8(element, context->Global(), isolate).As<v8::Object>();
ASSERT(!receiver.IsEmpty());
@@ -223,6 +226,8 @@ void V8CustomElementLifecycleCallbacks::attributeChanged(Element* element, const
newValue.isNull() ? v8::Handle<v8::Value>(v8::Null(isolate)) : v8::Handle<v8::Value>(v8String(isolate, newValue))
};
+ InspectorInstrumentation::willExecuteCustomElementCallback(element);
+
v8::TryCatch exceptionCatcher;
exceptionCatcher.SetVerbose(true);
ScriptController::callFunction(executionContext(), callback, receiver, WTF_ARRAY_LENGTH(argv), argv, isolate);
@@ -230,17 +235,17 @@ void V8CustomElementLifecycleCallbacks::attributeChanged(Element* element, const
void V8CustomElementLifecycleCallbacks::call(const ScopedPersistent<v8::Function>& weakCallback, Element* element)
{
- if (!canInvokeCallback())
+ // FIXME: callbacks while paused should be queued up for execution to
+ // continue then be delivered in order rather than delivered immediately.
+ // Bug 329665 tracks similar behavior for other synchronous events.
+ if (!executionContext() || executionContext()->activeDOMObjectsAreStopped())
return;
- v8::HandleScope handleScope(toIsolate(executionContext()));
- v8::Handle<v8::Context> context = toV8Context(executionContext(), m_world.get());
- if (context.IsEmpty())
+ if (m_scriptState->contextIsEmpty())
return;
-
- v8::Context::Scope scope(context);
- v8::Isolate* isolate = context->GetIsolate();
-
+ ScriptState::Scope scope(m_scriptState.get());
+ v8::Isolate* isolate = m_scriptState->isolate();
+ v8::Handle<v8::Context> context = m_scriptState->context();
v8::Handle<v8::Function> callback = weakCallback.newLocal(isolate);
if (callback.IsEmpty())
return;
@@ -248,6 +253,8 @@ void V8CustomElementLifecycleCallbacks::call(const ScopedPersistent<v8::Function
v8::Handle<v8::Object> receiver = toV8(element, context->Global(), isolate).As<v8::Object>();
ASSERT(!receiver.IsEmpty());
+ InspectorInstrumentation::willExecuteCustomElementCallback(element);
+
v8::TryCatch exceptionCatcher;
exceptionCatcher.SetVerbose(true);
ScriptController::callFunction(executionContext(), callback, receiver, 0, 0, isolate);
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8CustomElementLifecycleCallbacks.h b/chromium/third_party/WebKit/Source/bindings/v8/V8CustomElementLifecycleCallbacks.h
index e911e2899cc..fe32ad90ef4 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8CustomElementLifecycleCallbacks.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8CustomElementLifecycleCallbacks.h
@@ -31,9 +31,9 @@
#ifndef V8CustomElementLifecycleCallbacks_h
#define V8CustomElementLifecycleCallbacks_h
-#include "bindings/v8/ActiveDOMCallback.h"
-#include "bindings/v8/DOMWrapperWorld.h"
#include "bindings/v8/ScopedPersistent.h"
+#include "bindings/v8/ScriptState.h"
+#include "core/dom/ContextLifecycleObserver.h"
#include "core/dom/custom/CustomElementLifecycleCallbacks.h"
#include "wtf/PassOwnPtr.h"
#include "wtf/PassRefPtr.h"
@@ -46,16 +46,16 @@ class Element;
class ExecutionContext;
class V8PerContextData;
-class V8CustomElementLifecycleCallbacks : public CustomElementLifecycleCallbacks, ActiveDOMCallback {
+class V8CustomElementLifecycleCallbacks FINAL : public CustomElementLifecycleCallbacks, ContextLifecycleObserver {
public:
- static PassRefPtr<V8CustomElementLifecycleCallbacks> create(ExecutionContext*, v8::Handle<v8::Object> prototype, v8::Handle<v8::Function> created, v8::Handle<v8::Function> attached, v8::Handle<v8::Function> detached, v8::Handle<v8::Function> attributeChanged);
+ static PassRefPtr<V8CustomElementLifecycleCallbacks> create(ScriptState*, v8::Handle<v8::Object> prototype, v8::Handle<v8::Function> created, v8::Handle<v8::Function> attached, v8::Handle<v8::Function> detached, v8::Handle<v8::Function> attributeChanged);
virtual ~V8CustomElementLifecycleCallbacks();
bool setBinding(CustomElementDefinition* owner, PassOwnPtr<CustomElementBinding>);
private:
- V8CustomElementLifecycleCallbacks(ExecutionContext*, v8::Handle<v8::Object> prototype, v8::Handle<v8::Function> created, v8::Handle<v8::Function> attached, v8::Handle<v8::Function> detached, v8::Handle<v8::Function> attributeChanged);
+ V8CustomElementLifecycleCallbacks(ScriptState*, v8::Handle<v8::Object> prototype, v8::Handle<v8::Function> created, v8::Handle<v8::Function> attached, v8::Handle<v8::Function> detached, v8::Handle<v8::Function> attributeChanged);
virtual void created(Element*) OVERRIDE;
virtual void attached(Element*) OVERRIDE;
@@ -67,7 +67,7 @@ private:
V8PerContextData* creationContextData();
CustomElementDefinition* m_owner;
- RefPtr<DOMWrapperWorld> m_world;
+ RefPtr<ScriptState> m_scriptState;
ScopedPersistent<v8::Object> m_prototype;
ScopedPersistent<v8::Function> m_created;
ScopedPersistent<v8::Function> m_attached;
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8DOMActivityLogger.cpp b/chromium/third_party/WebKit/Source/bindings/v8/V8DOMActivityLogger.cpp
new file mode 100644
index 00000000000..20ead4f4ce0
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8DOMActivityLogger.cpp
@@ -0,0 +1,72 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "config.h"
+#include "bindings/v8/V8DOMActivityLogger.h"
+
+#include "bindings/v8/V8Binding.h"
+#include "platform/weborigin/KURL.h"
+#include "wtf/HashMap.h"
+#include "wtf/MainThread.h"
+#include "wtf/text/StringHash.h"
+
+namespace WebCore {
+
+typedef HashMap<String, OwnPtr<V8DOMActivityLogger> > DOMActivityLoggerMapForMainWorld;
+typedef HashMap<int, OwnPtr<V8DOMActivityLogger>, WTF::IntHash<int>, WTF::UnsignedWithZeroKeyHashTraits<int> > DOMActivityLoggerMapForIsolatedWorld;
+
+static DOMActivityLoggerMapForMainWorld& domActivityLoggersForMainWorld()
+{
+ ASSERT(isMainThread());
+ DEFINE_STATIC_LOCAL(DOMActivityLoggerMapForMainWorld, map, ());
+ return map;
+}
+
+static DOMActivityLoggerMapForIsolatedWorld& domActivityLoggersForIsolatedWorld()
+{
+ ASSERT(isMainThread());
+ DEFINE_STATIC_LOCAL(DOMActivityLoggerMapForIsolatedWorld, map, ());
+ return map;
+}
+
+void V8DOMActivityLogger::setActivityLogger(int worldId, const String& extensionId, PassOwnPtr<V8DOMActivityLogger> logger)
+{
+ if (worldId)
+ domActivityLoggersForIsolatedWorld().set(worldId, logger);
+ else
+ domActivityLoggersForMainWorld().set(extensionId, logger);
+}
+
+V8DOMActivityLogger* V8DOMActivityLogger::activityLogger(int worldId, const String& extensionId)
+{
+ if (worldId) {
+ DOMActivityLoggerMapForIsolatedWorld& loggers = domActivityLoggersForIsolatedWorld();
+ DOMActivityLoggerMapForIsolatedWorld::iterator it = loggers.find(worldId);
+ return it == loggers.end() ? 0 : it->value.get();
+ }
+
+ if (extensionId.isEmpty())
+ return 0;
+
+ DOMActivityLoggerMapForMainWorld& loggers = domActivityLoggersForMainWorld();
+ DOMActivityLoggerMapForMainWorld::iterator it = loggers.find(extensionId);
+ return it == loggers.end() ? 0 : it->value.get();
+}
+
+V8DOMActivityLogger* V8DOMActivityLogger::activityLogger(int worldId, const KURL& url)
+{
+ // extension ID is ignored for worldId != 0.
+ if (worldId)
+ return activityLogger(worldId, String());
+
+ // To find an activity logger that corresponds to the main world of an
+ // extension, we need to obtain the extension ID. Extension ID is a hostname
+ // of a background page's URL.
+ if (!url.protocolIs("chrome-extension"))
+ return 0;
+
+ return activityLogger(worldId, url.host());
+}
+
+} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8DOMActivityLogger.h b/chromium/third_party/WebKit/Source/bindings/v8/V8DOMActivityLogger.h
index 93915a65f2c..0f6b05c8e3c 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8DOMActivityLogger.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8DOMActivityLogger.h
@@ -31,16 +31,38 @@
#ifndef V8DOMActivityLogger_h
#define V8DOMActivityLogger_h
-#include <v8.h>
+#include "wtf/PassOwnPtr.h"
#include "wtf/text/WTFString.h"
+#include <v8.h>
namespace WebCore {
+class KURL;
+
class V8DOMActivityLogger {
public:
virtual ~V8DOMActivityLogger() { }
- virtual void log(const String& apiName, int argc, const v8::Handle<v8::Value>* argv, const String& extraInfo) { }
+ virtual void logGetter(const String& apiName) { }
+ virtual void logSetter(const String& apiName, const v8::Handle<v8::Value>& newValue) { }
+ virtual void logSetter(const String& apiName, const v8::Handle<v8::Value>& newValue, const v8::Handle<v8::Value>& oldValue) { }
+ virtual void logMethod(const String& apiName, int argc, const v8::Handle<v8::Value>* argv) { }
+
+ // Associates a logger with the world identified by worldId (worlId may be 0
+ // identifying the main world) and extension ID. Extension ID is used to
+ // identify a logger for main world only (worldId == 0). If the world is not
+ // a main world, an extension ID is ignored.
+ //
+ // A renderer process may host multiple extensions when the browser hits the
+ // renderer process limit. In such case, we assign multiple extensions to
+ // the same main world of a renderer process. In order to distinguish the
+ // extensions and their activity loggers in the main world, we require an
+ // extension ID. Otherwise, extension activities may be logged under
+ // a wrong extension ID.
+ static void setActivityLogger(int worldId, const String&, PassOwnPtr<V8DOMActivityLogger>);
+ static V8DOMActivityLogger* activityLogger(int worldId, const String& extensionId);
+ static V8DOMActivityLogger* activityLogger(int worldId, const KURL&);
+
};
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8DOMConfiguration.cpp b/chromium/third_party/WebKit/Source/bindings/v8/V8DOMConfiguration.cpp
index f92f9f0736e..13f2bf3659b 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8DOMConfiguration.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8DOMConfiguration.cpp
@@ -30,21 +30,24 @@
#include "bindings/v8/V8DOMConfiguration.h"
#include "bindings/v8/V8Binding.h"
+#include "bindings/v8/V8ObjectConstructor.h"
+#include "platform/TraceEvent.h"
namespace WebCore {
-void V8DOMConfiguration::installAttributes(v8::Handle<v8::ObjectTemplate> instanceTemplate, v8::Handle<v8::ObjectTemplate> prototype, const AttributeConfiguration* attributes, size_t attributeCount, v8::Isolate* isolate, WrapperWorldType currentWorldType)
+void V8DOMConfiguration::installAttributes(v8::Handle<v8::ObjectTemplate> instanceTemplate, v8::Handle<v8::ObjectTemplate> prototype, const AttributeConfiguration* attributes, size_t attributeCount, v8::Isolate* isolate)
{
for (size_t i = 0; i < attributeCount; ++i)
- installAttribute(instanceTemplate, prototype, attributes[i], isolate, currentWorldType);
+ installAttribute(instanceTemplate, prototype, attributes[i], isolate);
}
-void V8DOMConfiguration::installAccessors(v8::Handle<v8::ObjectTemplate> prototype, v8::Handle<v8::Signature> signature, const AccessorConfiguration* accessors, size_t accessorCount, v8::Isolate* isolate, WrapperWorldType currentWorldType)
+void V8DOMConfiguration::installAccessors(v8::Handle<v8::ObjectTemplate> prototype, v8::Handle<v8::Signature> signature, const AccessorConfiguration* accessors, size_t accessorCount, v8::Isolate* isolate)
{
+ bool isMainWorld = DOMWrapperWorld::current(isolate).isMainWorld();
for (size_t i = 0; i < accessorCount; ++i) {
v8::FunctionCallback getterCallback = accessors[i].getter;
v8::FunctionCallback setterCallback = accessors[i].setter;
- if (currentWorldType == MainWorld) {
+ if (isMainWorld) {
if (accessors[i].getterForMainWorld)
getterCallback = accessors[i].getterForMainWorld;
if (accessors[i].setterForMainWorld)
@@ -61,7 +64,7 @@ void V8DOMConfiguration::installAccessors(v8::Handle<v8::ObjectTemplate> prototy
setter = v8::FunctionTemplate::New(isolate, setterCallback, v8::External::New(isolate, const_cast<WrapperTypeInfo*>(accessors[i].data)), signature, 1);
setter->RemovePrototype();
}
- prototype->SetAccessorProperty(v8::String::NewFromUtf8(isolate, accessors[i].name, v8::String::kInternalizedString), getter, setter, accessors[i].attribute, accessors[i].settings);
+ prototype->SetAccessorProperty(v8AtomicString(isolate, accessors[i].name), getter, setter, accessors[i].attribute, accessors[i].settings);
}
}
@@ -69,20 +72,22 @@ void V8DOMConfiguration::installConstants(v8::Handle<v8::FunctionTemplate> funct
{
for (size_t i = 0; i < constantCount; ++i) {
const ConstantConfiguration* constant = &constants[i];
- functionDescriptor->Set(v8::String::NewFromUtf8(isolate, constant->name, v8::String::kInternalizedString), v8::Integer::New(isolate, constant->value), static_cast<v8::PropertyAttribute>(v8::ReadOnly | v8::DontDelete));
- prototype->Set(v8::String::NewFromUtf8(isolate, constant->name, v8::String::kInternalizedString), v8::Integer::New(isolate, constant->value), static_cast<v8::PropertyAttribute>(v8::ReadOnly | v8::DontDelete));
+ v8::Handle<v8::String> constantName = v8AtomicString(isolate, constant->name);
+ functionDescriptor->Set(constantName, v8::Integer::New(isolate, constant->value), static_cast<v8::PropertyAttribute>(v8::ReadOnly | v8::DontDelete));
+ prototype->Set(constantName, v8::Integer::New(isolate, constant->value), static_cast<v8::PropertyAttribute>(v8::ReadOnly | v8::DontDelete));
}
}
-void V8DOMConfiguration::installCallbacks(v8::Handle<v8::ObjectTemplate> prototype, v8::Handle<v8::Signature> signature, v8::PropertyAttribute attributes, const MethodConfiguration* callbacks, size_t callbackCount, v8::Isolate* isolate, WrapperWorldType currentWorldType)
+void V8DOMConfiguration::installCallbacks(v8::Handle<v8::ObjectTemplate> prototype, v8::Handle<v8::Signature> signature, v8::PropertyAttribute attributes, const MethodConfiguration* callbacks, size_t callbackCount, v8::Isolate* isolate)
{
+ bool isMainWorld = DOMWrapperWorld::current(isolate).isMainWorld();
for (size_t i = 0; i < callbackCount; ++i) {
v8::FunctionCallback callback = callbacks[i].callback;
- if (currentWorldType == MainWorld && callbacks[i].callbackForMainWorld)
+ if (isMainWorld && callbacks[i].callbackForMainWorld)
callback = callbacks[i].callbackForMainWorld;
v8::Local<v8::FunctionTemplate> functionTemplate = v8::FunctionTemplate::New(isolate, callback, v8Undefined(), signature, callbacks[i].length);
functionTemplate->RemovePrototype();
- prototype->Set(v8::String::NewFromUtf8(isolate, callbacks[i].name, v8::String::kInternalizedString), functionTemplate, attributes);
+ prototype->Set(v8AtomicString(isolate, callbacks[i].name), functionTemplate, attributes);
}
}
@@ -90,9 +95,9 @@ v8::Local<v8::Signature> V8DOMConfiguration::installDOMClassTemplate(v8::Handle<
const AttributeConfiguration* attributes, size_t attributeCount,
const AccessorConfiguration* accessors, size_t accessorCount,
const MethodConfiguration* callbacks, size_t callbackCount,
- v8::Isolate* isolate, WrapperWorldType currentWorldType)
+ v8::Isolate* isolate)
{
- functionDescriptor->SetClassName(v8::String::NewFromUtf8(isolate, interfaceName, v8::String::kInternalizedString));
+ functionDescriptor->SetClassName(v8AtomicString(isolate, interfaceName));
v8::Local<v8::ObjectTemplate> instanceTemplate = functionDescriptor->InstanceTemplate();
instanceTemplate->SetInternalFieldCount(fieldCount);
if (!parentClass.IsEmpty()) {
@@ -106,12 +111,26 @@ v8::Local<v8::Signature> V8DOMConfiguration::installDOMClassTemplate(v8::Handle<
v8::Local<v8::Signature> defaultSignature = v8::Signature::New(isolate, functionDescriptor);
if (attributeCount)
- installAttributes(instanceTemplate, functionDescriptor->PrototypeTemplate(), attributes, attributeCount, isolate, currentWorldType);
+ installAttributes(instanceTemplate, functionDescriptor->PrototypeTemplate(), attributes, attributeCount, isolate);
if (accessorCount)
- installAccessors(functionDescriptor->PrototypeTemplate(), defaultSignature, accessors, accessorCount, isolate, currentWorldType);
+ installAccessors(functionDescriptor->PrototypeTemplate(), defaultSignature, accessors, accessorCount, isolate);
if (callbackCount)
- installCallbacks(functionDescriptor->PrototypeTemplate(), defaultSignature, static_cast<v8::PropertyAttribute>(v8::DontDelete), callbacks, callbackCount, isolate, currentWorldType);
+ installCallbacks(functionDescriptor->PrototypeTemplate(), defaultSignature, static_cast<v8::PropertyAttribute>(v8::DontDelete), callbacks, callbackCount, isolate);
return defaultSignature;
}
+v8::Handle<v8::FunctionTemplate> V8DOMConfiguration::domClassTemplate(v8::Isolate* isolate, WrapperTypeInfo* wrapperTypeInfo, void (*configureDOMClassTemplate)(v8::Handle<v8::FunctionTemplate>, v8::Isolate*))
+{
+ V8PerIsolateData* data = V8PerIsolateData::from(isolate);
+ v8::Local<v8::FunctionTemplate> result = data->existingDOMTemplate(wrapperTypeInfo);
+ if (!result.IsEmpty())
+ return result;
+
+ TRACE_EVENT_SCOPED_SAMPLING_STATE("Blink", "BuildDOMTemplate");
+ result = v8::FunctionTemplate::New(isolate, V8ObjectConstructor::isValidConstructorMode);
+ configureDOMClassTemplate(result, isolate);
+ data->setDOMTemplate(wrapperTypeInfo, result);
+ return result;
+}
+
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8DOMConfiguration.h b/chromium/third_party/WebKit/Source/bindings/v8/V8DOMConfiguration.h
index 18a2e3bf0d5..28b1e504aef 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8DOMConfiguration.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8DOMConfiguration.h
@@ -69,25 +69,14 @@ public:
v8::PropertyAttribute attribute;
};
- static void installAttributes(v8::Handle<v8::ObjectTemplate>, v8::Handle<v8::ObjectTemplate>, const AttributeConfiguration*, size_t attributeCount, v8::Isolate*, WrapperWorldType currentWorldType);
+ static void installAttributes(v8::Handle<v8::ObjectTemplate>, v8::Handle<v8::ObjectTemplate>, const AttributeConfiguration*, size_t attributeCount, v8::Isolate*);
template<class ObjectOrTemplate>
static inline void installAttribute(v8::Handle<ObjectOrTemplate> instanceTemplate, v8::Handle<ObjectOrTemplate> prototype, const AttributeConfiguration& attribute, v8::Isolate* isolate)
{
- (attribute.onPrototype ? prototype : instanceTemplate)->SetAccessor(v8::String::NewFromUtf8(isolate, attribute.name, v8::String::kInternalizedString),
- attribute.getter,
- attribute.setter,
- v8::External::New(isolate, const_cast<WrapperTypeInfo*>(attribute.data)),
- attribute.settings,
- attribute.attribute);
- }
-
- template<class ObjectOrTemplate>
- static inline void installAttribute(v8::Handle<ObjectOrTemplate> instanceTemplate, v8::Handle<ObjectOrTemplate> prototype, const AttributeConfiguration& attribute, v8::Isolate* isolate, WrapperWorldType currentWorldType)
- {
v8::AccessorGetterCallback getter = attribute.getter;
v8::AccessorSetterCallback setter = attribute.setter;
- if (currentWorldType == MainWorld) {
+ if (DOMWrapperWorld::current(isolate).isMainWorld()) {
if (attribute.getterForMainWorld)
getter = attribute.getterForMainWorld;
if (attribute.setterForMainWorld)
@@ -120,15 +109,17 @@ public:
int length;
};
- static void installCallbacks(v8::Handle<v8::ObjectTemplate>, v8::Handle<v8::Signature>, v8::PropertyAttribute, const MethodConfiguration*, size_t callbackCount, v8::Isolate*, WrapperWorldType);
+ static void installCallbacks(v8::Handle<v8::ObjectTemplate>, v8::Handle<v8::Signature>, v8::PropertyAttribute, const MethodConfiguration*, size_t callbackCount, v8::Isolate*);
- static void installAccessors(v8::Handle<v8::ObjectTemplate>, v8::Handle<v8::Signature>, const AccessorConfiguration*, size_t accessorCount, v8::Isolate*, WrapperWorldType);
+ static void installAccessors(v8::Handle<v8::ObjectTemplate>, v8::Handle<v8::Signature>, const AccessorConfiguration*, size_t accessorCount, v8::Isolate*);
static v8::Local<v8::Signature> installDOMClassTemplate(v8::Handle<v8::FunctionTemplate>, const char* interfaceName, v8::Handle<v8::FunctionTemplate> parentClass, size_t fieldCount,
const AttributeConfiguration*, size_t attributeCount,
const AccessorConfiguration*, size_t accessorCount,
const MethodConfiguration*, size_t callbackCount,
- v8::Isolate*, WrapperWorldType);
+ v8::Isolate*);
+
+ static v8::Handle<v8::FunctionTemplate> domClassTemplate(v8::Isolate*, WrapperTypeInfo*, void (*)(v8::Handle<v8::FunctionTemplate>, v8::Isolate*));
};
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8DOMWrapper.cpp b/chromium/third_party/WebKit/Source/bindings/v8/V8DOMWrapper.cpp
index 41dca146507..8a52d8c4296 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8DOMWrapper.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8DOMWrapper.cpp
@@ -31,11 +31,10 @@
#include "config.h"
#include "bindings/v8/V8DOMWrapper.h"
-#include "V8HTMLCollection.h"
-#include "V8HTMLDocument.h"
-#include "V8Window.h"
+#include "bindings/core/v8/V8HTMLCollection.h"
+#include "bindings/core/v8/V8HTMLDocument.h"
+#include "bindings/core/v8/V8Window.h"
#include "bindings/v8/V8Binding.h"
-#include "bindings/v8/V8HiddenPropertyName.h"
#include "bindings/v8/V8ObjectConstructor.h"
#include "bindings/v8/V8PerContextData.h"
#include "bindings/v8/V8ScriptRunner.h"
@@ -44,30 +43,28 @@ namespace WebCore {
static v8::Local<v8::Object> wrapInShadowTemplate(v8::Local<v8::Object> wrapper, Node* impl, v8::Isolate* isolate)
{
- // This is only for getting a unique pointer which we can pass to privateTemplate.
- static int shadowTemplateUniqueKey;
- WrapperWorldType currentWorldType = worldType(isolate);
+ static int shadowTemplateKey; // This address is used for a key to look up the dom template.
V8PerIsolateData* data = V8PerIsolateData::from(isolate);
- v8::Handle<v8::FunctionTemplate> shadowTemplate = data->privateTemplateIfExists(currentWorldType, &shadowTemplateUniqueKey);
+ v8::Handle<v8::FunctionTemplate> shadowTemplate = data->existingDOMTemplate(&shadowTemplateKey);
if (shadowTemplate.IsEmpty()) {
shadowTemplate = v8::FunctionTemplate::New(isolate);
if (shadowTemplate.IsEmpty())
return v8::Local<v8::Object>();
shadowTemplate->SetClassName(v8AtomicString(isolate, "HTMLDocument"));
- shadowTemplate->Inherit(V8HTMLDocument::domTemplate(isolate, currentWorldType));
+ shadowTemplate->Inherit(V8HTMLDocument::domTemplate(isolate));
shadowTemplate->InstanceTemplate()->SetInternalFieldCount(V8HTMLDocument::internalFieldCount);
- data->setPrivateTemplate(currentWorldType, &shadowTemplateUniqueKey, shadowTemplate);
+ data->setDOMTemplate(&shadowTemplateKey, shadowTemplate);
}
v8::Local<v8::Function> shadowConstructor = shadowTemplate->GetFunction();
if (shadowConstructor.IsEmpty())
return v8::Local<v8::Object>();
- v8::Local<v8::Object> shadow = V8ScriptRunner::instantiateObject(shadowConstructor);
+ v8::Local<v8::Object> shadow = V8ScriptRunner::instantiateObject(isolate, shadowConstructor);
if (shadow.IsEmpty())
return v8::Local<v8::Object>();
shadow->SetPrototype(wrapper);
- V8DOMWrapper::setNativeInfo(wrapper, &V8HTMLDocument::wrapperTypeInfo, impl);
+ V8DOMWrapper::setNativeInfoForHiddenWrapper(wrapper, &V8HTMLDocument::wrapperTypeInfo, impl);
return shadow;
}
@@ -76,7 +73,7 @@ v8::Local<v8::Object> V8DOMWrapper::createWrapper(v8::Handle<v8::Object> creatio
V8WrapperInstantiationScope scope(creationContext, isolate);
V8PerContextData* perContextData = V8PerContextData::from(scope.context());
- v8::Local<v8::Object> wrapper = perContextData ? perContextData->createWrapperFromCache(type) : V8ObjectConstructor::newInstance(type->domTemplate(isolate, worldTypeInMainThread(isolate))->GetFunction());
+ v8::Local<v8::Object> wrapper = perContextData ? perContextData->createWrapperFromCache(type) : V8ObjectConstructor::newInstance(isolate, type->domTemplate(isolate)->GetFunction());
if (type == &V8HTMLDocument::wrapperTypeInfo && !wrapper.IsEmpty())
wrapper = wrapInShadowTemplate(wrapper, static_cast<Node*>(impl), isolate);
@@ -84,59 +81,22 @@ v8::Local<v8::Object> V8DOMWrapper::createWrapper(v8::Handle<v8::Object> creatio
return wrapper;
}
-static bool hasInternalField(v8::Handle<v8::Value> value)
+bool V8DOMWrapper::isDOMWrapper(v8::Handle<v8::Value> value)
{
if (value.IsEmpty() || !value->IsObject())
return false;
- return v8::Handle<v8::Object>::Cast(value)->InternalFieldCount();
-}
-#ifndef NDEBUG
-bool V8DOMWrapper::maybeDOMWrapper(v8::Handle<v8::Value> value)
-{
- if (!hasInternalField(value))
- return false;
-
- v8::Handle<v8::Object> object = v8::Handle<v8::Object>::Cast(value);
- ASSERT(object->InternalFieldCount() >= v8DefaultWrapperInternalFieldCount);
-
- v8::HandleScope scope(v8::Isolate::GetCurrent());
- ASSERT(object->GetAlignedPointerFromInternalField(v8DOMWrapperObjectIndex));
-
- const WrapperTypeInfo* typeInfo = static_cast<const WrapperTypeInfo*>(object->GetAlignedPointerFromInternalField(v8DOMWrapperTypeIndex));
-
- return typeInfo->ginEmbedder == gin::kEmbedderBlink;
-}
-#endif
-
-bool V8DOMWrapper::isDOMWrapper(v8::Handle<v8::Value> value)
-{
- if (value.IsEmpty() || !value->IsObject())
+ if (v8::Handle<v8::Object>::Cast(value)->InternalFieldCount() < v8DefaultWrapperInternalFieldCount)
return false;
v8::Handle<v8::Object> wrapper = v8::Handle<v8::Object>::Cast(value);
- if (wrapper->InternalFieldCount() < v8DefaultWrapperInternalFieldCount)
- return false;
ASSERT(wrapper->GetAlignedPointerFromInternalField(v8DOMWrapperObjectIndex));
ASSERT(wrapper->GetAlignedPointerFromInternalField(v8DOMWrapperTypeIndex));
const WrapperTypeInfo* typeInfo = static_cast<const WrapperTypeInfo*>(wrapper->GetAlignedPointerFromInternalField(v8DOMWrapperTypeIndex));
-
- // FIXME: Add class id checks.
+ // FIXME: We should add a more strict way to check if the typeInfo is a typeInfo of some DOM wrapper.
+ // Even if it's a typeInfo of Blink, it's not guaranteed that it's a typeInfo of a DOM wrapper.
return typeInfo->ginEmbedder == gin::kEmbedderBlink;
}
-bool V8DOMWrapper::isWrapperOfType(v8::Handle<v8::Value> value, const WrapperTypeInfo* type)
-{
- if (!hasInternalField(value))
- return false;
-
- v8::Handle<v8::Object> wrapper = v8::Handle<v8::Object>::Cast(value);
- ASSERT(wrapper->InternalFieldCount() >= v8DefaultWrapperInternalFieldCount);
- ASSERT(wrapper->GetAlignedPointerFromInternalField(v8DOMWrapperObjectIndex));
-
- const WrapperTypeInfo* typeInfo = static_cast<const WrapperTypeInfo*>(wrapper->GetAlignedPointerFromInternalField(v8DOMWrapperTypeIndex));
- return typeInfo->ginEmbedder == gin::kEmbedderBlink && typeInfo == type;
-}
-
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8DOMWrapper.h b/chromium/third_party/WebKit/Source/bindings/v8/V8DOMWrapper.h
index 4bda879805b..db41c8f9034 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8DOMWrapper.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8DOMWrapper.h
@@ -34,6 +34,7 @@
#include "bindings/v8/DOMDataStore.h"
#include <v8.h>
#include "wtf/PassRefPtr.h"
+#include "wtf/RawPtr.h"
#include "wtf/text/AtomicString.h"
namespace WebCore {
@@ -42,60 +43,115 @@ struct WrapperTypeInfo;
class V8DOMWrapper {
public:
-#ifndef NDEBUG
- // Checks if a v8 value can be a DOM wrapper
- static bool maybeDOMWrapper(v8::Handle<v8::Value>);
-#endif
-
static v8::Local<v8::Object> createWrapper(v8::Handle<v8::Object> creationContext, const WrapperTypeInfo*, void*, v8::Isolate*);
template<typename V8T, typename T>
static inline v8::Handle<v8::Object> associateObjectWithWrapper(PassRefPtr<T>, const WrapperTypeInfo*, v8::Handle<v8::Object>, v8::Isolate*, WrapperConfiguration::Lifetime);
+ template<typename V8T, typename T>
+ static inline v8::Handle<v8::Object> associateObjectWithWrapper(RawPtr<T> object, const WrapperTypeInfo* wrapperTypeInfo, v8::Handle<v8::Object> wrapper, v8::Isolate* isolate, WrapperConfiguration::Lifetime lifetime)
+ {
+ return associateObjectWithWrapper<V8T, T>(object.get(), wrapperTypeInfo, wrapper, isolate, lifetime);
+ }
+ template<typename V8T, typename T>
+ static inline v8::Handle<v8::Object> associateObjectWithWrapper(T*, const WrapperTypeInfo*, v8::Handle<v8::Object>, v8::Isolate*, WrapperConfiguration::Lifetime);
static inline void setNativeInfo(v8::Handle<v8::Object>, const WrapperTypeInfo*, void*);
+ static inline void setNativeInfoForHiddenWrapper(v8::Handle<v8::Object>, const WrapperTypeInfo*, void*);
+ static inline void setNativeInfoWithPersistentHandle(v8::Handle<v8::Object>, const WrapperTypeInfo*, void*, PersistentNode*);
static inline void clearNativeInfo(v8::Handle<v8::Object>, const WrapperTypeInfo*);
static bool isDOMWrapper(v8::Handle<v8::Value>);
- static bool isWrapperOfType(v8::Handle<v8::Value>, const WrapperTypeInfo*);
};
- inline void V8DOMWrapper::setNativeInfo(v8::Handle<v8::Object> wrapper, const WrapperTypeInfo* type, void* object)
+ inline void V8DOMWrapper::setNativeInfo(v8::Handle<v8::Object> wrapper, const WrapperTypeInfo* wrapperTypeInfo, void* object)
+ {
+ ASSERT(wrapper->InternalFieldCount() >= 2);
+ ASSERT(object);
+ ASSERT(wrapperTypeInfo);
+#if ENABLE(OILPAN)
+ ASSERT(wrapperTypeInfo->gcType == RefCountedObject);
+#else
+ ASSERT(wrapperTypeInfo->gcType == RefCountedObject || wrapperTypeInfo->gcType == WillBeGarbageCollectedObject);
+#endif
+ wrapper->SetAlignedPointerInInternalField(v8DOMWrapperObjectIndex, object);
+ wrapper->SetAlignedPointerInInternalField(v8DOMWrapperTypeIndex, const_cast<WrapperTypeInfo*>(wrapperTypeInfo));
+ }
+
+ inline void V8DOMWrapper::setNativeInfoForHiddenWrapper(v8::Handle<v8::Object> wrapper, const WrapperTypeInfo* wrapperTypeInfo, void* object)
{
+ // see V8WindowShell::installDOMWindow() comment for why this version is needed and safe.
ASSERT(wrapper->InternalFieldCount() >= 2);
ASSERT(object);
- ASSERT(type);
+ ASSERT(wrapperTypeInfo);
+#if ENABLE(OILPAN)
+ ASSERT(wrapperTypeInfo->gcType != RefCountedObject);
+#else
+ ASSERT(wrapperTypeInfo->gcType == RefCountedObject || wrapperTypeInfo->gcType == WillBeGarbageCollectedObject);
+#endif
+
+ // Clear out the last internal field, which is assumed to contain a valid persistent pointer value.
+ if (wrapperTypeInfo->gcType == GarbageCollectedObject) {
+ wrapper->SetAlignedPointerInInternalField(wrapper->InternalFieldCount() - 1, 0);
+ } else if (wrapperTypeInfo->gcType == WillBeGarbageCollectedObject) {
+#if ENABLE(OILPAN)
+ wrapper->SetAlignedPointerInInternalField(wrapper->InternalFieldCount() - 1, 0);
+#endif
+ }
+ wrapper->SetAlignedPointerInInternalField(v8DOMWrapperObjectIndex, object);
+ wrapper->SetAlignedPointerInInternalField(v8DOMWrapperTypeIndex, const_cast<WrapperTypeInfo*>(wrapperTypeInfo));
+ }
+
+ inline void V8DOMWrapper::setNativeInfoWithPersistentHandle(v8::Handle<v8::Object> wrapper, const WrapperTypeInfo* wrapperTypeInfo, void* object, PersistentNode* handle)
+ {
+ ASSERT(wrapper->InternalFieldCount() >= 3);
+ ASSERT(object);
+ ASSERT(wrapperTypeInfo);
+ ASSERT(wrapperTypeInfo->gcType != RefCountedObject);
wrapper->SetAlignedPointerInInternalField(v8DOMWrapperObjectIndex, object);
- wrapper->SetAlignedPointerInInternalField(v8DOMWrapperTypeIndex, const_cast<WrapperTypeInfo*>(type));
+ wrapper->SetAlignedPointerInInternalField(v8DOMWrapperTypeIndex, const_cast<WrapperTypeInfo*>(wrapperTypeInfo));
+ // Persistent handle is stored in the last internal field.
+ wrapper->SetAlignedPointerInInternalField(wrapper->InternalFieldCount() - 1, handle);
}
- inline void V8DOMWrapper::clearNativeInfo(v8::Handle<v8::Object> wrapper, const WrapperTypeInfo* type)
+ inline void V8DOMWrapper::clearNativeInfo(v8::Handle<v8::Object> wrapper, const WrapperTypeInfo* wrapperTypeInfo)
{
ASSERT(wrapper->InternalFieldCount() >= 2);
- ASSERT(type);
- wrapper->SetAlignedPointerInInternalField(v8DOMWrapperTypeIndex, const_cast<WrapperTypeInfo*>(type));
+ ASSERT(wrapperTypeInfo);
+ // clearNativeInfo() is used only by NP objects, which are not garbage collected.
+ ASSERT(wrapperTypeInfo->gcType == RefCountedObject);
+ wrapper->SetAlignedPointerInInternalField(v8DOMWrapperTypeIndex, const_cast<WrapperTypeInfo*>(wrapperTypeInfo));
wrapper->SetAlignedPointerInInternalField(v8DOMWrapperObjectIndex, 0);
}
template<typename V8T, typename T>
- inline v8::Handle<v8::Object> V8DOMWrapper::associateObjectWithWrapper(PassRefPtr<T> object, const WrapperTypeInfo* type, v8::Handle<v8::Object> wrapper, v8::Isolate* isolate, WrapperConfiguration::Lifetime lifetime)
+ inline v8::Handle<v8::Object> V8DOMWrapper::associateObjectWithWrapper(PassRefPtr<T> object, const WrapperTypeInfo* wrapperTypeInfo, v8::Handle<v8::Object> wrapper, v8::Isolate* isolate, WrapperConfiguration::Lifetime lifetime)
{
- setNativeInfo(wrapper, type, V8T::toInternalPointer(object.get()));
- ASSERT(maybeDOMWrapper(wrapper));
+ setNativeInfo(wrapper, wrapperTypeInfo, V8T::toInternalPointer(object.get()));
+ ASSERT(isDOMWrapper(wrapper));
WrapperConfiguration configuration = buildWrapperConfiguration(object.get(), lifetime);
DOMDataStore::setWrapper<V8T>(object.leakRef(), wrapper, isolate, configuration);
return wrapper;
}
+ template<typename V8T, typename T>
+ inline v8::Handle<v8::Object> V8DOMWrapper::associateObjectWithWrapper(T* object, const WrapperTypeInfo* wrapperTypeInfo, v8::Handle<v8::Object> wrapper, v8::Isolate* isolate, WrapperConfiguration::Lifetime lifetime)
+ {
+ setNativeInfoWithPersistentHandle(wrapper, wrapperTypeInfo, V8T::toInternalPointer(object), new Persistent<T>(object));
+ ASSERT(isDOMWrapper(wrapper));
+ WrapperConfiguration configuration = buildWrapperConfiguration(object, lifetime);
+ DOMDataStore::setWrapper<V8T>(object, wrapper, isolate, configuration);
+ return wrapper;
+ }
+
class V8WrapperInstantiationScope {
public:
V8WrapperInstantiationScope(v8::Handle<v8::Object> creationContext, v8::Isolate* isolate)
: m_didEnterContext(false)
, m_context(isolate->GetCurrentContext())
{
- // FIXME: Remove all empty creationContexts from caller sites.
- // If a creationContext is empty, we will end up creating a new object
- // in the context currently entered. This is wrong.
- if (creationContext.IsEmpty())
- return;
+ // creationContext should not be empty. Because if we have an
+ // empty creationContext, we will end up creating
+ // a new object in the context currently entered. This is wrong.
+ RELEASE_ASSERT(!creationContext.IsEmpty());
v8::Handle<v8::Context> contextForWrapper = creationContext->CreationContext();
// For performance, we enter the context only if the currently running context
// is different from the context that we are about to enter.
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8ErrorHandler.cpp b/chromium/third_party/WebKit/Source/bindings/v8/V8ErrorHandler.cpp
index 758eb47fedf..c72ac25806b 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8ErrorHandler.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8ErrorHandler.cpp
@@ -31,63 +31,61 @@
#include "config.h"
#include "bindings/v8/V8ErrorHandler.h"
-#include "V8ErrorEvent.h"
+#include "bindings/core/v8/V8ErrorEvent.h"
#include "bindings/v8/ScriptController.h"
#include "bindings/v8/V8Binding.h"
-#include "bindings/v8/V8HiddenPropertyName.h"
+#include "bindings/v8/V8HiddenValue.h"
#include "bindings/v8/V8ScriptRunner.h"
#include "core/dom/Document.h"
#include "core/dom/ExecutionContext.h"
#include "core/events/ErrorEvent.h"
-#include "core/events/ThreadLocalEventNames.h"
-#include "core/frame/Frame.h"
+#include "core/frame/LocalFrame.h"
namespace WebCore {
-V8ErrorHandler::V8ErrorHandler(v8::Local<v8::Object> listener, bool isInline, v8::Isolate* isolate)
- : V8EventListener(listener, isInline, isolate)
+V8ErrorHandler::V8ErrorHandler(v8::Local<v8::Object> listener, bool isInline, ScriptState* scriptState)
+ : V8EventListener(listener, isInline, scriptState)
{
}
-v8::Local<v8::Value> V8ErrorHandler::callListenerFunction(ExecutionContext* context, v8::Handle<v8::Value> jsEvent, Event* event)
+v8::Local<v8::Value> V8ErrorHandler::callListenerFunction(v8::Handle<v8::Value> jsEvent, Event* event)
{
if (!event->hasInterface(EventNames::ErrorEvent))
- return V8EventListener::callListenerFunction(context, jsEvent, event);
+ return V8EventListener::callListenerFunction(jsEvent, event);
ErrorEvent* errorEvent = static_cast<ErrorEvent*>(event);
- v8::Isolate* isolate = toV8Context(context, world())->GetIsolate();
- if (errorEvent->world() && errorEvent->world() != world())
- return v8::Null(isolate);
+ if (errorEvent->world() && errorEvent->world() != &world())
+ return v8::Null(isolate());
- v8::Local<v8::Object> listener = getListenerObject(context);
+ v8::Local<v8::Object> listener = getListenerObject(scriptState()->executionContext());
v8::Local<v8::Value> returnValue;
if (!listener.IsEmpty() && listener->IsFunction()) {
v8::Local<v8::Function> callFunction = v8::Local<v8::Function>::Cast(listener);
- v8::Local<v8::Object> thisValue = isolate->GetCurrentContext()->Global();
+ v8::Local<v8::Object> thisValue = scriptState()->context()->Global();
- v8::Local<v8::Value> error = jsEvent->ToObject()->GetHiddenValue(V8HiddenPropertyName::error(isolate));
+ v8::Local<v8::Value> error = V8HiddenValue::getHiddenValue(isolate(), jsEvent->ToObject(), V8HiddenValue::error(isolate()));
if (error.IsEmpty())
- error = v8::Null(isolate);
+ error = v8::Null(isolate());
- v8::Handle<v8::Value> parameters[5] = { v8String(isolate, errorEvent->message()), v8String(isolate, errorEvent->filename()), v8::Integer::New(errorEvent->lineno(), isolate), v8::Integer::New(errorEvent->colno(), isolate), error };
+ v8::Handle<v8::Value> parameters[5] = { v8String(isolate(), errorEvent->message()), v8String(isolate(), errorEvent->filename()), v8::Integer::New(isolate(), errorEvent->lineno()), v8::Integer::New(isolate(), errorEvent->colno()), error };
v8::TryCatch tryCatch;
tryCatch.SetVerbose(true);
- if (worldType(isolate) == WorkerWorld)
- returnValue = V8ScriptRunner::callFunction(callFunction, context, thisValue, WTF_ARRAY_LENGTH(parameters), parameters, isolate);
+ if (scriptState()->executionContext()->isWorkerGlobalScope())
+ returnValue = V8ScriptRunner::callFunction(callFunction, scriptState()->executionContext(), thisValue, WTF_ARRAY_LENGTH(parameters), parameters, isolate());
else
- returnValue = ScriptController::callFunction(context, callFunction, thisValue, WTF_ARRAY_LENGTH(parameters), parameters, isolate);
+ returnValue = ScriptController::callFunction(scriptState()->executionContext(), callFunction, thisValue, WTF_ARRAY_LENGTH(parameters), parameters, isolate());
}
return returnValue;
}
// static
-void V8ErrorHandler::storeExceptionOnErrorEventWrapper(ErrorEvent* event, v8::Handle<v8::Value> data, v8::Isolate* isolate)
+void V8ErrorHandler::storeExceptionOnErrorEventWrapper(ErrorEvent* event, v8::Handle<v8::Value> data, v8::Handle<v8::Object> creationContext, v8::Isolate* isolate)
{
- v8::Local<v8::Value> wrappedEvent = toV8(event, v8::Handle<v8::Object>(), isolate);
+ v8::Local<v8::Value> wrappedEvent = toV8(event, creationContext, isolate);
if (!wrappedEvent.IsEmpty()) {
ASSERT(wrappedEvent->IsObject());
- v8::Local<v8::Object>::Cast(wrappedEvent)->SetHiddenValue(V8HiddenPropertyName::error(isolate), data);
+ V8HiddenValue::setHiddenValue(isolate, v8::Local<v8::Object>::Cast(wrappedEvent), V8HiddenValue::error(isolate), data);
}
}
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8ErrorHandler.h b/chromium/third_party/WebKit/Source/bindings/v8/V8ErrorHandler.h
index cfaa69de587..8e1d5f22489 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8ErrorHandler.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8ErrorHandler.h
@@ -38,22 +38,22 @@
namespace WebCore {
class ErrorEvent;
-class Frame;
+class LocalFrame;
-class V8ErrorHandler : public V8EventListener {
+class V8ErrorHandler FINAL : public V8EventListener {
public:
- static PassRefPtr<V8ErrorHandler> create(v8::Local<v8::Object> listener, bool isInline, v8::Isolate* isolate)
+ static PassRefPtr<V8ErrorHandler> create(v8::Local<v8::Object> listener, bool isInline, ScriptState* scriptState)
{
- return adoptRef(new V8ErrorHandler(listener, isInline, isolate));
+ return adoptRef(new V8ErrorHandler(listener, isInline, scriptState));
}
- static void storeExceptionOnErrorEventWrapper(ErrorEvent*, v8::Handle<v8::Value>, v8::Isolate*);
+ static void storeExceptionOnErrorEventWrapper(ErrorEvent*, v8::Handle<v8::Value>, v8::Handle<v8::Object> creationContext, v8::Isolate*);
private:
- V8ErrorHandler(v8::Local<v8::Object> listener, bool isInline, v8::Isolate*);
+ V8ErrorHandler(v8::Local<v8::Object> listener, bool isInline, ScriptState*);
- virtual v8::Local<v8::Value> callListenerFunction(ExecutionContext*, v8::Handle<v8::Value> jsEvent, Event*);
- virtual bool shouldPreventDefault(v8::Local<v8::Value> returnValue);
+ virtual v8::Local<v8::Value> callListenerFunction(v8::Handle<v8::Value> jsEvent, Event*) OVERRIDE;
+ virtual bool shouldPreventDefault(v8::Local<v8::Value> returnValue) OVERRIDE;
};
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8EventListener.cpp b/chromium/third_party/WebKit/Source/bindings/v8/V8EventListener.cpp
index 13144b96e9d..fc204607cee 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8EventListener.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8EventListener.cpp
@@ -34,19 +34,19 @@
#include "bindings/v8/ScriptController.h"
#include "bindings/v8/V8Binding.h"
#include "core/dom/Document.h"
-#include "core/frame/Frame.h"
+#include "core/frame/LocalFrame.h"
namespace WebCore {
-V8EventListener::V8EventListener(v8::Local<v8::Object> listener, bool isAttribute, v8::Isolate* isolate)
- : V8AbstractEventListener(isAttribute, DOMWrapperWorld::current(), isolate)
+V8EventListener::V8EventListener(v8::Local<v8::Object> listener, bool isAttribute, ScriptState* scriptState)
+ : V8AbstractEventListener(isAttribute, scriptState)
{
setListenerObject(listener);
}
-v8::Local<v8::Function> V8EventListener::getListenerFunction(ExecutionContext* context)
+v8::Local<v8::Function> V8EventListener::getListenerFunction(ExecutionContext*)
{
- v8::Local<v8::Object> listener = getListenerObject(context);
+ v8::Local<v8::Object> listener = getListenerObject(scriptState()->executionContext());
// Has the listener been disposed?
if (listener.IsEmpty())
@@ -67,22 +67,18 @@ v8::Local<v8::Function> V8EventListener::getListenerFunction(ExecutionContext* c
return v8::Local<v8::Function>();
}
-v8::Local<v8::Value> V8EventListener::callListenerFunction(ExecutionContext* context, v8::Handle<v8::Value> jsEvent, Event* event)
+v8::Local<v8::Value> V8EventListener::callListenerFunction(v8::Handle<v8::Value> jsEvent, Event* event)
{
- v8::Local<v8::Function> handlerFunction = getListenerFunction(context);
- v8::Local<v8::Object> receiver = getReceiverObject(context, event);
+ v8::Local<v8::Function> handlerFunction = getListenerFunction(scriptState()->executionContext());
+ v8::Local<v8::Object> receiver = getReceiverObject(event);
if (handlerFunction.IsEmpty() || receiver.IsEmpty())
return v8::Local<v8::Value>();
- // FIXME: Can |context| be 0 here?
- if (!context)
+ if (!scriptState()->executionContext()->isDocument())
return v8::Local<v8::Value>();
- if (!context->isDocument())
- return v8::Local<v8::Value>();
-
- Frame* frame = toDocument(context)->frame();
+ LocalFrame* frame = toDocument(scriptState()->executionContext())->frame();
if (!frame)
return v8::Local<v8::Value>();
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8EventListener.h b/chromium/third_party/WebKit/Source/bindings/v8/V8EventListener.h
index 1358848a5f1..93296ae659e 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8EventListener.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8EventListener.h
@@ -31,7 +31,6 @@
#ifndef V8EventListener_h
#define V8EventListener_h
-#include "bindings/v8/DOMWrapperWorld.h"
#include "bindings/v8/V8AbstractEventListener.h"
#include <v8.h>
#include "wtf/PassRefPtr.h"
@@ -39,23 +38,23 @@
namespace WebCore {
class Event;
- class Frame;
+ class LocalFrame;
// V8EventListener is a wrapper of a JS object implements EventListener interface (has handleEvent(event) method), or a JS function
// that can handle the event.
class V8EventListener : public V8AbstractEventListener {
public:
- static PassRefPtr<V8EventListener> create(v8::Local<v8::Object> listener, bool isAttribute, v8::Isolate* isolate)
+ static PassRefPtr<V8EventListener> create(v8::Local<v8::Object> listener, bool isAttribute, ScriptState* scriptState)
{
- return adoptRef(new V8EventListener(listener, isAttribute, isolate));
+ return adoptRef(new V8EventListener(listener, isAttribute, scriptState));
}
protected:
- V8EventListener(v8::Local<v8::Object> listener, bool isAttribute, v8::Isolate*);
+ V8EventListener(v8::Local<v8::Object> listener, bool isAttribute, ScriptState*);
v8::Local<v8::Function> getListenerFunction(ExecutionContext*);
- virtual v8::Local<v8::Value> callListenerFunction(ExecutionContext*, v8::Handle<v8::Value> jsEvent, Event*);
+ virtual v8::Local<v8::Value> callListenerFunction(v8::Handle<v8::Value> jsEvent, Event*) OVERRIDE;
};
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8EventListenerList.cpp b/chromium/third_party/WebKit/Source/bindings/v8/V8EventListenerList.cpp
index 0606fb69fa6..ad44ef8bd1f 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8EventListenerList.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8EventListenerList.cpp
@@ -31,27 +31,24 @@
#include "config.h"
#include "bindings/v8/V8EventListenerList.h"
-#include "V8Window.h"
+#include "bindings/core/v8/V8Window.h"
#include "bindings/v8/V8Binding.h"
#include "bindings/v8/V8WorkerGlobalScopeEventListener.h"
namespace WebCore {
-PassRefPtr<EventListener> V8EventListenerList::getEventListener(v8::Local<v8::Value> value, bool isAttribute, ListenerLookupType lookup)
+PassRefPtr<EventListener> V8EventListenerList::getEventListener(ScriptState* scriptState, v8::Local<v8::Value> value, bool isAttribute, ListenerLookupType lookup)
{
- v8::Isolate* isolate = v8::Isolate::GetCurrent();
- v8::Handle<v8::Context> context = isolate->GetCurrentContext();
- if (context.IsEmpty())
- return 0;
+ ASSERT(!scriptState->contextIsEmpty());
if (lookup == ListenerFindOnly) {
// Used by EventTarget::removeEventListener, specifically
// EventTargetV8Internal::removeEventListenerMethod
ASSERT(!isAttribute);
- return V8EventListenerList::findWrapper(value, isolate);
+ return V8EventListenerList::findWrapper(value, scriptState);
}
- if (V8DOMWrapper::isWrapperOfType(toInnerGlobalObject(context), &V8Window::wrapperTypeInfo))
- return V8EventListenerList::findOrCreateWrapper<V8EventListener>(value, isAttribute, isolate);
- return V8EventListenerList::findOrCreateWrapper<V8WorkerGlobalScopeEventListener>(value, isAttribute, isolate);
+ if (toDOMWindow(scriptState->context()))
+ return V8EventListenerList::findOrCreateWrapper<V8EventListener>(value, isAttribute, scriptState);
+ return V8EventListenerList::findOrCreateWrapper<V8WorkerGlobalScopeEventListener>(value, isAttribute, scriptState);
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8EventListenerList.h b/chromium/third_party/WebKit/Source/bindings/v8/V8EventListenerList.h
index 3be3bb9f34f..34ee4106e01 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8EventListenerList.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8EventListenerList.h
@@ -31,15 +31,13 @@
#ifndef V8EventListenerList_h
#define V8EventListenerList_h
+#include "bindings/v8/V8Binding.h"
#include "bindings/v8/V8EventListener.h"
-#include "bindings/v8/V8HiddenPropertyName.h"
-
#include <v8.h>
-#include "wtf/PassRefPtr.h"
namespace WebCore {
-class Frame;
+class LocalFrame;
enum ListenerLookupType {
ListenerFindOnly,
@@ -49,18 +47,18 @@ enum ListenerLookupType {
// This is a container for V8EventListener objects that uses hidden properties of v8::Object to speed up lookups.
class V8EventListenerList {
public:
- static PassRefPtr<V8EventListener> findWrapper(v8::Local<v8::Value> value, v8::Isolate* isolate)
+ static PassRefPtr<V8EventListener> findWrapper(v8::Local<v8::Value> value, ScriptState* scriptState)
{
- ASSERT(isolate->InContext());
+ ASSERT(scriptState->isolate()->InContext());
if (!value->IsObject())
- return 0;
+ return nullptr;
- v8::Handle<v8::String> wrapperProperty = getHiddenProperty(false, isolate);
- return doFindWrapper(v8::Local<v8::Object>::Cast(value), wrapperProperty, isolate);
+ v8::Handle<v8::String> wrapperProperty = getHiddenProperty(false, scriptState->isolate());
+ return doFindWrapper(v8::Local<v8::Object>::Cast(value), wrapperProperty, scriptState);
}
template<typename WrapperType>
- static PassRefPtr<V8EventListener> findOrCreateWrapper(v8::Local<v8::Value>, bool isAttribute, v8::Isolate*);
+ static PassRefPtr<V8EventListener> findOrCreateWrapper(v8::Local<v8::Value>, bool isAttribute, ScriptState*);
static void clearWrapper(v8::Handle<v8::Object> listenerObject, bool isAttribute, v8::Isolate* isolate)
{
@@ -68,13 +66,13 @@ public:
listenerObject->DeleteHiddenValue(wrapperProperty);
}
- static PassRefPtr<EventListener> getEventListener(v8::Local<v8::Value>, bool isAttribute, ListenerLookupType);
+ static PassRefPtr<EventListener> getEventListener(ScriptState*, v8::Local<v8::Value>, bool isAttribute, ListenerLookupType);
private:
- static V8EventListener* doFindWrapper(v8::Local<v8::Object> object, v8::Handle<v8::String> wrapperProperty, v8::Isolate* isolate)
+ static V8EventListener* doFindWrapper(v8::Local<v8::Object> object, v8::Handle<v8::String> wrapperProperty, ScriptState* scriptState)
{
- ASSERT(isolate->InContext());
- v8::HandleScope scope(isolate);
+ v8::HandleScope scope(scriptState->isolate());
+ ASSERT(scriptState->isolate()->InContext());
v8::Local<v8::Value> listener = object->GetHiddenValue(wrapperProperty);
if (listener.IsEmpty())
return 0;
@@ -83,27 +81,28 @@ private:
static inline v8::Handle<v8::String> getHiddenProperty(bool isAttribute, v8::Isolate* isolate)
{
- return isAttribute ? V8HiddenPropertyName::attributeListener(isolate) : V8HiddenPropertyName::listener(isolate);
+ return isAttribute ? v8AtomicString(isolate, "attributeListener") : v8AtomicString(isolate, "listener");
}
};
template<typename WrapperType>
-PassRefPtr<V8EventListener> V8EventListenerList::findOrCreateWrapper(v8::Local<v8::Value> value, bool isAttribute, v8::Isolate* isolate)
+PassRefPtr<V8EventListener> V8EventListenerList::findOrCreateWrapper(v8::Local<v8::Value> value, bool isAttribute, ScriptState* scriptState)
{
+ v8::Isolate* isolate = scriptState->isolate();
ASSERT(isolate->InContext());
if (!value->IsObject()
// Non-callable attribute setter input is treated as null (no wrapper)
|| (isAttribute && !value->IsFunction()))
- return 0;
+ return nullptr;
v8::Local<v8::Object> object = v8::Local<v8::Object>::Cast(value);
v8::Handle<v8::String> wrapperProperty = getHiddenProperty(isAttribute, isolate);
- V8EventListener* wrapper = doFindWrapper(object, wrapperProperty, isolate);
+ V8EventListener* wrapper = doFindWrapper(object, wrapperProperty, scriptState);
if (wrapper)
return wrapper;
- RefPtr<V8EventListener> wrapperPtr = WrapperType::create(object, isAttribute, isolate);
+ RefPtr<V8EventListener> wrapperPtr = WrapperType::create(object, isAttribute, scriptState);
if (wrapperPtr)
object->SetHiddenValue(wrapperProperty, v8::External::New(isolate, wrapperPtr.get()));
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8GCController.cpp b/chromium/third_party/WebKit/Source/bindings/v8/V8GCController.cpp
index 133914ad9c4..b09bfe742a3 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8GCController.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8GCController.cpp
@@ -31,13 +31,12 @@
#include "config.h"
#include "bindings/v8/V8GCController.h"
-#include <algorithm>
-#include "V8MutationObserver.h"
-#include "V8Node.h"
-#include "V8ScriptRunner.h"
+#include "bindings/core/v8/V8MutationObserver.h"
+#include "bindings/core/v8/V8Node.h"
#include "bindings/v8/RetainedDOMInfo.h"
#include "bindings/v8/V8AbstractEventListener.h"
#include "bindings/v8/V8Binding.h"
+#include "bindings/v8/V8ScriptRunner.h"
#include "bindings/v8/WrapperTypeInfo.h"
#include "core/dom/Attr.h"
#include "core/dom/NodeTraversal.h"
@@ -46,8 +45,12 @@
#include "core/dom/shadow/ShadowRoot.h"
#include "core/html/HTMLImageElement.h"
#include "core/html/HTMLTemplateElement.h"
+#include "core/html/imports/HTMLImportsController.h"
+#include "core/inspector/InspectorTraceEvents.h"
#include "core/svg/SVGElement.h"
+#include "platform/Partitions.h"
#include "platform/TraceEvent.h"
+#include <algorithm>
namespace WebCore {
@@ -64,20 +67,23 @@ static void addReferencesForNodeWithEventListeners(v8::Isolate* isolate, Node* n
if (!v8listener->hasExistingListenerObject())
continue;
- // FIXME: update this to use the upcasting function which v8 will provide.
- v8::Persistent<v8::Value>* value = reinterpret_cast<v8::Persistent<v8::Value>*>(&(v8listener->existingListenerObjectPersistentHandle()));
- isolate->SetReference(wrapper, *value);
+ isolate->SetReference(wrapper, v8::Persistent<v8::Value>::Cast(v8listener->existingListenerObjectPersistentHandle()));
}
}
Node* V8GCController::opaqueRootForGC(Node* node, v8::Isolate*)
{
+ ASSERT(node);
// FIXME: Remove the special handling for image elements.
// The same special handling is in V8GCController::gcTree().
// Maybe should image elements be active DOM nodes?
// See https://code.google.com/p/chromium/issues/detail?id=164882
- if (node->inDocument() || (node->hasTagName(HTMLNames::imgTag) && toHTMLImageElement(node)->hasPendingActivity()))
- return &node->document();
+ if (node->inDocument() || (isHTMLImageElement(*node) && toHTMLImageElement(*node).hasPendingActivity())) {
+ Document& document = node->document();
+ if (HTMLImportsController* controller = document.importsController())
+ return controller->master();
+ return &document;
+ }
if (node->isAttributeNode()) {
Node* ownerElement = toAttr(node)->ownerElement();
@@ -117,12 +123,12 @@ public:
if (m_nodesInNewSpace.size() >= wrappersHandledByEachMinorGC)
return;
- // Casting to a Handle is safe here, since the Persistent cannot get GCd
+ // Casting to a Handle is safe here, since the Persistent doesn't get GCd
// during the GC prologue.
ASSERT((*reinterpret_cast<v8::Handle<v8::Value>*>(value))->IsObject());
v8::Handle<v8::Object>* wrapper = reinterpret_cast<v8::Handle<v8::Object>*>(value);
- ASSERT(V8DOMWrapper::maybeDOMWrapper(*wrapper));
- ASSERT(V8Node::hasInstanceInAnyWorld(*wrapper, m_isolate));
+ ASSERT(V8DOMWrapper::isDOMWrapper(*wrapper));
+ ASSERT(V8Node::hasInstance(*wrapper, m_isolate));
Node* node = V8Node::toNative(*wrapper);
// A minor DOM GC can handle only node wrappers in the main world.
// Note that node->wrapper().IsEmpty() returns true for nodes that
@@ -132,8 +138,18 @@ public:
ActiveDOMObject* activeDOMObject = type->toActiveDOMObject(*wrapper);
if (activeDOMObject && activeDOMObject->hasPendingActivity())
return;
+ // FIXME: Remove the special handling for image elements.
+ // The same special handling is in V8GCController::opaqueRootForGC().
+ // Maybe should image elements be active DOM nodes?
+ // See https://code.google.com/p/chromium/issues/detail?id=164882
+ if (isHTMLImageElement(*node) && toHTMLImageElement(*node).hasPendingActivity())
+ return;
+ // FIXME: Remove the special handling for SVG context elements.
+ if (node->isSVGElement() && toSVGElement(node)->isContextElement())
+ return;
+
m_nodesInNewSpace.append(node);
- node->setV8CollectableDuringMinorGC(true);
+ node->markV8CollectableDuringMinorGC();
}
}
@@ -144,82 +160,83 @@ public:
for (; nodeIterator < nodeIteratorEnd; ++nodeIterator) {
Node* node = *nodeIterator;
ASSERT(node->containsWrapper());
- if (node->isV8CollectableDuringMinorGC()) // This branch is just for performance.
+ if (node->isV8CollectableDuringMinorGC()) { // This branch is just for performance.
gcTree(m_isolate, node);
+ node->clearV8CollectableDuringMinorGC();
+ }
}
}
private:
- bool traverseTree(Node* rootNode, Vector<Node*, initialNodeVectorSize>* newSpaceNodes)
+ bool traverseTree(Node* rootNode, Vector<Node*, initialNodeVectorSize>* partiallyDependentNodes)
{
// To make each minor GC time bounded, we might need to give up
// traversing at some point for a large DOM tree. That being said,
// I could not observe the need even in pathological test cases.
for (Node* node = rootNode; node; node = NodeTraversal::next(*node)) {
if (node->containsWrapper()) {
- // FIXME: Remove the special handling for image elements.
- // FIXME: Remove the special handling for SVG context elements.
- // The same special handling is in V8GCController::opaqueRootForGC().
- // Maybe should image elements be active DOM nodes?
- // See https://code.google.com/p/chromium/issues/detail?id=164882
- if (!node->isV8CollectableDuringMinorGC() || (node->hasTagName(HTMLNames::imgTag) && toHTMLImageElement(node)->hasPendingActivity()) || (node->isSVGElement() && toSVGElement(node)->isContextElement())) {
+ if (!node->isV8CollectableDuringMinorGC()) {
// This node is not in the new space of V8. This indicates that
// the minor GC cannot anyway judge reachability of this DOM tree.
// Thus we give up traversing the DOM tree.
return false;
}
- node->setV8CollectableDuringMinorGC(false);
- newSpaceNodes->append(node);
+ node->clearV8CollectableDuringMinorGC();
+ partiallyDependentNodes->append(node);
}
if (ShadowRoot* shadowRoot = node->youngestShadowRoot()) {
- if (!traverseTree(shadowRoot, newSpaceNodes))
+ if (!traverseTree(shadowRoot, partiallyDependentNodes))
return false;
} else if (node->isShadowRoot()) {
if (ShadowRoot* shadowRoot = toShadowRoot(node)->olderShadowRoot()) {
- if (!traverseTree(shadowRoot, newSpaceNodes))
+ if (!traverseTree(shadowRoot, partiallyDependentNodes))
return false;
}
}
// <template> has a |content| property holding a DOM fragment which we must traverse,
// just like we do for the shadow trees above.
- if (node->hasTagName(HTMLNames::templateTag)) {
- if (!traverseTree(toHTMLTemplateElement(node)->content(), newSpaceNodes))
+ if (isHTMLTemplateElement(*node)) {
+ if (!traverseTree(toHTMLTemplateElement(*node).content(), partiallyDependentNodes))
return false;
}
+
+ // Document maintains the list of imported documents through HTMLImportsController.
+ if (node->isDocumentNode()) {
+ Document* document = toDocument(node);
+ HTMLImportsController* controller = document->importsController();
+ if (controller && document == controller->master()) {
+ for (unsigned i = 0; i < controller->loaderCount(); ++i) {
+ if (!traverseTree(controller->loaderDocumentAt(i), partiallyDependentNodes))
+ return false;
+ }
+ }
+ }
}
return true;
}
void gcTree(v8::Isolate* isolate, Node* startNode)
{
- Vector<Node*, initialNodeVectorSize> newSpaceNodes;
+ Vector<Node*, initialNodeVectorSize> partiallyDependentNodes;
Node* node = startNode;
while (Node* parent = node->parentOrShadowHostOrTemplateHostNode())
node = parent;
- if (!traverseTree(node, &newSpaceNodes))
+ if (!traverseTree(node, &partiallyDependentNodes))
return;
// We completed the DOM tree traversal. All wrappers in the DOM tree are
- // stored in newSpaceNodes and are expected to exist in the new space of V8.
+ // stored in partiallyDependentNodes and are expected to exist in the new space of V8.
// We report those wrappers to V8 as an object group.
- Node** nodeIterator = newSpaceNodes.begin();
- Node** const nodeIteratorEnd = newSpaceNodes.end();
+ Node** nodeIterator = partiallyDependentNodes.begin();
+ Node** const nodeIteratorEnd = partiallyDependentNodes.end();
if (nodeIterator == nodeIteratorEnd)
return;
- v8::UniqueId id(reinterpret_cast<intptr_t>((*nodeIterator)->unsafePersistent().value()));
+
+ Node* groupRoot = *nodeIterator;
for (; nodeIterator != nodeIteratorEnd; ++nodeIterator) {
- // This is safe because we know that GC won't happen before we
- // dispose the UnsafePersistent (we're just preparing a GC). Though,
- // we need to keep the UnsafePersistent alive until we're done with
- // v8::Persistent.
- UnsafePersistent<v8::Object> unsafeWrapper = (*nodeIterator)->unsafePersistent();
- v8::Persistent<v8::Object>* wrapper = unsafeWrapper.persistent();
- wrapper->MarkPartiallyDependent();
- // FIXME: update this to use the upcasting function which v8 will provide
- v8::Persistent<v8::Value>* value = reinterpret_cast<v8::Persistent<v8::Value>*>(wrapper);
- isolate->SetObjectGroupId(*value, id);
+ (*nodeIterator)->markAsDependentGroup(groupRoot, isolate);
}
}
@@ -238,16 +255,14 @@ public:
virtual void VisitPersistentHandle(v8::Persistent<v8::Value>* value, uint16_t classId) OVERRIDE
{
- // Casting to a Handle is safe here, since the Persistent cannot get GCd
- // during the GC prologue.
- ASSERT((*reinterpret_cast<v8::Handle<v8::Value>*>(value))->IsObject());
-
if (classId != v8DOMNodeClassId && classId != v8DOMObjectClassId)
return;
+ // Casting to a Handle is safe here, since the Persistent doesn't get GCd
+ // during the GC prologue.
+ ASSERT((*reinterpret_cast<v8::Handle<v8::Value>*>(value))->IsObject());
v8::Handle<v8::Object>* wrapper = reinterpret_cast<v8::Handle<v8::Object>*>(value);
-
- ASSERT(V8DOMWrapper::maybeDOMWrapper(*wrapper));
+ ASSERT(V8DOMWrapper::isDOMWrapper(*wrapper));
if (value->IsIndependent())
return;
@@ -255,26 +270,13 @@ public:
const WrapperTypeInfo* type = toWrapperTypeInfo(*wrapper);
void* object = toNative(*wrapper);
- if (V8MutationObserver::wrapperTypeInfo.equals(type)) {
- // FIXME: Allow opaqueRootForGC to operate on multiple roots and move this logic into V8MutationObserverCustom.
- MutationObserver* observer = static_cast<MutationObserver*>(object);
- HashSet<Node*> observedNodes = observer->getObservedNodes();
- for (HashSet<Node*>::iterator it = observedNodes.begin(); it != observedNodes.end(); ++it) {
- v8::UniqueId id(reinterpret_cast<intptr_t>(V8GCController::opaqueRootForGC(*it, m_isolate)));
- m_isolate->SetReferenceFromGroup(id, *value);
- }
- } else {
- ActiveDOMObject* activeDOMObject = type->toActiveDOMObject(*wrapper);
- if (activeDOMObject && activeDOMObject->hasPendingActivity())
- m_isolate->SetObjectGroupId(*value, liveRootId());
- }
+ ActiveDOMObject* activeDOMObject = type->toActiveDOMObject(*wrapper);
+ if (activeDOMObject && activeDOMObject->hasPendingActivity())
+ m_isolate->SetObjectGroupId(*value, liveRootId());
if (classId == v8DOMNodeClassId) {
- ASSERT(V8Node::hasInstanceInAnyWorld(*wrapper, m_isolate));
- ASSERT(!value->IsIndependent());
-
+ ASSERT(V8Node::hasInstance(*wrapper, m_isolate));
Node* node = static_cast<Node*>(object);
-
if (node->hasEventListeners())
addReferencesForNodeWithEventListeners(m_isolate, node, v8::Persistent<v8::Object>::Cast(*value));
Node* root = V8GCController::opaqueRootForGC(node, m_isolate);
@@ -282,9 +284,7 @@ public:
if (m_constructRetainedObjectInfos)
m_groupsWhichNeedRetainerInfo.append(root);
} else if (classId == v8DOMObjectClassId) {
- ASSERT(!value->IsIndependent());
- v8::Persistent<v8::Object>* wrapperPersistent = reinterpret_cast<v8::Persistent<v8::Object>*>(value);
- type->visitDOMWrapper(object, *wrapperPersistent, m_isolate);
+ type->visitDOMWrapper(object, v8::Persistent<v8::Object>::Cast(*value), m_isolate);
} else {
ASSERT_NOT_REACHED();
}
@@ -325,10 +325,18 @@ private:
bool m_constructRetainedObjectInfos;
};
+static unsigned long long usedHeapSize(v8::Isolate* isolate)
+{
+ v8::HeapStatistics heapStatistics;
+ isolate->GetHeapStatistics(&heapStatistics);
+ return heapStatistics.used_heap_size();
+}
+
void V8GCController::gcPrologue(v8::GCType type, v8::GCCallbackFlags flags)
{
// FIXME: It would be nice if the GC callbacks passed the Isolate directly....
v8::Isolate* isolate = v8::Isolate::GetCurrent();
+ TRACE_EVENT_BEGIN1(TRACE_DISABLED_BY_DEFAULT("devtools.timeline"), "GCEvent", "usedHeapSizeBefore", usedHeapSize(isolate));
if (type == v8::kGCTypeScavenge)
minorGCPrologue(isolate);
else if (type == v8::kGCTypeMarkSweepCompact)
@@ -340,14 +348,14 @@ void V8GCController::minorGCPrologue(v8::Isolate* isolate)
TRACE_EVENT_BEGIN0("v8", "minorGC");
if (isMainThread()) {
{
- TRACE_EVENT_SCOPED_SAMPLING_STATE("Blink", "MinorGC");
+ TRACE_EVENT_SCOPED_SAMPLING_STATE("Blink", "DOMMinorGC");
v8::HandleScope scope(isolate);
MinorGCWrapperVisitor visitor(isolate);
v8::V8::VisitHandlesForPartialDependence(isolate, &visitor);
visitor.notifyFinished();
}
V8PerIsolateData::from(isolate)->setPreviousSamplingState(TRACE_EVENT_GET_SAMPLING_STATE());
- TRACE_EVENT_SET_SAMPLING_STATE("V8", "MinorGC");
+ TRACE_EVENT_SET_SAMPLING_STATE("V8", "V8MinorGC");
}
}
@@ -358,13 +366,13 @@ void V8GCController::majorGCPrologue(bool constructRetainedObjectInfos, v8::Isol
TRACE_EVENT_BEGIN0("v8", "majorGC");
if (isMainThread()) {
{
- TRACE_EVENT_SCOPED_SAMPLING_STATE("Blink", "MajorGC");
+ TRACE_EVENT_SCOPED_SAMPLING_STATE("Blink", "DOMMajorGC");
MajorGCWrapperVisitor visitor(isolate, constructRetainedObjectInfos);
v8::V8::VisitHandlesWithClassIds(&visitor);
visitor.notifyFinished();
}
V8PerIsolateData::from(isolate)->setPreviousSamplingState(TRACE_EVENT_GET_SAMPLING_STATE());
- TRACE_EVENT_SET_SAMPLING_STATE("V8", "MajorGC");
+ TRACE_EVENT_SET_SAMPLING_STATE("V8", "V8MajorGC");
} else {
MajorGCWrapperVisitor visitor(isolate, constructRetainedObjectInfos);
v8::V8::VisitHandlesWithClassIds(&visitor);
@@ -380,6 +388,29 @@ void V8GCController::gcEpilogue(v8::GCType type, v8::GCCallbackFlags flags)
minorGCEpilogue(isolate);
else if (type == v8::kGCTypeMarkSweepCompact)
majorGCEpilogue(isolate);
+
+ // Forces a Blink heap garbage collection when a garbage collection
+ // was forced from V8. This is used for tests that force GCs from
+ // JavaScript to verify that objects die when expected.
+ if (flags & v8::kGCCallbackFlagForced) {
+ // This single GC is not enough for two reasons:
+ // (1) The GC is not precise because the GC scans on-stack pointers conservatively.
+ // (2) One GC is not enough to break a chain of persistent handles. It's possible that
+ // some heap allocated objects own objects that contain persistent handles
+ // pointing to other heap allocated objects. To break the chain, we need multiple GCs.
+ //
+ // Regarding (1), we force a precise GC at the end of the current event loop. So if you want
+ // to collect all garbage, you need to wait until the next event loop.
+ // Regarding (2), it would be OK in practice to trigger only one GC per gcEpilogue, because
+ // GCController.collectAll() forces 7 V8's GC.
+ Heap::collectGarbage(ThreadState::HeapPointersOnStack);
+
+ // Forces a precise GC at the end of the current event loop.
+ Heap::setForcePreciseGCForTesting();
+ }
+
+ TRACE_EVENT_END1(TRACE_DISABLED_BY_DEFAULT("devtools.timeline"), "GCEvent", "usedHeapSizeAfter", usedHeapSize(isolate));
+ TRACE_EVENT_INSTANT1(TRACE_DISABLED_BY_DEFAULT("devtools.timeline"), "UpdateCounters", "data", InspectorUpdateCountersEvent::data());
}
void V8GCController::minorGCEpilogue(v8::Isolate* isolate)
@@ -398,25 +429,27 @@ void V8GCController::majorGCEpilogue(v8::Isolate* isolate)
TRACE_EVENT_SET_NONCONST_SAMPLING_STATE(V8PerIsolateData::from(isolate)->previousSamplingState());
}
-void V8GCController::hintForCollectGarbage()
+void V8GCController::collectGarbage(v8::Isolate* isolate)
{
- V8PerIsolateData* data = V8PerIsolateData::current();
- if (!data->shouldCollectGarbageSoon())
- return;
- const int longIdlePauseInMS = 1000;
- data->clearShouldCollectGarbageSoon();
- v8::V8::ContextDisposedNotification();
- v8::V8::IdleNotification(longIdlePauseInMS);
+ v8::HandleScope handleScope(isolate);
+ RefPtr<ScriptState> scriptState = ScriptState::create(v8::Context::New(isolate), DOMWrapperWorld::create());
+ ScriptState::Scope scope(scriptState.get());
+ V8ScriptRunner::compileAndRunInternalScript(v8String(isolate, "if (gc) gc();"), isolate);
+ scriptState->disposePerContextData();
}
-void V8GCController::collectGarbage(v8::Isolate* isolate)
+void V8GCController::reportDOMMemoryUsageToV8(v8::Isolate* isolate)
{
- v8::HandleScope handleScope(isolate);
- v8::Local<v8::Context> context = v8::Context::New(isolate);
- if (context.IsEmpty())
+ if (!isMainThread())
return;
- v8::Context::Scope contextScope(context);
- V8ScriptRunner::compileAndRunInternalScript(v8String(isolate, "if (gc) gc();"), isolate);
+
+ static size_t lastUsageReportedToV8 = 0;
+
+ size_t currentUsage = Partitions::currentDOMMemoryUsage();
+ int64_t diff = static_cast<int64_t>(currentUsage) - static_cast<int64_t>(lastUsageReportedToV8);
+ isolate->AdjustAmountOfExternalAllocatedMemory(diff);
+
+ lastUsageReportedToV8 = currentUsage;
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8GCController.h b/chromium/third_party/WebKit/Source/bindings/v8/V8GCController.h
index b0aa80227d5..b0c541a84b5 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8GCController.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8GCController.h
@@ -47,10 +47,11 @@ public:
static void majorGCPrologue(bool constructRetainedObjectInfos, v8::Isolate*);
static void majorGCEpilogue(v8::Isolate*);
- static void hintForCollectGarbage();
static void collectGarbage(v8::Isolate*);
static Node* opaqueRootForGC(Node*, v8::Isolate*);
+
+ static void reportDOMMemoryUsageToV8(v8::Isolate*);
};
}
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8GCForContextDispose.cpp b/chromium/third_party/WebKit/Source/bindings/v8/V8GCForContextDispose.cpp
index e7d40bd129e..688a212a30c 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8GCForContextDispose.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8GCForContextDispose.cpp
@@ -32,6 +32,7 @@
#include "bindings/v8/V8GCForContextDispose.h"
#include "wtf/StdLibExtras.h"
+#include <v8.h>
namespace WebCore {
@@ -46,7 +47,7 @@ void V8GCForContextDispose::notifyContextDisposed(bool isMainFrame)
m_didDisposeContextForMainFrame = m_didDisposeContextForMainFrame || isMainFrame;
v8::V8::ContextDisposedNotification();
if (!m_pseudoIdleTimer.isActive())
- m_pseudoIdleTimer.startOneShot(0.8);
+ m_pseudoIdleTimer.startOneShot(0.8, FROM_HERE);
}
void V8GCForContextDispose::notifyIdleSooner(double maximumFireInterval)
@@ -55,7 +56,7 @@ void V8GCForContextDispose::notifyIdleSooner(double maximumFireInterval)
double nextFireInterval = m_pseudoIdleTimer.nextFireInterval();
if (nextFireInterval > maximumFireInterval) {
m_pseudoIdleTimer.stop();
- m_pseudoIdleTimer.startOneShot(maximumFireInterval);
+ m_pseudoIdleTimer.startOneShot(maximumFireInterval, FROM_HERE);
}
}
}
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8GCForContextDispose.h b/chromium/third_party/WebKit/Source/bindings/v8/V8GCForContextDispose.h
index 3d16be47de2..53fbbfd53e3 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8GCForContextDispose.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8GCForContextDispose.h
@@ -31,7 +31,6 @@
#ifndef V8GCForContextDispose_h
#define V8GCForContextDispose_h
-#include <v8.h>
#include "platform/Timer.h"
namespace WebCore {
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/ScriptObject.cpp b/chromium/third_party/WebKit/Source/bindings/v8/V8GarbageCollected.h
index 36b1a54451a..697974839d9 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/ScriptObject.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8GarbageCollected.h
@@ -1,5 +1,5 @@
/*
- * Copyright (C) 2009 Google Inc. All rights reserved.
+ * Copyright (C) 2014 Google Inc. All rights reserved.
*
* Redistribution and use in source and binary forms, with or without
* modification, are permitted provided that the following conditions are
@@ -28,55 +28,62 @@
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
-#include "config.h"
-#include "bindings/v8/ScriptObject.h"
-
-#include "bindings/v8/ScriptScope.h"
-#include "bindings/v8/ScriptState.h"
-
-#include "V8InspectorFrontendHost.h"
+#ifndef V8GarbageCollected_h
+#define V8GarbageCollected_h
#include <v8.h>
namespace WebCore {
-ScriptObject::ScriptObject(ScriptState* scriptState, v8::Handle<v8::Object> v8Object)
- : ScriptValue(v8Object, scriptState->isolate())
- , m_scriptState(scriptState)
-{
-}
+template<typename T>
+class V8GarbageCollected {
+ WTF_MAKE_NONCOPYABLE(V8GarbageCollected);
+public:
+ static T* Cast(v8::Handle<v8::Value> value)
+ {
+ ASSERT(value->IsExternal());
+ T* result = static_cast<T*>(value.As<v8::External>()->Value());
+ RELEASE_ASSERT(result->m_handle == value);
+ return result;
+ }
-ScriptObject::ScriptObject(ScriptState* scriptState, const ScriptValue& scriptValue)
- : ScriptValue(scriptValue)
- , m_scriptState(scriptState)
-{
-}
+protected:
+ V8GarbageCollected(v8::Isolate* isolate)
+ : m_isolate(isolate)
+ , m_handle(isolate, v8::External::New(isolate, static_cast<T*>(this)))
+ , m_releasedToV8GarbageCollector(false)
+ {
+ }
-v8::Handle<v8::Object> ScriptObject::v8Object() const
-{
- ASSERT(v8Value()->IsObject());
- return v8::Handle<v8::Object>::Cast(v8Value());
-}
+ v8::Handle<v8::External> releaseToV8GarbageCollector()
+ {
+ ASSERT(!m_handle.isWeak()); // Call this exactly once.
+ m_releasedToV8GarbageCollector = true;
+ v8::Handle<v8::External> result = m_handle.newLocal(m_isolate);
+ m_handle.setWeak(static_cast<T*>(this), &weakCallback);
+ return result;
+ }
-bool ScriptGlobalObject::set(ScriptState* scriptState, const char* name, InspectorFrontendHost* value)
-{
- ScriptScope scope(scriptState);
- scope.global()->Set(v8AtomicString(scriptState->isolate(), name), toV8(value, v8::Handle<v8::Object>(), scriptState->isolate()));
- return scope.success();
-}
+ ~V8GarbageCollected()
+ {
+ ASSERT(!m_releasedToV8GarbageCollector || m_handle.isEmpty());
+ }
-bool ScriptGlobalObject::get(ScriptState* scriptState, const char* name, ScriptObject& value)
-{
- ScriptScope scope(scriptState);
- v8::Local<v8::Value> v8Value = scope.global()->Get(v8AtomicString(scriptState->isolate(), name));
- if (v8Value.IsEmpty())
- return false;
+ v8::Isolate* isolate() { return m_isolate; }
- if (!v8Value->IsObject())
- return false;
+private:
+ static void weakCallback(const v8::WeakCallbackData<v8::External, T>& data)
+ {
+ T* self = data.GetParameter();
+ self->m_handle.clear();
+ delete self;
+ }
- value = ScriptObject(scriptState, v8::Handle<v8::Object>::Cast(v8Value));
- return true;
-}
+ v8::Isolate* m_isolate;
+ ScopedPersistent<v8::External> m_handle;
+ bool m_releasedToV8GarbageCollector;
+};
} // namespace WebCore
+
+#endif // V8GarbageCollected_h
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8HiddenPropertyName.cpp b/chromium/third_party/WebKit/Source/bindings/v8/V8HiddenPropertyName.cpp
deleted file mode 100644
index 1108e9e7aa0..00000000000
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8HiddenPropertyName.cpp
+++ /dev/null
@@ -1,79 +0,0 @@
-/*
- * Copyright (C) 2009 Google Inc. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions are
- * met:
- *
- * * Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * * Redistributions in binary form must reproduce the above
- * copyright notice, this list of conditions and the following disclaimer
- * in the documentation and/or other materials provided with the
- * distribution.
- * * Neither the name of Google Inc. nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
- * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
- * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
- * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
- * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
- * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
- * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
- * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
- * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-#include "config.h"
-#include "bindings/v8/V8HiddenPropertyName.h"
-
-#include "bindings/v8/V8Binding.h"
-#include <string.h>
-#include "wtf/StdLibExtras.h"
-#include "wtf/Vector.h"
-
-namespace WebCore {
-
-#define V8_AS_STRING(x) V8_AS_STRING_IMPL(x)
-#define V8_AS_STRING_IMPL(x) #x
-
-#define V8_HIDDEN_PROPERTY_PREFIX "WebCore::HiddenProperty::"
-
-#define V8_DEFINE_HIDDEN_PROPERTY(name) \
-v8::Handle<v8::String> V8HiddenPropertyName::name(v8::Isolate* isolate) \
-{ \
- V8HiddenPropertyName* hiddenPropertyName = V8PerIsolateData::from(isolate)->hiddenPropertyName(); \
- if (hiddenPropertyName->m_##name.IsEmpty()) { \
- createString(V8_HIDDEN_PROPERTY_PREFIX V8_AS_STRING(name), &(hiddenPropertyName->m_##name), isolate); \
- } \
- return v8::Local<v8::String>::New(isolate, hiddenPropertyName->m_##name); \
-}
-
-V8_HIDDEN_PROPERTIES(V8_DEFINE_HIDDEN_PROPERTY);
-
-static v8::Handle<v8::String> hiddenReferenceName(const char* name, unsigned length)
-{
- ASSERT(length);
- Vector<char, 64> prefixedName;
- prefixedName.append(V8_HIDDEN_PROPERTY_PREFIX, sizeof(V8_HIDDEN_PROPERTY_PREFIX) - 1);
- prefixedName.append(name, length);
- return v8AtomicString(v8::Isolate::GetCurrent(), prefixedName.data(), static_cast<int>(prefixedName.size()));
-}
-
-void V8HiddenPropertyName::setNamedHiddenReference(v8::Handle<v8::Object> parent, const char* name, v8::Handle<v8::Value> child)
-{
- ASSERT(name);
- parent->SetHiddenValue(hiddenReferenceName(name, strlen(name)), child);
-}
-
-void V8HiddenPropertyName::createString(const char* key, v8::Persistent<v8::String>* handle, v8::Isolate* isolate)
-{
- v8::HandleScope scope(isolate);
- handle->Reset(isolate, v8AtomicString(isolate, key));
-}
-
-} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8HiddenPropertyName.h b/chromium/third_party/WebKit/Source/bindings/v8/V8HiddenPropertyName.h
deleted file mode 100644
index 76dc17ca1ae..00000000000
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8HiddenPropertyName.h
+++ /dev/null
@@ -1,83 +0,0 @@
-/*
- * Copyright (C) 2012 Google Inc. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions are
- * met:
- *
- * * Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * * Redistributions in binary form must reproduce the above
- * copyright notice, this list of conditions and the following disclaimer
- * in the documentation and/or other materials provided with the
- * distribution.
- * * Neither the name of Google Inc. nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
- * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
- * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
- * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
- * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
- * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
- * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
- * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
- * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-#ifndef V8HiddenPropertyName_h
-#define V8HiddenPropertyName_h
-
-#include <v8.h>
-
-namespace WebCore {
-
-#define V8_HIDDEN_PROPERTIES(V) \
- V(adaptorFunctionPeer) \
- V(attributeListener) \
- V(callback) \
- V(condition) \
- V(customElementAttached) \
- V(customElementAttributeChanged) \
- V(customElementCreated) \
- V(customElementDetached) \
- V(customElementDocument) \
- V(customElementIsInterfacePrototypeObject) \
- V(customElementNamespaceURI) \
- V(customElementTagName) \
- V(customElementType) \
- V(data) \
- V(detail) \
- V(document) \
- V(event) \
- V(error) \
- V(listener) \
- V(scriptState) \
- V(sleepFunction) \
- V(state) \
- V(toStringString) \
- V(typedArrayHiddenCopyMethod) \
- V(thenableHiddenPromise)
-
-class V8HiddenPropertyName {
-public:
- V8HiddenPropertyName() { }
-#define V8_DECLARE_PROPERTY(name) static v8::Handle<v8::String> name(v8::Isolate*);
- V8_HIDDEN_PROPERTIES(V8_DECLARE_PROPERTY);
-#undef V8_DECLARE_PROPERTY
-
- static void setNamedHiddenReference(v8::Handle<v8::Object> parent, const char* name, v8::Handle<v8::Value> child);
-
-private:
- static void createString(const char* key, v8::Persistent<v8::String>* handle, v8::Isolate*);
-#define V8_DECLARE_FIELD(name) v8::Persistent<v8::String> m_##name;
- V8_HIDDEN_PROPERTIES(V8_DECLARE_FIELD);
-#undef V8_DECLARE_FIELD
-};
-
-}
-
-#endif // V8HiddenPropertyName_h
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8HiddenValue.cpp b/chromium/third_party/WebKit/Source/bindings/v8/V8HiddenValue.cpp
new file mode 100644
index 00000000000..ab6e97d147c
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8HiddenValue.cpp
@@ -0,0 +1,46 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "config.h"
+#include "bindings/v8/V8HiddenValue.h"
+
+#include "bindings/v8/ScriptWrappable.h"
+#include "bindings/v8/V8Binding.h"
+
+namespace WebCore {
+
+#define V8_DEFINE_METHOD(name) \
+v8::Handle<v8::String> V8HiddenValue::name(v8::Isolate* isolate) \
+{ \
+ V8HiddenValue* hiddenValue = V8PerIsolateData::from(isolate)->hiddenValue(); \
+ if (hiddenValue->m_##name.isEmpty()) { \
+ hiddenValue->m_##name.set(isolate, v8AtomicString(isolate, #name)); \
+ } \
+ return hiddenValue->m_##name.newLocal(isolate); \
+}
+
+V8_HIDDEN_VALUES(V8_DEFINE_METHOD);
+
+v8::Local<v8::Value> V8HiddenValue::getHiddenValue(v8::Isolate* isolate, v8::Handle<v8::Object> object, v8::Handle<v8::String> key)
+{
+ return object->GetHiddenValue(key);
+}
+
+bool V8HiddenValue::setHiddenValue(v8::Isolate* isolate, v8::Handle<v8::Object> object, v8::Handle<v8::String> key, v8::Handle<v8::Value> value)
+{
+ return object->SetHiddenValue(key, value);
+}
+
+bool V8HiddenValue::deleteHiddenValue(v8::Isolate* isolate, v8::Handle<v8::Object> object, v8::Handle<v8::String> key)
+{
+ return object->DeleteHiddenValue(key);
+}
+
+v8::Local<v8::Value> V8HiddenValue::getHiddenValueFromMainWorldWrapper(v8::Isolate* isolate, ScriptWrappable* wrappable, v8::Handle<v8::String> key)
+{
+ v8::Local<v8::Object> wrapper = wrappable->newLocalWrapper(isolate);
+ return wrapper.IsEmpty() ? v8::Local<v8::Value>() : getHiddenValue(isolate, wrapper, key);
+}
+
+} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8HiddenValue.h b/chromium/third_party/WebKit/Source/bindings/v8/V8HiddenValue.h
new file mode 100644
index 00000000000..75da4efe761
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8HiddenValue.h
@@ -0,0 +1,61 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#ifndef V8HiddenValue_h
+#define V8HiddenValue_h
+
+#include "bindings/v8/ScopedPersistent.h"
+#include <v8.h>
+
+namespace WebCore {
+
+class ScriptWrappable;
+
+#define V8_HIDDEN_VALUES(V) \
+ V(arrayBufferData) \
+ V(customElementAttached) \
+ V(customElementAttributeChanged) \
+ V(customElementCreated) \
+ V(customElementDetached) \
+ V(customElementDocument) \
+ V(customElementIsInterfacePrototypeObject) \
+ V(customElementNamespaceURI) \
+ V(customElementTagName) \
+ V(customElementType) \
+ V(callback) \
+ V(condition) \
+ V(data) \
+ V(detail) \
+ V(document) \
+ V(error) \
+ V(event) \
+ V(idbCursorRequest) \
+ V(port1) \
+ V(port2) \
+ V(state) \
+ V(stringData) \
+ V(scriptState) \
+ V(thenableHiddenPromise) \
+ V(toStringString)
+
+class V8HiddenValue {
+public:
+#define V8_DECLARE_METHOD(name) static v8::Handle<v8::String> name(v8::Isolate* isolate);
+ V8_HIDDEN_VALUES(V8_DECLARE_METHOD);
+#undef V8_DECLARE_METHOD
+
+ static v8::Local<v8::Value> getHiddenValue(v8::Isolate*, v8::Handle<v8::Object>, v8::Handle<v8::String>);
+ static bool setHiddenValue(v8::Isolate*, v8::Handle<v8::Object>, v8::Handle<v8::String>, v8::Handle<v8::Value>);
+ static bool deleteHiddenValue(v8::Isolate*, v8::Handle<v8::Object>, v8::Handle<v8::String>);
+ static v8::Local<v8::Value> getHiddenValueFromMainWorldWrapper(v8::Isolate*, ScriptWrappable*, v8::Handle<v8::String>);
+
+private:
+#define V8_DECLARE_FIELD(name) ScopedPersistent<v8::String> m_##name;
+ V8_HIDDEN_VALUES(V8_DECLARE_FIELD);
+#undef V8_DECLARE_FIELD
+};
+
+} // namespace WebCore
+
+#endif // V8HiddenValue_h
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8Initializer.cpp b/chromium/third_party/WebKit/Source/bindings/v8/V8Initializer.cpp
index 9646ae76204..0f2f1f13261 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8Initializer.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8Initializer.cpp
@@ -26,11 +26,11 @@
#include "config.h"
#include "bindings/v8/V8Initializer.h"
-#include "V8DOMException.h"
-#include "V8ErrorEvent.h"
-#include "V8History.h"
-#include "V8Location.h"
-#include "V8Window.h"
+#include "bindings/core/v8/V8DOMException.h"
+#include "bindings/core/v8/V8ErrorEvent.h"
+#include "bindings/core/v8/V8History.h"
+#include "bindings/core/v8/V8Location.h"
+#include "bindings/core/v8/V8Window.h"
#include "bindings/v8/DOMWrapperWorld.h"
#include "bindings/v8/ScriptCallStackFactory.h"
#include "bindings/v8/ScriptController.h"
@@ -38,15 +38,15 @@
#include "bindings/v8/V8Binding.h"
#include "bindings/v8/V8ErrorHandler.h"
#include "bindings/v8/V8GCController.h"
-#include "bindings/v8/V8HiddenPropertyName.h"
#include "bindings/v8/V8PerContextData.h"
#include "core/dom/Document.h"
#include "core/dom/ExceptionCode.h"
-#include "core/inspector/ScriptCallStack.h"
#include "core/frame/ConsoleTypes.h"
-#include "core/frame/ContentSecurityPolicy.h"
-#include "core/frame/DOMWindow.h"
-#include "core/frame/Frame.h"
+#include "core/frame/LocalDOMWindow.h"
+#include "core/frame/LocalFrame.h"
+#include "core/frame/csp/ContentSecurityPolicy.h"
+#include "core/inspector/ScriptCallStack.h"
+#include "platform/TraceEvent.h"
#include "public/platform/Platform.h"
#include "wtf/RefPtr.h"
#include "wtf/text/WTFString.h"
@@ -54,12 +54,12 @@
namespace WebCore {
-static Frame* findFrame(v8::Local<v8::Object> host, v8::Local<v8::Value> data, v8::Isolate* isolate)
+static LocalFrame* findFrame(v8::Local<v8::Object> host, v8::Local<v8::Value> data, v8::Isolate* isolate)
{
const WrapperTypeInfo* type = WrapperTypeInfo::unwrap(data);
if (V8Window::wrapperTypeInfo.equals(type)) {
- v8::Handle<v8::Object> windowWrapper = host->FindInstanceInPrototypeChain(V8Window::domTemplate(isolate, worldTypeInMainThread(isolate)));
+ v8::Handle<v8::Object> windowWrapper = V8Window::findInstanceInPrototypeChain(host, isolate);
if (windowWrapper.IsEmpty())
return 0;
return V8Window::toNative(windowWrapper)->frame();
@@ -85,30 +85,34 @@ static void reportFatalErrorInMainThread(const char* location, const char* messa
static void messageHandlerInMainThread(v8::Handle<v8::Message> message, v8::Handle<v8::Value> data)
{
- v8::Isolate* isolate = v8::Isolate::GetCurrent();
- // If called during context initialization, there will be no entered context.
- v8::Handle<v8::Context> enteredContext = isolate->GetEnteredContext();
- if (enteredContext.IsEmpty())
+ ASSERT(isMainThread());
+ // It's possible that messageHandlerInMainThread() is invoked while we're initializing a window.
+ // In that half-baked situation, we don't have a valid context nor a valid world,
+ // so just return immediately.
+ if (DOMWrapperWorld::windowIsBeingInitialized())
return;
- DOMWindow* firstWindow = toDOMWindow(enteredContext);
- if (!firstWindow->isCurrentlyDisplayedInFrame())
+ v8::Isolate* isolate = v8::Isolate::GetCurrent();
+ // If called during context initialization, there will be no entered window.
+ LocalDOMWindow* enteredWindow = enteredDOMWindow(isolate);
+ if (!enteredWindow || !enteredWindow->isCurrentlyDisplayedInFrame())
return;
String errorMessage = toCoreString(message->Get());
v8::Handle<v8::StackTrace> stackTrace = message->GetStackTrace();
- RefPtr<ScriptCallStack> callStack;
+ RefPtrWillBeRawPtr<ScriptCallStack> callStack = nullptr;
// Currently stack trace is only collected when inspector is open.
if (!stackTrace.IsEmpty() && stackTrace->GetFrameCount() > 0)
callStack = createScriptCallStack(stackTrace, ScriptCallStack::maxCallStackSizeToCapture, isolate);
v8::Handle<v8::Value> resourceName = message->GetScriptResourceName();
bool shouldUseDocumentURL = resourceName.IsEmpty() || !resourceName->IsString();
- String resource = shouldUseDocumentURL ? firstWindow->document()->url() : toCoreString(resourceName.As<v8::String>());
+ String resource = shouldUseDocumentURL ? enteredWindow->document()->url() : toCoreString(resourceName.As<v8::String>());
AccessControlStatus corsStatus = message->IsSharedCrossOrigin() ? SharableCrossOrigin : NotSharableCrossOrigin;
- RefPtr<ErrorEvent> event = ErrorEvent::create(errorMessage, resource, message->GetLineNumber(), message->GetStartColumn() + 1, DOMWrapperWorld::current());
+ ScriptState* scriptState = ScriptState::current(isolate);
+ RefPtrWillBeRawPtr<ErrorEvent> event = ErrorEvent::create(errorMessage, resource, message->GetLineNumber(), message->GetStartColumn() + 1, &scriptState->world());
if (V8DOMWrapper::isDOMWrapper(data)) {
v8::Handle<v8::Object> obj = v8::Handle<v8::Object>::Cast(data);
const WrapperTypeInfo* type = toWrapperTypeInfo(obj);
@@ -122,22 +126,24 @@ static void messageHandlerInMainThread(v8::Handle<v8::Message> message, v8::Hand
// This method might be called while we're creating a new context. In this case, we
// avoid storing the exception object, as we can't create a wrapper during context creation.
// FIXME: Can we even get here during initialization now that we bail out when GetEntered returns an empty handle?
- DOMWrapperWorld* world = DOMWrapperWorld::current();
- Frame* frame = firstWindow->document()->frame();
- if (world && frame && frame->script().existingWindowShell(world))
- V8ErrorHandler::storeExceptionOnErrorEventWrapper(event.get(), data, v8::Isolate::GetCurrent());
- firstWindow->document()->reportException(event.release(), callStack, corsStatus);
+ LocalFrame* frame = enteredWindow->document()->frame();
+ if (frame && frame->script().existingWindowShell(scriptState->world())) {
+ V8ErrorHandler::storeExceptionOnErrorEventWrapper(event.get(), data, scriptState->context()->Global(), isolate);
+ }
+ enteredWindow->document()->reportException(event.release(), callStack, corsStatus);
}
static void failedAccessCheckCallbackInMainThread(v8::Local<v8::Object> host, v8::AccessType type, v8::Local<v8::Value> data)
{
- Frame* target = findFrame(host, data, v8::Isolate::GetCurrent());
+ v8::Isolate* isolate = v8::Isolate::GetCurrent();
+ LocalFrame* target = findFrame(host, data, isolate);
if (!target)
return;
- DOMWindow* targetWindow = target->domWindow();
+ LocalDOMWindow* targetWindow = target->domWindow();
- ExceptionState exceptionState(v8::Handle<v8::Object>(), v8::Isolate::GetCurrent());
- exceptionState.throwSecurityError(targetWindow->sanitizedCrossDomainAccessErrorMessage(activeDOMWindow()), targetWindow->crossDomainAccessErrorMessage(activeDOMWindow()));
+ // FIXME: We should modify V8 to pass in more contextual information (context, property, and object).
+ ExceptionState exceptionState(ExceptionState::UnknownContext, 0, 0, isolate->GetCurrentContext()->Global(), isolate);
+ exceptionState.throwSecurityError(targetWindow->sanitizedCrossDomainAccessErrorMessage(callingDOMWindow(isolate)), targetWindow->crossDomainAccessErrorMessage(callingDOMWindow(isolate)));
exceptionState.throwIfNeeded();
}
@@ -145,22 +151,32 @@ static bool codeGenerationCheckCallbackInMainThread(v8::Local<v8::Context> conte
{
if (ExecutionContext* executionContext = toExecutionContext(context)) {
if (ContentSecurityPolicy* policy = toDocument(executionContext)->contentSecurityPolicy())
- return policy->allowEval(ScriptState::forContext(context));
+ return policy->allowEval(ScriptState::from(context));
}
return false;
}
+static void timerTraceProfilerInMainThread(const char* name, int status)
+{
+ if (!status) {
+ TRACE_EVENT_BEGIN0("V8", name);
+ } else {
+ TRACE_EVENT_END0("V8", name);
+ }
+}
+
static void initializeV8Common(v8::Isolate* isolate)
{
v8::ResourceConstraints constraints;
- constraints.ConfigureDefaults(static_cast<uint64_t>(blink::Platform::current()->physicalMemoryMB()) << 20, static_cast<uint32_t>(blink::Platform::current()->numberOfProcessors()));
+ constraints.ConfigureDefaults(static_cast<uint64_t>(blink::Platform::current()->physicalMemoryMB()) << 20, static_cast<uint32_t>(blink::Platform::current()->virtualMemoryLimitMB()) << 20, static_cast<uint32_t>(blink::Platform::current()->numberOfProcessors()));
v8::SetResourceConstraints(isolate, &constraints);
v8::V8::AddGCPrologueCallback(V8GCController::gcPrologue);
v8::V8::AddGCEpilogueCallback(V8GCController::gcEpilogue);
- v8::V8::IgnoreOutOfMemoryException();
- v8::Debug::SetLiveEditEnabled(false);
+ v8::Debug::SetLiveEditEnabled(isolate, false);
+
+ isolate->SetAutorunMicrotasks(false);
}
void V8Initializer::initializeMainThreadIfNeeded(v8::Isolate* isolate)
@@ -175,11 +191,14 @@ void V8Initializer::initializeMainThreadIfNeeded(v8::Isolate* isolate)
initializeV8Common(isolate);
v8::V8::SetFatalErrorHandler(reportFatalErrorInMainThread);
+ V8PerIsolateData::ensureInitialized(isolate);
v8::V8::AddMessageListener(messageHandlerInMainThread);
v8::V8::SetFailedAccessCheckCallbackFunction(failedAccessCheckCallbackInMainThread);
v8::V8::SetAllowCodeGenerationFromStringsCallback(codeGenerationCheckCallbackInMainThread);
+
+ isolate->SetEventLogger(timerTraceProfilerInMainThread);
+
ScriptProfiler::initialize();
- V8PerIsolateData::ensureInitialized(isolate);
}
static void reportFatalErrorInWorker(const char* location, const char* message)
@@ -197,16 +216,18 @@ static void messageHandlerInWorker(v8::Handle<v8::Message> message, v8::Handle<v
return;
isReportingException = true;
+ v8::Isolate* isolate = v8::Isolate::GetCurrent();
+ ScriptState* scriptState = ScriptState::current(isolate);
// During the frame teardown, there may not be a valid context.
- if (ExecutionContext* context = getExecutionContext()) {
+ if (ExecutionContext* context = scriptState->executionContext()) {
String errorMessage = toCoreString(message->Get());
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<>, sourceURL, message->GetScriptResourceName());
+ TOSTRING_VOID(V8StringResource<>, sourceURL, message->GetScriptResourceName());
- RefPtr<ErrorEvent> event = ErrorEvent::create(errorMessage, sourceURL, message->GetLineNumber(), message->GetStartColumn() + 1, DOMWrapperWorld::current());
+ RefPtrWillBeRawPtr<ErrorEvent> event = ErrorEvent::create(errorMessage, sourceURL, message->GetLineNumber(), message->GetStartColumn() + 1, &DOMWrapperWorld::current(isolate));
AccessControlStatus corsStatus = message->IsSharedCrossOrigin() ? SharableCrossOrigin : NotSharableCrossOrigin;
- V8ErrorHandler::storeExceptionOnErrorEventWrapper(event.get(), data, v8::Isolate::GetCurrent());
- context->reportException(event.release(), 0, corsStatus);
+ V8ErrorHandler::storeExceptionOnErrorEventWrapper(event.get(), data, scriptState->context()->Global(), isolate);
+ context->reportException(event.release(), nullptr, corsStatus);
}
isReportingException = false;
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8LazyEventListener.cpp b/chromium/third_party/WebKit/Source/bindings/v8/V8LazyEventListener.cpp
index 1d80ffd89bf..23b8fcf52f8 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8LazyEventListener.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8LazyEventListener.cpp
@@ -31,29 +31,29 @@
#include "config.h"
#include "bindings/v8/V8LazyEventListener.h"
-#include "V8Document.h"
-#include "V8HTMLFormElement.h"
-#include "V8Node.h"
+#include "bindings/core/v8/V8Document.h"
+#include "bindings/core/v8/V8HTMLFormElement.h"
+#include "bindings/core/v8/V8Node.h"
#include "bindings/v8/ScriptController.h"
#include "bindings/v8/ScriptSourceCode.h"
#include "bindings/v8/V8Binding.h"
#include "bindings/v8/V8DOMWrapper.h"
-#include "bindings/v8/V8HiddenPropertyName.h"
+#include "bindings/v8/V8HiddenValue.h"
#include "bindings/v8/V8ScriptRunner.h"
#include "core/dom/Document.h"
#include "core/dom/Node.h"
#include "core/html/HTMLElement.h"
#include "core/html/HTMLFormElement.h"
#include "core/inspector/InspectorInstrumentation.h"
-#include "core/frame/ContentSecurityPolicy.h"
-#include "core/frame/Frame.h"
+#include "core/frame/LocalFrame.h"
+#include "core/frame/csp/ContentSecurityPolicy.h"
#include "wtf/StdLibExtras.h"
namespace WebCore {
V8LazyEventListener::V8LazyEventListener(const AtomicString& functionName, const AtomicString& eventParameterName, const String& code, const String sourceURL, const TextPosition& position, Node* node, v8::Isolate* isolate)
- : V8AbstractEventListener(true, mainThreadNormalWorld(), isolate)
+ : V8AbstractEventListener(true, isolate)
, m_functionName(functionName)
, m_eventParameterName(eventParameterName)
, m_code(code)
@@ -64,35 +64,31 @@ V8LazyEventListener::V8LazyEventListener(const AtomicString& functionName, const
}
template<typename T>
-v8::Handle<v8::Object> toObjectWrapper(T* domObject, v8::Isolate* isolate)
+v8::Handle<v8::Object> toObjectWrapper(T* domObject, ScriptState* scriptState)
{
if (!domObject)
- return v8::Object::New();
- v8::Handle<v8::Value> value = toV8(domObject, v8::Handle<v8::Object>(), isolate);
+ return v8::Object::New(scriptState->isolate());
+ v8::Handle<v8::Value> value = toV8(domObject, scriptState->context()->Global(), scriptState->isolate());
if (value.IsEmpty())
- return v8::Object::New();
- return v8::Local<v8::Object>::New(isolate, value.As<v8::Object>());
+ return v8::Object::New(scriptState->isolate());
+ return v8::Local<v8::Object>::New(scriptState->isolate(), value.As<v8::Object>());
}
-v8::Local<v8::Value> V8LazyEventListener::callListenerFunction(ExecutionContext* context, v8::Handle<v8::Value> jsEvent, Event* event)
+v8::Local<v8::Value> V8LazyEventListener::callListenerFunction(v8::Handle<v8::Value> jsEvent, Event* event)
{
- v8::Local<v8::Object> listenerObject = getListenerObject(context);
+ v8::Local<v8::Object> listenerObject = getListenerObject(scriptState()->executionContext());
if (listenerObject.IsEmpty())
return v8::Local<v8::Value>();
v8::Local<v8::Function> handlerFunction = listenerObject.As<v8::Function>();
- v8::Local<v8::Object> receiver = getReceiverObject(context, event);
+ v8::Local<v8::Object> receiver = getReceiverObject(event);
if (handlerFunction.IsEmpty() || receiver.IsEmpty())
return v8::Local<v8::Value>();
- // FIXME: Can |context| be 0 here?
- if (!context)
+ if (!scriptState()->executionContext()->isDocument())
return v8::Local<v8::Value>();
- if (!context->isDocument())
- return v8::Local<v8::Value>();
-
- Frame* frame = toDocument(context)->frame();
+ LocalFrame* frame = toDocument(scriptState()->executionContext())->frame();
if (!frame)
return v8::Local<v8::Value>();
@@ -105,11 +101,32 @@ v8::Local<v8::Value> V8LazyEventListener::callListenerFunction(ExecutionContext*
static void V8LazyEventListenerToString(const v8::FunctionCallbackInfo<v8::Value>& info)
{
- v8SetReturnValue(info, info.Holder()->GetHiddenValue(V8HiddenPropertyName::toStringString(info.GetIsolate())));
+ v8SetReturnValue(info, V8HiddenValue::getHiddenValue(info.GetIsolate(), info.Holder(), V8HiddenValue::toStringString(info.GetIsolate())));
+}
+
+void V8LazyEventListener::handleEvent(ExecutionContext* context, Event* event)
+{
+ v8::HandleScope handleScope(toIsolate(context));
+ // V8LazyEventListener doesn't know the associated context when created.
+ // Thus we lazily get the associated context and set a ScriptState on V8AbstractEventListener.
+ v8::Local<v8::Context> v8Context = toV8Context(context, world());
+ if (v8Context.IsEmpty())
+ return;
+ setScriptState(ScriptState::from(v8Context));
+
+ V8AbstractEventListener::handleEvent(context, event);
}
void V8LazyEventListener::prepareListenerObject(ExecutionContext* context)
{
+ v8::HandleScope handleScope(toIsolate(context));
+ // V8LazyEventListener doesn't know the associated context when created.
+ // Thus we lazily get the associated context and set a ScriptState on V8AbstractEventListener.
+ v8::Local<v8::Context> v8Context = toV8Context(context, world());
+ if (v8Context.IsEmpty())
+ return;
+ setScriptState(ScriptState::from(v8Context));
+
if (context->isDocument() && !toDocument(context)->allowInlineEventHandlers(m_node, this, m_sourceURL, m_position.m_line)) {
clearListenerObject();
return;
@@ -120,17 +137,7 @@ void V8LazyEventListener::prepareListenerObject(ExecutionContext* context)
ASSERT(context->isDocument());
- v8::Isolate* isolate = toIsolate(context);
- v8::HandleScope handleScope(isolate);
-
- // Use the outer scope to hold context.
- v8::Local<v8::Context> v8Context = toV8Context(context, world());
- // Bail out if we cannot get the context.
- if (v8Context.IsEmpty())
- return;
-
- v8::Context::Scope scope(v8Context);
-
+ ScriptState::Scope scope(scriptState());
String listenerSource = InspectorInstrumentation::preprocessEventListener(toDocument(context)->frame(), m_code, m_sourceURL, m_functionName);
// FIXME: Remove the following 'with' hack.
@@ -159,9 +166,9 @@ void V8LazyEventListener::prepareListenerObject(ExecutionContext* context)
"};"
"}}}})";
- v8::Handle<v8::String> codeExternalString = v8String(isolate, code);
+ v8::Handle<v8::String> codeExternalString = v8String(isolate(), code);
- v8::Local<v8::Value> result = V8ScriptRunner::compileAndRunInternalScript(codeExternalString, isolate, m_sourceURL, m_position, 0);
+ v8::Local<v8::Value> result = V8ScriptRunner::compileAndRunInternalScript(codeExternalString, isolate(), m_sourceURL, m_position);
if (result.IsEmpty())
return;
@@ -173,22 +180,22 @@ void V8LazyEventListener::prepareListenerObject(ExecutionContext* context)
if (m_node && m_node->isHTMLElement())
formElement = toHTMLElement(m_node)->formOwner();
- v8::Handle<v8::Object> nodeWrapper = toObjectWrapper<Node>(m_node, isolate);
- v8::Handle<v8::Object> formWrapper = toObjectWrapper<HTMLFormElement>(formElement, isolate);
- v8::Handle<v8::Object> documentWrapper = toObjectWrapper<Document>(m_node ? m_node->ownerDocument() : 0, isolate);
+ v8::Handle<v8::Object> nodeWrapper = toObjectWrapper<Node>(m_node, scriptState());
+ v8::Handle<v8::Object> formWrapper = toObjectWrapper<HTMLFormElement>(formElement, scriptState());
+ v8::Handle<v8::Object> documentWrapper = toObjectWrapper<Document>(m_node ? m_node->ownerDocument() : 0, scriptState());
- v8::Local<v8::Object> thisObject = v8::Object::New();
+ v8::Local<v8::Object> thisObject = v8::Object::New(isolate());
if (thisObject.IsEmpty())
return;
- if (!thisObject->ForceSet(v8::Integer::New(0, isolate), nodeWrapper))
+ if (!thisObject->ForceSet(v8::Integer::New(isolate(), 0), nodeWrapper))
return;
- if (!thisObject->ForceSet(v8::Integer::New(1, isolate), formWrapper))
+ if (!thisObject->ForceSet(v8::Integer::New(isolate(), 1), formWrapper))
return;
- if (!thisObject->ForceSet(v8::Integer::New(2, isolate), documentWrapper))
+ if (!thisObject->ForceSet(v8::Integer::New(isolate(), 2), documentWrapper))
return;
// FIXME: Remove this code when we stop doing the 'with' hack above.
- v8::Local<v8::Value> innerValue = V8ScriptRunner::callInternalFunction(intermediateFunction, thisObject, 0, 0, isolate);
+ v8::Local<v8::Value> innerValue = V8ScriptRunner::callInternalFunction(intermediateFunction, thisObject, 0, 0, isolate());
if (innerValue.IsEmpty() || !innerValue->IsFunction())
return;
@@ -202,20 +209,12 @@ void V8LazyEventListener::prepareListenerObject(ExecutionContext* context)
// source returned (sometimes a RegExp is applied as well) for some
// other use. That fails miserably if the actual wrapper source is
// returned.
- v8::Handle<v8::FunctionTemplate> toStringTemplate =
- V8PerIsolateData::current()->lazyEventListenerToStringTemplate();
- if (toStringTemplate.IsEmpty())
- toStringTemplate = v8::FunctionTemplate::New(isolate, V8LazyEventListenerToString);
- v8::Local<v8::Function> toStringFunction;
- if (!toStringTemplate.IsEmpty())
- toStringFunction = toStringTemplate->GetFunction();
- if (!toStringFunction.IsEmpty()) {
- String toStringString = "function " + m_functionName + "(" + m_eventParameterName + ") {\n " + m_code + "\n}";
- wrappedFunction->SetHiddenValue(V8HiddenPropertyName::toStringString(isolate), v8String(isolate, toStringString));
- wrappedFunction->Set(v8AtomicString(isolate, "toString"), toStringFunction);
- }
-
- wrappedFunction->SetName(v8String(isolate, m_functionName));
+ v8::Local<v8::Function> toStringFunction = v8::Function::New(isolate(), V8LazyEventListenerToString);
+ ASSERT(!toStringFunction.IsEmpty());
+ String toStringString = "function " + m_functionName + "(" + m_eventParameterName + ") {\n " + m_code + "\n}";
+ V8HiddenValue::setHiddenValue(isolate(), wrappedFunction, V8HiddenValue::toStringString(isolate()), v8String(isolate(), toStringString));
+ wrappedFunction->Set(v8AtomicString(isolate(), "toString"), toStringFunction);
+ wrappedFunction->SetName(v8String(isolate(), m_functionName));
// FIXME: Remove the following comment-outs.
// See https://bugs.webkit.org/show_bug.cgi?id=85152 for more details.
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8LazyEventListener.h b/chromium/third_party/WebKit/Source/bindings/v8/V8LazyEventListener.h
index 4bc040ff95b..7ab4d7d7c18 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8LazyEventListener.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8LazyEventListener.h
@@ -40,34 +40,38 @@
namespace WebCore {
class Event;
- class Frame;
+ class LocalFrame;
class HTMLFormElement;
class Node;
// V8LazyEventListener is a wrapper for a JavaScript code string that is compiled and evaluated when an event is fired.
// A V8LazyEventListener is either a HTML or SVG event handler.
- class V8LazyEventListener : public V8AbstractEventListener {
+ class V8LazyEventListener FINAL : public V8AbstractEventListener {
public:
static PassRefPtr<V8LazyEventListener> create(const AtomicString& functionName, const AtomicString& eventParameterName, const String& code, const String& sourceURL, const TextPosition& position, Node* node, v8::Isolate* isolate)
{
return adoptRef(new V8LazyEventListener(functionName, eventParameterName, code, sourceURL, position, node, isolate));
}
- virtual bool isLazy() const { return true; }
+ virtual bool isLazy() const OVERRIDE { return true; }
+ // V8LazyEventListener is always for the main world.
+ virtual DOMWrapperWorld& world() const OVERRIDE { return DOMWrapperWorld::mainWorld(); }
+
+ virtual void handleEvent(ExecutionContext*, Event*) OVERRIDE;
protected:
- virtual void prepareListenerObject(ExecutionContext*);
+ virtual void prepareListenerObject(ExecutionContext*) OVERRIDE;
private:
V8LazyEventListener(const AtomicString& functionName, const AtomicString& eventParameterName, const String& code, const String sourceURL, const TextPosition&, Node*, v8::Isolate*);
- virtual v8::Local<v8::Value> callListenerFunction(ExecutionContext*, v8::Handle<v8::Value> jsEvent, Event*);
+ virtual v8::Local<v8::Value> callListenerFunction(v8::Handle<v8::Value> jsEvent, Event*) OVERRIDE;
// Needs to return true for all event handlers implemented in JavaScript so that
// the SVG code does not add the event handler in both
// SVGUseElement::buildShadowTree and again in
// SVGUseElement::transferEventListenersToShadowTree
- virtual bool wasCreatedFromMarkup() const { return true; }
+ virtual bool wasCreatedFromMarkup() const OVERRIDE { return true; }
AtomicString m_functionName;
AtomicString m_eventParameterName;
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8MutationCallback.cpp b/chromium/third_party/WebKit/Source/bindings/v8/V8MutationCallback.cpp
index 6be6f16d6fc..8e0581acdcc 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8MutationCallback.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8MutationCallback.cpp
@@ -26,44 +26,39 @@
#include "config.h"
#include "bindings/v8/V8MutationCallback.h"
-#include "V8MutationObserver.h"
-#include "V8MutationRecord.h"
+#include "bindings/core/v8/V8MutationObserver.h"
+#include "bindings/core/v8/V8MutationRecord.h"
#include "bindings/v8/ScriptController.h"
#include "bindings/v8/V8Binding.h"
-#include "bindings/v8/V8HiddenPropertyName.h"
+#include "bindings/v8/V8HiddenValue.h"
#include "core/dom/ExecutionContext.h"
#include "wtf/Assertions.h"
namespace WebCore {
-V8MutationCallback::V8MutationCallback(v8::Handle<v8::Function> callback, ExecutionContext* context, v8::Handle<v8::Object> owner, v8::Isolate* isolate)
- : ActiveDOMCallback(context)
- , m_callback(isolate, callback)
- , m_world(DOMWrapperWorld::current())
- , m_isolate(isolate)
+V8MutationCallback::V8MutationCallback(v8::Handle<v8::Function> callback, v8::Handle<v8::Object> owner, ScriptState* scriptState)
+ : ActiveDOMCallback(scriptState->executionContext())
+ , m_callback(scriptState->isolate(), callback)
+ , m_scriptState(scriptState)
{
- owner->SetHiddenValue(V8HiddenPropertyName::callback(m_isolate), callback);
+ V8HiddenValue::setHiddenValue(scriptState->isolate(), owner, V8HiddenValue::callback(scriptState->isolate()), callback);
m_callback.setWeak(this, &setWeakCallback);
}
-void V8MutationCallback::call(const Vector<RefPtr<MutationRecord> >& mutations, MutationObserver* observer)
+void V8MutationCallback::call(const WillBeHeapVector<RefPtrWillBeMember<MutationRecord> >& mutations, MutationObserver* observer)
{
if (!canInvokeCallback())
return;
- v8::HandleScope handleScope(m_isolate);
+ v8::Isolate* isolate = m_scriptState->isolate();
- v8::Handle<v8::Context> v8Context = toV8Context(executionContext(), m_world.get());
- if (v8Context.IsEmpty())
+ if (m_scriptState->contextIsEmpty())
return;
+ ScriptState::Scope scope(m_scriptState.get());
- v8::Context::Scope scope(v8Context);
-
- v8::Handle<v8::Function> callback = m_callback.newLocal(m_isolate);
- if (callback.IsEmpty())
+ if (m_callback.isEmpty())
return;
-
- v8::Handle<v8::Value> observerHandle = toV8(observer, v8::Handle<v8::Object>(), m_isolate);
+ v8::Handle<v8::Value> observerHandle = toV8(observer, m_scriptState->context()->Global(), isolate);
if (observerHandle.IsEmpty()) {
if (!isScriptControllerTerminating())
CRASH();
@@ -74,11 +69,11 @@ void V8MutationCallback::call(const Vector<RefPtr<MutationRecord> >& mutations,
return;
v8::Handle<v8::Object> thisObject = v8::Handle<v8::Object>::Cast(observerHandle);
- v8::Handle<v8::Value> argv[] = { v8Array(mutations, m_isolate), observerHandle };
+ v8::Handle<v8::Value> argv[] = { v8Array(mutations, m_scriptState->context()->Global(), isolate), observerHandle };
v8::TryCatch exceptionCatcher;
exceptionCatcher.SetVerbose(true);
- ScriptController::callFunction(executionContext(), callback, thisObject, 2, argv, m_isolate);
+ ScriptController::callFunction(executionContext(), m_callback.newLocal(isolate), thisObject, WTF_ARRAY_LENGTH(argv), argv, isolate);
}
void V8MutationCallback::setWeakCallback(const v8::WeakCallbackData<v8::Function, V8MutationCallback>& data)
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8MutationCallback.h b/chromium/third_party/WebKit/Source/bindings/v8/V8MutationCallback.h
index 93a4820998a..fc5589a629b 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8MutationCallback.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8MutationCallback.h
@@ -27,9 +27,8 @@
#define V8MutationCallback_h
#include "bindings/v8/ActiveDOMCallback.h"
-#include "bindings/v8/DOMWrapperWorld.h"
#include "bindings/v8/ScopedPersistent.h"
-#include "bindings/v8/V8Utilities.h"
+#include "bindings/v8/ScriptState.h"
#include "core/dom/MutationCallback.h"
#include "wtf/OwnPtr.h"
#include "wtf/RefPtr.h"
@@ -39,25 +38,23 @@ namespace WebCore {
class ExecutionContext;
-class V8MutationCallback : public MutationCallback, public ActiveDOMCallback {
+class V8MutationCallback FINAL : public MutationCallback, public ActiveDOMCallback {
public:
- static PassOwnPtr<V8MutationCallback> create(v8::Handle<v8::Function> callback, ExecutionContext* context, v8::Handle<v8::Object> owner, v8::Isolate* isolate)
+ static PassOwnPtr<V8MutationCallback> create(v8::Handle<v8::Function> callback, v8::Handle<v8::Object> owner, ScriptState* scriptState)
{
- ASSERT(context);
- return adoptPtr(new V8MutationCallback(callback, context, owner, isolate));
+ return adoptPtr(new V8MutationCallback(callback, owner, scriptState));
}
- virtual void call(const Vector<RefPtr<MutationRecord> >&, MutationObserver*) OVERRIDE;
+ virtual void call(const WillBeHeapVector<RefPtrWillBeMember<MutationRecord> >&, MutationObserver*) OVERRIDE;
virtual ExecutionContext* executionContext() const OVERRIDE { return ContextLifecycleObserver::executionContext(); }
private:
- V8MutationCallback(v8::Handle<v8::Function>, ExecutionContext*, v8::Handle<v8::Object>, v8::Isolate*);
+ V8MutationCallback(v8::Handle<v8::Function>, v8::Handle<v8::Object>, ScriptState*);
static void setWeakCallback(const v8::WeakCallbackData<v8::Function, V8MutationCallback>&);
ScopedPersistent<v8::Function> m_callback;
- RefPtr<DOMWrapperWorld> m_world;
- v8::Isolate* m_isolate;
+ RefPtr<ScriptState> m_scriptState;
};
}
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8NPObject.cpp b/chromium/third_party/WebKit/Source/bindings/v8/V8NPObject.cpp
index 2912723fb82..a16369915c4 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8NPObject.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8NPObject.cpp
@@ -32,17 +32,18 @@
#include "bindings/v8/V8NPObject.h"
-#include "V8HTMLAppletElement.h"
-#include "V8HTMLEmbedElement.h"
-#include "V8HTMLObjectElement.h"
+#include "bindings/core/v8/V8HTMLAppletElement.h"
+#include "bindings/core/v8/V8HTMLEmbedElement.h"
+#include "bindings/core/v8/V8HTMLObjectElement.h"
#include "bindings/v8/NPV8Object.h"
-#include "bindings/v8/UnsafePersistent.h"
#include "bindings/v8/V8Binding.h"
#include "bindings/v8/V8NPUtils.h"
#include "bindings/v8/V8ObjectConstructor.h"
+#include "bindings/v8/V8PersistentValueMap.h"
#include "bindings/v8/npruntime_impl.h"
#include "bindings/v8/npruntime_priv.h"
#include "core/html/HTMLPlugInElement.h"
+#include "v8-util.h"
#include "wtf/OwnPtr.h"
namespace WebCore {
@@ -69,21 +70,18 @@ struct IdentifierRep {
static void npObjectInvokeImpl(const v8::FunctionCallbackInfo<v8::Value>& info, InvokeFunctionType functionId)
{
NPObject* npObject;
+ v8::Isolate* isolate = info.GetIsolate();
- WrapperWorldType currentWorldType = worldType(info.GetIsolate());
// These three types are subtypes of HTMLPlugInElement.
- if (V8HTMLAppletElement::hasInstance(info.Holder(), info.GetIsolate(), currentWorldType) || V8HTMLEmbedElement::hasInstance(info.Holder(), info.GetIsolate(), currentWorldType)
- || V8HTMLObjectElement::hasInstance(info.Holder(), info.GetIsolate(), currentWorldType)) {
- // The holder object is a subtype of HTMLPlugInElement.
- HTMLPlugInElement* element;
- if (V8HTMLAppletElement::hasInstance(info.Holder(), info.GetIsolate(), currentWorldType))
- element = V8HTMLAppletElement::toNative(info.Holder());
- else if (V8HTMLEmbedElement::hasInstance(info.Holder(), info.GetIsolate(), currentWorldType))
- element = V8HTMLEmbedElement::toNative(info.Holder());
- else
- element = V8HTMLObjectElement::toNative(info.Holder());
+ HTMLPlugInElement* element = V8HTMLAppletElement::toNativeWithTypeCheck(isolate, info.Holder());
+ if (!element) {
+ element = V8HTMLEmbedElement::toNativeWithTypeCheck(isolate, info.Holder());
+ if (!element) {
+ element = V8HTMLObjectElement::toNativeWithTypeCheck(isolate, info.Holder());
+ }
+ }
+ if (element) {
if (RefPtr<SharedPersistent<v8::Object> > wrapper = element->pluginWrapper()) {
- v8::Isolate* isolate = v8::Isolate::GetCurrent();
v8::HandleScope handleScope(isolate);
npObject = v8ObjectToNPObject(wrapper->newLocal(isolate));
} else
@@ -101,7 +99,7 @@ static void npObjectInvokeImpl(const v8::FunctionCallbackInfo<v8::Value>& info,
// Verify that our wrapper wasn't using a NPObject which has already been deleted.
if (!npObject || !_NPN_IsAlive(npObject)) {
- throwError(v8ReferenceError, "NPObject deleted", info.GetIsolate());
+ throwError(v8ReferenceError, "NPObject deleted", isolate);
return;
}
@@ -110,7 +108,7 @@ static void npObjectInvokeImpl(const v8::FunctionCallbackInfo<v8::Value>& info,
OwnPtr<NPVariant[]> npArgs = adoptArrayPtr(new NPVariant[numArgs]);
for (int i = 0; i < numArgs; i++)
- convertV8ObjectToNPVariant(info[i], npObject, &npArgs[i], info.GetIsolate());
+ convertV8ObjectToNPVariant(info[i], npObject, &npArgs[i], isolate);
NPVariant result;
VOID_TO_NPVARIANT(result);
@@ -137,7 +135,7 @@ static void npObjectInvokeImpl(const v8::FunctionCallbackInfo<v8::Value>& info,
}
if (!retval)
- throwError(v8GeneralError, "Error calling method on NPObject.", info.GetIsolate());
+ throwError(v8GeneralError, "Error calling method on NPObject.", isolate);
for (int i = 0; i < numArgs; i++)
_NPN_ReleaseVariantValue(&npArgs[i]);
@@ -145,7 +143,7 @@ static void npObjectInvokeImpl(const v8::FunctionCallbackInfo<v8::Value>& info,
// Unwrap return values.
v8::Handle<v8::Value> returnValue;
if (_NPN_IsAlive(npObject))
- returnValue = convertNPVariantToV8Object(&result, npObject, info.GetIsolate());
+ returnValue = convertNPVariantToV8Object(&result, npObject, isolate);
_NPN_ReleaseVariantValue(&result);
v8SetReturnValue(info, returnValue);
@@ -168,54 +166,72 @@ void npObjectInvokeDefaultHandler(const v8::FunctionCallbackInfo<v8::Value>& inf
npObjectInvokeImpl(info, InvokeDefault);
}
+class V8TemplateMapTraits : public V8PersistentValueMapTraits<PrivateIdentifier*, v8::FunctionTemplate, true> {
+public:
+ typedef v8::PersistentValueMap<PrivateIdentifier*, v8::FunctionTemplate, V8TemplateMapTraits> MapType;
+ typedef PrivateIdentifier WeakCallbackDataType;
+
+ static WeakCallbackDataType* WeakCallbackParameter(MapType* map, PrivateIdentifier* key, const v8::Local<v8::FunctionTemplate>& value)
+ {
+ return key;
+ }
+
+ static void DisposeCallbackData(WeakCallbackDataType* callbackData) { }
+
+ static MapType* MapFromWeakCallbackData(
+ const v8::WeakCallbackData<v8::FunctionTemplate, WeakCallbackDataType>&);
+
+ static PrivateIdentifier* KeyFromWeakCallbackData(
+ const v8::WeakCallbackData<v8::FunctionTemplate, WeakCallbackDataType>& data)
+ {
+ return data.GetParameter();
+ }
+
+ // Dispose traits:
+ static void Dispose(v8::Isolate* isolate, v8::UniquePersistent<v8::FunctionTemplate> value, PrivateIdentifier* key) { }
+};
+
+
class V8NPTemplateMap {
public:
// NPIdentifier is PrivateIdentifier*.
- typedef HashMap<PrivateIdentifier*, UnsafePersistent<v8::FunctionTemplate> > MapType;
+ typedef v8::PersistentValueMap<PrivateIdentifier*, v8::FunctionTemplate, V8TemplateMapTraits> MapType;
- UnsafePersistent<v8::FunctionTemplate> get(PrivateIdentifier* key)
+ v8::Local<v8::FunctionTemplate> get(PrivateIdentifier* key)
{
- return m_map.get(key);
+ return m_map.Get(key);
}
void set(PrivateIdentifier* key, v8::Handle<v8::FunctionTemplate> handle)
{
- ASSERT(!m_map.contains(key));
- v8::Persistent<v8::FunctionTemplate> wrapper(m_isolate, handle);
- wrapper.SetWeak(key, &setWeakCallback);
- m_map.set(key, UnsafePersistent<v8::FunctionTemplate>(wrapper));
+ ASSERT(!m_map.Contains(key));
+ m_map.Set(key, handle);
}
static V8NPTemplateMap& sharedInstance(v8::Isolate* isolate)
{
DEFINE_STATIC_LOCAL(V8NPTemplateMap, map, (isolate));
- ASSERT(isolate == map.m_isolate);
+ ASSERT(isolate == map.m_map.GetIsolate());
return map;
}
+ friend class V8TemplateMapTraits;
+
private:
explicit V8NPTemplateMap(v8::Isolate* isolate)
- : m_isolate(isolate)
- {
- }
-
- void clear(PrivateIdentifier* key)
+ : m_map(isolate)
{
- MapType::iterator it = m_map.find(key);
- ASSERT_WITH_SECURITY_IMPLICATION(it != m_map.end());
- it->value.dispose();
- m_map.remove(it);
- }
-
- static void setWeakCallback(const v8::WeakCallbackData<v8::FunctionTemplate, PrivateIdentifier>& data)
- {
- V8NPTemplateMap::sharedInstance(data.GetIsolate()).clear(data.GetParameter());
}
MapType m_map;
- v8::Isolate* m_isolate;
};
+V8TemplateMapTraits::MapType* V8TemplateMapTraits::MapFromWeakCallbackData(const v8::WeakCallbackData<v8::FunctionTemplate, WeakCallbackDataType>& data)
+{
+ return &V8NPTemplateMap::sharedInstance(data.GetIsolate()).m_map;
+}
+
+
static v8::Handle<v8::Value> npObjectGetProperty(v8::Local<v8::Object> self, NPIdentifier identifier, v8::Local<v8::Value> key, v8::Isolate* isolate)
{
NPObject* npObject = v8ObjectToNPObject(self);
@@ -251,19 +267,15 @@ static v8::Handle<v8::Value> npObjectGetProperty(v8::Local<v8::Object> self, NPI
return throwError(v8ReferenceError, "NPObject deleted", isolate);
PrivateIdentifier* id = static_cast<PrivateIdentifier*>(identifier);
- UnsafePersistent<v8::FunctionTemplate> functionTemplate = V8NPTemplateMap::sharedInstance(isolate).get(id);
- // FunctionTemplate caches function for each context.
- v8::Local<v8::Function> v8Function;
+ v8::Local<v8::FunctionTemplate> functionTemplate = V8NPTemplateMap::sharedInstance(isolate).get(id);
// Cache templates using identifier as the key.
- if (functionTemplate.isEmpty()) {
+ if (functionTemplate.IsEmpty()) {
// Create a new template.
- v8::Local<v8::FunctionTemplate> temp = v8::FunctionTemplate::New(isolate);
- temp->SetCallHandler(npObjectMethodHandler, key);
- V8NPTemplateMap::sharedInstance(isolate).set(id, temp);
- v8Function = temp->GetFunction();
- } else {
- v8Function = functionTemplate.newLocal(isolate)->GetFunction();
+ functionTemplate = v8::FunctionTemplate::New(isolate);
+ functionTemplate->SetCallHandler(npObjectMethodHandler, key);
+ V8NPTemplateMap::sharedInstance(isolate).set(id, functionTemplate);
}
+ v8::Local<v8::Function> v8Function = functionTemplate->GetFunction();
v8Function->SetName(v8::Handle<v8::String>::Cast(key));
return v8Function;
}
@@ -367,13 +379,22 @@ void npObjectPropertyEnumerator(const v8::PropertyCallbackInfo<v8::Array>& info,
uint32_t count;
NPIdentifier* identifiers;
if (npObject->_class->enumerate(npObject, &identifiers, &count)) {
- v8::Handle<v8::Array> properties = v8::Array::New(info.GetIsolate(), count);
+ uint32_t propertiesCount = 0;
for (uint32_t i = 0; i < count; ++i) {
IdentifierRep* identifier = static_cast<IdentifierRep*>(identifiers[i]);
- if (namedProperty)
- properties->Set(v8::Integer::New(i, info.GetIsolate()), v8AtomicString(info.GetIsolate(), identifier->string()));
- else
- properties->Set(v8::Integer::New(i, info.GetIsolate()), v8::Integer::New(identifier->number(), info.GetIsolate()));
+ if (namedProperty == identifier->m_isString)
+ ++propertiesCount;
+ }
+ v8::Handle<v8::Array> properties = v8::Array::New(info.GetIsolate(), propertiesCount);
+ for (uint32_t i = 0, propertyIndex = 0; i < count; ++i) {
+ IdentifierRep* identifier = static_cast<IdentifierRep*>(identifiers[i]);
+ if (namedProperty == identifier->m_isString) {
+ ASSERT(propertyIndex < propertiesCount);
+ if (namedProperty)
+ properties->Set(v8::Integer::New(info.GetIsolate(), propertyIndex++), v8AtomicString(info.GetIsolate(), identifier->string()));
+ else
+ properties->Set(v8::Integer::New(info.GetIsolate(), propertyIndex++), v8::Integer::New(info.GetIsolate(), identifier->number()));
+ }
}
v8SetReturnValue(info, properties);
@@ -398,18 +419,13 @@ static DOMWrapperMap<NPObject>& staticNPObjectMap()
return npObjectMap;
}
-template<>
-inline void DOMWrapperMap<NPObject>::setWeakCallback(const v8::WeakCallbackData<v8::Object, DOMWrapperMap<NPObject> >& data)
+template <>
+inline void DOMWrapperMap<NPObject>::PersistentValueMapTraits::Dispose(
+ v8::Isolate* isolate,
+ v8::UniquePersistent<v8::Object> value,
+ NPObject* npObject)
{
- NPObject* npObject = static_cast<NPObject*>(toNative(data.GetValue()));
-
ASSERT(npObject);
- ASSERT(staticNPObjectMap().containsKeyAndValue(npObject, data.GetValue()));
-
- // Must remove from our map before calling _NPN_ReleaseObject(). _NPN_ReleaseObject can
- // call forgetV8ObjectForNPObject, which uses the table as well.
- staticNPObjectMap().removeAndDispose(npObject);
-
if (_NPN_IsAlive(npObject))
_NPN_ReleaseObject(npObject);
}
@@ -447,7 +463,7 @@ v8::Local<v8::Object> createV8ObjectForNPObject(NPObject* object, NPObject* root
// V8DOMWrapper::associateObjectWithWrapper()
// to create a wrapper object.
v8::Handle<v8::Function> v8Function = npObjectDesc.Get(isolate)->GetFunction();
- v8::Local<v8::Object> value = V8ObjectConstructor::newInstance(v8Function);
+ v8::Local<v8::Object> value = V8ObjectConstructor::newInstance(isolate, v8Function);
if (value.IsEmpty())
return value;
@@ -459,7 +475,7 @@ v8::Local<v8::Object> createV8ObjectForNPObject(NPObject* object, NPObject* root
WrapperConfiguration configuration = buildWrapperConfiguration(object, WrapperConfiguration::Dependent);
staticNPObjectMap().set(object, value, configuration);
- ASSERT(V8DOMWrapper::maybeDOMWrapper(value));
+ ASSERT(V8DOMWrapper::isDOMWrapper(value));
return value;
}
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8NPObject.h b/chromium/third_party/WebKit/Source/bindings/v8/V8NPObject.h
index 4465b039868..dc5d336fbe5 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8NPObject.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8NPObject.h
@@ -31,9 +31,10 @@
#ifndef V8NPObject_h
#define V8NPObject_h
-#include <bindings/npruntime.h>
#include <v8.h>
+struct NPObject;
+
namespace WebCore {
// These functions can be replaced by normal JS operation.
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8NPUtils.cpp b/chromium/third_party/WebKit/Source/bindings/v8/V8NPUtils.cpp
index 7c0645f7a1f..df6eefe3b42 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8NPUtils.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8NPUtils.cpp
@@ -36,7 +36,7 @@
#include "bindings/v8/V8NPObject.h"
#include "bindings/v8/npruntime_impl.h"
#include "bindings/v8/npruntime_priv.h"
-#include "core/frame/DOMWindow.h"
+#include "core/frame/LocalDOMWindow.h"
#include "wtf/text/WTFString.h"
#include <stdlib.h>
@@ -69,7 +69,7 @@ void convertV8ObjectToNPVariant(v8::Local<v8::Value> object, NPObject* owner, NP
str->WriteUtf8(utf8Chars, length, 0, v8::String::HINT_MANY_WRITES_EXPECTED);
STRINGN_TO_NPVARIANT(utf8Chars, length-1, *result);
} else if (object->IsObject()) {
- DOMWindow* window = toDOMWindow(isolate->GetCurrentContext());
+ LocalDOMWindow* window = currentDOMWindow(isolate);
NPObject* npobject = npCreateV8ScriptObject(0, v8::Handle<v8::Object>::Cast(object), window, isolate);
if (npobject)
_NPN_RegisterObject(npobject, owner);
@@ -83,7 +83,7 @@ v8::Handle<v8::Value> convertNPVariantToV8Object(const NPVariant* variant, NPObj
switch (type) {
case NPVariantType_Int32:
- return v8::Integer::New(NPVARIANT_TO_INT32(*variant), isolate);
+ return v8::Integer::New(isolate, NPVARIANT_TO_INT32(*variant));
case NPVariantType_Double:
return v8::Number::New(isolate, NPVARIANT_TO_DOUBLE(*variant));
case NPVariantType_Bool:
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8NodeFilterCondition.cpp b/chromium/third_party/WebKit/Source/bindings/v8/V8NodeFilterCondition.cpp
index 3fcbc3c0f94..deecfa7b5c6 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8NodeFilterCondition.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8NodeFilterCondition.cpp
@@ -31,35 +31,41 @@
#include "config.h"
#include "bindings/v8/V8NodeFilterCondition.h"
-#include "V8Node.h"
+#include "bindings/core/v8/V8Node.h"
#include "bindings/v8/ScriptController.h"
-#include "bindings/v8/ScriptState.h"
-#include "bindings/v8/V8HiddenPropertyName.h"
+#include "bindings/v8/V8HiddenValue.h"
#include "core/dom/Node.h"
#include "core/dom/NodeFilter.h"
#include "wtf/OwnPtr.h"
namespace WebCore {
-V8NodeFilterCondition::V8NodeFilterCondition(v8::Handle<v8::Value> filter, v8::Handle<v8::Object> owner, v8::Isolate* isolate)
- : m_filter(isolate, filter)
+V8NodeFilterCondition::V8NodeFilterCondition(v8::Handle<v8::Value> filter, v8::Handle<v8::Object> owner, ScriptState* scriptState)
+ : m_scriptState(scriptState)
{
- owner->SetHiddenValue(V8HiddenPropertyName::condition(isolate), filter);
- m_filter.setWeak(this, &setWeakCallback);
+ // ..acceptNode(..) will only dispatch m_filter if m_filter->IsObject().
+ // We'll make sure m_filter is either usable by acceptNode or empty.
+ // (See the fast/dom/node-filter-gc test for a case where 'empty' happens.)
+ if (!filter.IsEmpty() && filter->IsObject()) {
+ V8HiddenValue::setHiddenValue(scriptState->isolate(), owner, V8HiddenValue::condition(scriptState->isolate()), filter);
+ m_filter.set(scriptState->isolate(), filter);
+ m_filter.setWeak(this, &setWeakCallback);
+ }
}
V8NodeFilterCondition::~V8NodeFilterCondition()
{
}
-short V8NodeFilterCondition::acceptNode(ScriptState* state, Node* node) const
+short V8NodeFilterCondition::acceptNode(Node* node, ExceptionState& exceptionState) const
{
- v8::Isolate* isolate = state->isolate();
- ASSERT(isolate->InContext());
+ v8::Isolate* isolate = m_scriptState->isolate();
+ ASSERT(!m_scriptState->context().IsEmpty());
v8::HandleScope handleScope(isolate);
v8::Handle<v8::Value> filter = m_filter.newLocal(isolate);
- ASSERT(!filter.IsEmpty());
- if (!filter->IsObject())
+
+ ASSERT(filter.IsEmpty() || filter->IsObject());
+ if (filter.IsEmpty())
return NodeFilter::FILTER_ACCEPT;
v8::TryCatch exceptionCatcher;
@@ -69,21 +75,21 @@ short V8NodeFilterCondition::acceptNode(ScriptState* state, Node* node) const
callback = v8::Handle<v8::Function>::Cast(filter);
else {
v8::Local<v8::Value> value = filter->ToObject()->Get(v8AtomicString(isolate, "acceptNode"));
- if (!value->IsFunction()) {
- throwTypeError("NodeFilter object does not have an acceptNode function", state->isolate());
+ if (value.IsEmpty() || !value->IsFunction()) {
+ exceptionState.throwTypeError("NodeFilter object does not have an acceptNode function");
return NodeFilter::FILTER_REJECT;
}
callback = v8::Handle<v8::Function>::Cast(value);
}
OwnPtr<v8::Handle<v8::Value>[]> info = adoptArrayPtr(new v8::Handle<v8::Value>[1]);
- info[0] = toV8(node, v8::Handle<v8::Object>(), state->isolate());
+ v8::Handle<v8::Object> context = m_scriptState->context()->Global();
+ info[0] = toV8(node, context, isolate);
- v8::Handle<v8::Object> object = isolate->GetCurrentContext()->Global();
- v8::Handle<v8::Value> result = ScriptController::callFunction(state->executionContext(), callback, object, 1, info.get(), isolate);
+ v8::Handle<v8::Value> result = ScriptController::callFunction(m_scriptState->executionContext(), callback, context, 1, info.get(), isolate);
if (exceptionCatcher.HasCaught()) {
- state->setException(exceptionCatcher.Exception());
+ exceptionState.rethrowV8Exception(exceptionCatcher.Exception());
return NodeFilter::FILTER_REJECT;
}
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8NodeFilterCondition.h b/chromium/third_party/WebKit/Source/bindings/v8/V8NodeFilterCondition.h
index 3d87020d5f2..de42cb5c13a 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8NodeFilterCondition.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8NodeFilterCondition.h
@@ -32,14 +32,16 @@
#define V8NodeFilterCondition_h
#include "bindings/v8/ScopedPersistent.h"
+#include "bindings/v8/ScriptState.h"
#include "core/dom/NodeFilterCondition.h"
+#include "platform/heap/Handle.h"
#include <v8.h>
#include "wtf/PassRefPtr.h"
namespace WebCore {
class Node;
-class ScriptState;
+class ExceptionState;
// V8NodeFilterCondition maintains a Javascript implemented callback for
// filtering Node returned by NodeIterator/TreeWalker.
@@ -58,25 +60,26 @@ class ScriptState;
// v | v | v
// NodeIterator --HiddenValue--> NodeFilter --HiddenValue--> JS Callback
// (V8)
-class V8NodeFilterCondition : public NodeFilterCondition {
+class V8NodeFilterCondition FINAL : public NodeFilterCondition {
public:
- static PassRefPtr<V8NodeFilterCondition> create(v8::Handle<v8::Value> filter, v8::Handle<v8::Object> owner, v8::Isolate* isolate)
+ static PassRefPtrWillBeRawPtr<V8NodeFilterCondition> create(v8::Handle<v8::Value> filter, v8::Handle<v8::Object> owner, ScriptState* scriptState)
{
- return adoptRef(new V8NodeFilterCondition(filter, owner, isolate));
+ return adoptRefWillBeNoop(new V8NodeFilterCondition(filter, owner, scriptState));
}
virtual ~V8NodeFilterCondition();
- virtual short acceptNode(ScriptState*, Node*) const;
+ virtual short acceptNode(Node*, ExceptionState&) const OVERRIDE;
private:
// As the value |filter| is maintained by V8GC, the |owner| which references
// V8NodeFilterCondition, usually a wrapper of NodeFilter, is specified here
// to hold a strong reference to |filter|.
- V8NodeFilterCondition(v8::Handle<v8::Value> filter, v8::Handle<v8::Object> owner, v8::Isolate*);
+ V8NodeFilterCondition(v8::Handle<v8::Value> filter, v8::Handle<v8::Object> owner, ScriptState*);
static void setWeakCallback(const v8::WeakCallbackData<v8::Value, V8NodeFilterCondition>&);
+ RefPtr<ScriptState> m_scriptState;
ScopedPersistent<v8::Value> m_filter;
};
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8ObjectConstructor.cpp b/chromium/third_party/WebKit/Source/bindings/v8/V8ObjectConstructor.cpp
index 6ebfbab7b71..d52bdc1a910 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8ObjectConstructor.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8ObjectConstructor.cpp
@@ -28,46 +28,38 @@
#include "bindings/v8/V8Binding.h"
#include "bindings/v8/V8ScriptRunner.h"
#include "core/dom/Document.h"
-#include "core/frame/Frame.h"
+#include "core/frame/LocalFrame.h"
#include "platform/TraceEvent.h"
namespace WebCore {
-v8::Local<v8::Object> V8ObjectConstructor::newInstance(v8::Handle<v8::Function> function)
+v8::Local<v8::Object> V8ObjectConstructor::newInstance(v8::Isolate* isolate, v8::Handle<v8::Function> function)
{
if (function.IsEmpty())
return v8::Local<v8::Object>();
- ConstructorMode constructorMode;
- return V8ScriptRunner::instantiateObject(function);
+ ConstructorMode constructorMode(isolate);
+ return V8ScriptRunner::instantiateObject(isolate, function);
}
-v8::Local<v8::Object> V8ObjectConstructor::newInstance(v8::Handle<v8::ObjectTemplate> objectTemplate)
-{
- if (objectTemplate.IsEmpty())
- return v8::Local<v8::Object>();
- ConstructorMode constructorMode;
- return V8ScriptRunner::instantiateObject(objectTemplate);
-}
-
-v8::Local<v8::Object> V8ObjectConstructor::newInstance(v8::Handle<v8::Function> function, int argc, v8::Handle<v8::Value> argv[])
+v8::Local<v8::Object> V8ObjectConstructor::newInstance(v8::Isolate* isolate, v8::Handle<v8::Function> function, int argc, v8::Handle<v8::Value> argv[])
{
if (function.IsEmpty())
return v8::Local<v8::Object>();
- ConstructorMode constructorMode;
- return V8ScriptRunner::instantiateObject(function, argc, argv);
+ ConstructorMode constructorMode(isolate);
+ return V8ScriptRunner::instantiateObject(isolate, function, argc, argv);
}
-v8::Local<v8::Object> V8ObjectConstructor::newInstanceInDocument(v8::Handle<v8::Function> function, int argc, v8::Handle<v8::Value> argv[], Document* document)
+v8::Local<v8::Object> V8ObjectConstructor::newInstanceInDocument(v8::Isolate* isolate, v8::Handle<v8::Function> function, int argc, v8::Handle<v8::Value> argv[], Document* document)
{
if (function.IsEmpty())
return v8::Local<v8::Object>();
- return V8ScriptRunner::instantiateObjectInDocument(function, document, argc, argv);
+ return V8ScriptRunner::instantiateObjectInDocument(isolate, function, document, argc, argv);
}
void V8ObjectConstructor::isValidConstructorMode(const v8::FunctionCallbackInfo<v8::Value>& info)
{
- if (ConstructorMode::current() == ConstructorMode::CreateNewObject) {
+ if (ConstructorMode::current(info.GetIsolate()) == ConstructorMode::CreateNewObject) {
throwTypeError("Illegal constructor", info.GetIsolate());
return;
}
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8ObjectConstructor.h b/chromium/third_party/WebKit/Source/bindings/v8/V8ObjectConstructor.h
index 2c9f6a26020..e1d204fa606 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8ObjectConstructor.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8ObjectConstructor.h
@@ -32,6 +32,7 @@
#define V8ObjectConstructor_h
#include "bindings/v8/V8PerIsolateData.h"
+#include "bindings/v8/V8RecursionScope.h"
#include <v8.h>
@@ -46,31 +47,37 @@ public:
CreateNewObject
};
- ConstructorMode()
+ ConstructorMode(v8::Isolate* isolate)
+ : m_isolate(isolate)
+ , m_microtaskSuppression(isolate)
{
- V8PerIsolateData* data = V8PerIsolateData::current();
+ V8PerIsolateData* data = V8PerIsolateData::from(m_isolate);
m_previous = data->m_constructorMode;
data->m_constructorMode = WrapExistingObject;
}
~ConstructorMode()
{
- V8PerIsolateData* data = V8PerIsolateData::current();
+ V8PerIsolateData* data = V8PerIsolateData::from(m_isolate);
data->m_constructorMode = m_previous;
}
- static bool current() { return V8PerIsolateData::current()->m_constructorMode; }
+ static bool current(v8::Isolate* isolate)
+ {
+ return V8PerIsolateData::from(isolate)->m_constructorMode;
+ }
private:
+ v8::Isolate* m_isolate;
bool m_previous;
+ V8RecursionScope::MicrotaskSuppression m_microtaskSuppression;
};
class V8ObjectConstructor {
public:
- static v8::Local<v8::Object> newInstance(v8::Handle<v8::Function>);
- static v8::Local<v8::Object> newInstance(v8::Handle<v8::ObjectTemplate>);
- static v8::Local<v8::Object> newInstance(v8::Handle<v8::Function>, int, v8::Handle<v8::Value> argv[]);
- static v8::Local<v8::Object> newInstanceInDocument(v8::Handle<v8::Function>, int, v8::Handle<v8::Value> argv[], Document*);
+ static v8::Local<v8::Object> newInstance(v8::Isolate*, v8::Handle<v8::Function>);
+ static v8::Local<v8::Object> newInstance(v8::Isolate*, v8::Handle<v8::Function>, int, v8::Handle<v8::Value> argv[]);
+ static v8::Local<v8::Object> newInstanceInDocument(v8::Isolate*, v8::Handle<v8::Function>, int, v8::Handle<v8::Value> argv[], Document*);
static void isValidConstructorMode(const v8::FunctionCallbackInfo<v8::Value>&);
};
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8PerContextData.cpp b/chromium/third_party/WebKit/Source/bindings/v8/V8PerContextData.cpp
index 8bf80076f08..1456bed0748 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8PerContextData.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8PerContextData.cpp
@@ -31,6 +31,7 @@
#include "config.h"
#include "bindings/v8/V8PerContextData.h"
+#include "bindings/v8/ScriptState.h"
#include "bindings/v8/V8Binding.h"
#include "bindings/v8/V8ObjectConstructor.h"
#include "wtf/StringExtras.h"
@@ -39,67 +40,49 @@
namespace WebCore {
-template<typename Map>
-static void disposeMapWithUnsafePersistentValues(Map* map)
+V8PerContextData::V8PerContextData(v8::Handle<v8::Context> context)
+ : m_wrapperBoilerplates(context->GetIsolate())
+ , m_constructorMap(context->GetIsolate())
+ , m_isolate(context->GetIsolate())
+ , m_contextHolder(adoptPtr(new gin::ContextHolder(context->GetIsolate())))
+ , m_context(m_isolate, context)
+ , m_customElementBindings(adoptPtr(new CustomElementBindingMap()))
+ , m_activityLogger(0)
{
- typename Map::iterator it = map->begin();
- for (; it != map->end(); ++it)
- it->value.dispose();
- map->clear();
+ m_contextHolder->SetContext(context);
+
+ v8::Context::Scope contextScope(context);
+ ASSERT(m_errorPrototype.isEmpty());
+ v8::Handle<v8::Object> object = v8::Handle<v8::Object>::Cast(context->Global()->Get(v8AtomicString(m_isolate, "Error")));
+ ASSERT(!object.IsEmpty());
+ v8::Handle<v8::Value> prototypeValue = object->Get(v8AtomicString(m_isolate, "prototype"));
+ ASSERT(!prototypeValue.IsEmpty());
+ m_errorPrototype.set(m_isolate, prototypeValue);
}
-void V8PerContextData::dispose()
+V8PerContextData::~V8PerContextData()
{
- v8::HandleScope handleScope(m_isolate);
- V8PerContextDataHolder::from(v8::Local<v8::Context>::New(m_isolate, m_context))->setPerContextData(0);
-
- disposeMapWithUnsafePersistentValues(&m_wrapperBoilerplates);
- disposeMapWithUnsafePersistentValues(&m_constructorMap);
- m_customElementBindings.clear();
-
- m_context.Reset();
}
-#define V8_STORE_PRIMORDIAL(name, Name) \
-{ \
- ASSERT(m_##name##Prototype.isEmpty()); \
- v8::Handle<v8::String> symbol = v8::String::NewFromUtf8(m_isolate, #Name, v8::String::kInternalizedString); \
- if (symbol.IsEmpty()) \
- return false; \
- v8::Handle<v8::Object> object = v8::Handle<v8::Object>::Cast(v8::Local<v8::Context>::New(m_isolate, m_context)->Global()->Get(symbol)); \
- if (object.IsEmpty()) \
- return false; \
- v8::Handle<v8::Value> prototypeValue = object->Get(prototypeString); \
- if (prototypeValue.IsEmpty()) \
- return false; \
- m_##name##Prototype.set(m_isolate, prototypeValue); \
+PassOwnPtr<V8PerContextData> V8PerContextData::create(v8::Handle<v8::Context> context)
+{
+ return adoptPtr(new V8PerContextData(context));
}
-bool V8PerContextData::init()
+V8PerContextData* V8PerContextData::from(v8::Handle<v8::Context> context)
{
- v8::Handle<v8::Context> context = v8::Local<v8::Context>::New(m_isolate, m_context);
- V8PerContextDataHolder::from(context)->setPerContextData(this);
-
- v8::Handle<v8::String> prototypeString = v8AtomicString(m_isolate, "prototype");
- if (prototypeString.IsEmpty())
- return false;
-
- V8_STORE_PRIMORDIAL(error, Error);
-
- return true;
+ return ScriptState::from(context)->perContextData();
}
-#undef V8_STORE_PRIMORDIAL
-
v8::Local<v8::Object> V8PerContextData::createWrapperFromCacheSlowCase(const WrapperTypeInfo* type)
{
ASSERT(!m_errorPrototype.isEmpty());
- v8::Context::Scope scope(v8::Local<v8::Context>::New(m_isolate, m_context));
+ v8::Context::Scope scope(context());
v8::Local<v8::Function> function = constructorForType(type);
- v8::Local<v8::Object> instanceTemplate = V8ObjectConstructor::newInstance(function);
+ v8::Local<v8::Object> instanceTemplate = V8ObjectConstructor::newInstance(m_isolate, function);
if (!instanceTemplate.IsEmpty()) {
- m_wrapperBoilerplates.set(type, UnsafePersistent<v8::Object>(m_isolate, instanceTemplate));
+ m_wrapperBoilerplates.Set(type, instanceTemplate);
return instanceTemplate->Clone();
}
return v8::Local<v8::Object>();
@@ -109,8 +92,8 @@ v8::Local<v8::Function> V8PerContextData::constructorForTypeSlowCase(const Wrapp
{
ASSERT(!m_errorPrototype.isEmpty());
- v8::Context::Scope scope(v8::Local<v8::Context>::New(m_isolate, m_context));
- v8::Handle<v8::FunctionTemplate> functionTemplate = type->domTemplate(m_isolate, worldType(m_isolate));
+ v8::Context::Scope scope(context());
+ v8::Handle<v8::FunctionTemplate> functionTemplate = type->domTemplate(m_isolate);
// Getting the function might fail if we're running out of stack or memory.
v8::TryCatch tryCatch;
v8::Local<v8::Function> function = functionTemplate->GetFunction();
@@ -131,11 +114,11 @@ v8::Local<v8::Function> V8PerContextData::constructorForTypeSlowCase(const Wrapp
&& type->wrapperTypePrototype == WrapperTypeObjectPrototype)
prototypeObject->SetAlignedPointerInInternalField(v8PrototypeTypeIndex, const_cast<WrapperTypeInfo*>(type));
type->installPerContextEnabledMethods(prototypeObject, m_isolate);
- if (type->wrapperTypePrototype == WrapperTypeErrorPrototype)
+ if (type->wrapperTypePrototype == WrapperTypeExceptionPrototype)
prototypeObject->SetPrototype(m_errorPrototype.newLocal(m_isolate));
}
- m_constructorMap.set(type, UnsafePersistent<v8::Function>(m_isolate, function));
+ m_constructorMap.Set(type, function);
return function;
}
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8PerContextData.h b/chromium/third_party/WebKit/Source/bindings/v8/V8PerContextData.h
index 63634f85cbe..7987c616892 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8PerContextData.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8PerContextData.h
@@ -33,8 +33,7 @@
#include "bindings/v8/CustomElementBinding.h"
#include "bindings/v8/ScopedPersistent.h"
-#include "bindings/v8/UnsafePersistent.h"
-#include "bindings/v8/V8DOMActivityLogger.h"
+#include "bindings/v8/V8PersistentValueMap.h"
#include "bindings/v8/WrapperTypeInfo.h"
#include "gin/public/context_holder.h"
#include "gin/public/gin_embedders.h"
@@ -48,7 +47,7 @@
namespace WebCore {
class CustomElementDefinition;
-class DOMWrapperWorld;
+class V8DOMActivityLogger;
class V8PerContextData;
struct V8NPObject;
typedef WTF::Vector<V8NPObject*> V8NPObjectVector;
@@ -59,139 +58,69 @@ enum V8ContextEmbedderDataField {
v8ContextPerContextDataIndex = static_cast<int>(gin::kPerContextDataStartIndex + gin::kEmbedderBlink),
};
-class V8PerContextDataHolder {
- WTF_MAKE_NONCOPYABLE(V8PerContextDataHolder);
-public:
- static void install(v8::Handle<v8::Context> context)
- {
- new V8PerContextDataHolder(context);
- }
-
- static V8PerContextDataHolder* from(v8::Handle<v8::Context> context)
- {
- return static_cast<V8PerContextDataHolder*>(context->GetAlignedPointerFromEmbedderData(v8ContextPerContextDataIndex));
- }
-
- V8PerContextData* perContextData() const { return m_perContextData; }
- void setPerContextData(V8PerContextData* data) { m_perContextData = data; }
-
- DOMWrapperWorld* isolatedWorld() const { return m_isolatedWorld; }
- void setIsolatedWorld(DOMWrapperWorld* world) { m_isolatedWorld = world; }
-
-private:
- explicit V8PerContextDataHolder(v8::Handle<v8::Context> context)
- : m_context(v8::Isolate::GetCurrent(), context)
- , m_perContextData(0)
- , m_isolatedWorld(0)
- {
- m_context.SetWeak(this, &V8PerContextDataHolder::weakCallback);
- context->SetAlignedPointerInEmbedderData(v8ContextPerContextDataIndex, this);
- }
-
- ~V8PerContextDataHolder() {}
-
- static void weakCallback(const v8::WeakCallbackData<v8::Context, V8PerContextDataHolder>& data)
- {
- data.GetValue()->SetAlignedPointerInEmbedderData(v8ContextPerContextDataIndex, 0);
- data.GetParameter()->m_context.Reset();
- delete data.GetParameter();
- }
-
- v8::Persistent<v8::Context> m_context;
- V8PerContextData* m_perContextData;
- DOMWrapperWorld* m_isolatedWorld;
-};
-
class V8PerContextData {
public:
- static PassOwnPtr<V8PerContextData> create(v8::Handle<v8::Context> context)
- {
- return adoptPtr(new V8PerContextData(context));
- }
+ static PassOwnPtr<V8PerContextData> create(v8::Handle<v8::Context>);
- ~V8PerContextData()
- {
- dispose();
- }
+ static V8PerContextData* from(v8::Handle<v8::Context>);
- bool init();
+ ~V8PerContextData();
- static V8PerContextData* from(v8::Handle<v8::Context> context)
- {
- return V8PerContextDataHolder::from(context)->perContextData();
- }
+ v8::Handle<v8::Context> context() { return m_context.newLocal(m_isolate); }
// To create JS Wrapper objects, we create a cache of a 'boiler plate'
// object, and then simply Clone that object each time we need a new one.
// This is faster than going through the full object creation process.
v8::Local<v8::Object> createWrapperFromCache(const WrapperTypeInfo* type)
{
- UnsafePersistent<v8::Object> boilerplate = m_wrapperBoilerplates.get(type);
- return !boilerplate.isEmpty() ? boilerplate.newLocal(v8::Isolate::GetCurrent())->Clone() : createWrapperFromCacheSlowCase(type);
+ v8::Local<v8::Object> boilerplate = m_wrapperBoilerplates.Get(type);
+ return !boilerplate.IsEmpty() ? boilerplate->Clone() : createWrapperFromCacheSlowCase(type);
}
v8::Local<v8::Function> constructorForType(const WrapperTypeInfo* type)
{
- UnsafePersistent<v8::Function> function = m_constructorMap.get(type);
- if (!function.isEmpty())
- return function.newLocal(v8::Isolate::GetCurrent());
- return constructorForTypeSlowCase(type);
+ v8::Local<v8::Function> function = m_constructorMap.Get(type);
+ return (!function.IsEmpty()) ? function : constructorForTypeSlowCase(type);
}
v8::Local<v8::Object> prototypeForType(const WrapperTypeInfo*);
- V8NPObjectMap* v8NPObjectMap()
- {
- return &m_v8NPObjectMap;
- }
-
- V8DOMActivityLogger* activityLogger()
- {
- return m_activityLogger;
- }
-
- void setActivityLogger(V8DOMActivityLogger* logger)
- {
- m_activityLogger = logger;
- }
+ V8NPObjectMap* v8NPObjectMap() { return &m_v8NPObjectMap; }
void addCustomElementBinding(CustomElementDefinition*, PassOwnPtr<CustomElementBinding>);
void clearCustomElementBinding(CustomElementDefinition*);
CustomElementBinding* customElementBinding(CustomElementDefinition*);
-private:
- explicit V8PerContextData(v8::Handle<v8::Context> context)
- : m_activityLogger(0)
- , m_isolate(v8::Isolate::GetCurrent())
- , m_context(m_isolate, context)
- , m_customElementBindings(adoptPtr(new CustomElementBindingMap()))
- {
- }
+ V8DOMActivityLogger* activityLogger() const { return m_activityLogger; }
+ void setActivityLogger(V8DOMActivityLogger* activityLogger) { m_activityLogger = activityLogger; }
- void dispose();
+private:
+ V8PerContextData(v8::Handle<v8::Context>);
v8::Local<v8::Object> createWrapperFromCacheSlowCase(const WrapperTypeInfo*);
v8::Local<v8::Function> constructorForTypeSlowCase(const WrapperTypeInfo*);
// For each possible type of wrapper, we keep a boilerplate object.
// The boilerplate is used to create additional wrappers of the same type.
- typedef WTF::HashMap<const WrapperTypeInfo*, UnsafePersistent<v8::Object> > WrapperBoilerplateMap;
+ typedef V8PersistentValueMap<const WrapperTypeInfo*, v8::Object, false> WrapperBoilerplateMap;
WrapperBoilerplateMap m_wrapperBoilerplates;
- typedef WTF::HashMap<const WrapperTypeInfo*, UnsafePersistent<v8::Function> > ConstructorMap;
+ typedef V8PersistentValueMap<const WrapperTypeInfo*, v8::Function, false> ConstructorMap;
ConstructorMap m_constructorMap;
V8NPObjectMap m_v8NPObjectMap;
- // We cache a pointer to the V8DOMActivityLogger associated with the world
- // corresponding to this context. The ownership of the pointer is retained
- // by the DOMActivityLoggerMap in DOMWrapperWorld.
- V8DOMActivityLogger* m_activityLogger;
+
v8::Isolate* m_isolate;
- v8::Persistent<v8::Context> m_context;
+ OwnPtr<gin::ContextHolder> m_contextHolder;
+
+ ScopedPersistent<v8::Context> m_context;
ScopedPersistent<v8::Value> m_errorPrototype;
typedef WTF::HashMap<CustomElementDefinition*, OwnPtr<CustomElementBinding> > CustomElementBindingMap;
OwnPtr<CustomElementBindingMap> m_customElementBindings;
+
+ // This is owned by a static hash map in V8DOMActivityLogger.
+ V8DOMActivityLogger* m_activityLogger;
};
class V8PerContextDebugData {
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8PerIsolateData.cpp b/chromium/third_party/WebKit/Source/bindings/v8/V8PerIsolateData.cpp
index 10064bc2dde..43dd26351e8 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8PerIsolateData.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8PerIsolateData.cpp
@@ -27,48 +27,74 @@
#include "bindings/v8/V8PerIsolateData.h"
#include "bindings/v8/DOMDataStore.h"
+#include "bindings/v8/PageScriptDebugServer.h"
#include "bindings/v8/ScriptGCEvent.h"
#include "bindings/v8/ScriptProfiler.h"
#include "bindings/v8/V8Binding.h"
-#include "bindings/v8/V8HiddenPropertyName.h"
+#include "bindings/v8/V8HiddenValue.h"
#include "bindings/v8/V8ObjectConstructor.h"
+#include "bindings/v8/V8RecursionScope.h"
#include "bindings/v8/V8ScriptRunner.h"
+#include "public/platform/Platform.h"
+#include "wtf/MainThread.h"
namespace WebCore {
+static V8PerIsolateData* mainThreadPerIsolateData = 0;
+
+#ifndef NDEBUG
+static void assertV8RecursionScope()
+{
+ ASSERT(V8RecursionScope::properlyUsed(v8::Isolate::GetCurrent()));
+}
+#endif
+
V8PerIsolateData::V8PerIsolateData(v8::Isolate* isolate)
: m_isolate(isolate)
- , m_stringCache(adoptPtr(new StringCache()))
- , m_workerDomDataStore(0)
- , m_hiddenPropertyName(adoptPtr(new V8HiddenPropertyName()))
+ , m_isolateHolder(adoptPtr(new gin::IsolateHolder(m_isolate, v8ArrayBufferAllocator())))
+ , m_stringCache(adoptPtr(new StringCache(m_isolate)))
+ , m_hiddenValue(adoptPtr(new V8HiddenValue()))
, m_constructorMode(ConstructorMode::CreateNewObject)
, m_recursionLevel(0)
#ifndef NDEBUG
, m_internalScriptRecursionLevel(0)
#endif
, m_gcEventData(adoptPtr(new GCEventData()))
- , m_shouldCollectGarbageSoon(false)
+ , m_performingMicrotaskCheckpoint(false)
{
+#ifndef NDEBUG
+ // currentThread will always be non-null in production, but can be null in Chromium unit tests.
+ if (blink::Platform::current()->currentThread())
+ isolate->AddCallCompletedCallback(&assertV8RecursionScope);
+#endif
+ if (isMainThread()) {
+ mainThreadPerIsolateData = this;
+ PageScriptDebugServer::setMainThreadIsolate(isolate);
+ }
}
V8PerIsolateData::~V8PerIsolateData()
{
+ if (m_scriptRegexpScriptState)
+ m_scriptRegexpScriptState->disposePerContextData();
+ if (isMainThread())
+ mainThreadPerIsolateData = 0;
}
-V8PerIsolateData* V8PerIsolateData::create(v8::Isolate* isolate)
+v8::Isolate* V8PerIsolateData::mainThreadIsolate()
{
- ASSERT(isolate);
- ASSERT(!isolate->GetData(gin::kEmbedderBlink));
- V8PerIsolateData* data = new V8PerIsolateData(isolate);
- isolate->SetData(gin::kEmbedderBlink, data);
- return data;
+ ASSERT(isMainThread());
+ ASSERT(mainThreadPerIsolateData);
+ return mainThreadPerIsolateData->isolate();
}
void V8PerIsolateData::ensureInitialized(v8::Isolate* isolate)
{
ASSERT(isolate);
- if (!isolate->GetData(gin::kEmbedderBlink))
- create(isolate);
+ if (!isolate->GetData(gin::kEmbedderBlink)) {
+ V8PerIsolateData* data = new V8PerIsolateData(isolate);
+ isolate->SetData(gin::kEmbedderBlink, data);
+ }
}
v8::Persistent<v8::Value>& V8PerIsolateData::ensureLiveRoot()
@@ -80,76 +106,92 @@ v8::Persistent<v8::Value>& V8PerIsolateData::ensureLiveRoot()
void V8PerIsolateData::dispose(v8::Isolate* isolate)
{
+#ifndef NDEBUG
+ if (blink::Platform::current()->currentThread())
+ isolate->RemoveCallCompletedCallback(&assertV8RecursionScope);
+#endif
void* data = isolate->GetData(gin::kEmbedderBlink);
delete static_cast<V8PerIsolateData*>(data);
isolate->SetData(gin::kEmbedderBlink, 0);
}
-v8::Handle<v8::FunctionTemplate> V8PerIsolateData::toStringTemplate()
+V8PerIsolateData::DOMTemplateMap& V8PerIsolateData::currentDOMTemplateMap()
{
- if (m_toStringTemplate.isEmpty())
- m_toStringTemplate.set(m_isolate, v8::FunctionTemplate::New(m_isolate, constructorOfToString));
- return m_toStringTemplate.newLocal(m_isolate);
+ if (DOMWrapperWorld::current(m_isolate).isMainWorld())
+ return m_domTemplateMapForMainWorld;
+ return m_domTemplateMapForNonMainWorld;
}
-v8::Handle<v8::FunctionTemplate> V8PerIsolateData::privateTemplate(WrapperWorldType currentWorldType, void* privatePointer, v8::FunctionCallback callback, v8::Handle<v8::Value> data, v8::Handle<v8::Signature> signature, int length)
+v8::Handle<v8::FunctionTemplate> V8PerIsolateData::domTemplate(void* domTemplateKey, v8::FunctionCallback callback, v8::Handle<v8::Value> data, v8::Handle<v8::Signature> signature, int length)
{
- TemplateMap& templates = templateMap(currentWorldType);
- TemplateMap::iterator result = templates.find(privatePointer);
- if (result != templates.end())
- return result->value.newLocal(m_isolate);
+ DOMTemplateMap& domTemplateMap = currentDOMTemplateMap();
+ DOMTemplateMap::iterator result = domTemplateMap.find(domTemplateKey);
+ if (result != domTemplateMap.end())
+ return result->value.Get(m_isolate);
+
v8::Local<v8::FunctionTemplate> templ = v8::FunctionTemplate::New(m_isolate, callback, data, signature, length);
- templates.add(privatePointer, UnsafePersistent<v8::FunctionTemplate>(m_isolate, templ));
+ domTemplateMap.add(domTemplateKey, v8::Eternal<v8::FunctionTemplate>(m_isolate, templ));
return templ;
}
-v8::Handle<v8::FunctionTemplate> V8PerIsolateData::privateTemplateIfExists(WrapperWorldType currentWorldType, void* privatePointer)
+v8::Handle<v8::FunctionTemplate> V8PerIsolateData::existingDOMTemplate(void* domTemplateKey)
{
- TemplateMap& templates = templateMap(currentWorldType);
- TemplateMap::iterator result = templates.find(privatePointer);
- if (result != templates.end())
- return result->value.newLocal(m_isolate);
+ DOMTemplateMap& domTemplateMap = currentDOMTemplateMap();
+ DOMTemplateMap::iterator result = domTemplateMap.find(domTemplateKey);
+ if (result != domTemplateMap.end())
+ return result->value.Get(m_isolate);
return v8::Local<v8::FunctionTemplate>();
}
-void V8PerIsolateData::setPrivateTemplate(WrapperWorldType currentWorldType, void* privatePointer, v8::Handle<v8::FunctionTemplate> templ)
+void V8PerIsolateData::setDOMTemplate(void* domTemplateKey, v8::Handle<v8::FunctionTemplate> templ)
{
- templateMap(currentWorldType).add(privatePointer, UnsafePersistent<v8::FunctionTemplate>(m_isolate, templ));
+ currentDOMTemplateMap().add(domTemplateKey, v8::Eternal<v8::FunctionTemplate>(m_isolate, v8::Local<v8::FunctionTemplate>(templ)));
}
-v8::Handle<v8::FunctionTemplate> V8PerIsolateData::rawDOMTemplate(const WrapperTypeInfo* info, WrapperWorldType currentWorldType)
+v8::Local<v8::Context> V8PerIsolateData::ensureScriptRegexpContext()
{
- TemplateMap& templates = rawDOMTemplateMap(currentWorldType);
- TemplateMap::iterator result = templates.find(info);
- if (result != templates.end())
- return result->value.newLocal(m_isolate);
-
- v8::EscapableHandleScope handleScope(m_isolate);
- v8::Local<v8::FunctionTemplate> templ = createRawTemplate(m_isolate);
- templates.add(info, UnsafePersistent<v8::FunctionTemplate>(m_isolate, templ));
- return handleScope.Escape(templ);
+ if (!m_scriptRegexpScriptState) {
+ v8::Local<v8::Context> context(v8::Context::New(m_isolate));
+ m_scriptRegexpScriptState = ScriptState::create(context, DOMWrapperWorld::create());
+ }
+ return m_scriptRegexpScriptState->context();
}
-v8::Local<v8::Context> V8PerIsolateData::ensureRegexContext()
+bool V8PerIsolateData::hasInstance(const WrapperTypeInfo* info, v8::Handle<v8::Value> value)
{
- if (m_regexContext.isEmpty()) {
- v8::HandleScope handleScope(m_isolate);
- m_regexContext.set(m_isolate, v8::Context::New(m_isolate));
- }
- return m_regexContext.newLocal(m_isolate);
+ return hasInstance(info, value, m_domTemplateMapForMainWorld)
+ || hasInstance(info, value, m_domTemplateMapForNonMainWorld);
}
-bool V8PerIsolateData::hasInstance(const WrapperTypeInfo* info, v8::Handle<v8::Value> value, WrapperWorldType currentWorldType)
+bool V8PerIsolateData::hasInstance(const WrapperTypeInfo* info, v8::Handle<v8::Value> value, DOMTemplateMap& domTemplateMap)
{
- TemplateMap& templates = rawDOMTemplateMap(currentWorldType);
- TemplateMap::iterator result = templates.find(info);
- if (result == templates.end())
+ DOMTemplateMap::iterator result = domTemplateMap.find(info);
+ if (result == domTemplateMap.end())
return false;
- v8::HandleScope handleScope(m_isolate);
- return result->value.newLocal(m_isolate)->HasInstance(value);
+ v8::Handle<v8::FunctionTemplate> templ = result->value.Get(m_isolate);
+ return templ->HasInstance(value);
}
-void V8PerIsolateData::constructorOfToString(const v8::FunctionCallbackInfo<v8::Value>& info)
+v8::Handle<v8::Object> V8PerIsolateData::findInstanceInPrototypeChain(const WrapperTypeInfo* info, v8::Handle<v8::Value> value)
+{
+ v8::Handle<v8::Object> wrapper = findInstanceInPrototypeChain(info, value, m_domTemplateMapForMainWorld);
+ if (!wrapper.IsEmpty())
+ return wrapper;
+ return findInstanceInPrototypeChain(info, value, m_domTemplateMapForNonMainWorld);
+}
+
+v8::Handle<v8::Object> V8PerIsolateData::findInstanceInPrototypeChain(const WrapperTypeInfo* info, v8::Handle<v8::Value> value, DOMTemplateMap& domTemplateMap)
+{
+ if (value.IsEmpty() || !value->IsObject())
+ return v8::Handle<v8::Object>();
+ DOMTemplateMap::iterator result = domTemplateMap.find(info);
+ if (result == domTemplateMap.end())
+ return v8::Handle<v8::Object>();
+ v8::Handle<v8::FunctionTemplate> templ = result->value.Get(m_isolate);
+ return v8::Handle<v8::Object>::Cast(value)->FindInstanceInPrototypeChain(templ);
+}
+
+static void constructorOfToString(const v8::FunctionCallbackInfo<v8::Value>& info)
{
// The DOM constructors' toString functions grab the current toString
// for Functions by taking the toString function of itself and then
@@ -164,7 +206,14 @@ void V8PerIsolateData::constructorOfToString(const v8::FunctionCallbackInfo<v8::
v8SetReturnValue(info, v8::String::Empty(info.GetIsolate()));
return;
}
- v8SetReturnValue(info, V8ScriptRunner::callInternalFunction(v8::Handle<v8::Function>::Cast(value), info.This(), 0, 0, v8::Isolate::GetCurrent()));
+ v8SetReturnValue(info, V8ScriptRunner::callInternalFunction(v8::Handle<v8::Function>::Cast(value), info.This(), 0, 0, info.GetIsolate()));
+}
+
+v8::Handle<v8::FunctionTemplate> V8PerIsolateData::toStringTemplate()
+{
+ if (m_toStringTemplate.isEmpty())
+ m_toStringTemplate.set(m_isolate, v8::FunctionTemplate::New(m_isolate, constructorOfToString));
+ return m_toStringTemplate.newLocal(m_isolate);
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8PerIsolateData.h b/chromium/third_party/WebKit/Source/bindings/v8/V8PerIsolateData.h
index bfe9f5a636f..ead107cfd1f 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8PerIsolateData.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8PerIsolateData.h
@@ -27,9 +27,11 @@
#define V8PerIsolateData_h
#include "bindings/v8/ScopedPersistent.h"
-#include "bindings/v8/UnsafePersistent.h"
+#include "bindings/v8/ScriptState.h"
+#include "bindings/v8/V8HiddenValue.h"
#include "bindings/v8/WrapperTypeInfo.h"
#include "gin/public/gin_embedders.h"
+#include "gin/public/isolate_holder.h"
#include <v8.h>
#include "wtf/Forward.h"
#include "wtf/HashMap.h"
@@ -41,21 +43,15 @@ namespace WebCore {
class DOMDataStore;
class GCEventData;
class StringCache;
-class V8HiddenPropertyName;
struct WrapperTypeInfo;
class ExternalStringVisitor;
-typedef WTF::Vector<DOMDataStore*> DOMDataList;
+typedef WTF::Vector<DOMDataStore*> DOMDataStoreList;
class V8PerIsolateData {
public:
- static V8PerIsolateData* create(v8::Isolate*);
static void ensureInitialized(v8::Isolate*);
- static V8PerIsolateData* current()
- {
- return from(v8::Isolate::GetCurrent());
- }
static V8PerIsolateData* from(v8::Isolate* isolate)
{
ASSERT(isolate);
@@ -63,57 +59,23 @@ public:
return static_cast<V8PerIsolateData*>(isolate->GetData(gin::kEmbedderBlink));
}
static void dispose(v8::Isolate*);
+ static v8::Isolate* mainThreadIsolate();
- typedef HashMap<const void*, UnsafePersistent<v8::FunctionTemplate> > TemplateMap;
-
- TemplateMap& rawDOMTemplateMap(WrapperWorldType worldType)
- {
- if (worldType == MainWorld)
- return m_rawDOMTemplatesForMainWorld;
- return m_rawDOMTemplatesForNonMainWorld;
- }
-
- TemplateMap& templateMap(WrapperWorldType worldType)
- {
- if (worldType == MainWorld)
- return m_templatesForMainWorld;
- return m_templatesForNonMainWorld;
- }
+ v8::Isolate* isolate() { return m_isolate; }
v8::Handle<v8::FunctionTemplate> toStringTemplate();
- v8::Handle<v8::FunctionTemplate> lazyEventListenerToStringTemplate()
- {
- return v8::Local<v8::FunctionTemplate>::New(m_isolate, m_lazyEventListenerToStringTemplate);
- }
StringCache* stringCache() { return m_stringCache.get(); }
v8::Persistent<v8::Value>& ensureLiveRoot();
- DOMDataList& allStores() { return m_domDataList; }
-
- V8HiddenPropertyName* hiddenPropertyName() { return m_hiddenPropertyName.get(); }
-
- void registerDOMDataStore(DOMDataStore* domDataStore)
- {
- ASSERT(m_domDataList.find(domDataStore) == kNotFound);
- m_domDataList.append(domDataStore);
- }
-
- void unregisterDOMDataStore(DOMDataStore* domDataStore)
- {
- ASSERT(m_domDataList.find(domDataStore) != kNotFound);
- m_domDataList.remove(m_domDataList.find(domDataStore));
- }
-
- // DOMDataStore is owned outside V8PerIsolateData.
- DOMDataStore* workerDOMDataStore() { return m_workerDomDataStore; }
- void setWorkerDOMDataStore(DOMDataStore* store) { m_workerDomDataStore = store; }
-
int recursionLevel() const { return m_recursionLevel; }
int incrementRecursionLevel() { return ++m_recursionLevel; }
int decrementRecursionLevel() { return --m_recursionLevel; }
+ bool performingMicrotaskCheckpoint() const { return m_performingMicrotaskCheckpoint; }
+ void setPerformingMicrotaskCheckpoint(bool performingMicrotaskCheckpoint) { m_performingMicrotaskCheckpoint = performingMicrotaskCheckpoint; }
+
#ifndef NDEBUG
int internalScriptRecursionLevel() const { return m_internalScriptRecursionLevel; }
int incrementInternalScriptRecursionLevel() { return ++m_internalScriptRecursionLevel; }
@@ -121,24 +83,16 @@ public:
#endif
GCEventData* gcEventData() { return m_gcEventData.get(); }
+ V8HiddenValue* hiddenValue() { return m_hiddenValue.get(); }
- // Gives the system a hint that we should request garbage collection
- // upon the next close or navigation event, because some expensive
- // objects have been allocated that we want to take every opportunity
- // to collect.
- void setShouldCollectGarbageSoon() { m_shouldCollectGarbageSoon = true; }
- void clearShouldCollectGarbageSoon() { m_shouldCollectGarbageSoon = false; }
- bool shouldCollectGarbageSoon() const { return m_shouldCollectGarbageSoon; }
-
- v8::Handle<v8::FunctionTemplate> privateTemplate(WrapperWorldType, void* privatePointer, v8::FunctionCallback = 0, v8::Handle<v8::Value> data = v8::Handle<v8::Value>(), v8::Handle<v8::Signature> = v8::Handle<v8::Signature>(), int length = 0);
- v8::Handle<v8::FunctionTemplate> privateTemplateIfExists(WrapperWorldType, void* privatePointer);
- void setPrivateTemplate(WrapperWorldType, void* privatePointer, v8::Handle<v8::FunctionTemplate>);
-
- v8::Handle<v8::FunctionTemplate> rawDOMTemplate(const WrapperTypeInfo*, WrapperWorldType);
+ v8::Handle<v8::FunctionTemplate> domTemplate(void* domTemplateKey, v8::FunctionCallback = 0, v8::Handle<v8::Value> data = v8::Handle<v8::Value>(), v8::Handle<v8::Signature> = v8::Handle<v8::Signature>(), int length = 0);
+ v8::Handle<v8::FunctionTemplate> existingDOMTemplate(void* domTemplateKey);
+ void setDOMTemplate(void* domTemplateKey, v8::Handle<v8::FunctionTemplate>);
- bool hasInstance(const WrapperTypeInfo*, v8::Handle<v8::Value>, WrapperWorldType);
+ bool hasInstance(const WrapperTypeInfo*, v8::Handle<v8::Value>);
+ v8::Handle<v8::Object> findInstanceInPrototypeChain(const WrapperTypeInfo*, v8::Handle<v8::Value>);
- v8::Local<v8::Context> ensureRegexContext();
+ v8::Local<v8::Context> ensureScriptRegexpContext();
const char* previousSamplingState() const { return m_previousSamplingState; }
void setPreviousSamplingState(const char* name) { m_previousSamplingState = name; }
@@ -146,23 +100,21 @@ public:
private:
explicit V8PerIsolateData(v8::Isolate*);
~V8PerIsolateData();
- static void constructorOfToString(const v8::FunctionCallbackInfo<v8::Value>&);
+
+ typedef HashMap<const void*, v8::Eternal<v8::FunctionTemplate> > DOMTemplateMap;
+ DOMTemplateMap& currentDOMTemplateMap();
+ bool hasInstance(const WrapperTypeInfo*, v8::Handle<v8::Value>, DOMTemplateMap&);
+ v8::Handle<v8::Object> findInstanceInPrototypeChain(const WrapperTypeInfo*, v8::Handle<v8::Value>, DOMTemplateMap&);
v8::Isolate* m_isolate;
- TemplateMap m_rawDOMTemplatesForMainWorld;
- TemplateMap m_rawDOMTemplatesForNonMainWorld;
- TemplateMap m_templatesForMainWorld;
- TemplateMap m_templatesForNonMainWorld;
+ OwnPtr<gin::IsolateHolder> m_isolateHolder;
+ DOMTemplateMap m_domTemplateMapForMainWorld;
+ DOMTemplateMap m_domTemplateMapForNonMainWorld;
ScopedPersistent<v8::FunctionTemplate> m_toStringTemplate;
- v8::Persistent<v8::FunctionTemplate> m_lazyEventListenerToStringTemplate;
OwnPtr<StringCache> m_stringCache;
-
- Vector<DOMDataStore*> m_domDataList;
- DOMDataStore* m_workerDomDataStore;
-
- OwnPtr<V8HiddenPropertyName> m_hiddenPropertyName;
+ OwnPtr<V8HiddenValue> m_hiddenValue;
ScopedPersistent<v8::Value> m_liveRoot;
- ScopedPersistent<v8::Context> m_regexContext;
+ RefPtr<ScriptState> m_scriptRegexpScriptState;
const char* m_previousSamplingState;
@@ -175,7 +127,7 @@ private:
int m_internalScriptRecursionLevel;
#endif
OwnPtr<GCEventData> m_gcEventData;
- bool m_shouldCollectGarbageSoon;
+ bool m_performingMicrotaskCheckpoint;
};
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8PersistentValueMap.h b/chromium/third_party/WebKit/Source/bindings/v8/V8PersistentValueMap.h
new file mode 100644
index 00000000000..0fa2ac2c902
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8PersistentValueMap.h
@@ -0,0 +1,128 @@
+/*
+ * Copyright (C) 2014 Google Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are
+ * met:
+ *
+ * * Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * * Redistributions in binary form must reproduce the above
+ * copyright notice, this list of conditions and the following disclaimer
+ * in the documentation and/or other materials provided with the
+ * distribution.
+ * * Neither the name of Google Inc. nor the names of its
+ * contributors may be used to endorse or promote products derived from
+ * this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+ * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+ * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+ * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#ifndef V8PersistentValueMap_h
+#define V8PersistentValueMap_h
+
+#include "wtf/HashMap.h"
+#include <v8-util.h>
+#include <v8.h>
+
+namespace WebCore {
+
+/**
+ * A Traits class for v8::PersistentValueMap that uses wtf/HashMap as a
+ * backing store.
+ *
+ * The parameter is_weak will determine whether the references are 'weak'.
+ * If so, entries will be removed from the map as the weak references are
+ * collected.
+ */
+template<class KeyType, class ValueType, bool is_weak>
+class V8PersistentValueMapTraits {
+public:
+ // Map traits:
+ typedef HashMap<KeyType, v8::PersistentContainerValue> Impl;
+ typedef typename Impl::iterator Iterator;
+ static size_t Size(const Impl* impl) { return impl->size(); }
+ static bool Empty(Impl* impl) { return impl->isEmpty(); }
+ static void Swap(Impl& impl, Impl& other) { impl.swap(other); }
+ static Iterator Begin(Impl* impl) { return impl->begin(); }
+ static Iterator End(Impl* impl) { return impl->end(); }
+ static v8::PersistentContainerValue Value(Iterator& iter)
+ {
+ return iter->value;
+ }
+ static KeyType Key(Iterator& iter) { return iter->key; }
+ static v8::PersistentContainerValue Set(
+ Impl* impl, KeyType key, v8::PersistentContainerValue value)
+ {
+ v8::PersistentContainerValue oldValue = Get(impl, key);
+ impl->set(key, value);
+ return oldValue;
+ }
+ static v8::PersistentContainerValue Get(const Impl* impl, KeyType key)
+ {
+ return impl->get(key);
+ }
+
+ static v8::PersistentContainerValue Remove(Impl* impl, KeyType key)
+ {
+ return impl->take(key);
+ }
+
+ // Weak traits:
+ static const v8::PersistentContainerCallbackType kCallbackType = is_weak ? v8::kWeak : v8::kNotWeak;
+ typedef v8::PersistentValueMap<KeyType, ValueType, V8PersistentValueMapTraits<KeyType, ValueType, is_weak> > MapType;
+
+ typedef void WeakCallbackDataType;
+
+ static WeakCallbackDataType* WeakCallbackParameter(MapType* map, KeyType key, const v8::Local<ValueType>& value)
+ {
+ return 0;
+ }
+
+ static void DisposeCallbackData(WeakCallbackDataType* callbackData)
+ {
+ }
+
+ static MapType* MapFromWeakCallbackData(
+ const v8::WeakCallbackData<ValueType, WeakCallbackDataType>& data)
+ {
+ return 0;
+ }
+
+ static KeyType KeyFromWeakCallbackData(
+ const v8::WeakCallbackData<ValueType, WeakCallbackDataType>& data)
+ {
+ return KeyType();
+ }
+
+ // Dispose traits:
+ static void Dispose(v8::Isolate* isolate, v8::UniquePersistent<ValueType> value, KeyType key) { }
+};
+
+/**
+ * A map for safely storing persistent V8 values, based on
+ * v8::PersistentValueMap.
+ *
+ * If is_weak is set, values will be held weakly and map entries will be
+ * removed as their values are being collected.
+ */
+template<class KeyType, class ValueType, bool is_weak = true>
+class V8PersistentValueMap : public v8::PersistentValueMap<KeyType, ValueType, V8PersistentValueMapTraits<KeyType, ValueType, is_weak> > {
+public:
+ typedef V8PersistentValueMapTraits<KeyType, ValueType, is_weak> Traits;
+ explicit V8PersistentValueMap(v8::Isolate* isolate) : v8::PersistentValueMap<KeyType, ValueType, Traits>(isolate) { }
+};
+
+} // namespace WebCore
+
+#endif // V8PersistentValueMap_h
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8NodeListCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/V8PersistentValueVector.h
index 341f1c23d5d..02f8314e937 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8NodeListCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8PersistentValueVector.h
@@ -28,33 +28,50 @@
* OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
*/
-#include "config.h"
-#include "V8NodeList.h"
+#ifndef V8PersistentValueVector_h
+#define V8PersistentValueVector_h
-#include "V8Node.h"
-#include "bindings/v8/V8Binding.h"
-#include "bindings/v8/V8GCController.h"
-#include "core/dom/LiveNodeList.h"
-#include "core/dom/NodeList.h"
-#include "wtf/RefPtr.h"
-#include "wtf/StdLibExtras.h"
+#include "wtf/Vector.h"
+#include <v8-util.h>
+#include <v8.h>
namespace WebCore {
-void V8NodeList::visitDOMWrapper(void* object, const v8::Persistent<v8::Object>& wrapper, v8::Isolate* isolate)
-{
- NodeList* impl = static_cast<NodeList*>(object);
- if (!impl->isLiveNodeList()) {
- setObjectGroup(object, wrapper, isolate);
- return;
+class WTFVectorPersistentValueVectorTraits {
+public:
+ typedef Vector<v8::PersistentContainerValue> Impl;
+ static void Append(Impl* impl, v8::PersistentContainerValue value)
+ {
+ impl->append(value);
}
- Node* owner = static_cast<LiveNodeList*>(impl)->ownerNode();
- if (!owner) {
- setObjectGroup(object, wrapper, isolate);
- return;
+ static bool IsEmpty(const Impl* impl)
+ {
+ return impl->isEmpty();
}
+ static size_t Size(const Impl* impl)
+ {
+ return impl->size();
+ }
+ static v8::PersistentContainerValue Get(const Impl* impl, size_t i)
+ {
+ return (i < impl->size()) ? impl->at(i) : v8::kPersistentContainerNotFound;
+ }
+ static void ReserveCapacity(Impl* impl, size_t capacity)
+ {
+ impl->reserveCapacity(capacity);
+ }
+ static void Clear(Impl* impl)
+ {
+ impl->clear();
+ }
+};
- setObjectGroup(V8GCController::opaqueRootForGC(owner, isolate), wrapper, isolate);
-}
+template<class ValueType>
+class V8PersistentValueVector : public v8::PersistentValueVector<ValueType, WTFVectorPersistentValueVectorTraits> {
+public:
+ explicit V8PersistentValueVector(v8::Isolate* isolate) : v8::PersistentValueVector<ValueType, WTFVectorPersistentValueVectorTraits>(isolate) { }
+};
} // namespace WebCore
+
+#endif // V8PersistentValueVector_h
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8RecursionScope.cpp b/chromium/third_party/WebKit/Source/bindings/v8/V8RecursionScope.cpp
index c08fba7c855..2519250f28f 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8RecursionScope.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8RecursionScope.cpp
@@ -38,14 +38,11 @@ namespace WebCore {
void V8RecursionScope::didLeaveScriptContext()
{
- // FIXME: Instrument any work that takes place when script exits to c++ (e.g. Mutation Observers).
+ Microtask::performCheckpoint();
// Indexed DB requires that transactions are created with an internal |active| flag
// set to true, but the flag becomes false when control returns to the event loop.
- IDBPendingTransactionMonitor::deactivateNewTransactions();
-
- if (m_isDocumentContext)
- Microtask::performCheckpoint();
+ IDBPendingTransactionMonitor::from(m_executionContext).deactivateNewTransactions();
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8RecursionScope.h b/chromium/third_party/WebKit/Source/bindings/v8/V8RecursionScope.h
index 3bc3da7d024..a73d93a8dc0 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8RecursionScope.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8RecursionScope.h
@@ -33,7 +33,9 @@
#include "bindings/v8/V8PerIsolateData.h"
#include "core/dom/ExecutionContext.h"
+#include "core/dom/ScriptForbiddenScope.h"
#include "wtf/Noncopyable.h"
+#include <v8.h>
namespace WebCore {
@@ -57,51 +59,66 @@ namespace WebCore {
class V8RecursionScope {
WTF_MAKE_NONCOPYABLE(V8RecursionScope);
public:
- explicit V8RecursionScope(ExecutionContext* context)
- : m_isDocumentContext(context && context->isDocument())
+ V8RecursionScope(v8::Isolate* isolate, ExecutionContext* context)
+ : m_isolate(isolate)
+ , m_executionContext(*context)
{
- V8PerIsolateData::current()->incrementRecursionLevel();
+ V8PerIsolateData::from(m_isolate)->incrementRecursionLevel();
+ ASSERT(!ScriptForbiddenScope::isScriptForbidden());
+ // If you want V8 to autorun microtasks, this class needs to have a
+ // v8::Isolate::SuppressMicrotaskExecutionScope member.
+ ASSERT(!isolate->WillAutorunMicrotasks());
}
~V8RecursionScope()
{
- if (!V8PerIsolateData::current()->decrementRecursionLevel())
+ if (!V8PerIsolateData::from(m_isolate)->decrementRecursionLevel())
didLeaveScriptContext();
}
- static int recursionLevel()
+ static int recursionLevel(v8::Isolate* isolate)
{
- return V8PerIsolateData::current()->recursionLevel();
+ return V8PerIsolateData::from(isolate)->recursionLevel();
}
#ifndef NDEBUG
- static bool properlyUsed()
+ static bool properlyUsed(v8::Isolate* isolate)
{
- return recursionLevel() > 0 || V8PerIsolateData::current()->internalScriptRecursionLevel() > 0;
+ return recursionLevel(isolate) > 0 || V8PerIsolateData::from(isolate)->internalScriptRecursionLevel() > 0;
}
#endif
class MicrotaskSuppression {
public:
- MicrotaskSuppression()
+ MicrotaskSuppression(v8::Isolate* isolate)
+#ifndef NDEBUG
+ : m_isolate(isolate)
+#endif
{
+ ASSERT(!ScriptForbiddenScope::isScriptForbidden());
#ifndef NDEBUG
- V8PerIsolateData::current()->incrementInternalScriptRecursionLevel();
+ V8PerIsolateData::from(m_isolate)->incrementInternalScriptRecursionLevel();
#endif
}
~MicrotaskSuppression()
{
#ifndef NDEBUG
- V8PerIsolateData::current()->decrementInternalScriptRecursionLevel();
+ V8PerIsolateData::from(m_isolate)->decrementInternalScriptRecursionLevel();
#endif
}
+
+ private:
+#ifndef NDEBUG
+ v8::Isolate* m_isolate;
+#endif
};
private:
void didLeaveScriptContext();
- bool m_isDocumentContext;
+ v8::Isolate* m_isolate;
+ ExecutionContext& m_executionContext;
};
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8ScriptRunner.cpp b/chromium/third_party/WebKit/Source/bindings/v8/V8ScriptRunner.cpp
index ed6a1730117..625fddf8095 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8ScriptRunner.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8ScriptRunner.cpp
@@ -26,6 +26,7 @@
#include "config.h"
#include "bindings/v8/V8ScriptRunner.h"
+#include "bindings/v8/ScriptSourceCode.h"
#include "bindings/v8/V8Binding.h"
#include "bindings/v8/V8GCController.h"
#include "bindings/v8/V8RecursionScope.h"
@@ -36,70 +37,74 @@
namespace WebCore {
-PassOwnPtr<v8::ScriptData> V8ScriptRunner::precompileScript(v8::Handle<v8::String> code, ScriptResource* resource)
+v8::Local<v8::Script> V8ScriptRunner::compileScript(const ScriptSourceCode& source, v8::Isolate* isolate, AccessControlStatus corsStatus)
+{
+ return compileScript(v8String(isolate, source.source()), source.url(), source.startPosition(), source.resource(), isolate, corsStatus);
+}
+
+v8::Local<v8::Script> V8ScriptRunner::compileScript(v8::Handle<v8::String> code, const String& fileName, const TextPosition& scriptStartPosition, ScriptResource* resource, v8::Isolate* isolate, AccessControlStatus corsStatus)
{
- TRACE_EVENT0("v8", "v8.compile");
- TRACE_EVENT_SCOPED_SAMPLING_STATE("V8", "Compile");
// A pseudo-randomly chosen ID used to store and retrieve V8 ScriptData from
// the ScriptResource. If the format changes, this ID should be changed too.
static const unsigned dataTypeID = 0xECC13BD7;
- // Very small scripts are not worth the effort to preparse.
- static const int minPreparseLength = 1024;
-
- if (!resource || code->Length() < minPreparseLength)
- return nullptr;
-
- CachedMetadata* cachedMetadata = resource->cachedMetadata(dataTypeID);
- if (cachedMetadata)
- return adoptPtr(v8::ScriptData::New(cachedMetadata->data(), cachedMetadata->size()));
-
- OwnPtr<v8::ScriptData> scriptData = adoptPtr(v8::ScriptData::PreCompile(code));
- if (!scriptData)
- return nullptr;
+ // Very small scripts are not worth the effort to store cached data.
+ static const int minLengthForCachedData = 1024;
- resource->setCachedMetadata(dataTypeID, scriptData->Data(), scriptData->Length());
+ TRACE_EVENT1("v8", "v8.compile", "fileName", fileName.utf8());
+ TRACE_EVENT_SCOPED_SAMPLING_STATE("V8", "V8Compile");
- return scriptData.release();
-}
-
-v8::Local<v8::Script> V8ScriptRunner::compileScript(v8::Handle<v8::String> code, const String& fileName, const TextPosition& scriptStartPosition, v8::ScriptData* scriptData, v8::Isolate* isolate, AccessControlStatus corsStatus)
-{
- TRACE_EVENT0("v8", "v8.compile");
- TRACE_EVENT_SCOPED_SAMPLING_STATE("V8", "Compile");
+ // NOTE: For compatibility with WebCore, ScriptSourceCode's line starts at
+ // 1, whereas v8 starts at 0.
v8::Handle<v8::String> name = v8String(isolate, fileName);
- v8::Handle<v8::Integer> line = v8::Integer::New(scriptStartPosition.m_line.zeroBasedInt(), isolate);
- v8::Handle<v8::Integer> column = v8::Integer::New(scriptStartPosition.m_column.zeroBasedInt(), isolate);
+ v8::Handle<v8::Integer> line = v8::Integer::New(isolate, scriptStartPosition.m_line.zeroBasedInt());
+ v8::Handle<v8::Integer> column = v8::Integer::New(isolate, scriptStartPosition.m_column.zeroBasedInt());
v8::Handle<v8::Boolean> isSharedCrossOrigin = corsStatus == SharableCrossOrigin ? v8::True(isolate) : v8::False(isolate);
v8::ScriptOrigin origin(name, line, column, isSharedCrossOrigin);
- return v8::Script::Compile(code, &origin, scriptData);
+
+ v8::ScriptCompiler::CompileOptions options = v8::ScriptCompiler::kNoCompileOptions;
+ OwnPtr<v8::ScriptCompiler::CachedData> cachedData;
+ if (resource) {
+ CachedMetadata* cachedMetadata = resource->cachedMetadata(dataTypeID);
+ if (cachedMetadata) {
+ // Ownership of the buffer is not transferred to CachedData.
+ cachedData = adoptPtr(new v8::ScriptCompiler::CachedData(reinterpret_cast<const uint8_t*>(cachedMetadata->data()), cachedMetadata->size()));
+ } else if (code->Length() >= minLengthForCachedData) {
+ options = v8::ScriptCompiler::kProduceDataToCache;
+ }
+ }
+ // source takes ownership of cachedData.
+ v8::ScriptCompiler::Source source(code, origin, cachedData.leakPtr());
+ v8::Local<v8::Script> script = v8::ScriptCompiler::Compile(isolate, &source, options);
+ if (options == v8::ScriptCompiler::kProduceDataToCache) {
+ const v8::ScriptCompiler::CachedData* newCachedData = source.GetCachedData();
+ if (newCachedData) {
+ // Ownership of the buffer is not transferred; source's cachedData continues to own it.
+ resource->setCachedMetadata(dataTypeID, reinterpret_cast<const char*>(newCachedData->data), newCachedData->length);
+ }
+ }
+ return script;
}
v8::Local<v8::Value> V8ScriptRunner::runCompiledScript(v8::Handle<v8::Script> script, ExecutionContext* context, v8::Isolate* isolate)
{
- TRACE_EVENT0("v8", "v8.run");
- TRACE_EVENT_SCOPED_SAMPLING_STATE("V8", "Execution");
if (script.IsEmpty())
return v8::Local<v8::Value>();
+ TRACE_EVENT_SCOPED_SAMPLING_STATE("V8", "V8Execution");
+ TRACE_EVENT1("v8", "v8.run", "fileName", TRACE_STR_COPY(*v8::String::Utf8Value(script->GetUnboundScript()->GetScriptName())));
- if (V8RecursionScope::recursionLevel() >= kMaxRecursionDepth)
+ if (V8RecursionScope::recursionLevel(isolate) >= kMaxRecursionDepth)
return handleMaxRecursionDepthExceeded(isolate);
- if (handleOutOfMemory())
- return v8::Local<v8::Value>();
-
RELEASE_ASSERT(!context->isIteratingOverObservers());
// Run the script and keep track of the current recursion depth.
v8::Local<v8::Value> result;
{
- V8RecursionScope recursionScope(context);
+ V8RecursionScope recursionScope(isolate, context);
result = script->Run();
}
- if (handleOutOfMemory())
- ASSERT(result.IsEmpty());
-
if (result.IsEmpty())
return v8::Local<v8::Value>();
@@ -107,95 +112,84 @@ v8::Local<v8::Value> V8ScriptRunner::runCompiledScript(v8::Handle<v8::Script> sc
return result;
}
-v8::Local<v8::Value> V8ScriptRunner::compileAndRunInternalScript(v8::Handle<v8::String> source, v8::Isolate* isolate, const String& fileName, const TextPosition& scriptStartPosition, v8::ScriptData* scriptData)
+v8::Local<v8::Value> V8ScriptRunner::compileAndRunInternalScript(v8::Handle<v8::String> source, v8::Isolate* isolate, const String& fileName, const TextPosition& scriptStartPosition)
{
TRACE_EVENT0("v8", "v8.run");
- TRACE_EVENT_SCOPED_SAMPLING_STATE("V8", "Execution");
- v8::Handle<v8::Script> script = V8ScriptRunner::compileScript(source, fileName, scriptStartPosition, scriptData, isolate);
+ TRACE_EVENT_SCOPED_SAMPLING_STATE("V8", "V8Execution");
+ v8::Handle<v8::Script> script = V8ScriptRunner::compileScript(source, fileName, scriptStartPosition, 0, isolate);
if (script.IsEmpty())
return v8::Local<v8::Value>();
- V8RecursionScope::MicrotaskSuppression recursionScope;
+ V8RecursionScope::MicrotaskSuppression recursionScope(isolate);
v8::Local<v8::Value> result = script->Run();
crashIfV8IsDead();
return result;
}
-v8::Local<v8::Value> V8ScriptRunner::callFunction(v8::Handle<v8::Function> function, ExecutionContext* context, v8::Handle<v8::Value> receiver, int argc, v8::Handle<v8::Value> info[], v8::Isolate* isolate)
+v8::Local<v8::Value> V8ScriptRunner::callFunction(v8::Handle<v8::Function> function, ExecutionContext* context, v8::Handle<v8::Value> receiver, int argc, v8::Handle<v8::Value> args[], v8::Isolate* isolate)
{
TRACE_EVENT0("v8", "v8.callFunction");
- TRACE_EVENT_SCOPED_SAMPLING_STATE("V8", "Execution");
+ TRACE_EVENT_SCOPED_SAMPLING_STATE("V8", "V8Execution");
- if (V8RecursionScope::recursionLevel() >= kMaxRecursionDepth)
+ if (V8RecursionScope::recursionLevel(isolate) >= kMaxRecursionDepth)
return handleMaxRecursionDepthExceeded(isolate);
RELEASE_ASSERT(!context->isIteratingOverObservers());
- V8RecursionScope recursionScope(context);
- v8::Local<v8::Value> result = function->Call(receiver, argc, info);
+ V8RecursionScope recursionScope(isolate, context);
+ v8::Local<v8::Value> result = function->Call(receiver, argc, args);
crashIfV8IsDead();
return result;
}
-v8::Local<v8::Value> V8ScriptRunner::callInternalFunction(v8::Handle<v8::Function> function, v8::Handle<v8::Value> receiver, int argc, v8::Handle<v8::Value> info[], v8::Isolate* isolate)
+v8::Local<v8::Value> V8ScriptRunner::callInternalFunction(v8::Handle<v8::Function> function, v8::Handle<v8::Value> receiver, int argc, v8::Handle<v8::Value> args[], v8::Isolate* isolate)
{
TRACE_EVENT0("v8", "v8.callFunction");
- TRACE_EVENT_SCOPED_SAMPLING_STATE("V8", "Execution");
- V8RecursionScope::MicrotaskSuppression recursionScope;
- v8::Local<v8::Value> result = function->Call(receiver, argc, info);
- crashIfV8IsDead();
- return result;
-}
-
-v8::Local<v8::Value> V8ScriptRunner::callAsFunction(v8::Handle<v8::Object> object, v8::Handle<v8::Value> receiver, int argc, v8::Handle<v8::Value> info[])
-{
- TRACE_EVENT0("v8", "v8.callFunction");
- TRACE_EVENT_SCOPED_SAMPLING_STATE("V8", "Execution");
-
- V8RecursionScope::MicrotaskSuppression recursionScope;
- v8::Local<v8::Value> result = object->CallAsFunction(receiver, argc, info);
+ TRACE_EVENT_SCOPED_SAMPLING_STATE("V8", "V8Execution");
+ V8RecursionScope::MicrotaskSuppression recursionScope(isolate);
+ v8::Local<v8::Value> result = function->Call(receiver, argc, args);
crashIfV8IsDead();
return result;
}
-v8::Local<v8::Value> V8ScriptRunner::callAsConstructor(v8::Handle<v8::Object> object, int argc, v8::Handle<v8::Value> info[])
+v8::Local<v8::Value> V8ScriptRunner::callAsFunction(v8::Isolate* isolate, v8::Handle<v8::Object> object, v8::Handle<v8::Value> receiver, int argc, v8::Handle<v8::Value> args[])
{
TRACE_EVENT0("v8", "v8.callFunction");
- TRACE_EVENT_SCOPED_SAMPLING_STATE("V8", "Execution");
+ TRACE_EVENT_SCOPED_SAMPLING_STATE("V8", "V8Execution");
- V8RecursionScope::MicrotaskSuppression recursionScope;
- v8::Local<v8::Value> result = object->CallAsConstructor(argc, info);
+ V8RecursionScope::MicrotaskSuppression recursionScope(isolate);
+ v8::Local<v8::Value> result = object->CallAsFunction(receiver, argc, args);
crashIfV8IsDead();
return result;
}
-v8::Local<v8::Object> V8ScriptRunner::instantiateObject(v8::Handle<v8::ObjectTemplate> objectTemplate)
+v8::Local<v8::Object> V8ScriptRunner::instantiateObject(v8::Isolate* isolate, v8::Handle<v8::ObjectTemplate> objectTemplate)
{
TRACE_EVENT0("v8", "v8.newInstance");
- TRACE_EVENT_SCOPED_SAMPLING_STATE("V8", "Execution");
+ TRACE_EVENT_SCOPED_SAMPLING_STATE("V8", "V8Execution");
- V8RecursionScope::MicrotaskSuppression scope;
+ V8RecursionScope::MicrotaskSuppression scope(isolate);
v8::Local<v8::Object> result = objectTemplate->NewInstance();
crashIfV8IsDead();
return result;
}
-v8::Local<v8::Object> V8ScriptRunner::instantiateObject(v8::Handle<v8::Function> function, int argc, v8::Handle<v8::Value> argv[])
+v8::Local<v8::Object> V8ScriptRunner::instantiateObject(v8::Isolate* isolate, v8::Handle<v8::Function> function, int argc, v8::Handle<v8::Value> argv[])
{
TRACE_EVENT0("v8", "v8.newInstance");
- TRACE_EVENT_SCOPED_SAMPLING_STATE("V8", "Execution");
+ TRACE_EVENT_SCOPED_SAMPLING_STATE("V8", "V8Execution");
- V8RecursionScope::MicrotaskSuppression scope;
+ V8RecursionScope::MicrotaskSuppression scope(isolate);
v8::Local<v8::Object> result = function->NewInstance(argc, argv);
crashIfV8IsDead();
return result;
}
-v8::Local<v8::Object> V8ScriptRunner::instantiateObjectInDocument(v8::Handle<v8::Function> function, ExecutionContext* context, int argc, v8::Handle<v8::Value> argv[])
+v8::Local<v8::Object> V8ScriptRunner::instantiateObjectInDocument(v8::Isolate* isolate, v8::Handle<v8::Function> function, ExecutionContext* context, int argc, v8::Handle<v8::Value> argv[])
{
TRACE_EVENT0("v8", "v8.newInstance");
- TRACE_EVENT_SCOPED_SAMPLING_STATE("V8", "Execution");
- V8RecursionScope scope(context);
+ TRACE_EVENT_SCOPED_SAMPLING_STATE("V8", "V8Execution");
+ V8RecursionScope scope(isolate, context);
v8::Local<v8::Object> result = function->NewInstance(argc, argv);
crashIfV8IsDead();
return result;
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8ScriptRunner.h b/chromium/third_party/WebKit/Source/bindings/v8/V8ScriptRunner.h
index b36102f20ba..368401be41f 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8ScriptRunner.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8ScriptRunner.h
@@ -35,23 +35,23 @@
namespace WebCore {
class ScriptResource;
+class ScriptSourceCode;
class ExecutionContext;
class V8ScriptRunner {
public:
// For the following methods, the caller sites have to hold
// a HandleScope and a ContextScope.
- static PassOwnPtr<v8::ScriptData> precompileScript(v8::Handle<v8::String>, ScriptResource*);
- static v8::Local<v8::Script> compileScript(v8::Handle<v8::String>, const String&, const TextPosition&, v8::ScriptData*, v8::Isolate*, AccessControlStatus = SharableCrossOrigin);
+ static v8::Local<v8::Script> compileScript(const ScriptSourceCode&, v8::Isolate*, AccessControlStatus = SharableCrossOrigin);
+ static v8::Local<v8::Script> compileScript(v8::Handle<v8::String>, const String& fileName, const TextPosition&, ScriptResource*, v8::Isolate*, AccessControlStatus = SharableCrossOrigin);
static v8::Local<v8::Value> runCompiledScript(v8::Handle<v8::Script>, ExecutionContext*, v8::Isolate*);
- static v8::Local<v8::Value> compileAndRunInternalScript(v8::Handle<v8::String>, v8::Isolate*, const String& = String(), const TextPosition& = TextPosition(), v8::ScriptData* = 0);
+ static v8::Local<v8::Value> compileAndRunInternalScript(v8::Handle<v8::String>, v8::Isolate*, const String& = String(), const TextPosition& = TextPosition());
static v8::Local<v8::Value> callInternalFunction(v8::Handle<v8::Function>, v8::Handle<v8::Value> receiver, int argc, v8::Handle<v8::Value> info[], v8::Isolate*);
static v8::Local<v8::Value> callFunction(v8::Handle<v8::Function>, ExecutionContext*, v8::Handle<v8::Value> receiver, int argc, v8::Handle<v8::Value> info[], v8::Isolate*);
- static v8::Local<v8::Value> callAsFunction(v8::Handle<v8::Object>, v8::Handle<v8::Value> receiver, int argc, v8::Handle<v8::Value> info[]);
- static v8::Local<v8::Value> callAsConstructor(v8::Handle<v8::Object>, int argc, v8::Handle<v8::Value> info[]);
- static v8::Local<v8::Object> instantiateObject(v8::Handle<v8::ObjectTemplate>);
- static v8::Local<v8::Object> instantiateObject(v8::Handle<v8::Function>, int argc = 0, v8::Handle<v8::Value> argv[] = 0);
- static v8::Local<v8::Object> instantiateObjectInDocument(v8::Handle<v8::Function>, ExecutionContext*, int argc = 0, v8::Handle<v8::Value> argv[] = 0);
+ static v8::Local<v8::Value> callAsFunction(v8::Isolate*, v8::Handle<v8::Object>, v8::Handle<v8::Value> receiver, int argc, v8::Handle<v8::Value> info[]);
+ static v8::Local<v8::Object> instantiateObject(v8::Isolate*, v8::Handle<v8::ObjectTemplate>);
+ static v8::Local<v8::Object> instantiateObject(v8::Isolate*, v8::Handle<v8::Function>, int argc = 0, v8::Handle<v8::Value> argv[] = 0);
+ static v8::Local<v8::Object> instantiateObjectInDocument(v8::Isolate*, v8::Handle<v8::Function>, ExecutionContext*, int argc = 0, v8::Handle<v8::Value> argv[] = 0);
};
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8StringResource.cpp b/chromium/third_party/WebKit/Source/bindings/v8/V8StringResource.cpp
index bce62d4c2fa..3b76e8243f9 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8StringResource.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8StringResource.cpp
@@ -32,27 +32,9 @@
namespace WebCore {
-WebCoreStringResourceBase* WebCoreStringResourceBase::toWebCoreStringResourceBase(v8::Handle<v8::String> string)
-{
- v8::String::Encoding encoding;
- v8::String::ExternalStringResourceBase* resource = string->GetExternalStringResourceBase(&encoding);
- if (!resource)
- return 0;
- if (encoding == v8::String::ONE_BYTE_ENCODING)
- return static_cast<WebCoreStringResource8*>(resource);
- return static_cast<WebCoreStringResource16*>(resource);
-}
-
-void WebCoreStringResourceBase::visitStrings(ExternalStringVisitor* visitor)
-{
- visitor->visitJSExternalString(m_plainString.impl());
- if (m_plainString.impl() != m_atomicString.impl() && !m_atomicString.isNull())
- visitor->visitJSExternalString(m_atomicString.impl());
-}
-
template<class StringClass> struct StringTraits {
static const StringClass& fromStringResource(WebCoreStringResourceBase*);
- template<bool oneByte>
+ template <typename V8StringTrait>
static StringClass fromV8String(v8::Handle<v8::String>, int);
};
@@ -62,7 +44,7 @@ struct StringTraits<String> {
{
return resource->webcoreString();
}
- template<bool oneByte>
+ template <typename V8StringTrait>
static String fromV8String(v8::Handle<v8::String>, int);
};
@@ -72,59 +54,49 @@ struct StringTraits<AtomicString> {
{
return resource->atomicString();
}
- template<bool oneByte>
+ template <typename V8StringTrait>
static AtomicString fromV8String(v8::Handle<v8::String>, int);
};
-template<>
-String StringTraits<String>::fromV8String<false>(v8::Handle<v8::String> v8String, int length)
-{
- ASSERT(v8String->Length() == length);
- UChar* buffer;
- String result = String::createUninitialized(length, buffer);
- v8String->Write(reinterpret_cast<uint16_t*>(buffer), 0, length);
- return result;
-}
+struct V8StringTwoBytesTrait {
+ typedef UChar CharType;
+ ALWAYS_INLINE static void write(v8::Handle<v8::String> v8String, CharType* buffer, int length)
+ {
+ v8String->Write(reinterpret_cast<uint16_t*>(buffer), 0, length);
+ }
+};
-template<>
-AtomicString StringTraits<AtomicString>::fromV8String<false>(v8::Handle<v8::String> v8String, int length)
-{
- ASSERT(v8String->Length() == length);
- static const int inlineBufferSize = 16;
- if (length <= inlineBufferSize) {
- UChar inlineBuffer[inlineBufferSize];
- v8String->Write(reinterpret_cast<uint16_t*>(inlineBuffer), 0, length);
- return AtomicString(inlineBuffer, length);
+struct V8StringOneByteTrait {
+ typedef LChar CharType;
+ ALWAYS_INLINE static void write(v8::Handle<v8::String> v8String, CharType* buffer, int length)
+ {
+ v8String->WriteOneByte(buffer, 0, length);
}
- UChar* buffer;
- String result = String::createUninitialized(length, buffer);
- v8String->Write(reinterpret_cast<uint16_t*>(buffer), 0, length);
- return AtomicString(result);
-}
+};
-template<>
-String StringTraits<String>::fromV8String<true>(v8::Handle<v8::String> v8String, int length)
+template <typename V8StringTrait>
+String StringTraits<String>::fromV8String(v8::Handle<v8::String> v8String, int length)
{
ASSERT(v8String->Length() == length);
- LChar* buffer;
+ typename V8StringTrait::CharType* buffer;
String result = String::createUninitialized(length, buffer);
- v8String->WriteOneByte(buffer, 0, length);
+ V8StringTrait::write(v8String, buffer, length);
return result;
}
-template<>
-AtomicString StringTraits<AtomicString>::fromV8String<true>(v8::Handle<v8::String> v8String, int length)
+template <typename V8StringTrait>
+AtomicString StringTraits<AtomicString>::fromV8String(v8::Handle<v8::String> v8String, int length)
{
ASSERT(v8String->Length() == length);
- static const int inlineBufferSize = 32;
+ static const int inlineBufferSize = 32 / sizeof(typename V8StringTrait::CharType);
if (length <= inlineBufferSize) {
- LChar inlineBuffer[inlineBufferSize];
- v8String->WriteOneByte(inlineBuffer, 0, length);
+ typename V8StringTrait::CharType inlineBuffer[inlineBufferSize];
+ V8StringTrait::write(v8String, inlineBuffer, length);
return AtomicString(inlineBuffer, length);
}
- LChar* buffer;
+ typename V8StringTrait::CharType* buffer;
String string = String::createUninitialized(length, buffer);
- v8String->WriteOneByte(buffer, 0, length);
+ V8StringTrait::write(v8String, buffer, length);
return AtomicString(string);
}
@@ -132,7 +104,6 @@ template<typename StringType>
StringType v8StringToWebCoreString(v8::Handle<v8::String> v8String, ExternalMode external)
{
{
- // A lot of WebCoreStringResourceBase::toWebCoreStringResourceBase is copied here by hand for performance reasons.
// This portion of this function is very hot in certain Dromeao benchmarks.
v8::String::Encoding encoding;
v8::String::ExternalStringResourceBase* resource = v8String->GetExternalStringResourceBase(&encoding);
@@ -151,7 +122,7 @@ StringType v8StringToWebCoreString(v8::Handle<v8::String> v8String, ExternalMode
return StringType("");
bool oneByte = v8String->ContainsOnlyOneByte();
- StringType result(oneByte ? StringTraits<StringType>::template fromV8String<true>(v8String, length) : StringTraits<StringType>::template fromV8String<false>(v8String, length));
+ StringType result(oneByte ? StringTraits<StringType>::template fromV8String<V8StringOneByteTrait>(v8String, length) : StringTraits<StringType>::template fromV8String<V8StringTwoBytesTrait>(v8String, length));
if (external != Externalize || !v8String->CanMakeExternal())
return result;
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8StringResource.h b/chromium/third_party/WebKit/Source/bindings/v8/V8StringResource.h
index b8b57944a47..69f849b31e9 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8StringResource.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8StringResource.h
@@ -39,8 +39,6 @@ class ExternalStringVisitor;
// to manage the life-cycle of the underlying buffer of the external string.
class WebCoreStringResourceBase {
public:
- static WebCoreStringResourceBase* toWebCoreStringResourceBase(v8::Handle<v8::String>);
-
explicit WebCoreStringResourceBase(const String& string)
: m_plainString(string)
{
@@ -89,8 +87,6 @@ public:
return m_atomicString;
}
- void visitStrings(ExternalStringVisitor*);
-
protected:
// A shallow copy of the string. Keeps the string buffer alive until the V8 engine garbage collects it.
String m_plainString;
@@ -111,7 +107,7 @@ private:
#endif
};
-class WebCoreStringResource16 : public WebCoreStringResourceBase, public v8::String::ExternalStringResource {
+class WebCoreStringResource16 FINAL : public WebCoreStringResourceBase, public v8::String::ExternalStringResource {
public:
explicit WebCoreStringResource16(const String& string)
: WebCoreStringResourceBase(string)
@@ -132,7 +128,7 @@ public:
}
};
-class WebCoreStringResource8 : public WebCoreStringResourceBase, public v8::String::ExternalAsciiStringResource {
+class WebCoreStringResource8 FINAL : public WebCoreStringResourceBase, public v8::String::ExternalAsciiStringResource {
public:
explicit WebCoreStringResource8(const String& string)
: WebCoreStringResourceBase(string)
@@ -173,23 +169,37 @@ enum V8StringResourceMode {
template <V8StringResourceMode Mode = DefaultMode>
class V8StringResource {
public:
+ V8StringResource()
+ : m_mode(Externalize)
+ {
+ }
+
V8StringResource(v8::Handle<v8::Value> object)
: m_v8Object(object)
, m_mode(Externalize)
- , m_string()
{
}
- bool prepare();
- operator String() const { return toString<String>(); }
- operator AtomicString() const { return toString<AtomicString>(); }
+ void operator=(v8::Handle<v8::Value> object)
+ {
+ m_v8Object = object;
+ }
-private:
- bool prepareBase()
+ void operator=(const String& string)
+ {
+ setString(string);
+ }
+
+ bool prepare()
{
if (m_v8Object.IsEmpty())
return true;
+ if (!isValid()) {
+ setString(String());
+ return true;
+ }
+
if (LIKELY(m_v8Object->IsString()))
return true;
@@ -208,6 +218,11 @@ private:
}
return true;
}
+ operator String() const { return toString<String>(); }
+ operator AtomicString() const { return toString<AtomicString>(); }
+
+private:
+ bool isValid() const;
void setString(const String& string)
{
@@ -229,27 +244,19 @@ private:
String m_string;
};
-template<> inline bool V8StringResource<DefaultMode>::prepare()
+template<> inline bool V8StringResource<DefaultMode>::isValid() const
{
- return prepareBase();
+ return true;
}
-template<> inline bool V8StringResource<WithNullCheck>::prepare()
+template<> inline bool V8StringResource<WithNullCheck>::isValid() const
{
- if (m_v8Object.IsEmpty() || m_v8Object->IsNull()) {
- setString(String());
- return true;
- }
- return prepareBase();
+ return !m_v8Object->IsNull();
}
-template<> inline bool V8StringResource<WithUndefinedOrNullCheck>::prepare()
+template<> inline bool V8StringResource<WithUndefinedOrNullCheck>::isValid() const
{
- if (m_v8Object.IsEmpty() || m_v8Object->IsNull() || m_v8Object->IsUndefined()) {
- setString(String());
- return true;
- }
- return prepareBase();
+ return !m_v8Object->IsNull() && !m_v8Object->IsUndefined();
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8ThrowException.cpp b/chromium/third_party/WebKit/Source/bindings/v8/V8ThrowException.cpp
index 0f1ffcc69d3..ae2be273cff 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8ThrowException.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8ThrowException.cpp
@@ -25,7 +25,7 @@
#include "config.h"
#include "bindings/v8/V8ThrowException.h"
-#include "V8DOMException.h"
+#include "bindings/core/v8/V8DOMException.h"
#include "bindings/v8/V8Binding.h"
#include "core/dom/DOMException.h"
#include "core/dom/ExceptionCode.h"
@@ -55,7 +55,7 @@ v8::Handle<v8::Value> V8ThrowException::createDOMException(int ec, const String&
if (ec == TypeError)
return V8ThrowException::createTypeError(sanitizedMessage, isolate);
- RefPtr<DOMException> domException = DOMException::create(ec, sanitizedMessage, unsanitizedMessage);
+ RefPtrWillBeRawPtr<DOMException> domException = DOMException::create(ec, sanitizedMessage, unsanitizedMessage);
v8::Handle<v8::Value> exception = toV8(domException, creationContext, isolate);
if (exception.IsEmpty())
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8ThrowException.h b/chromium/third_party/WebKit/Source/bindings/v8/V8ThrowException.h
index 7a4d20f0609..26addf08538 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8ThrowException.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8ThrowException.h
@@ -47,10 +47,6 @@ public:
}
static v8::Handle<v8::Value> createDOMException(int, const String& sanitizedMessage, const String& unsanitizedMessage, const v8::Handle<v8::Object>& creationContext, v8::Isolate*);
- static v8::Handle<v8::Value> throwDOMException(int ec, const v8::Handle<v8::Object>& creationContext, v8::Isolate* isolate)
- {
- return throwDOMException(ec, String(), creationContext, isolate);
- }
static v8::Handle<v8::Value> throwDOMException(int ec, const String& message, const v8::Handle<v8::Object>& creationContext, v8::Isolate* isolate)
{
return throwDOMException(ec, message, String(), creationContext, isolate);
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8Utilities.cpp b/chromium/third_party/WebKit/Source/bindings/v8/V8Utilities.cpp
deleted file mode 100644
index 6a70b502c32..00000000000
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8Utilities.cpp
+++ /dev/null
@@ -1,181 +0,0 @@
-/*
- * Copyright (C) 2008, 2009 Google Inc. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions are
- * met:
- *
- * * Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * * Redistributions in binary form must reproduce the above
- * copyright notice, this list of conditions and the following disclaimer
- * in the documentation and/or other materials provided with the
- * distribution.
- * * Neither the name of Google Inc. nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
- * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
- * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
- * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
- * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
- * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
- * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
- * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
- * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-#include "config.h"
-#include "bindings/v8/V8Utilities.h"
-
-#include "V8MessagePort.h"
-#include "bindings/v8/ExceptionMessages.h"
-#include "bindings/v8/ScriptState.h"
-#include "bindings/v8/V8AbstractEventListener.h"
-#include "bindings/v8/V8Binding.h"
-#include "bindings/v8/custom/V8ArrayBufferCustom.h"
-#include "core/dom/Document.h"
-#include "core/dom/ExceptionCode.h"
-#include "core/dom/ExecutionContext.h"
-#include "core/dom/MessagePort.h"
-#include "core/frame/Frame.h"
-#include "core/workers/WorkerGlobalScope.h"
-#include "wtf/ArrayBuffer.h"
-#include "wtf/text/WTFString.h"
-#include <v8.h>
-
-
-namespace WebCore {
-
-// Use an array to hold dependents. It works like a ref-counted scheme.
-// A value can be added more than once to the DOM object.
-void createHiddenDependency(v8::Handle<v8::Object> object, v8::Local<v8::Value> value, int cacheIndex, v8::Isolate* isolate)
-{
- v8::Local<v8::Value> cache = object->GetInternalField(cacheIndex);
- if (cache->IsNull() || cache->IsUndefined()) {
- cache = v8::Array::New(isolate);
- object->SetInternalField(cacheIndex, cache);
- }
-
- v8::Local<v8::Array> cacheArray = v8::Local<v8::Array>::Cast(cache);
- cacheArray->Set(v8::Integer::New(cacheArray->Length(), isolate), value);
-}
-
-bool extractTransferables(v8::Local<v8::Value> value, MessagePortArray& ports, ArrayBufferArray& arrayBuffers, bool& notASequence, v8::Isolate* isolate)
-{
- if (isUndefinedOrNull(value)) {
- ports.resize(0);
- arrayBuffers.resize(0);
- return true;
- }
-
- uint32_t length = 0;
- if (value->IsArray()) {
- v8::Local<v8::Array> array = v8::Local<v8::Array>::Cast(value);
- length = array->Length();
- } else if (toV8Sequence(value, length, isolate).IsEmpty()) {
- notASequence = true;
- return false;
- }
-
- v8::Local<v8::Object> transferrables = v8::Local<v8::Object>::Cast(value);
-
- // Validate the passed array of transferrables.
- for (unsigned int i = 0; i < length; ++i) {
- v8::Local<v8::Value> transferrable = transferrables->Get(i);
- // Validation of non-null objects, per HTML5 spec 10.3.3.
- if (isUndefinedOrNull(transferrable)) {
- setDOMException(DataCloneError, isolate);
- return false;
- }
- // Validation of Objects implementing an interface, per WebIDL spec 4.1.15.
- if (V8MessagePort::hasInstance(transferrable, isolate, worldType(isolate))) {
- RefPtr<MessagePort> port = V8MessagePort::toNative(v8::Handle<v8::Object>::Cast(transferrable));
- // Check for duplicate MessagePorts.
- if (ports.contains(port)) {
- setDOMException(DataCloneError, isolate);
- return false;
- }
- ports.append(port.release());
- } else if (V8ArrayBuffer::hasInstance(transferrable, isolate, worldType(isolate)))
- arrayBuffers.append(V8ArrayBuffer::toNative(v8::Handle<v8::Object>::Cast(transferrable)));
- else {
- setDOMException(DataCloneError, isolate);
- return false;
- }
- }
- return true;
-}
-
-bool getMessagePortArray(v8::Local<v8::Value> value, const String& propertyName, MessagePortArray& ports, v8::Isolate* isolate)
-{
- if (isUndefinedOrNull(value)) {
- ports.resize(0);
- return true;
- }
- if (!value->IsArray()) {
- throwTypeError(ExceptionMessages::notASequenceTypeProperty(propertyName), isolate);
- return false;
- }
- bool success = false;
- ports = toRefPtrNativeArray<MessagePort, V8MessagePort>(value, propertyName, isolate, &success);
- return success;
-}
-
-bool getMessagePortArray(v8::Local<v8::Value> value, int argumentIndex, MessagePortArray& ports, v8::Isolate* isolate)
-{
- if (isUndefinedOrNull(value)) {
- ports.resize(0);
- return true;
- }
- if (!value->IsArray()) {
- throwTypeError(ExceptionMessages::notAnArrayTypeArgumentOrValue(argumentIndex), isolate);
- return false;
- }
- bool success = false;
- ports = toRefPtrNativeArray<MessagePort, V8MessagePort>(value, argumentIndex, isolate, &success);
- return success;
-}
-
-void removeHiddenDependency(v8::Handle<v8::Object> object, v8::Local<v8::Value> value, int cacheIndex, v8::Isolate* isolate)
-{
- v8::Local<v8::Value> cache = object->GetInternalField(cacheIndex);
- if (!cache->IsArray())
- return;
- v8::Local<v8::Array> cacheArray = v8::Local<v8::Array>::Cast(cache);
- for (int i = cacheArray->Length() - 1; i >= 0; --i) {
- v8::Local<v8::Value> cached = cacheArray->Get(v8::Integer::New(i, isolate));
- if (cached->StrictEquals(value)) {
- cacheArray->Delete(i);
- return;
- }
- }
-}
-
-void transferHiddenDependency(v8::Handle<v8::Object> object, EventListener* oldValue, v8::Local<v8::Value> newValue, int cacheIndex, v8::Isolate* isolate)
-{
- if (oldValue) {
- V8AbstractEventListener* oldListener = V8AbstractEventListener::cast(oldValue);
- if (oldListener) {
- v8::Local<v8::Object> oldListenerObject = oldListener->getExistingListenerObject();
- if (!oldListenerObject.IsEmpty())
- removeHiddenDependency(object, oldListenerObject, cacheIndex, isolate);
- }
- }
- // Non-callable input is treated as null and ignored
- if (newValue->IsFunction())
- createHiddenDependency(object, newValue, cacheIndex, isolate);
-}
-
-ExecutionContext* getExecutionContext()
-{
- if (WorkerScriptController* controller = WorkerScriptController::controllerForContext())
- return &controller->workerGlobalScope();
-
- return currentDocument();
-}
-
-} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8Utilities.h b/chromium/third_party/WebKit/Source/bindings/v8/V8Utilities.h
deleted file mode 100644
index 4a0efd41b96..00000000000
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8Utilities.h
+++ /dev/null
@@ -1,72 +0,0 @@
-/*
- * Copyright (C) 2006, 2007, 2008, 2009 Google Inc. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions are
- * met:
- *
- * * Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * * Redistributions in binary form must reproduce the above
- * copyright notice, this list of conditions and the following disclaimer
- * in the documentation and/or other materials provided with the
- * distribution.
- * * Neither the name of Google Inc. nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
- * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
- * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
- * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
- * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
- * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
- * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
- * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
- * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-#ifndef V8Utilities_h
-#define V8Utilities_h
-
-#include "wtf/Forward.h"
-#include <v8.h>
-
-namespace WTF {
-class ArrayBuffer;
-}
-
-namespace WebCore {
-
- class EventListener;
- class MessagePort;
- class ExecutionContext;
-
- // Use an array to hold dependents. It works like a ref-counted scheme. A value can be added more than once to the DOM object.
- void createHiddenDependency(v8::Handle<v8::Object>, v8::Local<v8::Value>, int cacheIndex, v8::Isolate*);
- void removeHiddenDependency(v8::Handle<v8::Object>, v8::Local<v8::Value>, int cacheIndex, v8::Isolate*);
-
- // Combo create/remove, for EventHandler setters in generated bindings:
- void transferHiddenDependency(v8::Handle<v8::Object>, EventListener* oldValue, v8::Local<v8::Value> newValue, int cacheIndex, v8::Isolate*);
-
- ExecutionContext* getExecutionContext();
-
- typedef WTF::Vector<RefPtr<MessagePort>, 1> MessagePortArray;
- typedef WTF::Vector<RefPtr<ArrayBuffer>, 1> ArrayBufferArray;
-
- // Helper function which pulls the values out of a JS sequence and into a MessagePortArray.
- // Also validates the elements per sections 4.1.13 and 4.1.15 of the WebIDL spec and section 8.3.3
- // of the HTML5 spec and generates exceptions as appropriate. If the supplied argument's type isn't
- // a JS sequence, a type error is signalled by setting 'notASequence' to true -- the caller
- // then being responsible for generating a TypeError having a message that fits the context.
- // Returns true if the array was filled, or false if the passed value was not of an appropriate type.
- bool extractTransferables(v8::Local<v8::Value>, MessagePortArray&, ArrayBufferArray&, bool& notASequence, v8::Isolate*);
-
- bool getMessagePortArray(v8::Local<v8::Value>, const String& propertyName, MessagePortArray&, v8::Isolate*);
- bool getMessagePortArray(v8::Local<v8::Value>, int argumentIndex, MessagePortArray&, v8::Isolate*);
-
-} // namespace WebCore
-
-#endif // V8Utilities_h
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8ValueCache.cpp b/chromium/third_party/WebKit/Source/bindings/v8/V8ValueCache.cpp
index 0681d0c059b..6d64a56169c 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8ValueCache.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8ValueCache.cpp
@@ -27,11 +27,33 @@
#include "bindings/v8/V8ValueCache.h"
#include "bindings/v8/V8Binding.h"
-#include "bindings/v8/V8Utilities.h"
#include "wtf/text/StringHash.h"
namespace WebCore {
+StringCacheMapTraits::MapType* StringCacheMapTraits::MapFromWeakCallbackData(
+ const v8::WeakCallbackData<v8::String, WeakCallbackDataType>& data)
+{
+ return &(V8PerIsolateData::from(data.GetIsolate())->stringCache()->m_stringCache);
+}
+
+
+void StringCacheMapTraits::Dispose(
+ v8::Isolate* isolate, v8::UniquePersistent<v8::String> value, StringImpl* key)
+{
+ V8PerIsolateData::from(isolate)->stringCache()->InvalidateLastString();
+ key->deref();
+}
+
+
+StringCache::~StringCache()
+{
+ // The MapType::Dispose callback calls StringCache::InvalidateLastString,
+ // which will only work while the destructor has not yet finished. Thus,
+ // we need to clear the map before the destructor has completed.
+ m_stringCache.Clear();
+}
+
static v8::Local<v8::String> makeExternalString(const String& string, v8::Isolate* isolate)
{
if (string.is8Bit()) {
@@ -54,11 +76,11 @@ v8::Handle<v8::String> StringCache::v8ExternalStringSlow(StringImpl* stringImpl,
if (!stringImpl->length())
return v8::String::Empty(isolate);
- UnsafePersistent<v8::String> cachedV8String = m_stringCache.get(stringImpl);
- if (!cachedV8String.isEmpty()) {
+ StringCacheMapTraits::MapType::PersistentValueReference cachedV8String = m_stringCache.GetReference(stringImpl);
+ if (!cachedV8String.IsEmpty()) {
m_lastStringImpl = stringImpl;
m_lastV8String = cachedV8String;
- return cachedV8String.newLocal(isolate);
+ return m_lastV8String.NewLocal(isolate);
}
return createStringAndInsertIntoCache(stringImpl, isolate);
@@ -71,11 +93,11 @@ void StringCache::setReturnValueFromStringSlow(v8::ReturnValue<v8::Value> return
return;
}
- UnsafePersistent<v8::String> cachedV8String = m_stringCache.get(stringImpl);
- if (!cachedV8String.isEmpty()) {
+ StringCacheMapTraits::MapType::PersistentValueReference cachedV8String = m_stringCache.GetReference(stringImpl);
+ if (!cachedV8String.IsEmpty()) {
m_lastStringImpl = stringImpl;
m_lastV8String = cachedV8String;
- returnValue.Set(*cachedV8String.persistent());
+ m_lastV8String.SetReturnValue(returnValue);
return;
}
@@ -84,34 +106,27 @@ void StringCache::setReturnValueFromStringSlow(v8::ReturnValue<v8::Value> return
v8::Local<v8::String> StringCache::createStringAndInsertIntoCache(StringImpl* stringImpl, v8::Isolate* isolate)
{
- ASSERT(!m_stringCache.contains(stringImpl));
+ ASSERT(!m_stringCache.Contains(stringImpl));
ASSERT(stringImpl->length());
v8::Local<v8::String> newString = makeExternalString(String(stringImpl), isolate);
if (newString.IsEmpty())
return newString;
- v8::Persistent<v8::String> wrapper(isolate, newString);
+ v8::UniquePersistent<v8::String> wrapper(isolate, newString);
stringImpl->ref();
wrapper.MarkIndependent();
- wrapper.SetWeak(stringImpl, &setWeakCallback);
- m_lastV8String = UnsafePersistent<v8::String>(wrapper);
+ m_stringCache.Set(stringImpl, wrapper.Pass(), &m_lastV8String);
m_lastStringImpl = stringImpl;
- m_stringCache.set(stringImpl, m_lastV8String);
return newString;
}
-void StringCache::setWeakCallback(const v8::WeakCallbackData<v8::String, StringImpl>& data)
+void StringCache::InvalidateLastString()
{
- StringCache* stringCache = V8PerIsolateData::from(data.GetIsolate())->stringCache();
- stringCache->m_lastStringImpl = 0;
- stringCache->m_lastV8String.clear();
- ASSERT(stringCache->m_stringCache.contains(data.GetParameter()));
- stringCache->m_stringCache.get(data.GetParameter()).dispose();
- stringCache->m_stringCache.remove(data.GetParameter());
- data.GetParameter()->deref();
+ m_lastStringImpl = nullptr;
+ m_lastV8String.Reset();
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8ValueCache.h b/chromium/third_party/WebKit/Source/bindings/v8/V8ValueCache.h
index 44ee8db6e80..8110cd38d27 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8ValueCache.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8ValueCache.h
@@ -26,7 +26,7 @@
#ifndef V8ValueCache_h
#define V8ValueCache_h
-#include "bindings/v8/UnsafePersistent.h"
+#include "bindings/v8/V8PersistentValueMap.h"
#include <v8.h>
#include "wtf/HashMap.h"
#include "wtf/RefPtr.h"
@@ -35,15 +35,39 @@
namespace WebCore {
+class StringCacheMapTraits : public V8PersistentValueMapTraits<StringImpl*, v8::String, true> {
+public:
+ // Weak traits:
+ typedef StringImpl WeakCallbackDataType;
+ typedef v8::PersistentValueMap<StringImpl*, v8::String, StringCacheMapTraits> MapType;
+
+ static WeakCallbackDataType* WeakCallbackParameter(
+ MapType* map, StringImpl* key, v8::Local<v8::String>& value) { return key; }
+ static void DisposeCallbackData(WeakCallbackDataType* callbackData) { }
+
+ static MapType* MapFromWeakCallbackData(
+ const v8::WeakCallbackData<v8::String, WeakCallbackDataType>&);
+
+ static StringImpl* KeyFromWeakCallbackData(
+ const v8::WeakCallbackData<v8::String, WeakCallbackDataType>& data)
+ {
+ return data.GetParameter();
+ }
+
+ static void Dispose(v8::Isolate*, v8::UniquePersistent<v8::String> value, StringImpl* key);
+};
+
+
class StringCache {
public:
- StringCache() { }
+ StringCache(v8::Isolate* isolate) : m_stringCache(isolate) { }
+ ~StringCache();
v8::Handle<v8::String> v8ExternalString(StringImpl* stringImpl, v8::Isolate* isolate)
{
ASSERT(stringImpl);
if (m_lastStringImpl.get() == stringImpl)
- return m_lastV8String.newLocal(isolate);
+ return m_lastV8String.NewLocal(isolate);
return v8ExternalStringSlow(stringImpl, isolate);
}
@@ -51,20 +75,22 @@ public:
{
ASSERT(stringImpl);
if (m_lastStringImpl.get() == stringImpl)
- returnValue.Set(*m_lastV8String.persistent());
+ m_lastV8String.SetReturnValue(returnValue);
else
setReturnValueFromStringSlow(returnValue, stringImpl);
}
-private:
- static void setWeakCallback(const v8::WeakCallbackData<v8::String, StringImpl>&);
+ friend class StringCacheMapTraits;
+private:
v8::Handle<v8::String> v8ExternalStringSlow(StringImpl*, v8::Isolate*);
void setReturnValueFromStringSlow(v8::ReturnValue<v8::Value>, StringImpl*);
v8::Local<v8::String> createStringAndInsertIntoCache(StringImpl*, v8::Isolate*);
+ void InvalidateLastString();
+
+ StringCacheMapTraits::MapType m_stringCache;
+ StringCacheMapTraits::MapType::PersistentValueReference m_lastV8String;
- HashMap<StringImpl*, UnsafePersistent<v8::String> > m_stringCache;
- UnsafePersistent<v8::String> m_lastV8String;
// Note: RefPtr is a must as we cache by StringImpl* equality, not identity
// hence lastStringImpl might be not a key of the cache (in sense of identity)
// and hence it's not refed on addition.
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8WindowShell.cpp b/chromium/third_party/WebKit/Source/bindings/v8/V8WindowShell.cpp
index 3474312da86..8b9e8b2dbfb 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8WindowShell.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8WindowShell.cpp
@@ -31,28 +31,30 @@
#include "config.h"
#include "bindings/v8/V8WindowShell.h"
-#include "RuntimeEnabledFeatures.h"
-#include "V8Document.h"
-#include "V8HTMLCollection.h"
-#include "V8HTMLDocument.h"
-#include "V8Window.h"
+#include "bindings/core/v8/V8Document.h"
+#include "bindings/core/v8/V8HTMLCollection.h"
+#include "bindings/core/v8/V8HTMLDocument.h"
+#include "bindings/core/v8/V8Window.h"
#include "bindings/v8/DOMWrapperWorld.h"
#include "bindings/v8/ScriptController.h"
#include "bindings/v8/V8Binding.h"
+#include "bindings/v8/V8DOMActivityLogger.h"
#include "bindings/v8/V8GCForContextDispose.h"
-#include "bindings/v8/V8HiddenPropertyName.h"
+#include "bindings/v8/V8HiddenValue.h"
#include "bindings/v8/V8Initializer.h"
#include "bindings/v8/V8ObjectConstructor.h"
-#include "bindings/v8/V8PerContextData.h"
+#include "core/dom/ScriptForbiddenScope.h"
+#include "core/frame/LocalFrame.h"
+#include "core/frame/csp/ContentSecurityPolicy.h"
#include "core/html/HTMLCollection.h"
#include "core/html/HTMLIFrameElement.h"
#include "core/inspector/InspectorInstrumentation.h"
#include "core/loader/DocumentLoader.h"
#include "core/loader/FrameLoader.h"
#include "core/loader/FrameLoaderClient.h"
-#include "core/frame/ContentSecurityPolicy.h"
-#include "core/frame/Frame.h"
+#include "platform/RuntimeEnabledFeatures.h"
#include "platform/TraceEvent.h"
+#include "platform/heap/Handle.h"
#include "platform/weborigin/SecurityOrigin.h"
#include "public/platform/Platform.h"
#include "wtf/Assertions.h"
@@ -77,33 +79,31 @@ static void setInjectedScriptContextDebugId(v8::Handle<v8::Context> targetContex
V8PerContextDebugData::setContextDebugData(targetContext, "injected", debugId);
}
-PassOwnPtr<V8WindowShell> V8WindowShell::create(Frame* frame, PassRefPtr<DOMWrapperWorld> world, v8::Isolate* isolate)
+PassOwnPtr<V8WindowShell> V8WindowShell::create(LocalFrame* frame, DOMWrapperWorld& world, v8::Isolate* isolate)
{
- return adoptPtr(new V8WindowShell(frame, world, isolate));
+ return adoptPtr(new V8WindowShell(frame, &world, isolate));
}
-V8WindowShell::V8WindowShell(Frame* frame, PassRefPtr<DOMWrapperWorld> world, v8::Isolate* isolate)
+V8WindowShell::V8WindowShell(LocalFrame* frame, PassRefPtr<DOMWrapperWorld> world, v8::Isolate* isolate)
: m_frame(frame)
- , m_world(world)
, m_isolate(isolate)
+ , m_world(world)
{
}
void V8WindowShell::disposeContext(GlobalDetachmentBehavior behavior)
{
- m_perContextData.clear();
-
- if (!m_contextHolder)
+ if (!isContextInitialized())
return;
v8::HandleScope handleScope(m_isolate);
- v8::Handle<v8::Context> context = m_contextHolder->context();
+ v8::Handle<v8::Context> context = m_scriptState->context();
m_frame->loader().client()->willReleaseScriptContext(context, m_world->worldId());
if (behavior == DetachGlobal)
context->DetachGlobal();
- m_contextHolder.clear();
+ m_scriptState->disposePerContextData();
// It's likely that disposing the context has created a lot of
// garbage. Notify V8 about this so it'll have a chance of cleaning
@@ -111,12 +111,9 @@ void V8WindowShell::disposeContext(GlobalDetachmentBehavior behavior)
V8GCForContextDispose::instanceTemplate().notifyContextDisposed(m_frame->isMainFrame());
}
-void V8WindowShell::clearForClose(bool destroyGlobal)
+void V8WindowShell::clearForClose()
{
- if (destroyGlobal)
- m_global.clear();
-
- if (!m_contextHolder)
+ if (!isContextInitialized())
return;
m_document.clear();
@@ -125,21 +122,19 @@ void V8WindowShell::clearForClose(bool destroyGlobal)
void V8WindowShell::clearForNavigation()
{
- if (!m_contextHolder)
+ if (!isContextInitialized())
return;
- v8::HandleScope handleScope(m_isolate);
- m_document.clear();
+ ScriptState::Scope scope(m_scriptState.get());
- v8::Handle<v8::Context> context = m_contextHolder->context();
- v8::Context::Scope contextScope(context);
+ m_document.clear();
// Clear the document wrapper cache before turning on access checks on
- // the old DOMWindow wrapper. This way, access to the document wrapper
- // will be protected by the security checks on the DOMWindow wrapper.
+ // the old LocalDOMWindow wrapper. This way, access to the document wrapper
+ // will be protected by the security checks on the LocalDOMWindow wrapper.
clearDocumentProperty();
- v8::Handle<v8::Object> windowWrapper = m_global.newLocal(m_isolate)->FindInstanceInPrototypeChain(V8Window::domTemplate(m_isolate, worldTypeInMainThread(m_isolate)));
+ v8::Handle<v8::Object> windowWrapper = V8Window::findInstanceInPrototypeChain(m_global.newLocal(m_isolate), m_isolate);
ASSERT(!windowWrapper.IsEmpty());
windowWrapper->TurnOnAccessCheck();
disposeContext(DetachGlobal);
@@ -147,16 +142,16 @@ void V8WindowShell::clearForNavigation()
// Create a new environment and setup the global object.
//
-// The global object corresponds to a DOMWindow instance. However, to
-// allow properties of the JS DOMWindow instance to be shadowed, we
-// use a shadow object as the global object and use the JS DOMWindow
-// instance as the prototype for that shadow object. The JS DOMWindow
+// The global object corresponds to a LocalDOMWindow instance. However, to
+// allow properties of the JS LocalDOMWindow instance to be shadowed, we
+// use a shadow object as the global object and use the JS LocalDOMWindow
+// instance as the prototype for that shadow object. The JS LocalDOMWindow
// instance is undetectable from JavaScript code because the __proto__
// accessors skip that object.
//
-// The shadow object and the DOMWindow instance are seen as one object
+// The shadow object and the LocalDOMWindow instance are seen as one object
// from JavaScript. The JavaScript object that corresponds to a
-// DOMWindow instance is the shadow object. When mapping a DOMWindow
+// LocalDOMWindow instance is the shadow object. When mapping a LocalDOMWindow
// instance to a V8 object, we return the shadow object.
//
// To implement split-window, see
@@ -169,7 +164,7 @@ void V8WindowShell::clearForNavigation()
// global object of the context. A variable declared in the global
// scope is a property of the inner window.
//
-// The outer window sticks to a Frame, it is exposed to JavaScript
+// The outer window sticks to a LocalFrame, it is exposed to JavaScript
// via window.window, window.self, window.parent, etc. The outer window
// has a security token which is the domain. The outer window cannot
// have its own properties. window.foo = 'x' is delegated to the
@@ -182,27 +177,31 @@ void V8WindowShell::clearForNavigation()
// it won't be able to reach the outer window via its global object.
bool V8WindowShell::initializeIfNeeded()
{
- if (m_contextHolder)
+ if (isContextInitialized())
return true;
- TRACE_EVENT0("v8", "V8WindowShell::initializeIfNeeded");
-
- v8::HandleScope handleScope(m_isolate);
-
- createContext();
- if (!m_contextHolder)
- return false;
+ DOMWrapperWorld::setWorldOfInitializingWindow(m_world.get());
+ bool result = initialize();
+ DOMWrapperWorld::setWorldOfInitializingWindow(0);
+ return result;
+}
- v8::Handle<v8::Context> context = m_contextHolder->context();
+bool V8WindowShell::initialize()
+{
+ TRACE_EVENT0("v8", "V8WindowShell::initialize");
+ TRACE_EVENT_SCOPED_SAMPLING_STATE("Blink", "InitializeWindow");
- V8PerContextDataHolder::install(context);
+ ScriptForbiddenScope::AllowUserAgentScript allowScript;
- m_world->setIsolatedWorldField(context);
+ v8::HandleScope handleScope(m_isolate);
- bool isMainWorld = m_world->isMainWorld();
+ createContext();
- v8::Context::Scope contextScope(context);
+ if (!isContextInitialized())
+ return false;
+ ScriptState::Scope scope(m_scriptState.get());
+ v8::Handle<v8::Context> context = m_scriptState->context();
if (m_global.isEmpty()) {
m_global.set(m_isolate, context->Global());
if (m_global.isEmpty()) {
@@ -211,44 +210,32 @@ bool V8WindowShell::initializeIfNeeded()
}
}
- if (!isMainWorld) {
- V8WindowShell* mainWindow = m_frame->script().existingWindowShell(mainThreadNormalWorld());
+ if (!m_world->isMainWorld()) {
+ V8WindowShell* mainWindow = m_frame->script().existingWindowShell(DOMWrapperWorld::mainWorld());
if (mainWindow && !mainWindow->context().IsEmpty())
setInjectedScriptContextDebugId(context, m_frame->script().contextDebugId(mainWindow->context()));
}
- m_perContextData = V8PerContextData::create(context);
- if (!m_perContextData->init()) {
- disposeContext(DoNotDetachGlobal);
- return false;
- }
- m_perContextData->setActivityLogger(DOMWrapperWorld::activityLogger(m_world->worldId()));
if (!installDOMWindow()) {
disposeContext(DoNotDetachGlobal);
return false;
}
- if (isMainWorld) {
+ if (m_world->isMainWorld()) {
+ // ActivityLogger for main world is updated within updateDocument().
updateDocument();
- setSecurityToken();
if (m_frame->document()) {
+ setSecurityToken(m_frame->document()->securityOrigin());
ContentSecurityPolicy* csp = m_frame->document()->contentSecurityPolicy();
context->AllowCodeGenerationFromStrings(csp->allowEval(0, ContentSecurityPolicy::SuppressReport));
context->SetErrorMessageForCodeGenerationFromStrings(v8String(m_isolate, csp->evalDisabledErrorMessage()));
}
} else {
- // Using the default security token means that the canAccess is always
- // called, which is slow.
- // FIXME: Use tokens where possible. This will mean keeping track of all
- // created contexts so that they can all be updated when the
- // document domain
- // changes.
- context->UseDefaultSecurityToken();
-
+ updateActivityLogger();
SecurityOrigin* origin = m_world->isolatedWorldSecurityOrigin();
+ setSecurityToken(origin);
if (origin && InspectorInstrumentation::hasFrontends()) {
- ScriptState* scriptState = ScriptState::forContext(v8::Local<v8::Context>::New(m_isolate, context));
- InspectorInstrumentation::didCreateIsolatedContext(m_frame, scriptState, origin);
+ InspectorInstrumentation::didCreateIsolatedContext(m_frame, m_scriptState.get(), origin);
}
}
m_frame->loader().client()->didCreateScriptContext(context, m_world->extensionGroup(), m_world->worldId());
@@ -257,14 +244,14 @@ bool V8WindowShell::initializeIfNeeded()
void V8WindowShell::createContext()
{
- // The activeDocumentLoader pointer could be 0 during frame shutdown.
+ // The documentLoader pointer could be 0 during frame shutdown.
// FIXME: Can we remove this check?
- if (!m_frame->loader().activeDocumentLoader())
+ if (!m_frame->loader().documentLoader())
return;
// Create a new environment using an empty template for the shadow
// object. Reuse the global object if one has been created earlier.
- v8::Handle<v8::ObjectTemplate> globalTemplate = V8Window::GetShadowObjectTemplate(m_isolate, m_world->isMainWorld() ? MainWorld : IsolatedWorld);
+ v8::Handle<v8::ObjectTemplate> globalTemplate = V8Window::getShadowObjectTemplate(m_isolate);
if (globalTemplate.IsEmpty())
return;
@@ -284,12 +271,10 @@ void V8WindowShell::createContext()
}
v8::ExtensionConfiguration extensionConfiguration(index, extensionNames.get());
- v8::HandleScope handleScope(m_isolate);
v8::Handle<v8::Context> context = v8::Context::New(m_isolate, &extensionConfiguration, globalTemplate, m_global.newLocal(m_isolate));
- if (!context.IsEmpty()) {
- m_contextHolder = adoptPtr(new gin::ContextHolder(m_isolate));
- m_contextHolder->SetContext(context);
- }
+ if (context.IsEmpty())
+ return;
+ m_scriptState = ScriptState::create(context, m_world);
double contextCreationDurationInMilliseconds = (currentTime() - contextCreationStartInSeconds) * 1000;
const char* histogramName = "WebCore.V8WindowShell.createContext.MainWorld";
@@ -298,36 +283,46 @@ void V8WindowShell::createContext()
blink::Platform::current()->histogramCustomCounts(histogramName, contextCreationDurationInMilliseconds, 0, 10000, 50);
}
+static v8::Handle<v8::Object> toInnerGlobalObject(v8::Handle<v8::Context> context)
+{
+ return v8::Handle<v8::Object>::Cast(context->Global()->GetPrototype());
+}
+
bool V8WindowShell::installDOMWindow()
{
- DOMWrapperWorld::setInitializingWindow(true);
- DOMWindow* window = m_frame->domWindow();
- v8::Local<v8::Object> windowWrapper = V8ObjectConstructor::newInstance(V8PerContextData::from(m_contextHolder->context())->constructorForType(&V8Window::wrapperTypeInfo));
+ LocalDOMWindow* window = m_frame->domWindow();
+ v8::Local<v8::Object> windowWrapper = V8ObjectConstructor::newInstance(m_isolate, m_scriptState->perContextData()->constructorForType(&V8Window::wrapperTypeInfo));
if (windowWrapper.IsEmpty())
return false;
V8Window::installPerContextEnabledProperties(windowWrapper, window, m_isolate);
- V8DOMWrapper::setNativeInfo(v8::Handle<v8::Object>::Cast(windowWrapper->GetPrototype()), &V8Window::wrapperTypeInfo, window);
+ V8DOMWrapper::setNativeInfoForHiddenWrapper(v8::Handle<v8::Object>::Cast(windowWrapper->GetPrototype()), &V8Window::wrapperTypeInfo, window);
// Install the windowWrapper as the prototype of the innerGlobalObject.
// The full structure of the global object is as follows:
//
// outerGlobalObject (Empty object, remains after navigation)
// -- has prototype --> innerGlobalObject (Holds global variables, changes during navigation)
- // -- has prototype --> DOMWindow instance
+ // -- has prototype --> LocalDOMWindow instance
// -- has prototype --> Window.prototype
// -- has prototype --> Object.prototype
//
// Note: Much of this prototype structure is hidden from web content. The
- // outer, inner, and DOMWindow instance all appear to be the same
+ // outer, inner, and LocalDOMWindow instance all appear to be the same
// JavaScript object.
//
- v8::Handle<v8::Object> innerGlobalObject = toInnerGlobalObject(m_contextHolder->context());
- V8DOMWrapper::setNativeInfo(innerGlobalObject, &V8Window::wrapperTypeInfo, window);
+ // Note: With Oilpan, the LocalDOMWindow object is garbage collected.
+ // Persistent references to this inner global object view of the LocalDOMWindow
+ // aren't kept, as that would prevent the global object from ever being released.
+ // It is safe not to do so, as the wrapper for the LocalDOMWindow being installed here
+ // already keeps a persistent reference, and it along with the inner global object
+ // views of the LocalDOMWindow will die together once that wrapper clears the persistent
+ // reference.
+ v8::Handle<v8::Object> innerGlobalObject = toInnerGlobalObject(m_scriptState->context());
+ V8DOMWrapper::setNativeInfoForHiddenWrapper(innerGlobalObject, &V8Window::wrapperTypeInfo, window);
innerGlobalObject->SetPrototype(windowWrapper);
- V8DOMWrapper::associateObjectWithWrapper<V8Window>(PassRefPtr<DOMWindow>(window), &V8Window::wrapperTypeInfo, windowWrapper, m_isolate, WrapperConfiguration::Dependent);
- DOMWrapperWorld::setInitializingWindow(false);
+ V8DOMWrapper::associateObjectWithWrapper<V8Window>(PassRefPtrWillBeRawPtr<LocalDOMWindow>(window), &V8Window::wrapperTypeInfo, windowWrapper, m_isolate, WrapperConfiguration::Dependent);
return true;
}
@@ -342,18 +337,16 @@ void V8WindowShell::updateDocumentProperty()
if (!m_world->isMainWorld())
return;
- v8::HandleScope handleScope(m_isolate);
- v8::Handle<v8::Context> context = m_contextHolder->context();
- v8::Context::Scope contextScope(context);
-
- v8::Handle<v8::Value> documentWrapper = toV8(m_frame->document(), v8::Handle<v8::Object>(), context->GetIsolate());
+ ScriptState::Scope scope(m_scriptState.get());
+ v8::Handle<v8::Context> context = m_scriptState->context();
+ v8::Handle<v8::Value> documentWrapper = toV8(m_frame->document(), context->Global(), context->GetIsolate());
ASSERT(documentWrapper == m_document.newLocal(m_isolate) || m_document.isEmpty());
if (m_document.isEmpty())
updateDocumentWrapper(v8::Handle<v8::Object>::Cast(documentWrapper));
checkDocumentWrapper(m_document.newLocal(m_isolate), m_frame->document());
// If instantiation of the document wrapper fails, clear the cache
- // and let the DOMWindow accessor handle access to the document.
+ // and let the LocalDOMWindow accessor handle access to the document.
if (documentWrapper.IsEmpty()) {
clearDocumentProperty();
return;
@@ -362,38 +355,40 @@ void V8WindowShell::updateDocumentProperty()
context->Global()->ForceSet(v8AtomicString(m_isolate, "document"), documentWrapper, static_cast<v8::PropertyAttribute>(v8::ReadOnly | v8::DontDelete));
// We also stash a reference to the document on the inner global object so that
- // DOMWindow objects we obtain from JavaScript references are guaranteed to have
+ // LocalDOMWindow objects we obtain from JavaScript references are guaranteed to have
// live Document objects.
- toInnerGlobalObject(context)->SetHiddenValue(V8HiddenPropertyName::document(m_isolate), documentWrapper);
+ V8HiddenValue::setHiddenValue(m_isolate, toInnerGlobalObject(context), V8HiddenValue::document(m_isolate), documentWrapper);
}
void V8WindowShell::clearDocumentProperty()
{
- ASSERT(m_contextHolder);
+ ASSERT(isContextInitialized());
if (!m_world->isMainWorld())
return;
v8::HandleScope handleScope(m_isolate);
- m_contextHolder->context()->Global()->ForceDelete(v8AtomicString(m_isolate, "document"));
+ m_scriptState->context()->Global()->ForceDelete(v8AtomicString(m_isolate, "document"));
}
-void V8WindowShell::setSecurityToken()
+void V8WindowShell::updateActivityLogger()
{
- ASSERT(m_world->isMainWorld());
-
- Document* document = m_frame->document();
+ m_scriptState->perContextData()->setActivityLogger(V8DOMActivityLogger::activityLogger(
+ m_world->worldId(), m_frame->document() ? m_frame->document()->baseURI() : KURL()));
+}
- // Ask the document's SecurityOrigin to generate a security token.
+void V8WindowShell::setSecurityToken(SecurityOrigin* origin)
+{
// If two tokens are equal, then the SecurityOrigins canAccess each other.
// If two tokens are not equal, then we have to call canAccess.
// Note: we can't use the HTTPOrigin if it was set from the DOM.
- SecurityOrigin* origin = document->securityOrigin();
String token;
// We stick with an empty token if document.domain was modified or if we
// are in the initial empty document, so that we can do a full canAccess
// check in those cases.
- if (!origin->domainWasSetInDOM()
- && !m_frame->loader().stateMachine()->isDisplayingInitialEmptyDocument())
- token = document->securityOrigin()->toString();
+ bool delaySet = m_world->isMainWorld()
+ && (origin->domainWasSetInDOM()
+ || m_frame->loader().stateMachine()->isDisplayingInitialEmptyDocument());
+ if (origin && !delaySet)
+ token = origin->toString();
// An empty or "null" token means we always have to call
// canAccess. The toString method on securityOrigins returns the
@@ -402,7 +397,7 @@ void V8WindowShell::setSecurityToken()
// case, we use the global object as the security token to avoid
// calling canAccess when a script accesses its own objects.
v8::HandleScope handleScope(m_isolate);
- v8::Handle<v8::Context> context = m_contextHolder->context();
+ v8::Handle<v8::Context> context = m_scriptState->context();
if (token.isEmpty() || token == "null") {
context->UseDefaultSecurityToken();
return;
@@ -417,12 +412,13 @@ void V8WindowShell::setSecurityToken()
void V8WindowShell::updateDocument()
{
ASSERT(m_world->isMainWorld());
- if (m_global.isEmpty())
+ if (!isGlobalInitialized())
return;
- if (!m_contextHolder)
+ if (!isContextInitialized())
return;
+ updateActivityLogger();
updateDocumentProperty();
- updateSecurityOrigin();
+ updateSecurityOrigin(m_frame->document()->securityOrigin());
}
static v8::Handle<v8::Value> getNamedProperty(HTMLDocument* htmlDocument, const AtomicString& key, v8::Handle<v8::Object> creationContext, v8::Isolate* isolate)
@@ -430,16 +426,17 @@ static v8::Handle<v8::Value> getNamedProperty(HTMLDocument* htmlDocument, const
if (!htmlDocument->hasNamedItem(key) && !htmlDocument->hasExtraNamedItem(key))
return v8Undefined();
- RefPtr<HTMLCollection> items = htmlDocument->documentNamedItems(key);
+ RefPtrWillBeRawPtr<HTMLCollection> items = htmlDocument->documentNamedItems(key);
if (items->isEmpty())
return v8Undefined();
if (items->hasExactlyOneItem()) {
- Node* node = items->item(0);
+ Element* element = items->item(0);
+ ASSERT(element);
Frame* frame = 0;
- if (node->hasTagName(HTMLNames::iframeTag) && (frame = toHTMLIFrameElement(node)->contentFrame()))
+ if (isHTMLIFrameElement(*element) && (frame = toHTMLIFrameElement(*element).contentFrame()))
return toV8(frame->domWindow(), creationContext, isolate);
- return toV8(node, creationContext, isolate);
+ return toV8(element, creationContext, isolate);
}
return toV8(items.release(), creationContext, isolate);
}
@@ -466,12 +463,10 @@ void V8WindowShell::namedItemAdded(HTMLDocument* document, const AtomicString& n
{
ASSERT(m_world->isMainWorld());
- if (!m_contextHolder)
+ if (!isContextInitialized())
return;
- v8::HandleScope handleScope(m_isolate);
- v8::Context::Scope contextScope(m_contextHolder->context());
-
+ ScriptState::Scope scope(m_scriptState.get());
ASSERT(!m_document.isEmpty());
v8::Handle<v8::Object> documentHandle = m_document.newLocal(m_isolate);
checkDocumentWrapper(documentHandle, document);
@@ -482,28 +477,25 @@ void V8WindowShell::namedItemRemoved(HTMLDocument* document, const AtomicString&
{
ASSERT(m_world->isMainWorld());
- if (!m_contextHolder)
+ if (!isContextInitialized())
return;
if (document->hasNamedItem(name) || document->hasExtraNamedItem(name))
return;
- v8::HandleScope handleScope(m_isolate);
- v8::Context::Scope contextScope(m_contextHolder->context());
-
+ ScriptState::Scope scope(m_scriptState.get());
ASSERT(!m_document.isEmpty());
v8::Handle<v8::Object> documentHandle = m_document.newLocal(m_isolate);
checkDocumentWrapper(documentHandle, document);
documentHandle->Delete(v8String(m_isolate, name));
}
-void V8WindowShell::updateSecurityOrigin()
+void V8WindowShell::updateSecurityOrigin(SecurityOrigin* origin)
{
ASSERT(m_world->isMainWorld());
- if (!m_contextHolder)
+ if (!isContextInitialized())
return;
- v8::HandleScope handleScope(m_isolate);
- setSecurityToken();
+ setSecurityToken(origin);
}
} // WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8WindowShell.h b/chromium/third_party/WebKit/Source/bindings/v8/V8WindowShell.h
index b1c65ab9f42..548caa388fe 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8WindowShell.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8WindowShell.h
@@ -33,9 +33,8 @@
#include "bindings/v8/DOMWrapperWorld.h"
#include "bindings/v8/ScopedPersistent.h"
-#include "bindings/v8/V8PerContextData.h"
+#include "bindings/v8/ScriptState.h"
#include "bindings/v8/WrapperTypeInfo.h"
-#include "gin/public/context_holder.h"
#include "platform/weborigin/SecurityOrigin.h"
#include "wtf/Forward.h"
#include "wtf/HashMap.h"
@@ -47,17 +46,19 @@
namespace WebCore {
-class DOMWindow;
-class Frame;
+class LocalDOMWindow;
+class LocalFrame;
class HTMLDocument;
+class SecurityOrigin;
-// V8WindowShell represents all the per-global object state for a Frame that
+// V8WindowShell represents all the per-global object state for a LocalFrame that
// persist between navigations.
class V8WindowShell {
public:
- static PassOwnPtr<V8WindowShell> create(Frame*, PassRefPtr<DOMWrapperWorld>, v8::Isolate*);
+ static PassOwnPtr<V8WindowShell> create(LocalFrame*, DOMWrapperWorld&, v8::Isolate*);
- v8::Local<v8::Context> context() const { return m_contextHolder ? m_contextHolder->context() : v8::Local<v8::Context>(); }
+ v8::Local<v8::Context> context() const { return m_scriptState ? m_scriptState->context() : v8::Local<v8::Context>(); }
+ ScriptState* scriptState() const { return m_scriptState.get(); }
// Update document object of the frame.
void updateDocument();
@@ -67,21 +68,22 @@ public:
// Update the security origin of a document
// (e.g., after setting docoument.domain).
- void updateSecurityOrigin();
+ void updateSecurityOrigin(SecurityOrigin*);
- bool isContextInitialized() { return m_contextHolder; }
+ bool isContextInitialized() { return m_scriptState && !!m_scriptState->perContextData(); }
bool isGlobalInitialized() { return !m_global.isEmpty(); }
bool initializeIfNeeded();
void updateDocumentWrapper(v8::Handle<v8::Object> wrapper);
void clearForNavigation();
- void clearForClose(bool destroyGlobal);
+ void clearForClose();
- DOMWrapperWorld* world() { return m_world.get(); }
+ DOMWrapperWorld& world() { return *m_world; }
private:
- V8WindowShell(Frame*, PassRefPtr<DOMWrapperWorld>, v8::Isolate*);
+ V8WindowShell(LocalFrame*, PassRefPtr<DOMWrapperWorld>, v8::Isolate*);
+ bool initialize();
enum GlobalDetachmentBehavior {
DoNotDetachGlobal,
@@ -89,7 +91,7 @@ private:
};
void disposeContext(GlobalDetachmentBehavior);
- void setSecurityToken();
+ void setSecurityToken(SecurityOrigin*);
// The JavaScript wrapper for the document object is cached on the global
// object for fast access. UpdateDocumentProperty sets the wrapper
@@ -98,18 +100,18 @@ private:
void updateDocumentProperty();
void clearDocumentProperty();
+ // Updates Activity Logger for the current context.
+ void updateActivityLogger();
+
void createContext();
bool installDOMWindow();
static V8WindowShell* enteredIsolatedWorldContext();
- Frame* m_frame;
- RefPtr<DOMWrapperWorld> m_world;
+ LocalFrame* m_frame;
v8::Isolate* m_isolate;
-
- OwnPtr<V8PerContextData> m_perContextData;
-
- OwnPtr<gin::ContextHolder> m_contextHolder;
+ RefPtr<ScriptState> m_scriptState;
+ RefPtr<DOMWrapperWorld> m_world;
ScopedPersistent<v8::Object> m_global;
ScopedPersistent<v8::Object> m_document;
};
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8WorkerGlobalScopeEventListener.cpp b/chromium/third_party/WebKit/Source/bindings/v8/V8WorkerGlobalScopeEventListener.cpp
index da79d52d1c8..c66b8a24dc9 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8WorkerGlobalScopeEventListener.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8WorkerGlobalScopeEventListener.cpp
@@ -32,94 +32,84 @@
#include "bindings/v8/V8WorkerGlobalScopeEventListener.h"
-#include "V8Event.h"
-#include "V8EventTarget.h"
+#include "bindings/core/v8/V8Event.h"
+#include "bindings/core/v8/V8EventTarget.h"
#include "bindings/v8/V8Binding.h"
#include "bindings/v8/V8DOMWrapper.h"
#include "bindings/v8/V8GCController.h"
#include "bindings/v8/V8ScriptRunner.h"
#include "bindings/v8/WorkerScriptController.h"
#include "core/inspector/InspectorInstrumentation.h"
+#include "core/inspector/InspectorTraceEvents.h"
#include "core/workers/WorkerGlobalScope.h"
namespace WebCore {
-V8WorkerGlobalScopeEventListener::V8WorkerGlobalScopeEventListener(v8::Local<v8::Object> listener, bool isInline, v8::Isolate* isolate)
- : V8EventListener(listener, isInline, isolate)
+V8WorkerGlobalScopeEventListener::V8WorkerGlobalScopeEventListener(v8::Local<v8::Object> listener, bool isInline, ScriptState* scriptState)
+ : V8EventListener(listener, isInline, scriptState)
{
}
-void V8WorkerGlobalScopeEventListener::handleEvent(ExecutionContext* context, Event* event)
+void V8WorkerGlobalScopeEventListener::handleEvent(ExecutionContext*, Event* event)
{
- if (!context)
- return;
-
// The callback function on XMLHttpRequest can clear the event listener and destroys 'this' object. Keep a local reference to it.
// See issue 889829.
RefPtr<V8AbstractEventListener> protect(this);
- v8::Isolate* isolate = toIsolate(context);
- v8::HandleScope handleScope(isolate);
-
- WorkerScriptController* script = toWorkerGlobalScope(context)->script();
+ WorkerScriptController* script = toWorkerGlobalScope(scriptState()->executionContext())->script();
if (!script)
return;
- v8::Handle<v8::Context> v8Context = script->context();
- if (v8Context.IsEmpty())
+ if (scriptState()->contextIsEmpty())
return;
-
- // Enter the V8 context in which to perform the event handling.
- v8::Context::Scope scope(v8Context);
+ ScriptState::Scope scope(scriptState());
// Get the V8 wrapper for the event object.
- v8::Handle<v8::Value> jsEvent = toV8(event, v8::Handle<v8::Object>(), isolate);
+ v8::Handle<v8::Value> jsEvent = toV8(event, scriptState()->context()->Global(), isolate());
- invokeEventHandler(context, event, v8::Local<v8::Value>::New(isolate, jsEvent));
+ invokeEventHandler(event, v8::Local<v8::Value>::New(isolate(), jsEvent));
}
-v8::Local<v8::Value> V8WorkerGlobalScopeEventListener::callListenerFunction(ExecutionContext* context, v8::Handle<v8::Value> jsEvent, Event* event)
+v8::Local<v8::Value> V8WorkerGlobalScopeEventListener::callListenerFunction(v8::Handle<v8::Value> jsEvent, Event* event)
{
- v8::Local<v8::Function> handlerFunction = getListenerFunction(context);
- v8::Local<v8::Object> receiver = getReceiverObject(context, event);
+ v8::Local<v8::Function> handlerFunction = getListenerFunction(scriptState()->executionContext());
+ v8::Local<v8::Object> receiver = getReceiverObject(event);
if (handlerFunction.IsEmpty() || receiver.IsEmpty())
return v8::Local<v8::Value>();
+ TRACE_EVENT1(TRACE_DISABLED_BY_DEFAULT("devtools.timeline"), "FunctionCall", "data", devToolsTraceEventData(scriptState()->executionContext(), handlerFunction, isolate()));
+ TRACE_EVENT_INSTANT1(TRACE_DISABLED_BY_DEFAULT("devtools.timeline.stack"), "CallStack", "stack", InspectorCallStackEvent::currentCallStack());
+ // FIXME(361045): remove InspectorInstrumentation calls once DevTools Timeline migrates to tracing.
InspectorInstrumentationCookie cookie;
- if (InspectorInstrumentation::timelineAgentEnabled(context)) {
- String resourceName("undefined");
+ if (InspectorInstrumentation::timelineAgentEnabled(scriptState()->executionContext())) {
+ int scriptId = 0;
+ String resourceName;
int lineNumber = 1;
- v8::ScriptOrigin origin = handlerFunction->GetScriptOrigin();
- if (!origin.ResourceName().IsEmpty()) {
- V8TRYCATCH_FOR_V8STRINGRESOURCE_RETURN(V8StringResource<>, stringResourceName, origin.ResourceName(), v8::Local<v8::Value>());
- resourceName = stringResourceName;
- lineNumber = handlerFunction->GetScriptLineNumber() + 1;
- }
- cookie = InspectorInstrumentation::willCallFunction(context, resourceName, lineNumber);
+ GetDevToolsFunctionInfo(handlerFunction, isolate(), scriptId, resourceName, lineNumber);
+ cookie = InspectorInstrumentation::willCallFunction(scriptState()->executionContext(), scriptId, resourceName, lineNumber);
}
- v8::Isolate* isolate = toIsolate(context);
v8::Handle<v8::Value> parameters[1] = { jsEvent };
- v8::Local<v8::Value> result = V8ScriptRunner::callFunction(handlerFunction, context, receiver, WTF_ARRAY_LENGTH(parameters), parameters, isolate);
+ v8::Local<v8::Value> result = V8ScriptRunner::callFunction(handlerFunction, scriptState()->executionContext(), receiver, WTF_ARRAY_LENGTH(parameters), parameters, isolate());
InspectorInstrumentation::didCallFunction(cookie);
+ TRACE_EVENT_INSTANT1(TRACE_DISABLED_BY_DEFAULT("devtools.timeline"), "UpdateCounters", "data", InspectorUpdateCountersEvent::data());
return result;
}
-v8::Local<v8::Object> V8WorkerGlobalScopeEventListener::getReceiverObject(ExecutionContext* context, Event* event)
+v8::Local<v8::Object> V8WorkerGlobalScopeEventListener::getReceiverObject(Event* event)
{
- v8::Local<v8::Object> listener = getListenerObject(context);
+ v8::Local<v8::Object> listener = getListenerObject(scriptState()->executionContext());
if (!listener.IsEmpty() && !listener->IsFunction())
return listener;
EventTarget* target = event->currentTarget();
- v8::Isolate* isolate = toIsolate(context);
- v8::Handle<v8::Value> value = toV8(target, v8::Handle<v8::Object>(), isolate);
+ v8::Handle<v8::Value> value = toV8(target, scriptState()->context()->Global(), isolate());
if (value.IsEmpty())
return v8::Local<v8::Object>();
- return v8::Local<v8::Object>::New(isolate, v8::Handle<v8::Object>::Cast(value));
+ return v8::Local<v8::Object>::New(isolate(), v8::Handle<v8::Object>::Cast(value));
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/V8WorkerGlobalScopeEventListener.h b/chromium/third_party/WebKit/Source/bindings/v8/V8WorkerGlobalScopeEventListener.h
index 1acf7c44d7d..355a424afbc 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/V8WorkerGlobalScopeEventListener.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/V8WorkerGlobalScopeEventListener.h
@@ -39,21 +39,21 @@ namespace WebCore {
class Event;
- class V8WorkerGlobalScopeEventListener : public V8EventListener {
+ class V8WorkerGlobalScopeEventListener FINAL : public V8EventListener {
public:
- static PassRefPtr<V8WorkerGlobalScopeEventListener> create(v8::Local<v8::Object> listener, bool isInline, v8::Isolate* isolate)
+ static PassRefPtr<V8WorkerGlobalScopeEventListener> create(v8::Local<v8::Object> listener, bool isInline, ScriptState* scriptState)
{
- return adoptRef(new V8WorkerGlobalScopeEventListener(listener, isInline, isolate));
+ return adoptRef(new V8WorkerGlobalScopeEventListener(listener, isInline, scriptState));
}
- virtual void handleEvent(ExecutionContext*, Event*);
+ virtual void handleEvent(ExecutionContext*, Event*) OVERRIDE;
protected:
- V8WorkerGlobalScopeEventListener(v8::Local<v8::Object> listener, bool isInline, v8::Isolate*);
+ V8WorkerGlobalScopeEventListener(v8::Local<v8::Object> listener, bool isInline, ScriptState*);
private:
- virtual v8::Local<v8::Value> callListenerFunction(ExecutionContext*, v8::Handle<v8::Value> jsEvent, Event*);
- v8::Local<v8::Object> getReceiverObject(ExecutionContext*, Event*);
+ virtual v8::Local<v8::Value> callListenerFunction(v8::Handle<v8::Value> jsEvent, Event*) OVERRIDE;
+ v8::Local<v8::Object> getReceiverObject(Event*);
};
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/WorkerScriptController.cpp b/chromium/third_party/WebKit/Source/bindings/v8/WorkerScriptController.cpp
index 27170fecf89..3381f46b221 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/WorkerScriptController.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/WorkerScriptController.cpp
@@ -32,10 +32,10 @@
#include "bindings/v8/WorkerScriptController.h"
-#include "V8DedicatedWorkerGlobalScope.h"
-#include "V8ServiceWorkerGlobalScope.h"
-#include "V8SharedWorkerGlobalScope.h"
-#include "V8WorkerGlobalScope.h"
+#include "bindings/core/v8/V8DedicatedWorkerGlobalScope.h"
+#include "bindings/core/v8/V8SharedWorkerGlobalScope.h"
+#include "bindings/core/v8/V8WorkerGlobalScope.h"
+#include "bindings/modules/v8/V8ServiceWorkerGlobalScope.h"
#include "bindings/v8/ScriptSourceCode.h"
#include "bindings/v8/ScriptValue.h"
#include "bindings/v8/V8ErrorHandler.h"
@@ -50,6 +50,7 @@
#include "core/workers/WorkerGlobalScope.h"
#include "core/workers/WorkerObjectProxy.h"
#include "core/workers/WorkerThread.h"
+#include "platform/heap/ThreadState.h"
#include <v8.h>
#include "public/platform/Platform.h"
@@ -58,67 +59,77 @@
namespace WebCore {
WorkerScriptController::WorkerScriptController(WorkerGlobalScope& workerGlobalScope)
- : m_workerGlobalScope(workerGlobalScope)
+ : m_isolate(v8::Isolate::New())
+ , m_workerGlobalScope(workerGlobalScope)
, m_executionForbidden(false)
, m_executionScheduledToTerminate(false)
{
- v8::Isolate* isolate = v8::Isolate::New();
- isolate->Enter();
- V8Initializer::initializeWorker(isolate);
+ m_isolate->Enter();
+ V8Initializer::initializeWorker(m_isolate);
v8::V8::Initialize();
- m_isolateHolder = adoptPtr(new gin::IsolateHolder(isolate));
- V8PerIsolateData* data = V8PerIsolateData::create(isolate);
- m_domDataStore = adoptPtr(new DOMDataStore(WorkerWorld));
- data->setWorkerDOMDataStore(m_domDataStore.get());
+ V8PerIsolateData::ensureInitialized(m_isolate);
+ m_world = DOMWrapperWorld::create(WorkerWorldId);
+ m_interruptor = adoptPtr(new V8IsolateInterruptor(m_isolate));
+ ThreadState::current()->addInterruptor(m_interruptor.get());
}
+// We need to postpone V8 Isolate destruction until the very end of
+// worker thread finalization when all objects on the worker heap
+// are destroyed.
+class IsolateCleanupTask : public ThreadState::CleanupTask {
+public:
+ static PassOwnPtr<IsolateCleanupTask> create(v8::Isolate* isolate)
+ {
+ return adoptPtr(new IsolateCleanupTask(isolate));
+ }
+
+ virtual void postCleanup()
+ {
+ V8PerIsolateData::dispose(m_isolate);
+ m_isolate->Exit();
+ m_isolate->Dispose();
+ }
+
+private:
+ explicit IsolateCleanupTask(v8::Isolate* isolate) : m_isolate(isolate) { }
+
+ v8::Isolate* m_isolate;
+};
+
WorkerScriptController::~WorkerScriptController()
{
- m_domDataStore.clear();
+ ThreadState::current()->removeInterruptor(m_interruptor.get());
+
+ m_world->dispose();
// The corresponding call to didStartWorkerRunLoop is in
// WorkerThread::workerThread().
// See http://webkit.org/b/83104#c14 for why this is here.
blink::Platform::current()->didStopWorkerRunLoop(blink::WebWorkerRunLoop(&m_workerGlobalScope.thread()->runLoop()));
- disposeContext();
- V8PerIsolateData::dispose(isolate());
- v8::Isolate* v8Isolate = isolate();
- v8Isolate->Exit();
- m_isolateHolder.clear();
- v8Isolate->Dispose();
-}
+ if (isContextInitialized())
+ m_scriptState->disposePerContextData();
-void WorkerScriptController::disposeContext()
-{
- m_perContextData.clear();
- m_contextHolder.clear();
+ ThreadState::current()->addCleanupTask(IsolateCleanupTask::create(m_isolate));
}
bool WorkerScriptController::initializeContextIfNeeded()
{
- if (m_contextHolder)
+ v8::HandleScope handleScope(m_isolate);
+
+ if (isContextInitialized())
return true;
- v8::Handle<v8::Context> context = v8::Context::New(isolate());
+ v8::Handle<v8::Context> context = v8::Context::New(m_isolate);
if (context.IsEmpty())
return false;
- m_contextHolder = adoptPtr(new gin::ContextHolder(isolate()));
- m_contextHolder->SetContext(context);
-
- v8::Context::Scope scope(context);
-
- V8PerContextDataHolder::install(context);
+ m_scriptState = ScriptState::create(context, m_world);
- m_perContextData = V8PerContextData::create(context);
- if (!m_perContextData->init()) {
- disposeContext();
- return false;
- }
+ ScriptState::Scope scope(m_scriptState.get());
// Set DebugId for the new context.
- context->SetEmbedderData(0, v8AtomicString(isolate(), "worker"));
+ context->SetEmbedderData(0, v8AtomicString(m_isolate, "worker"));
// Create a new JS object and use it as the prototype for the shadow global object.
const WrapperTypeInfo* contextType = &V8DedicatedWorkerGlobalScope::wrapperTypeInfo;
@@ -126,17 +137,17 @@ bool WorkerScriptController::initializeContextIfNeeded()
contextType = &V8ServiceWorkerGlobalScope::wrapperTypeInfo;
else if (!m_workerGlobalScope.isDedicatedWorkerGlobalScope())
contextType = &V8SharedWorkerGlobalScope::wrapperTypeInfo;
- v8::Handle<v8::Function> workerGlobalScopeConstructor = m_perContextData->constructorForType(contextType);
- v8::Local<v8::Object> jsWorkerGlobalScope = V8ObjectConstructor::newInstance(workerGlobalScopeConstructor);
+ v8::Handle<v8::Function> workerGlobalScopeConstructor = m_scriptState->perContextData()->constructorForType(contextType);
+ v8::Local<v8::Object> jsWorkerGlobalScope = V8ObjectConstructor::newInstance(m_isolate, workerGlobalScopeConstructor);
if (jsWorkerGlobalScope.IsEmpty()) {
- disposeContext();
+ m_scriptState->disposePerContextData();
return false;
}
- V8DOMWrapper::associateObjectWithWrapper<V8WorkerGlobalScope>(PassRefPtr<WorkerGlobalScope>(m_workerGlobalScope), contextType, jsWorkerGlobalScope, isolate(), WrapperConfiguration::Dependent);
+ V8DOMWrapper::associateObjectWithWrapper<V8WorkerGlobalScope>(PassRefPtrWillBeRawPtr<WorkerGlobalScope>(&m_workerGlobalScope), contextType, jsWorkerGlobalScope, m_isolate, WrapperConfiguration::Dependent);
// Insert the object instance as the prototype of the shadow object.
- v8::Handle<v8::Object> globalObject = v8::Handle<v8::Object>::Cast(m_contextHolder->context()->Global()->GetPrototype());
+ v8::Handle<v8::Object> globalObject = v8::Handle<v8::Object>::Cast(m_scriptState->context()->Global()->GetPrototype());
globalObject->SetPrototype(jsWorkerGlobalScope);
return true;
@@ -144,25 +155,22 @@ bool WorkerScriptController::initializeContextIfNeeded()
ScriptValue WorkerScriptController::evaluate(const String& script, const String& fileName, const TextPosition& scriptStartPosition, WorkerGlobalScopeExecutionState* state)
{
- v8::HandleScope handleScope(isolate());
-
if (!initializeContextIfNeeded())
return ScriptValue();
- v8::Handle<v8::Context> context = m_contextHolder->context();
+ ScriptState::Scope scope(m_scriptState.get());
+
if (!m_disableEvalPending.isEmpty()) {
- context->AllowCodeGenerationFromStrings(false);
- context->SetErrorMessageForCodeGenerationFromStrings(v8String(isolate(), m_disableEvalPending));
+ m_scriptState->context()->AllowCodeGenerationFromStrings(false);
+ m_scriptState->context()->SetErrorMessageForCodeGenerationFromStrings(v8String(m_isolate, m_disableEvalPending));
m_disableEvalPending = String();
}
- v8::Context::Scope scope(context);
-
v8::TryCatch block;
- v8::Handle<v8::String> scriptString = v8String(isolate(), script);
- v8::Handle<v8::Script> compiledScript = V8ScriptRunner::compileScript(scriptString, fileName, scriptStartPosition, 0, isolate());
- v8::Local<v8::Value> result = V8ScriptRunner::runCompiledScript(compiledScript, &m_workerGlobalScope, isolate());
+ v8::Handle<v8::String> scriptString = v8String(m_isolate, script);
+ v8::Handle<v8::Script> compiledScript = V8ScriptRunner::compileScript(scriptString, fileName, scriptStartPosition, 0, m_isolate);
+ v8::Local<v8::Value> result = V8ScriptRunner::runCompiledScript(compiledScript, &m_workerGlobalScope, m_isolate);
if (!block.CanContinue()) {
m_workerGlobalScope.script()->forbidExecution();
@@ -175,9 +183,9 @@ ScriptValue WorkerScriptController::evaluate(const String& script, const String&
state->errorMessage = toCoreString(message->Get());
state->lineNumber = message->GetLineNumber();
state->columnNumber = message->GetStartColumn() + 1;
- V8TRYCATCH_FOR_V8STRINGRESOURCE_RETURN(V8StringResource<>, sourceURL, message->GetScriptResourceName(), ScriptValue());
+ TOSTRING_DEFAULT(V8StringResource<>, sourceURL, message->GetScriptResourceName(), ScriptValue());
state->sourceURL = sourceURL;
- state->exception = ScriptValue(block.Exception(), isolate());
+ state->exception = ScriptValue(m_scriptState.get(), block.Exception());
block.Reset();
} else
state->hadException = false;
@@ -185,10 +193,10 @@ ScriptValue WorkerScriptController::evaluate(const String& script, const String&
if (result.IsEmpty() || result->IsUndefined())
return ScriptValue();
- return ScriptValue(result, isolate());
+ return ScriptValue(m_scriptState.get(), result);
}
-void WorkerScriptController::evaluate(const ScriptSourceCode& sourceCode, RefPtr<ErrorEvent>* errorEvent)
+void WorkerScriptController::evaluate(const ScriptSourceCode& sourceCode, RefPtrWillBeRawPtr<ErrorEvent>* errorEvent)
{
if (isExecutionForbidden())
return;
@@ -198,12 +206,17 @@ void WorkerScriptController::evaluate(const ScriptSourceCode& sourceCode, RefPtr
if (state.hadException) {
if (errorEvent) {
*errorEvent = m_workerGlobalScope.shouldSanitizeScriptError(state.sourceURL, NotSharableCrossOrigin) ?
- ErrorEvent::createSanitizedError(0) : ErrorEvent::create(state.errorMessage, state.sourceURL, state.lineNumber, state.columnNumber, 0);
- V8ErrorHandler::storeExceptionOnErrorEventWrapper(errorEvent->get(), state.exception.v8Value(), isolate());
+ ErrorEvent::createSanitizedError(m_world.get()) : ErrorEvent::create(state.errorMessage, state.sourceURL, state.lineNumber, state.columnNumber, m_world.get());
+ V8ErrorHandler::storeExceptionOnErrorEventWrapper(errorEvent->get(), state.exception.v8Value(), m_scriptState->context()->Global(), m_isolate);
} else {
ASSERT(!m_workerGlobalScope.shouldSanitizeScriptError(state.sourceURL, NotSharableCrossOrigin));
- RefPtr<ErrorEvent> event = m_errorEventFromImportedScript ? m_errorEventFromImportedScript.release() : ErrorEvent::create(state.errorMessage, state.sourceURL, state.lineNumber, state.columnNumber, 0);
- m_workerGlobalScope.reportException(event, 0, NotSharableCrossOrigin);
+ RefPtrWillBeRawPtr<ErrorEvent> event = nullptr;
+ if (m_errorEventFromImportedScript) {
+ event = m_errorEventFromImportedScript.release();
+ } else {
+ event = ErrorEvent::create(state.errorMessage, state.sourceURL, state.lineNumber, state.columnNumber, m_world.get());
+ }
+ m_workerGlobalScope.reportException(event, nullptr, NotSharableCrossOrigin);
}
}
}
@@ -217,7 +230,7 @@ void WorkerScriptController::scheduleExecutionTermination()
MutexLocker locker(m_scheduledTerminationMutex);
m_executionScheduledToTerminate = true;
}
- v8::V8::TerminateExecution(isolate());
+ v8::V8::TerminateExecution(m_isolate);
}
bool WorkerScriptController::isExecutionTerminating() const
@@ -244,26 +257,10 @@ void WorkerScriptController::disableEval(const String& errorMessage)
m_disableEvalPending = errorMessage;
}
-void WorkerScriptController::rethrowExceptionFromImportedScript(PassRefPtr<ErrorEvent> errorEvent)
+void WorkerScriptController::rethrowExceptionFromImportedScript(PassRefPtrWillBeRawPtr<ErrorEvent> errorEvent)
{
m_errorEventFromImportedScript = errorEvent;
- throwError(V8ThrowException::createError(v8GeneralError, m_errorEventFromImportedScript->message(), isolate()), isolate());
-}
-
-WorkerScriptController* WorkerScriptController::controllerForContext()
-{
- v8::Isolate* isolate = v8::Isolate::GetCurrent();
- // Happens on frame destruction, check otherwise GetCurrent() will crash.
- if (!isolate || !isolate->InContext())
- return 0;
- v8::Handle<v8::Context> context = isolate->GetCurrentContext();
- v8::Handle<v8::Object> global = context->Global();
- global = global->FindInstanceInPrototypeChain(V8WorkerGlobalScope::domTemplate(isolate, WorkerWorld));
- // Return 0 if the current executing context is not the worker context.
- if (global.IsEmpty())
- return 0;
- WorkerGlobalScope* workerGlobalScope = V8WorkerGlobalScope::toNative(global);
- return workerGlobalScope->script();
+ throwError(V8ThrowException::createError(v8GeneralError, m_errorEventFromImportedScript->message(), m_isolate), m_isolate);
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/WorkerScriptController.h b/chromium/third_party/WebKit/Source/bindings/v8/WorkerScriptController.h
index 7b7ea1af507..2559269fdd0 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/WorkerScriptController.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/WorkerScriptController.h
@@ -34,17 +34,11 @@
#include "bindings/v8/ScriptValue.h"
#include "bindings/v8/V8Binding.h"
#include "core/events/ErrorEvent.h"
-#include "gin/public/context_holder.h"
-#include "gin/public/isolate_holder.h"
#include "wtf/OwnPtr.h"
#include "wtf/ThreadingPrimitives.h"
#include "wtf/text/TextPosition.h"
#include <v8.h>
-namespace gin {
-class IsolateHolder;
-}
-
namespace WebCore {
class ScriptSourceCode;
@@ -74,9 +68,11 @@ namespace WebCore {
WorkerGlobalScope& workerGlobalScope() { return m_workerGlobalScope; }
- void evaluate(const ScriptSourceCode&, RefPtr<ErrorEvent>* = 0);
+ bool initializeContextIfNeeded();
+
+ void evaluate(const ScriptSourceCode&, RefPtrWillBeRawPtr<ErrorEvent>* = 0);
- void rethrowExceptionFromImportedScript(PassRefPtr<ErrorEvent>);
+ void rethrowExceptionFromImportedScript(PassRefPtrWillBeRawPtr<ErrorEvent>);
// Async request to terminate a future JS execution. Eventually causes termination
// exception raised during JS execution, if the worker thread happens to run JS.
@@ -93,36 +89,32 @@ namespace WebCore {
void disableEval(const String&);
- // Returns WorkerScriptController for the currently executing context. 0 will be returned if the current executing context is not the worker context.
- static WorkerScriptController* controllerForContext();
-
// Evaluate a script file in the current execution environment.
ScriptValue evaluate(const String& script, const String& fileName, const TextPosition& scriptStartPosition, WorkerGlobalScopeExecutionState*);
- // Returns a local handle of the context.
- v8::Local<v8::Context> context() { return m_contextHolder ? m_contextHolder->context() : v8::Local<v8::Context>(); }
+ v8::Isolate* isolate() const { return m_isolate; }
+ DOMWrapperWorld& world() const { return *m_world; }
+ ScriptState* scriptState() { return m_scriptState.get(); }
+ v8::Local<v8::Context> context() { return m_scriptState ? m_scriptState->context() : v8::Local<v8::Context>(); }
+ bool isContextInitialized() { return m_scriptState && !!m_scriptState->perContextData(); }
// Send a notification about current thread is going to be idle.
// Returns true if the embedder should stop calling idleNotification
// until real work has been done.
bool idleNotification() { return v8::V8::IdleNotification(); }
- v8::Isolate* isolate() const { return m_isolateHolder->isolate(); }
private:
- bool initializeContextIfNeeded();
- void disposeContext();
-
+ v8::Isolate* m_isolate;
WorkerGlobalScope& m_workerGlobalScope;
- OwnPtr<gin::IsolateHolder> m_isolateHolder;
- OwnPtr<gin::ContextHolder> m_contextHolder;
- OwnPtr<V8PerContextData> m_perContextData;
+ RefPtr<ScriptState> m_scriptState;
+ RefPtr<DOMWrapperWorld> m_world;
String m_disableEvalPending;
- OwnPtr<DOMDataStore> m_domDataStore;
bool m_executionForbidden;
bool m_executionScheduledToTerminate;
mutable Mutex m_scheduledTerminationMutex;
- RefPtr<ErrorEvent> m_errorEventFromImportedScript;
+ RefPtrWillBePersistent<ErrorEvent> m_errorEventFromImportedScript;
+ OwnPtr<V8IsolateInterruptor> m_interruptor;
};
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/WorkerScriptDebugServer.cpp b/chromium/third_party/WebKit/Source/bindings/v8/WorkerScriptDebugServer.cpp
index 935a2d26dc5..920508e1e43 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/WorkerScriptDebugServer.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/WorkerScriptDebugServer.cpp
@@ -42,11 +42,10 @@
namespace WebCore {
-WorkerScriptDebugServer::WorkerScriptDebugServer(WorkerGlobalScope* workerGlobalScope, const String& mode)
+WorkerScriptDebugServer::WorkerScriptDebugServer(WorkerGlobalScope* workerGlobalScope)
: ScriptDebugServer(v8::Isolate::GetCurrent())
, m_listener(0)
, m_workerGlobalScope(workerGlobalScope)
- , m_debuggerTaskMode(mode)
{
ASSERT(m_isolate);
}
@@ -54,16 +53,17 @@ WorkerScriptDebugServer::WorkerScriptDebugServer(WorkerGlobalScope* workerGlobal
void WorkerScriptDebugServer::addListener(ScriptDebugListener* listener)
{
v8::HandleScope scope(m_isolate);
- v8::Local<v8::Context> debuggerContext = v8::Debug::GetDebugContext();
- v8::Context::Scope contextScope(debuggerContext);
-
ASSERT(!m_listener);
- m_listener = listener;
+ v8::Debug::SetDebugEventListener(&WorkerScriptDebugServer::v8DebugEventCallback, v8::External::New(m_isolate, this));
ensureDebuggerScriptCompiled();
+ m_listener = listener;
+
+ v8::Local<v8::Context> debuggerContext = v8::Debug::GetDebugContext();
+ v8::Context::Scope contextScope(debuggerContext);
+
v8::Local<v8::Object> debuggerScript = m_debuggerScript.newLocal(m_isolate);
ASSERT(!debuggerScript->IsUndefined());
- v8::Debug::SetDebugEventListener2(&WorkerScriptDebugServer::v8DebugEventCallback, v8::External::New(m_isolate, this));
v8::Handle<v8::Function> getScriptsFunction = v8::Local<v8::Function>::Cast(debuggerScript->Get(v8AtomicString(m_isolate, "getWorkerScripts")));
v8::Handle<v8::Value> value = V8ScriptRunner::callInternalFunction(getScriptsFunction, debuggerScript, 0, 0, m_isolate);
@@ -72,15 +72,16 @@ void WorkerScriptDebugServer::addListener(ScriptDebugListener* listener)
ASSERT(!value->IsUndefined() && value->IsArray());
v8::Handle<v8::Array> scriptsArray = v8::Handle<v8::Array>::Cast(value);
for (unsigned i = 0; i < scriptsArray->Length(); ++i)
- dispatchDidParseSource(listener, v8::Handle<v8::Object>::Cast(scriptsArray->Get(v8::Integer::New(i, m_isolate))));
+ dispatchDidParseSource(listener, v8::Handle<v8::Object>::Cast(scriptsArray->Get(v8::Integer::New(m_isolate, i))));
}
void WorkerScriptDebugServer::removeListener(ScriptDebugListener* listener)
{
ASSERT(m_listener == listener);
continueProgram();
+ discardDebuggerScript();
m_listener = 0;
- v8::Debug::SetDebugEventListener2(0);
+ v8::Debug::SetDebugEventListener(0);
}
void WorkerScriptDebugServer::interruptAndRunTask(PassOwnPtr<Task> task)
@@ -98,7 +99,7 @@ void WorkerScriptDebugServer::runMessageLoopOnPause(v8::Handle<v8::Context>)
{
MessageQueueWaitResult result;
do {
- result = m_workerGlobalScope->thread()->runLoop().runInMode(m_workerGlobalScope, m_debuggerTaskMode);
+ result = m_workerGlobalScope->thread()->runLoop().runDebuggerTask();
// Keep waiting until execution is resumed.
} while (result == MessageQueueMessageReceived && isPaused());
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/WorkerScriptDebugServer.h b/chromium/third_party/WebKit/Source/bindings/v8/WorkerScriptDebugServer.h
index befaaa90942..81fde7da0e5 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/WorkerScriptDebugServer.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/WorkerScriptDebugServer.h
@@ -32,21 +32,18 @@
#define WorkerScriptDebugServer_h
#include "bindings/v8/ScriptDebugServer.h"
-
-namespace v8 {
-class Isolate;
-}
+#include <v8.h>
namespace WebCore {
class WorkerGlobalScope;
class WorkerThread;
-class WorkerScriptDebugServer : public ScriptDebugServer {
+class WorkerScriptDebugServer FINAL : public ScriptDebugServer {
WTF_MAKE_NONCOPYABLE(WorkerScriptDebugServer);
public:
- WorkerScriptDebugServer(WorkerGlobalScope*, const String&);
- ~WorkerScriptDebugServer() { }
+ explicit WorkerScriptDebugServer(WorkerGlobalScope*);
+ virtual ~WorkerScriptDebugServer() { }
void addListener(ScriptDebugListener*);
void removeListener(ScriptDebugListener*);
@@ -54,14 +51,13 @@ public:
void interruptAndRunTask(PassOwnPtr<Task>);
private:
- virtual ScriptDebugListener* getDebugListenerForContext(v8::Handle<v8::Context>);
- virtual void runMessageLoopOnPause(v8::Handle<v8::Context>);
- virtual void quitMessageLoopOnPause();
+ virtual ScriptDebugListener* getDebugListenerForContext(v8::Handle<v8::Context>) OVERRIDE;
+ virtual void runMessageLoopOnPause(v8::Handle<v8::Context>) OVERRIDE;
+ virtual void quitMessageLoopOnPause() OVERRIDE;
typedef HashMap<WorkerGlobalScope*, ScriptDebugListener*> ListenersMap;
ScriptDebugListener* m_listener;
WorkerGlobalScope* m_workerGlobalScope;
- String m_debuggerTaskMode;
};
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/WrapperTypeInfo.h b/chromium/third_party/WebKit/Source/bindings/v8/WrapperTypeInfo.h
index 227083d018b..3d92f6adb0d 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/WrapperTypeInfo.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/WrapperTypeInfo.h
@@ -32,13 +32,13 @@
#define WrapperTypeInfo_h
#include "gin/public/wrapper_info.h"
+#include "platform/heap/Handle.h"
#include "wtf/Assertions.h"
#include <v8.h>
namespace WebCore {
class ActiveDOMObject;
- class DOMDataStore;
class EventTarget;
class Node;
@@ -51,13 +51,7 @@ namespace WebCore {
static const uint16_t v8DOMNodeClassId = 1;
static const uint16_t v8DOMObjectClassId = 2;
- enum WrapperWorldType {
- MainWorld,
- IsolatedWorld,
- WorkerWorld
- };
-
- typedef v8::Handle<v8::FunctionTemplate> (*DomTemplateFunction)(v8::Isolate*, WrapperWorldType);
+ typedef v8::Handle<v8::FunctionTemplate> (*DomTemplateFunction)(v8::Isolate*);
typedef void (*DerefObjectFunction)(void*);
typedef ActiveDOMObject* (*ToActiveDOMObjectFunction)(v8::Handle<v8::Object>);
typedef EventTarget* (*ToEventTargetFunction)(v8::Handle<v8::Object>);
@@ -66,7 +60,13 @@ namespace WebCore {
enum WrapperTypePrototype {
WrapperTypeObjectPrototype,
- WrapperTypeErrorPrototype
+ WrapperTypeExceptionPrototype
+ };
+
+ enum GCType {
+ GarbageCollectedObject,
+ WillBeGarbageCollectedObject,
+ RefCountedObject,
};
inline void setObjectGroup(void* object, const v8::Persistent<v8::Object>& wrapper, v8::Isolate* isolate)
@@ -100,12 +100,9 @@ namespace WebCore {
return false;
}
- v8::Handle<v8::FunctionTemplate> domTemplate(v8::Isolate* isolate, WrapperWorldType worldType) const { return domTemplateFunction(isolate, worldType); }
-
- void derefObject(void* object) const
+ v8::Handle<v8::FunctionTemplate> domTemplate(v8::Isolate* isolate) const
{
- if (derefObjectFunction)
- derefObjectFunction(object);
+ return domTemplateFunction(isolate);
}
void installPerContextEnabledMethods(v8::Handle<v8::Object> prototypeTemplate, v8::Isolate* isolate) const
@@ -147,6 +144,7 @@ namespace WebCore {
const InstallPerContextEnabledPrototypePropertiesFunction installPerContextEnabledMethodsFunction;
const WrapperTypeInfo* parentClass;
const WrapperTypePrototype wrapperTypePrototype;
+ const GCType gcType;
};
@@ -162,30 +160,60 @@ namespace WebCore {
}
template<typename T, int offset>
- inline T* getInternalField(v8::Handle<v8::Object> object)
+ inline T* getInternalField(v8::Handle<v8::Object> wrapper)
{
- ASSERT(offset < object->InternalFieldCount());
- return static_cast<T*>(object->GetAlignedPointerFromInternalField(offset));
+ ASSERT(offset < wrapper->InternalFieldCount());
+ return static_cast<T*>(wrapper->GetAlignedPointerFromInternalField(offset));
+ }
+
+ inline void* toNative(const v8::Persistent<v8::Object>& wrapper)
+ {
+ return getInternalField<void, v8DOMWrapperObjectIndex>(wrapper);
+ }
+
+ inline void* toNative(v8::Handle<v8::Object> wrapper)
+ {
+ return getInternalField<void, v8DOMWrapperObjectIndex>(wrapper);
}
- inline void* toNative(const v8::Persistent<v8::Object>& object)
+ inline const WrapperTypeInfo* toWrapperTypeInfo(const v8::Persistent<v8::Object>& wrapper)
{
- return getInternalField<void, v8DOMWrapperObjectIndex>(object);
+ return getInternalField<WrapperTypeInfo, v8DOMWrapperTypeIndex>(wrapper);
}
- inline void* toNative(v8::Handle<v8::Object> object)
+ inline const WrapperTypeInfo* toWrapperTypeInfo(v8::Handle<v8::Object> wrapper)
{
- return getInternalField<void, v8DOMWrapperObjectIndex>(object);
+ return getInternalField<WrapperTypeInfo, v8DOMWrapperTypeIndex>(wrapper);
}
- inline const WrapperTypeInfo* toWrapperTypeInfo(const v8::Persistent<v8::Object>& object)
+ inline const PersistentNode* toPersistentHandle(const v8::Handle<v8::Object>& wrapper)
{
- return getInternalField<WrapperTypeInfo, v8DOMWrapperTypeIndex>(object);
+ // Persistent handle is stored in the last internal field.
+ return static_cast<PersistentNode*>(wrapper->GetAlignedPointerFromInternalField(wrapper->InternalFieldCount() - 1));
}
- inline const WrapperTypeInfo* toWrapperTypeInfo(v8::Handle<v8::Object> object)
+ inline void releaseObject(v8::Handle<v8::Object> wrapper)
{
- return getInternalField<WrapperTypeInfo, v8DOMWrapperTypeIndex>(object);
+ const WrapperTypeInfo* typeInfo = toWrapperTypeInfo(wrapper);
+ if (typeInfo->gcType == GarbageCollectedObject) {
+ const PersistentNode* handle = toPersistentHandle(wrapper);
+ // This will be null iff a wrapper for a hidden wrapper object,
+ // see V8DOMWrapper::setNativeInfoForHiddenWrapper().
+ delete handle;
+ } else if (typeInfo->gcType == WillBeGarbageCollectedObject) {
+#if ENABLE(OILPAN)
+ const PersistentNode* handle = toPersistentHandle(wrapper);
+ // This will be null iff a wrapper for a hidden wrapper object,
+ // see V8DOMWrapper::setNativeInfoForHiddenWrapper().
+ delete handle;
+#else
+ ASSERT(typeInfo->derefObjectFunction);
+ typeInfo->derefObjectFunction(toNative(wrapper));
+#endif
+ } else {
+ ASSERT(typeInfo->derefObjectFunction);
+ typeInfo->derefObjectFunction(toNative(wrapper));
+ }
}
struct WrapperConfiguration {
@@ -194,7 +222,7 @@ namespace WebCore {
Dependent, Independent
};
- void configureWrapper(v8::Persistent<v8::Object>* wrapper) const
+ void configureWrapper(v8::PersistentBase<v8::Object>* wrapper) const
{
wrapper->SetWrapperClassId(classId);
if (lifetime == Independent)
@@ -216,11 +244,6 @@ namespace WebCore {
WrapperConfiguration configuration = {v8DOMNodeClassId, lifetime};
return configuration;
}
-
- template<class ElementType>
- class WrapperTypeTraits {
- // specialized classes have thier own functions, which are generated by binding generator.
- };
}
#endif // WrapperTypeInfo_h
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8AlgorithmCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8AlgorithmCustom.cpp
deleted file mode 100644
index c8c4ccaa0e8..00000000000
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8AlgorithmCustom.cpp
+++ /dev/null
@@ -1,78 +0,0 @@
-/*
- * Copyright (C) 2013 Google Inc. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions are
- * met:
- *
- * * Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * * Redistributions in binary form must reproduce the above
- * copyright notice, this list of conditions and the following disclaimer
- * in the documentation and/or other materials provided with the
- * distribution.
- * * Neither the name of Google Inc. nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
- * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
- * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
- * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
- * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
- * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
- * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
- * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
- * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-#include "config.h"
-#include "V8Algorithm.h"
-
-#include "V8AesCbcParams.h"
-#include "V8AesCtrParams.h"
-#include "V8AesKeyGenParams.h"
-#include "V8HmacKeyParams.h"
-#include "V8HmacParams.h"
-#include "V8RsaKeyGenParams.h"
-#include "V8RsaSsaParams.h"
-#include "platform/NotImplemented.h"
-
-namespace WebCore {
-
-v8::Handle<v8::Object> wrap(Algorithm* impl, v8::Handle<v8::Object> creationContext, v8::Isolate* isolate)
-{
- ASSERT(impl);
-
- // Wrap as the more derived type.
- switch (impl->type()) {
- case blink::WebCryptoAlgorithmParamsTypeNone:
- return V8Algorithm::createWrapper(impl, creationContext, isolate);
- case blink::WebCryptoAlgorithmParamsTypeAesCbcParams:
- return wrap(static_cast<AesCbcParams*>(impl), creationContext, isolate);
- case blink::WebCryptoAlgorithmParamsTypeAesKeyGenParams:
- return wrap(static_cast<AesKeyGenParams*>(impl), creationContext, isolate);
- case blink::WebCryptoAlgorithmParamsTypeHmacParams:
- return wrap(static_cast<HmacParams*>(impl), creationContext, isolate);
- case blink::WebCryptoAlgorithmParamsTypeHmacKeyParams:
- return wrap(static_cast<HmacKeyParams*>(impl), creationContext, isolate);
- case blink::WebCryptoAlgorithmParamsTypeRsaSsaParams:
- return wrap(static_cast<RsaSsaParams*>(impl), creationContext, isolate);
- case blink::WebCryptoAlgorithmParamsTypeRsaKeyGenParams:
- return wrap(static_cast<RsaKeyGenParams*>(impl), creationContext, isolate);
- case blink::WebCryptoAlgorithmParamsTypeAesCtrParams:
- return wrap(static_cast<AesCtrParams*>(impl), creationContext, isolate);
- case blink::WebCryptoAlgorithmParamsTypeAesGcmParams:
- case blink::WebCryptoAlgorithmParamsTypeRsaOaepParams:
- // TODO
- notImplemented();
- break;
- }
-
- ASSERT_NOT_REACHED();
- return v8::Handle<v8::Object>();
-}
-
-} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8ArrayBufferCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8ArrayBufferCustom.cpp
index 8eb4c2b818d..f3494cf694e 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8ArrayBufferCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8ArrayBufferCustom.cpp
@@ -31,7 +31,6 @@
#include "config.h"
#include "bindings/v8/custom/V8ArrayBufferCustom.h"
-#include "bindings/v8/ScriptPromiseResolver.h"
#include "bindings/v8/V8Binding.h"
#include "wtf/ArrayBuffer.h"
#include "wtf/StdLibExtras.h"
@@ -49,15 +48,10 @@ V8ArrayBufferDeallocationObserver* V8ArrayBufferDeallocationObserver::instanceTe
const WrapperTypeInfo V8ArrayBuffer::wrapperTypeInfo = {
gin::kEmbedderBlink,
0, V8ArrayBuffer::derefObject,
- 0, 0, 0, 0, 0, WrapperTypeObjectPrototype
+ 0, 0, 0, 0, 0, WrapperTypeObjectPrototype, RefCountedObject
};
-bool V8ArrayBuffer::hasInstance(v8::Handle<v8::Value> value, v8::Isolate*, WrapperWorldType)
-{
- return value->IsArrayBuffer();
-}
-
-bool V8ArrayBuffer::hasInstanceInAnyWorld(v8::Handle<v8::Value> value, v8::Isolate*)
+bool V8ArrayBuffer::hasInstance(v8::Handle<v8::Value> value, v8::Isolate*)
{
return value->IsArrayBuffer();
}
@@ -82,12 +76,11 @@ v8::Handle<v8::Object> V8ArrayBuffer::createWrapper(PassRefPtr<ArrayBuffer> impl
ArrayBuffer* V8ArrayBuffer::toNative(v8::Handle<v8::Object> object)
{
ASSERT(object->IsArrayBuffer());
- void* arraybufferPtr = object->GetAlignedPointerFromInternalField(v8DOMWrapperObjectIndex);
- if (arraybufferPtr)
- return reinterpret_cast<ArrayBuffer*>(arraybufferPtr);
-
v8::Local<v8::ArrayBuffer> v8buffer = object.As<v8::ArrayBuffer>();
- ASSERT(!v8buffer->IsExternal());
+ if (v8buffer->IsExternal()) {
+ RELEASE_ASSERT(toWrapperTypeInfo(object)->ginEmbedder == gin::kEmbedderBlink);
+ return reinterpret_cast<ArrayBuffer*>(WebCore::toNative(object));
+ }
v8::ArrayBuffer::Contents v8Contents = v8buffer->Externalize();
ArrayBufferContents contents(v8Contents.Data(), v8Contents.ByteLength(),
@@ -95,9 +88,12 @@ ArrayBuffer* V8ArrayBuffer::toNative(v8::Handle<v8::Object> object)
RefPtr<ArrayBuffer> buffer = ArrayBuffer::create(contents);
V8DOMWrapper::associateObjectWithWrapper<V8ArrayBuffer>(buffer.release(), &wrapperTypeInfo, object, v8::Isolate::GetCurrent(), WrapperConfiguration::Dependent);
- arraybufferPtr = object->GetAlignedPointerFromInternalField(v8DOMWrapperObjectIndex);
- ASSERT(arraybufferPtr);
- return reinterpret_cast<ArrayBuffer*>(arraybufferPtr);
+ return reinterpret_cast<ArrayBuffer*>(WebCore::toNative(object));
+}
+
+ArrayBuffer* V8ArrayBuffer::toNativeWithTypeCheck(v8::Isolate* isolate, v8::Handle<v8::Value> value)
+{
+ return V8ArrayBuffer::hasInstance(value, isolate) ? V8ArrayBuffer::toNative(v8::Handle<v8::Object>::Cast(value)) : 0;
}
template<>
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8ArrayBufferCustom.h b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8ArrayBufferCustom.h
index 2c5ff8e1cac..779095f7c9a 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8ArrayBufferCustom.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8ArrayBufferCustom.h
@@ -34,9 +34,9 @@
namespace WebCore {
-class V8ArrayBufferDeallocationObserver: public WTF::ArrayBufferDeallocationObserver {
+class V8ArrayBufferDeallocationObserver FINAL: public WTF::ArrayBufferDeallocationObserver {
public:
- virtual void arrayBufferDeallocated(unsigned sizeInBytes)
+ virtual void arrayBufferDeallocated(unsigned sizeInBytes) OVERRIDE
{
v8::Isolate::GetCurrent()->AdjustAmountOfExternalAllocatedMemory(-static_cast<int>(sizeInBytes));
}
@@ -51,9 +51,9 @@ protected:
class V8ArrayBuffer {
public:
- static bool hasInstance(v8::Handle<v8::Value>, v8::Isolate*, WrapperWorldType);
- static bool hasInstanceInAnyWorld(v8::Handle<v8::Value>, v8::Isolate*);
+ static bool hasInstance(v8::Handle<v8::Value>, v8::Isolate*);
static ArrayBuffer* toNative(v8::Handle<v8::Object>);
+ static ArrayBuffer* toNativeWithTypeCheck(v8::Isolate*, v8::Handle<v8::Value>);
static void derefObject(void*);
static const WrapperTypeInfo wrapperTypeInfo;
static const int internalFieldCount = v8DefaultWrapperInternalFieldCount;
@@ -75,13 +75,6 @@ private:
static v8::Handle<v8::Object> createWrapper(PassRefPtr<ArrayBuffer>, v8::Handle<v8::Object> creationContext, v8::Isolate*);
};
-template<>
-class WrapperTypeTraits<ArrayBuffer > {
-public:
- static const WrapperTypeInfo* wrapperTypeInfo() { return &V8ArrayBuffer::wrapperTypeInfo; }
-};
-
-
inline v8::Handle<v8::Object> wrap(ArrayBuffer* impl, v8::Handle<v8::Object> creationContext, v8::Isolate* isolate)
{
ASSERT(impl);
@@ -115,7 +108,7 @@ inline void v8SetReturnValue(const CallbackInfo& info, ArrayBuffer* impl)
template<class CallbackInfo>
inline void v8SetReturnValueForMainWorld(const CallbackInfo& info, ArrayBuffer* impl)
{
- ASSERT(worldType(info.GetIsolate()) == MainWorld);
+ ASSERT(DOMWrapperWorld::current(info.GetIsolate()).isMainWorld());
if (UNLIKELY(!impl)) {
v8SetReturnValueNull(info);
return;
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8ArrayBufferViewCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8ArrayBufferViewCustom.cpp
index 4f00d0df933..5ee873dd6cb 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8ArrayBufferViewCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8ArrayBufferViewCustom.cpp
@@ -82,5 +82,9 @@ ArrayBufferView* V8ArrayBufferView::toNative(v8::Handle<v8::Object> object)
return 0;
}
+ArrayBufferView* V8ArrayBufferView::toNativeWithTypeCheck(v8::Isolate* isolate, v8::Handle<v8::Value> value)
+{
+ return V8ArrayBufferView::hasInstance(value, isolate) ? V8ArrayBufferView::toNative(v8::Handle<v8::Object>::Cast(value)) : 0;
+}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8ArrayBufferViewCustom.h b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8ArrayBufferViewCustom.h
index 94fcd1344d8..7ff95bf68ee 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8ArrayBufferViewCustom.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8ArrayBufferViewCustom.h
@@ -43,15 +43,12 @@ namespace WebCore {
class V8ArrayBufferView {
public:
- static bool hasInstance(v8::Handle<v8::Value> value, v8::Isolate*, WrapperWorldType)
- {
- return value->IsArrayBufferView();
- }
- static bool hasInstanceInAnyWorld(v8::Handle<v8::Value> value, v8::Isolate*)
+ static bool hasInstance(v8::Handle<v8::Value> value, v8::Isolate*)
{
return value->IsArrayBufferView();
}
static ArrayBufferView* toNative(v8::Handle<v8::Object>);
+ static ArrayBufferView* toNativeWithTypeCheck(v8::Isolate*, v8::Handle<v8::Value>);
static inline void* toInternalPointer(ArrayBufferView* impl)
{
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8ArrayBufferViewCustomScript.js b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8ArrayBufferViewCustomScript.js
deleted file mode 100644
index d3448599a90..00000000000
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8ArrayBufferViewCustomScript.js
+++ /dev/null
@@ -1,36 +0,0 @@
-/*
- * Copyright (C) 2011 Google Inc. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- * 1. Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * 2. Redistributions in binary form must reproduce the above copyright
- * notice, this list of conditions and the following disclaimer in the
- * documentation and/or other materials provided with the distribution.
- *
- * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS'' AND ANY
- * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
- * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
- * DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS BE LIABLE FOR ANY
- * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
- * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
- * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
- * ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
- * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-(function() {
- return function(source, length, offset) {
- if (offset == 0) {
- for (var i = 0; i < length; i++)
- this[i] = source[i];
- } else {
- for (var i = 0; i < length; i++)
- this[i + offset] = source[i];
- }
- }
-})();
-
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8AudioNodeCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8AudioNodeCustom.cpp
index fcc9d085027..762b58580fb 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8AudioNodeCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8AudioNodeCustom.cpp
@@ -24,25 +24,25 @@
#include "config.h"
#if ENABLE(WEB_AUDIO)
-#include "V8AudioNode.h"
+#include "bindings/modules/v8/V8AudioNode.h"
-#include "V8AnalyserNode.h"
-#include "V8AudioBufferSourceNode.h"
-#include "V8AudioDestinationNode.h"
-#include "V8BiquadFilterNode.h"
-#include "V8ChannelMergerNode.h"
-#include "V8ChannelSplitterNode.h"
-#include "V8ConvolverNode.h"
-#include "V8DelayNode.h"
-#include "V8DynamicsCompressorNode.h"
-#include "V8GainNode.h"
-#include "V8MediaElementAudioSourceNode.h"
-#include "V8MediaStreamAudioDestinationNode.h"
-#include "V8MediaStreamAudioSourceNode.h"
-#include "V8OscillatorNode.h"
-#include "V8PannerNode.h"
-#include "V8ScriptProcessorNode.h"
-#include "V8WaveShaperNode.h"
+#include "bindings/modules/v8/V8AnalyserNode.h"
+#include "bindings/modules/v8/V8AudioBufferSourceNode.h"
+#include "bindings/modules/v8/V8AudioDestinationNode.h"
+#include "bindings/modules/v8/V8BiquadFilterNode.h"
+#include "bindings/modules/v8/V8ChannelMergerNode.h"
+#include "bindings/modules/v8/V8ChannelSplitterNode.h"
+#include "bindings/modules/v8/V8ConvolverNode.h"
+#include "bindings/modules/v8/V8DelayNode.h"
+#include "bindings/modules/v8/V8DynamicsCompressorNode.h"
+#include "bindings/modules/v8/V8GainNode.h"
+#include "bindings/modules/v8/V8MediaElementAudioSourceNode.h"
+#include "bindings/modules/v8/V8MediaStreamAudioDestinationNode.h"
+#include "bindings/modules/v8/V8MediaStreamAudioSourceNode.h"
+#include "bindings/modules/v8/V8OscillatorNode.h"
+#include "bindings/modules/v8/V8PannerNode.h"
+#include "bindings/modules/v8/V8ScriptProcessorNode.h"
+#include "bindings/modules/v8/V8WaveShaperNode.h"
#include "bindings/v8/V8Binding.h"
#include "modules/webaudio/AnalyserNode.h"
#include "modules/webaudio/AudioBufferSourceNode.h"
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8BiquadFilterNodeCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8BiquadFilterNodeCustom.cpp
deleted file mode 100644
index 862d040c3b4..00000000000
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8BiquadFilterNodeCustom.cpp
+++ /dev/null
@@ -1,60 +0,0 @@
-/*
- * Copyright (C) 2012, Google Inc. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- * 1. Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * 2. Redistributions in binary form must reproduce the above copyright
- * notice, this list of conditions and the following disclaimer in the
- * documentation and/or other materials provided with the distribution.
- *
- * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS'' AND ANY
- * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
- * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
- * DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS BE LIABLE FOR ANY
- * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
- * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
- * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
- * ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
- * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-#include "config.h"
-#if ENABLE(WEB_AUDIO)
-#include "V8BiquadFilterNode.h"
-
-#include "bindings/v8/V8Binding.h"
-#include "modules/webaudio/BiquadFilterNode.h"
-
-namespace WebCore {
-
-void V8BiquadFilterNode::typeAttributeSetterCustom(v8::Local<v8::Value> value, const v8::PropertyCallbackInfo<void>& info)
-{
- BiquadFilterNode* imp = V8BiquadFilterNode::toNative(info.Holder());
-
- if (value->IsNumber()) {
- bool ok = false;
- uint32_t type = toUInt32(value, ok);
- ASSERT(ok);
- if (!imp->setType(type))
- throwTypeError("Illegal BiquadFilterNode type", info.GetIsolate());
- return;
- }
-
- if (value->IsString()) {
- String type = toCoreString(value.As<v8::String>());
- if (type == "lowpass" || type == "highpass" || type == "bandpass" || type == "lowshelf" || type == "highshelf" || type == "peaking" || type == "notch" || type == "allpass") {
- imp->setType(type);
- return;
- }
- }
-
- throwTypeError("Illegal BiquadFilterNode type", info.GetIsolate());
-}
-
-} // namespace WebCore
-
-#endif // ENABLE(WEB_AUDIO)
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8BlobCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8BlobCustom.cpp
index db9fbbb4295..594b9772cbd 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8BlobCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8BlobCustom.cpp
@@ -29,11 +29,10 @@
*/
#include "config.h"
-#include "V8Blob.h"
+#include "bindings/core/v8/V8Blob.h"
#include "bindings/v8/ExceptionState.h"
#include "bindings/v8/custom/V8BlobCustomHelpers.h"
-#include "core/fileapi/BlobBuilder.h"
namespace WebCore {
@@ -41,7 +40,7 @@ void V8Blob::constructorCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
ExceptionState exceptionState(ExceptionState::ConstructionContext, "Blob", info.Holder(), info.GetIsolate());
if (!info.Length()) {
- RefPtr<Blob> blob = Blob::create();
+ RefPtrWillBeRawPtr<Blob> blob = Blob::create();
v8SetReturnValue(info, blob.release());
return;
}
@@ -72,12 +71,14 @@ void V8Blob::constructorCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
}
}
- BlobBuilder blobBuilder;
+ OwnPtr<BlobData> blobData = BlobData::create();
+ blobData->setContentType(properties.contentType());
v8::Local<v8::Object> blobParts = v8::Local<v8::Object>::Cast(info[0]);
- if (!V8BlobCustomHelpers::processBlobParts(blobParts, length, properties.endings(), blobBuilder, info.GetIsolate()))
+ if (!V8BlobCustomHelpers::processBlobParts(blobParts, length, properties.normalizeLineEndingsToNative(), *blobData, info.GetIsolate()))
return;
- RefPtr<Blob> blob = blobBuilder.createBlob(properties.contentType());
+ long long blobSize = blobData->length();
+ RefPtrWillBeRawPtr<Blob> blob = Blob::create(BlobDataHandle::create(blobData.release(), blobSize));
v8SetReturnValue(info, blob.release());
}
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8BlobCustomHelpers.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8BlobCustomHelpers.cpp
index 62bdc36e7b2..e6ec3535ba6 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8BlobCustomHelpers.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8BlobCustomHelpers.cpp
@@ -29,16 +29,14 @@
*/
#include "config.h"
-#include "V8BlobCustomHelpers.h"
+#include "bindings/v8/custom/V8BlobCustomHelpers.h"
-#include "V8Blob.h"
+#include "bindings/core/v8/V8Blob.h"
#include "bindings/v8/Dictionary.h"
#include "bindings/v8/ExceptionState.h"
#include "bindings/v8/V8Binding.h"
-#include "bindings/v8/V8Utilities.h"
#include "bindings/v8/custom/V8ArrayBufferCustom.h"
#include "bindings/v8/custom/V8ArrayBufferViewCustom.h"
-#include "core/fileapi/BlobBuilder.h"
#include "wtf/DateMath.h"
namespace WebCore {
@@ -46,7 +44,7 @@ namespace WebCore {
namespace V8BlobCustomHelpers {
ParsedProperties::ParsedProperties(bool hasFileProperties)
- : m_endings("transparent")
+ : m_normalizeLineEndingsToNative(false)
, m_hasFileProperties(hasFileProperties)
#ifndef NDEBUG
, m_hasLastModified(false)
@@ -71,19 +69,20 @@ void ParsedProperties::setDefaultLastModified()
bool ParsedProperties::parseBlobPropertyBag(v8::Local<v8::Value> propertyBag, const char* blobClassName, ExceptionState& exceptionState, v8::Isolate* isolate)
{
- ASSERT(m_endings == "transparent");
+ TONATIVE_DEFAULT(Dictionary, dictionary, Dictionary(propertyBag, isolate), false);
- V8TRYCATCH_RETURN(Dictionary, dictionary, Dictionary(propertyBag, isolate), false);
-
- V8TRYCATCH_RETURN(bool, containsEndings, dictionary.get("endings", m_endings), false);
+ String endings;
+ TONATIVE_DEFAULT(bool, containsEndings, dictionary.get("endings", endings), false);
if (containsEndings) {
- if (m_endings != "transparent" && m_endings != "native") {
+ if (endings != "transparent" && endings != "native") {
exceptionState.throwTypeError("The 'endings' property must be either 'transparent' or 'native'.");
return false;
}
+ if (endings == "native")
+ m_normalizeLineEndingsToNative = true;
}
- V8TRYCATCH_RETURN(bool, containsType, dictionary.get("type", m_contentType), false);
+ TONATIVE_DEFAULT(bool, containsType, dictionary.get("type", m_contentType), false);
if (containsType) {
if (!m_contentType.containsOnlyASCII()) {
exceptionState.throwDOMException(SyntaxError, "The 'type' property must consist of ASCII characters.");
@@ -96,9 +95,9 @@ bool ParsedProperties::parseBlobPropertyBag(v8::Local<v8::Value> propertyBag, co
return true;
v8::Local<v8::Value> lastModified;
- V8TRYCATCH_RETURN(bool, containsLastModified, dictionary.get("lastModified", lastModified), false);
+ TONATIVE_DEFAULT(bool, containsLastModified, dictionary.get("lastModified", lastModified), false);
if (containsLastModified) {
- V8TRYCATCH_RETURN(long long, lastModifiedInt, toInt64(lastModified), false);
+ TONATIVE_DEFAULT(long long, lastModifiedInt, toInt64(lastModified), false);
setLastModified(static_cast<double>(lastModifiedInt) / msPerSecond);
} else {
setDefaultLastModified();
@@ -107,30 +106,28 @@ bool ParsedProperties::parseBlobPropertyBag(v8::Local<v8::Value> propertyBag, co
return true;
}
-bool processBlobParts(v8::Local<v8::Object> blobParts, uint32_t blobPartsLength, const String& endings, BlobBuilder& blobBuilder, v8::Isolate* isolate)
+bool processBlobParts(v8::Local<v8::Object> blobParts, uint32_t blobPartsLength, bool normalizeLineEndingsToNative, BlobData& blobData, v8::Isolate* isolate)
{
- ASSERT(endings == "transparent" || endings == "native");
-
for (uint32_t i = 0; i < blobPartsLength; ++i) {
- v8::Local<v8::Value> item = blobParts->Get(v8::Uint32::New(i, isolate));
+ v8::Local<v8::Value> item = blobParts->Get(v8::Uint32::New(isolate, i));
if (item.IsEmpty())
return false;
- if (V8ArrayBuffer::hasInstance(item, isolate, worldType(isolate))) {
+ if (V8ArrayBuffer::hasInstance(item, isolate)) {
ArrayBuffer* arrayBuffer = V8ArrayBuffer::toNative(v8::Handle<v8::Object>::Cast(item));
ASSERT(arrayBuffer);
- blobBuilder.append(arrayBuffer);
- } else if (V8ArrayBufferView::hasInstance(item, isolate, worldType(isolate))) {
+ blobData.appendArrayBuffer(arrayBuffer);
+ } else if (V8ArrayBufferView::hasInstance(item, isolate)) {
ArrayBufferView* arrayBufferView = V8ArrayBufferView::toNative(v8::Handle<v8::Object>::Cast(item));
ASSERT(arrayBufferView);
- blobBuilder.append(arrayBufferView);
- } else if (V8Blob::hasInstance(item, isolate, worldType(isolate))) {
+ blobData.appendArrayBufferView(arrayBufferView);
+ } else if (V8Blob::hasInstance(item, isolate)) {
Blob* blob = V8Blob::toNative(v8::Handle<v8::Object>::Cast(item));
ASSERT(blob);
- blobBuilder.append(blob);
+ blob->appendTo(blobData);
} else {
- V8TRYCATCH_FOR_V8STRINGRESOURCE_RETURN(V8StringResource<>, stringValue, item, false);
- blobBuilder.append(stringValue, endings);
+ TOSTRING_DEFAULT(V8StringResource<>, stringValue, item, false);
+ blobData.appendText(stringValue, normalizeLineEndingsToNative);
}
}
return true;
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8BlobCustomHelpers.h b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8BlobCustomHelpers.h
index 37a173120bb..93cc08dce79 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8BlobCustomHelpers.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8BlobCustomHelpers.h
@@ -35,7 +35,7 @@
namespace WebCore {
-class BlobBuilder;
+class BlobData;
class ExceptionState;
// Shared code between the custom constructor bindings for Blob and File.
@@ -53,7 +53,7 @@ public:
explicit ParsedProperties(bool hasFileProperties);
const String& contentType() const { return m_contentType; }
- const String& endings() const { return m_endings; }
+ bool normalizeLineEndingsToNative() const { return m_normalizeLineEndingsToNative; }
void setLastModified(double);
void setDefaultLastModified();
double lastModified() const
@@ -70,7 +70,7 @@ public:
private:
String m_contentType;
- String m_endings;
+ bool m_normalizeLineEndingsToNative;
// False if this contains the properties of a BlobPropertyBag.
bool m_hasFileProperties;
@@ -81,10 +81,10 @@ private:
#endif // NDEBUG
};
-// Appends the blobParts passed to a Blob or File constructor into a BlobBuilder.
+// Appends the blobParts passed to a Blob or File constructor into a BlobData.
// http://www.w3.org/TR/FileAPI/#constructorParams
// Returns true if everything went well, false if a JS exception was thrown.
-bool processBlobParts(v8::Local<v8::Object> blobParts, uint32_t blobPartsLength, const String& endings, BlobBuilder&, v8::Isolate*);
+bool processBlobParts(v8::Local<v8::Object> blobParts, uint32_t blobPartsLength, bool normalizeLineEndingsToNative, BlobData&, v8::Isolate*);
} // namespace V8BlobCustomHelpers
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8CSSRuleCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8CSSRuleCustom.cpp
index 0fbd080bbd4..4aff8aa4090 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8CSSRuleCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8CSSRuleCustom.cpp
@@ -29,20 +29,19 @@
*/
#include "config.h"
-#include "V8CSSRule.h"
+#include "bindings/core/v8/V8CSSRule.h"
-#include "V8CSSCharsetRule.h"
-#include "V8CSSFontFaceRule.h"
-#include "V8CSSImportRule.h"
-#include "V8CSSKeyframeRule.h"
-#include "V8CSSKeyframesRule.h"
-#include "V8CSSMediaRule.h"
-#include "V8CSSPageRule.h"
-#include "V8CSSStyleRule.h"
-#include "V8CSSSupportsRule.h"
-#include "V8CSSViewportRule.h"
-#include "V8WebKitCSSFilterRule.h"
-#include "V8WebKitCSSRegionRule.h"
+#include "bindings/core/v8/V8CSSCharsetRule.h"
+#include "bindings/core/v8/V8CSSFontFaceRule.h"
+#include "bindings/core/v8/V8CSSImportRule.h"
+#include "bindings/core/v8/V8CSSKeyframeRule.h"
+#include "bindings/core/v8/V8CSSKeyframesRule.h"
+#include "bindings/core/v8/V8CSSMediaRule.h"
+#include "bindings/core/v8/V8CSSPageRule.h"
+#include "bindings/core/v8/V8CSSStyleRule.h"
+#include "bindings/core/v8/V8CSSSupportsRule.h"
+#include "bindings/core/v8/V8CSSViewportRule.h"
+#include "bindings/core/v8/V8WebKitCSSFilterRule.h"
namespace WebCore {
@@ -52,7 +51,7 @@ v8::Handle<v8::Object> wrap(CSSRule* impl, v8::Handle<v8::Object> creationContex
switch (impl->type()) {
case CSSRule::UNKNOWN_RULE:
// CSSUnknownRule.idl is explicitly excluded as it doesn't add anything
- // over CSSRule.idl (see bindings/derived_sources.gyp: 'idl_files').
+ // over CSSRule.idl (see core/core.gypi: 'core_idl_files').
// -> Use the base class wrapper here.
return V8CSSRule::createWrapper(impl, creationContext, isolate);
case CSSRule::STYLE_RULE:
@@ -75,8 +74,6 @@ v8::Handle<v8::Object> wrap(CSSRule* impl, v8::Handle<v8::Object> creationContex
return wrap(toCSSSupportsRule(impl), creationContext, isolate);
case CSSRule::VIEWPORT_RULE:
return wrap(toCSSViewportRule(impl), creationContext, isolate);
- case CSSRule::WEBKIT_REGION_RULE:
- return wrap(toCSSRegionRule(impl), creationContext, isolate);
case CSSRule::WEBKIT_FILTER_RULE:
return wrap(toCSSFilterRule(impl), creationContext, isolate);
}
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8CSSStyleDeclarationCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8CSSStyleDeclarationCustom.cpp
index 6d118a383c3..c7f3d7ab009 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8CSSStyleDeclarationCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8CSSStyleDeclarationCustom.cpp
@@ -29,12 +29,12 @@
*/
#include "config.h"
-#include "V8CSSStyleDeclaration.h"
+#include "bindings/core/v8/V8CSSStyleDeclaration.h"
-#include "CSSPropertyNames.h"
#include "bindings/v8/ExceptionState.h"
#include "bindings/v8/V8Binding.h"
-#include "core/css/CSSParser.h"
+#include "core/CSSPropertyNames.h"
+#include "core/css/parser/BisonCSSParser.h"
#include "core/css/CSSPrimitiveValue.h"
#include "core/css/CSSStyleDeclaration.h"
#include "core/css/CSSValue.h"
@@ -49,7 +49,6 @@
#include "wtf/text/StringConcatenate.h"
using namespace WTF;
-using namespace std;
namespace WebCore {
@@ -81,17 +80,51 @@ static bool hasCSSPropertyNamePrefix(const String& propertyName, const char* pre
}
struct CSSPropertyInfo {
- unsigned propID: 30; // CSSPropertyID
- unsigned nameWithDash: 1;
- unsigned nameWithCssPrefix: 1;
+ CSSPropertyID propID;
};
-static inline void countCssPropertyInfoUsage(const CSSPropertyInfo& propInfo)
+static CSSPropertyID cssResolvedPropertyID(const String& propertyName)
{
- if (propInfo.nameWithDash)
- UseCounter::count(activeDOMWindow(), UseCounter::CSSStyleDeclarationPropertyName);
- if (propInfo.propID == CSSPropertyFloat && !propInfo.nameWithCssPrefix)
- UseCounter::count(activeDOMWindow(), UseCounter::CSSStyleDeclarationFloatPropertyName);
+ unsigned length = propertyName.length();
+ if (!length)
+ return CSSPropertyInvalid;
+
+ StringBuilder builder;
+ builder.reserveCapacity(length);
+
+ unsigned i = 0;
+ bool hasSeenDash = false;
+
+ if (hasCSSPropertyNamePrefix(propertyName, "css"))
+ i += 3;
+ else if (hasCSSPropertyNamePrefix(propertyName, "webkit"))
+ builder.append('-');
+ else if (isASCIIUpper(propertyName[0]))
+ return CSSPropertyInvalid;
+
+ bool hasSeenUpper = isASCIIUpper(propertyName[i]);
+
+ builder.append(toASCIILower(propertyName[i++]));
+
+ for (; i < length; ++i) {
+ UChar c = propertyName[i];
+ if (!isASCIIUpper(c)) {
+ if (c == '-')
+ hasSeenDash = true;
+ builder.append(c);
+ } else {
+ hasSeenUpper = true;
+ builder.append('-');
+ builder.append(toASCIILower(c));
+ }
+ }
+
+ // Reject names containing both dashes and upper-case characters, such as "border-rightColor".
+ if (hasSeenDash && hasSeenUpper)
+ return CSSPropertyInvalid;
+
+ String propName = builder.toString();
+ return cssPropertyID(propName);
}
// When getting properties on CSSStyleDeclarations, the name used from
@@ -110,52 +143,13 @@ static CSSPropertyInfo* cssPropertyInfo(v8::Handle<v8::String> v8PropertyName)
DEFINE_STATIC_LOCAL(CSSPropertyInfoMap, map, ());
CSSPropertyInfo* propInfo = map.get(propertyName);
if (!propInfo) {
- unsigned length = propertyName.length();
- if (!length)
- return 0;
-
- StringBuilder builder;
- builder.reserveCapacity(length);
-
- unsigned i = 0;
- bool hasSeenDash = false;
- bool hasSeenCssPrefix = false;
-
- if (hasCSSPropertyNamePrefix(propertyName, "css")) {
- hasSeenCssPrefix = true;
- i += 3;
- } else if (hasCSSPropertyNamePrefix(propertyName, "webkit")) {
- builder.append('-');
- } else if (isASCIIUpper(propertyName[0])) {
- return 0;
- }
-
- builder.append(toASCIILower(propertyName[i++]));
-
- for (; i < length; ++i) {
- UChar c = propertyName[i];
- if (!isASCIIUpper(c)) {
- if (c == '-')
- hasSeenDash = true;
- builder.append(c);
- }
- else {
- builder.append('-');
- builder.append(toASCIILower(c));
- }
- }
-
- String propName = builder.toString();
- CSSPropertyID propertyID = cssPropertyID(propName);
- if (propertyID && RuntimeCSSEnabled::isCSSPropertyEnabled(propertyID)) {
- propInfo = new CSSPropertyInfo();
- propInfo->propID = propertyID;
- propInfo->nameWithDash = hasSeenDash;
- propInfo->nameWithCssPrefix = hasSeenCssPrefix;
- map.add(propertyName, propInfo);
- }
+ propInfo = new CSSPropertyInfo();
+ propInfo->propID = cssResolvedPropertyID(propertyName);
+ map.add(propertyName, propInfo);
}
- return propInfo;
+ if (propInfo->propID && RuntimeCSSEnabled::isCSSPropertyEnabled(propInfo->propID))
+ return propInfo;
+ return 0;
}
void V8CSSStyleDeclaration::namedPropertyEnumeratorCustom(const v8::PropertyCallbackInfo<v8::Array>& info)
@@ -170,7 +164,7 @@ void V8CSSStyleDeclaration::namedPropertyEnumeratorCustom(const v8::PropertyCall
if (RuntimeCSSEnabled::isCSSPropertyEnabled(propertyId))
propertyNames.append(getJSPropertyName(propertyId));
}
- sort(propertyNames.begin(), propertyNames.end(), codePointCompareLessThan);
+ std::sort(propertyNames.begin(), propertyNames.end(), codePointCompareLessThan);
propertyNamesLength = propertyNames.size();
}
@@ -178,7 +172,7 @@ void V8CSSStyleDeclaration::namedPropertyEnumeratorCustom(const v8::PropertyCall
for (unsigned i = 0; i < propertyNamesLength; ++i) {
String key = propertyNames.at(i);
ASSERT(!key.isNull());
- properties->Set(v8::Integer::New(i, info.GetIsolate()), v8String(info.GetIsolate(), key));
+ properties->Set(v8::Integer::New(info.GetIsolate(), i), v8String(info.GetIsolate(), key));
}
v8SetReturnValue(info, properties);
@@ -188,8 +182,7 @@ void V8CSSStyleDeclaration::namedPropertyQueryCustom(v8::Local<v8::String> v8Nam
{
// NOTE: cssPropertyInfo lookups incur several mallocs.
// Successful lookups have the same cost the first time, but are cached.
- if (CSSPropertyInfo* propInfo = cssPropertyInfo(v8Name)) {
- countCssPropertyInfoUsage(*propInfo);
+ if (cssPropertyInfo(v8Name)) {
v8SetReturnValueInt(info, 0);
return;
}
@@ -208,32 +201,27 @@ void V8CSSStyleDeclaration::namedPropertyGetterCustom(v8::Local<v8::String> name
if (!propInfo)
return;
- countCssPropertyInfoUsage(*propInfo);
- CSSStyleDeclaration* imp = V8CSSStyleDeclaration::toNative(info.Holder());
- RefPtr<CSSValue> cssValue = imp->getPropertyCSSValueInternal(static_cast<CSSPropertyID>(propInfo->propID));
+ CSSStyleDeclaration* impl = V8CSSStyleDeclaration::toNative(info.Holder());
+ RefPtrWillBeRawPtr<CSSValue> cssValue = impl->getPropertyCSSValueInternal(static_cast<CSSPropertyID>(propInfo->propID));
if (cssValue) {
v8SetReturnValueStringOrNull(info, cssValue->cssText(), info.GetIsolate());
return;
}
- String result = imp->getPropertyValueInternal(static_cast<CSSPropertyID>(propInfo->propID));
- if (result.isNull())
- result = ""; // convert null to empty string.
-
+ String result = impl->getPropertyValueInternal(static_cast<CSSPropertyID>(propInfo->propID));
v8SetReturnValueString(info, result, info.GetIsolate());
}
void V8CSSStyleDeclaration::namedPropertySetterCustom(v8::Local<v8::String> name, v8::Local<v8::Value> value, const v8::PropertyCallbackInfo<v8::Value>& info)
{
- CSSStyleDeclaration* imp = V8CSSStyleDeclaration::toNative(info.Holder());
+ CSSStyleDeclaration* impl = V8CSSStyleDeclaration::toNative(info.Holder());
CSSPropertyInfo* propInfo = cssPropertyInfo(name);
if (!propInfo)
return;
- countCssPropertyInfoUsage(*propInfo);
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<WithNullCheck>, propertyValue, value);
+ TOSTRING_VOID(V8StringResource<WithNullCheck>, propertyValue, value);
ExceptionState exceptionState(ExceptionState::SetterContext, getPropertyName(static_cast<CSSPropertyID>(propInfo->propID)), "CSSStyleDeclaration", info.Holder(), info.GetIsolate());
- imp->setPropertyInternal(static_cast<CSSPropertyID>(propInfo->propID), propertyValue, false, exceptionState);
+ impl->setPropertyInternal(static_cast<CSSPropertyID>(propInfo->propID), propertyValue, false, exceptionState);
if (exceptionState.throwIfNeeded())
return;
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8CSSValueCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8CSSValueCustom.cpp
index 3db5c35477c..44dc8e69ab8 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8CSSValueCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8CSSValueCustom.cpp
@@ -29,16 +29,12 @@
*/
#include "config.h"
-#include "V8CSSValue.h"
+#include "bindings/core/v8/V8CSSValue.h"
-#include "V8CSSPrimitiveValue.h"
-#include "V8CSSValueList.h"
-#include "V8SVGColor.h"
-#include "V8SVGPaint.h"
-#include "V8WebKitCSSFilterValue.h"
-#include "V8WebKitCSSMixFunctionValue.h"
-#include "V8WebKitCSSTransformValue.h"
-#include "core/css/CSSMixFunctionValue.h"
+#include "bindings/core/v8/V8CSSPrimitiveValue.h"
+#include "bindings/core/v8/V8CSSValueList.h"
+#include "bindings/core/v8/V8WebKitCSSFilterValue.h"
+#include "bindings/core/v8/V8WebKitCSSTransformValue.h"
namespace WebCore {
@@ -47,18 +43,12 @@ v8::Handle<v8::Object> wrap(CSSValue* impl, v8::Handle<v8::Object> creationConte
ASSERT(impl);
if (impl->isTransformValue())
return wrap(toCSSTransformValue(impl), creationContext, isolate);
- if (impl->isMixFunctionValue())
- return wrap(toCSSMixFunctionValue(impl), creationContext, isolate);
if (impl->isFilterValue())
return wrap(toCSSFilterValue(impl), creationContext, isolate);
if (impl->isValueList())
return wrap(toCSSValueList(impl), creationContext, isolate);
if (impl->isPrimitiveValue())
return wrap(toCSSPrimitiveValue(impl), creationContext, isolate);
- if (impl->isSVGPaint())
- return wrap(toSVGPaint(impl), creationContext, isolate);
- if (impl->isSVGColor())
- return wrap(toSVGColor(impl), creationContext, isolate);
return V8CSSValue::createWrapper(impl, creationContext, isolate);
}
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8CanvasRenderingContext2DCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8CanvasRenderingContext2DCustom.cpp
index 3e13d83e57e..d9d036df3cc 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8CanvasRenderingContext2DCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8CanvasRenderingContext2DCustom.cpp
@@ -29,14 +29,14 @@
*/
#include "config.h"
-#include "V8CanvasRenderingContext2D.h"
+#include "bindings/core/v8/V8CanvasRenderingContext2D.h"
-#include "V8CanvasGradient.h"
-#include "V8CanvasPattern.h"
-#include "V8HTMLCanvasElement.h"
-#include "V8HTMLImageElement.h"
-#include "V8HTMLVideoElement.h"
-#include "V8ImageData.h"
+#include "bindings/core/v8/V8CanvasGradient.h"
+#include "bindings/core/v8/V8CanvasPattern.h"
+#include "bindings/core/v8/V8HTMLCanvasElement.h"
+#include "bindings/core/v8/V8HTMLImageElement.h"
+#include "bindings/core/v8/V8HTMLVideoElement.h"
+#include "bindings/core/v8/V8ImageData.h"
#include "bindings/v8/V8Binding.h"
#include "core/html/canvas/CanvasGradient.h"
#include "core/html/canvas/CanvasPattern.h"
@@ -59,13 +59,10 @@ static v8::Handle<v8::Value> toV8Object(CanvasStyle* style, v8::Handle<v8::Objec
static PassRefPtr<CanvasStyle> toCanvasStyle(v8::Handle<v8::Value> value, v8::Isolate* isolate)
{
- if (V8CanvasGradient::hasInstance(value, isolate, worldType(isolate)))
- return CanvasStyle::createFromGradient(V8CanvasGradient::toNative(v8::Handle<v8::Object>::Cast(value)));
-
- if (V8CanvasPattern::hasInstance(value, isolate, worldType(isolate)))
- return CanvasStyle::createFromPattern(V8CanvasPattern::toNative(v8::Handle<v8::Object>::Cast(value)));
-
- return 0;
+ RefPtr<CanvasStyle> canvasStyle = CanvasStyle::createFromGradient(V8CanvasGradient::toNativeWithTypeCheck(isolate, value));
+ if (canvasStyle)
+ return canvasStyle;
+ return CanvasStyle::createFromPattern(V8CanvasPattern::toNativeWithTypeCheck(isolate, value));
}
void V8CanvasRenderingContext2D::strokeStyleAttributeGetterCustom(const v8::PropertyCallbackInfo<v8::Value>& info)
@@ -77,10 +74,12 @@ void V8CanvasRenderingContext2D::strokeStyleAttributeGetterCustom(const v8::Prop
void V8CanvasRenderingContext2D::strokeStyleAttributeSetterCustom(v8::Local<v8::Value> value, const v8::PropertyCallbackInfo<void>& info)
{
CanvasRenderingContext2D* impl = V8CanvasRenderingContext2D::toNative(info.Holder());
- if (value->IsString())
- impl->setStrokeColor(toCoreString(value.As<v8::String>()));
- else
- impl->setStrokeStyle(toCanvasStyle(value, info.GetIsolate()));
+ if (RefPtr<CanvasStyle> canvasStyle = toCanvasStyle(value, info.GetIsolate())) {
+ impl->setStrokeStyle(canvasStyle);
+ } else {
+ TOSTRING_VOID(V8StringResource<>, colorString, value);
+ impl->setStrokeColor(colorString);
+ }
}
void V8CanvasRenderingContext2D::fillStyleAttributeGetterCustom(const v8::PropertyCallbackInfo<v8::Value>& info)
@@ -92,10 +91,12 @@ void V8CanvasRenderingContext2D::fillStyleAttributeGetterCustom(const v8::Proper
void V8CanvasRenderingContext2D::fillStyleAttributeSetterCustom(v8::Local<v8::Value> value, const v8::PropertyCallbackInfo<void>& info)
{
CanvasRenderingContext2D* impl = V8CanvasRenderingContext2D::toNative(info.Holder());
- if (value->IsString())
- impl->setFillColor(toCoreString(value.As<v8::String>()));
- else
- impl->setFillStyle(toCanvasStyle(value, info.GetIsolate()));
+ if (RefPtr<CanvasStyle> canvasStyle = toCanvasStyle(value, info.GetIsolate())) {
+ impl->setFillStyle(canvasStyle);
+ } else {
+ TOSTRING_VOID(V8StringResource<>, colorString, value);
+ impl->setFillColor(colorString);
+ }
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8CanvasRenderingContextCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8CanvasRenderingContextCustom.cpp
deleted file mode 100644
index 66a73c48541..00000000000
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8CanvasRenderingContextCustom.cpp
+++ /dev/null
@@ -1,51 +0,0 @@
-/*
- * Copyright (C) 2007-2009 Google Inc. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions are
- * met:
- *
- * * Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * * Redistributions in binary form must reproduce the above
- * copyright notice, this list of conditions and the following disclaimer
- * in the documentation and/or other materials provided with the
- * distribution.
- * * Neither the name of Google Inc. nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
- * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
- * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
- * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
- * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
- * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
- * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
- * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
- * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-#include "config.h"
-#include "V8CanvasRenderingContext.h"
-
-#include "V8CanvasRenderingContext2D.h"
-#include "V8WebGLRenderingContext.h"
-#include "core/html/canvas/CanvasRenderingContext.h"
-
-namespace WebCore {
-
-v8::Handle<v8::Object> wrap(CanvasRenderingContext* impl, v8::Handle<v8::Object> creationContext, v8::Isolate* isolate)
-{
- ASSERT(impl);
- if (impl->is2d())
- return wrap(toCanvasRenderingContext2D(impl), creationContext, isolate);
- if (impl->is3d())
- return wrap(toWebGLRenderingContext(impl), creationContext, isolate);
- ASSERT_NOT_REACHED();
- return v8::Handle<v8::Object>();
-}
-
-} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8ClientCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8ClientCustom.cpp
new file mode 100644
index 00000000000..b7975759511
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8ClientCustom.cpp
@@ -0,0 +1,39 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "config.h"
+#include "bindings/modules/v8/V8Client.h"
+
+#include "bindings/v8/ExceptionMessages.h"
+#include "bindings/v8/ExceptionState.h"
+#include "bindings/v8/SerializedScriptValue.h"
+#include "bindings/v8/V8Binding.h"
+#include "core/dom/MessagePort.h"
+#include "modules/serviceworkers/ServiceWorker.h"
+#include "wtf/ArrayBuffer.h"
+
+namespace WebCore {
+
+void V8Client::postMessageMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
+{
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "postMessage", "ServiceWorker", info.Holder(), info.GetIsolate());
+ Client* client = V8Client::toNative(info.Holder());
+ MessagePortArray ports;
+ ArrayBufferArray arrayBuffers;
+ if (info.Length() > 1) {
+ const int transferablesArgIndex = 1;
+ if (!SerializedScriptValue::extractTransferables(info[transferablesArgIndex], transferablesArgIndex, ports, arrayBuffers, exceptionState, info.GetIsolate())) {
+ exceptionState.throwIfNeeded();
+ return;
+ }
+ }
+ RefPtr<SerializedScriptValue> message = SerializedScriptValue::create(info[0], &ports, &arrayBuffers, exceptionState, info.GetIsolate());
+ if (exceptionState.throwIfNeeded())
+ return;
+ ExecutionContext* context = currentExecutionContext(info.GetIsolate());
+ client->postMessage(context, message.release(), &ports, exceptionState);
+ exceptionState.throwIfNeeded();
+}
+
+} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8CryptoCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8CryptoCustom.cpp
index d183e31f9f5..d69042811c2 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8CryptoCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8CryptoCustom.cpp
@@ -23,12 +23,11 @@
*/
#include "config.h"
-#include "V8Crypto.h"
+#include "bindings/modules/v8/V8Crypto.h"
#include "bindings/v8/ExceptionMessages.h"
#include "bindings/v8/ExceptionState.h"
#include "bindings/v8/V8Binding.h"
-#include "bindings/v8/V8Utilities.h"
#include "bindings/v8/custom/V8ArrayBufferViewCustom.h"
#include "core/dom/ExceptionCode.h"
#include "modules/crypto/Crypto.h"
@@ -36,9 +35,6 @@
namespace WebCore {
-// This custom binding is shared by V8WorkerCrypto. As such:
-// * Do not call V8Crypto::toNative()
-// * Must be threadsafe
void V8Crypto::getRandomValuesMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
ExceptionState exceptionState(ExceptionState::ExecutionContext, "getRandomValues", "Crypto", info.Holder(), info.GetIsolate());
@@ -49,13 +45,14 @@ void V8Crypto::getRandomValuesMethodCustom(const v8::FunctionCallbackInfo<v8::Va
}
v8::Handle<v8::Value> buffer = info[0];
- if (!V8ArrayBufferView::hasInstance(buffer, info.GetIsolate(), worldType(info.GetIsolate()))) {
+ if (!V8ArrayBufferView::hasInstance(buffer, info.GetIsolate())) {
exceptionState.throwTypeError("First argument is not an ArrayBufferView");
} else {
ArrayBufferView* arrayBufferView = V8ArrayBufferView::toNative(v8::Handle<v8::Object>::Cast(buffer));
ASSERT(arrayBufferView);
- Crypto::getRandomValues(arrayBufferView, exceptionState);
+ Crypto* crypto = V8Crypto::toNative(info.Holder());
+ crypto->getRandomValues(arrayBufferView, exceptionState);
}
if (exceptionState.throwIfNeeded())
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8CustomEventCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8CustomEventCustom.cpp
index 143f0cac326..f0ef6e4d600 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8CustomEventCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8CustomEventCustom.cpp
@@ -29,23 +29,22 @@
*/
#include "config.h"
-#include "V8CustomEvent.h"
+#include "bindings/core/v8/V8CustomEvent.h"
-#include "RuntimeEnabledFeatures.h"
-#include "V8Event.h"
+#include "bindings/core/v8/V8Event.h"
#include "bindings/v8/Dictionary.h"
-#include "bindings/v8/ScriptState.h"
#include "bindings/v8/SerializedScriptValue.h"
#include "bindings/v8/V8Binding.h"
#include "bindings/v8/V8DOMWrapper.h"
-#include "bindings/v8/V8HiddenPropertyName.h"
+#include "bindings/v8/V8HiddenValue.h"
#include "core/dom/ContextFeatures.h"
+#include "platform/RuntimeEnabledFeatures.h"
namespace WebCore {
static v8::Handle<v8::Value> cacheState(v8::Handle<v8::Object> customEvent, v8::Handle<v8::Value> detail, v8::Isolate* isolate)
{
- customEvent->SetHiddenValue(V8HiddenPropertyName::detail(isolate), detail);
+ V8HiddenValue::setHiddenValue(isolate, customEvent, V8HiddenValue::detail(isolate), detail);
return detail;
}
@@ -54,7 +53,7 @@ void V8CustomEvent::detailAttributeGetterCustom(const v8::PropertyCallbackInfo<v
{
CustomEvent* event = V8CustomEvent::toNative(info.Holder());
- v8::Handle<v8::Value> result = info.Holder()->GetHiddenValue(V8HiddenPropertyName::detail(info.GetIsolate()));
+ v8::Handle<v8::Value> result = V8HiddenValue::getHiddenValue(info.GetIsolate(), info.Holder(), V8HiddenValue::detail(info.GetIsolate()));
if (!result.IsEmpty()) {
v8SetReturnValue(info, result);
@@ -64,7 +63,7 @@ void V8CustomEvent::detailAttributeGetterCustom(const v8::PropertyCallbackInfo<v
if (!event->serializedDetail()) {
// If we're in an isolated world and the event was created in the main world,
// we need to find the 'detail' property on the main world wrapper and clone it.
- v8::Local<v8::Value> mainWorldDetail = getHiddenValueFromMainWorldWrapper(info.GetIsolate(), event, V8HiddenPropertyName::detail(info.GetIsolate()));
+ v8::Local<v8::Value> mainWorldDetail = V8HiddenValue::getHiddenValueFromMainWorldWrapper(info.GetIsolate(), event, V8HiddenValue::detail(info.GetIsolate()));
if (!mainWorldDetail.IsEmpty())
event->setSerializedDetail(SerializedScriptValue::createAndSwallowExceptions(mainWorldDetail, info.GetIsolate()));
}
@@ -83,16 +82,16 @@ void V8CustomEvent::initCustomEventMethodCustom(const v8::FunctionCallbackInfo<v
CustomEvent* event = V8CustomEvent::toNative(info.Holder());
ASSERT(!event->serializedDetail());
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<>, typeArg, info[0]);
- V8TRYCATCH_VOID(bool, canBubbleArg, info[1]->BooleanValue());
- V8TRYCATCH_VOID(bool, cancelableArg, info[2]->BooleanValue());
+ TOSTRING_VOID(V8StringResource<>, typeArg, info[0]);
+ TONATIVE_VOID(bool, canBubbleArg, info[1]->BooleanValue());
+ TONATIVE_VOID(bool, cancelableArg, info[2]->BooleanValue());
v8::Handle<v8::Value> detailsArg = info[3];
event->initEvent(typeArg, canBubbleArg, cancelableArg);
if (!detailsArg.IsEmpty()) {
- info.Holder()->SetHiddenValue(V8HiddenPropertyName::detail(info.GetIsolate()), detailsArg);
- if (isolatedWorldForIsolate(info.GetIsolate()))
+ V8HiddenValue::setHiddenValue(info.GetIsolate(), info.Holder(), V8HiddenValue::detail(info.GetIsolate()), detailsArg);
+ if (DOMWrapperWorld::current(info.GetIsolate()).isIsolatedWorld())
event->setSerializedDetail(SerializedScriptValue::createAndSwallowExceptions(detailsArg, info.GetIsolate()));
}
}
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8CustomSQLStatementErrorCallback.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8CustomSQLStatementErrorCallback.cpp
index fc597c11034..0f411122352 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8CustomSQLStatementErrorCallback.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8CustomSQLStatementErrorCallback.cpp
@@ -29,10 +29,10 @@
*/
#include "config.h"
-#include "V8SQLStatementErrorCallback.h"
-#include "V8SQLError.h"
-#include "V8SQLTransaction.h"
+#include "bindings/modules/v8/V8SQLError.h"
+#include "bindings/modules/v8/V8SQLStatementErrorCallback.h"
+#include "bindings/modules/v8/V8SQLTransaction.h"
#include "bindings/v8/ScriptController.h"
#include "core/dom/ExecutionContext.h"
#include "wtf/Assertions.h"
@@ -44,23 +44,22 @@ bool V8SQLStatementErrorCallback::handleEvent(SQLTransaction* transaction, SQLEr
if (!canInvokeCallback())
return true;
- v8::Isolate* isolate = v8::Isolate::GetCurrent();
- v8::HandleScope handleScope(isolate);
-
- v8::Handle<v8::Context> v8Context = toV8Context(executionContext(), m_world.get());
- if (v8Context.IsEmpty())
+ v8::Isolate* isolate = m_scriptState->isolate();
+ if (m_scriptState->contextIsEmpty())
return true;
- v8::Context::Scope scope(v8Context);
+ ScriptState::Scope scope(m_scriptState.get());
- v8::Handle<v8::Value> transactionHandle = toV8(transaction, v8::Handle<v8::Object>(), v8Context->GetIsolate());
- v8::Handle<v8::Value> errorHandle = toV8(error, v8::Handle<v8::Object>(), isolate);
+ v8::Handle<v8::Value> transactionHandle = toV8(transaction, m_scriptState->context()->Global(), isolate);
+ v8::Handle<v8::Value> errorHandle = toV8(error, m_scriptState->context()->Global(), isolate);
if (transactionHandle.IsEmpty() || errorHandle.IsEmpty()) {
if (!isScriptControllerTerminating())
CRASH();
return true;
}
+ ASSERT(transactionHandle->IsObject());
+
v8::Handle<v8::Value> argv[] = {
transactionHandle,
errorHandle
@@ -69,7 +68,7 @@ bool V8SQLStatementErrorCallback::handleEvent(SQLTransaction* transaction, SQLEr
v8::TryCatch exceptionCatcher;
exceptionCatcher.SetVerbose(true);
- v8::Handle<v8::Value> result = ScriptController::callFunction(executionContext(), m_callback.newLocal(isolate), isolate->GetCurrentContext()->Global(), 2, argv, isolate);
+ v8::Handle<v8::Value> result = ScriptController::callFunction(executionContext(), m_callback.newLocal(isolate), m_scriptState->context()->Global(), WTF_ARRAY_LENGTH(argv), argv, isolate);
// FIXME: This comment doesn't make much sense given what the code is actually doing.
//
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8CustomXPathNSResolver.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8CustomXPathNSResolver.cpp
index f2c4d730d24..6331ef1bf99 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8CustomXPathNSResolver.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8CustomXPathNSResolver.cpp
@@ -32,20 +32,19 @@
#include "bindings/v8/ScriptController.h"
#include "bindings/v8/V8Binding.h"
-#include "bindings/v8/V8Utilities.h"
#include "core/dom/ExecutionContext.h"
+#include "core/frame/LocalDOMWindow.h"
+#include "core/frame/FrameConsole.h"
+#include "core/frame/FrameHost.h"
+#include "core/frame/LocalFrame.h"
#include "core/inspector/ScriptCallStack.h"
-#include "core/frame/DOMWindow.h"
-#include "core/frame/Frame.h"
-#include "core/page/Page.h"
-#include "core/page/PageConsole.h"
#include "wtf/text/WTFString.h"
namespace WebCore {
-PassRefPtr<V8CustomXPathNSResolver> V8CustomXPathNSResolver::create(v8::Handle<v8::Object> resolver, v8::Isolate* isolate)
+PassRefPtrWillBeRawPtr<V8CustomXPathNSResolver> V8CustomXPathNSResolver::create(v8::Handle<v8::Object> resolver, v8::Isolate* isolate)
{
- return adoptRef(new V8CustomXPathNSResolver(resolver, isolate));
+ return adoptRefWillBeNoop(new V8CustomXPathNSResolver(resolver, isolate));
}
V8CustomXPathNSResolver::V8CustomXPathNSResolver(v8::Handle<v8::Object> resolver, v8::Isolate* isolate)
@@ -71,9 +70,9 @@ AtomicString V8CustomXPathNSResolver::lookupNamespaceURI(const String& prefix)
}
if (lookupNamespaceURIFunc.IsEmpty() && !m_resolver->IsFunction()) {
- Frame* frame = activeDOMWindow()->frame();
- if (frame && frame->page())
- frame->page()->console().addMessage(JSMessageSource, ErrorMessageLevel, "XPathNSResolver does not have a lookupNamespaceURI method.");
+ LocalFrame* frame = callingDOMWindow(m_isolate)->frame();
+ if (frame && frame->host())
+ frame->console().addMessage(JSMessageSource, ErrorMessageLevel, "XPathNSResolver does not have a lookupNamespaceURI method.");
return nullAtom;
}
@@ -85,14 +84,19 @@ AtomicString V8CustomXPathNSResolver::lookupNamespaceURI(const String& prefix)
v8::Handle<v8::Value> argv[argc] = { v8String(m_isolate, prefix) };
v8::Handle<v8::Function> function = lookupNamespaceURIFunc.IsEmpty() ? v8::Handle<v8::Function>::Cast(m_resolver) : lookupNamespaceURIFunc;
- v8::Handle<v8::Value> retval = ScriptController::callFunction(activeExecutionContext(), function, m_resolver, argc, argv, m_isolate);
+ v8::Handle<v8::Value> retval = ScriptController::callFunction(callingExecutionContext(m_isolate), function, m_resolver, argc, argv, m_isolate);
// Eat exceptions from namespace resolver and return an empty string. This will most likely cause NamespaceError.
if (tryCatch.HasCaught())
return nullAtom;
- V8TRYCATCH_FOR_V8STRINGRESOURCE_RETURN(V8StringResource<WithNullCheck>, returnString, retval, nullAtom);
+ TOSTRING_DEFAULT(V8StringResource<WithNullCheck>, returnString, retval, nullAtom);
return returnString;
}
+void V8CustomXPathNSResolver::trace(Visitor* visitor)
+{
+ XPathNSResolver::trace(visitor);
+}
+
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8CustomXPathNSResolver.h b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8CustomXPathNSResolver.h
index aa3e01a243d..4c6712bb9f3 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8CustomXPathNSResolver.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8CustomXPathNSResolver.h
@@ -42,13 +42,15 @@ namespace WebCore {
// V8CustomXPathNSResolver does not create a persistent handle to the
// given resolver object. So the lifetime of V8CustomXPathNSResolver
// must not exceed the lifetime of the passed handle.
-class V8CustomXPathNSResolver : public XPathNSResolver {
+class V8CustomXPathNSResolver FINAL : public XPathNSResolver {
public:
- static PassRefPtr<V8CustomXPathNSResolver> create(v8::Handle<v8::Object> resolver, v8::Isolate*);
+ static PassRefPtrWillBeRawPtr<V8CustomXPathNSResolver> create(v8::Handle<v8::Object> resolver, v8::Isolate*);
virtual ~V8CustomXPathNSResolver();
virtual AtomicString lookupNamespaceURI(const String& prefix) OVERRIDE;
+ virtual void trace(Visitor*) OVERRIDE;
+
private:
V8CustomXPathNSResolver(v8::Handle<v8::Object> resolver, v8::Isolate*);
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8DataViewCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8DataViewCustom.cpp
index 73efbd69ad4..3d7572ca3ca 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8DataViewCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8DataViewCustom.cpp
@@ -35,7 +35,7 @@ namespace WebCore {
static void initializeScriptWrappableForInterface(DataView* object)
{
if (ScriptWrappable::wrapperCanBeStoredInObject(object))
- ScriptWrappable::setTypeInfoInObject(object, &V8DataView::wrapperTypeInfo);
+ ScriptWrappable::fromObject(object)->setTypeInfo(&V8DataView::wrapperTypeInfo);
else
ASSERT_NOT_REACHED();
}
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8DataViewCustom.h b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8DataViewCustom.h
index 502c010fe46..6459cbdd6e2 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8DataViewCustom.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8DataViewCustom.h
@@ -59,10 +59,6 @@ public:
typedef V8TypedArray<DataView> V8DataView;
-template<>
-class WrapperTypeTraits<DataView> : public TypedArrayWrapperTraits<DataView> { };
-
-
inline v8::Handle<v8::Object> wrap(DataView* impl, v8::Handle<v8::Object> creationContext, v8::Isolate* isolate)
{
return V8TypedArray<DataView>::wrap(impl, creationContext, isolate);
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8DedicatedWorkerGlobalScopeCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8DedicatedWorkerGlobalScopeCustom.cpp
index a356f03e4fe..b95c50747e7 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8DedicatedWorkerGlobalScopeCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8DedicatedWorkerGlobalScopeCustom.cpp
@@ -29,13 +29,12 @@
*/
#include "config.h"
-#include "V8DedicatedWorkerGlobalScope.h"
+#include "bindings/core/v8/V8DedicatedWorkerGlobalScope.h"
#include "bindings/v8/ExceptionMessages.h"
#include "bindings/v8/ExceptionState.h"
#include "bindings/v8/SerializedScriptValue.h"
#include "bindings/v8/V8Binding.h"
-#include "bindings/v8/V8Utilities.h"
#include "bindings/v8/V8WorkerGlobalScopeEventListener.h"
#include "core/workers/DedicatedWorkerGlobalScope.h"
#include "wtf/ArrayBuffer.h"
@@ -44,23 +43,21 @@ namespace WebCore {
void V8DedicatedWorkerGlobalScope::postMessageMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "postMessage", "WorkerGlobalScope", info.Holder(), info.GetIsolate());
DedicatedWorkerGlobalScope* workerGlobalScope = V8DedicatedWorkerGlobalScope::toNative(info.Holder());
MessagePortArray ports;
ArrayBufferArray arrayBuffers;
if (info.Length() > 1) {
const int transferablesArgIndex = 1;
- bool notASequence = false;
- if (!extractTransferables(info[transferablesArgIndex], ports, arrayBuffers, notASequence, info.GetIsolate())) {
- if (notASequence)
- throwTypeError(ExceptionMessages::failedToExecute("postMessage", "WorkerGlobalScope", ExceptionMessages::notAnArrayTypeArgumentOrValue(transferablesArgIndex + 1)), info.GetIsolate());
+ if (!SerializedScriptValue::extractTransferables(info[transferablesArgIndex], transferablesArgIndex, ports, arrayBuffers, exceptionState, info.GetIsolate())) {
+ exceptionState.throwIfNeeded();
return;
}
}
- bool didThrow = false;
- RefPtr<SerializedScriptValue> message = SerializedScriptValue::create(info[0], &ports, &arrayBuffers, didThrow, info.GetIsolate());
- if (didThrow)
+ RefPtr<SerializedScriptValue> message = SerializedScriptValue::create(info[0], &ports, &arrayBuffers, exceptionState, info.GetIsolate());
+ if (exceptionState.throwIfNeeded())
return;
- ExceptionState exceptionState(info.Holder(), info.GetIsolate());
+
workerGlobalScope->postMessage(message.release(), &ports, exceptionState);
exceptionState.throwIfNeeded();
}
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8DeviceMotionEventCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8DeviceMotionEventCustom.cpp
index a170e1cde5f..ecf0ca7e9ee 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8DeviceMotionEventCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8DeviceMotionEventCustom.cpp
@@ -24,7 +24,7 @@
*/
#include "config.h"
-#include "V8DeviceMotionEvent.h"
+#include "bindings/modules/v8/V8DeviceMotionEvent.h"
#include "bindings/v8/V8Binding.h"
#include "modules/device_orientation/DeviceMotionData.h"
@@ -34,66 +34,66 @@ namespace WebCore {
namespace {
-RefPtr<DeviceMotionData::Acceleration> readAccelerationArgument(v8::Local<v8::Value> value, v8::Isolate* isolate)
+PassRefPtrWillBeRawPtr<DeviceMotionData::Acceleration> readAccelerationArgument(v8::Local<v8::Value> value, v8::Isolate* isolate)
{
if (isUndefinedOrNull(value))
- return 0;
+ return nullptr;
// Given the test above, this will always yield an object.
v8::Local<v8::Object> object = value->ToObject();
v8::Local<v8::Value> xValue = object->Get(v8AtomicString(isolate, "x"));
if (xValue.IsEmpty())
- return 0;
+ return nullptr;
bool canProvideX = !isUndefinedOrNull(xValue);
double x = xValue->NumberValue();
v8::Local<v8::Value> yValue = object->Get(v8AtomicString(isolate, "y"));
if (yValue.IsEmpty())
- return 0;
+ return nullptr;
bool canProvideY = !isUndefinedOrNull(yValue);
double y = yValue->NumberValue();
v8::Local<v8::Value> zValue = object->Get(v8AtomicString(isolate, "z"));
if (zValue.IsEmpty())
- return 0;
+ return nullptr;
bool canProvideZ = !isUndefinedOrNull(zValue);
double z = zValue->NumberValue();
if (!canProvideX && !canProvideY && !canProvideZ)
- return 0;
+ return nullptr;
return DeviceMotionData::Acceleration::create(canProvideX, x, canProvideY, y, canProvideZ, z);
}
-RefPtr<DeviceMotionData::RotationRate> readRotationRateArgument(v8::Local<v8::Value> value, v8::Isolate* isolate)
+PassRefPtrWillBeRawPtr<DeviceMotionData::RotationRate> readRotationRateArgument(v8::Local<v8::Value> value, v8::Isolate* isolate)
{
if (isUndefinedOrNull(value))
- return 0;
+ return nullptr;
// Given the test above, this will always yield an object.
v8::Local<v8::Object> object = value->ToObject();
v8::Local<v8::Value> alphaValue = object->Get(v8AtomicString(isolate, "alpha"));
if (alphaValue.IsEmpty())
- return 0;
+ return nullptr;
bool canProvideAlpha = !isUndefinedOrNull(alphaValue);
double alpha = alphaValue->NumberValue();
v8::Local<v8::Value> betaValue = object->Get(v8AtomicString(isolate, "beta"));
if (betaValue.IsEmpty())
- return 0;
+ return nullptr;
bool canProvideBeta = !isUndefinedOrNull(betaValue);
double beta = betaValue->NumberValue();
v8::Local<v8::Value> gammaValue = object->Get(v8AtomicString(isolate, "gamma"));
if (gammaValue.IsEmpty())
- return 0;
+ return nullptr;
bool canProvideGamma = !isUndefinedOrNull(gammaValue);
double gamma = gammaValue->NumberValue();
if (!canProvideAlpha && !canProvideBeta && !canProvideGamma)
- return 0;
+ return nullptr;
return DeviceMotionData::RotationRate::create(canProvideAlpha, alpha, canProvideBeta, beta, canProvideGamma, gamma);
}
@@ -102,18 +102,18 @@ RefPtr<DeviceMotionData::RotationRate> readRotationRateArgument(v8::Local<v8::Va
void V8DeviceMotionEvent::initDeviceMotionEventMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
- DeviceMotionEvent* imp = V8DeviceMotionEvent::toNative(info.Holder());
+ DeviceMotionEvent* impl = V8DeviceMotionEvent::toNative(info.Holder());
v8::Isolate* isolate = info.GetIsolate();
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<>, type, info[0]);
+ TOSTRING_VOID(V8StringResource<>, type, info[0]);
bool bubbles = info[1]->BooleanValue();
bool cancelable = info[2]->BooleanValue();
- RefPtr<DeviceMotionData::Acceleration> acceleration = readAccelerationArgument(info[3], isolate);
- RefPtr<DeviceMotionData::Acceleration> accelerationIncludingGravity = readAccelerationArgument(info[4], isolate);
- RefPtr<DeviceMotionData::RotationRate> rotationRate = readRotationRateArgument(info[5], isolate);
+ RefPtrWillBeRawPtr<DeviceMotionData::Acceleration> acceleration = readAccelerationArgument(info[3], isolate);
+ RefPtrWillBeRawPtr<DeviceMotionData::Acceleration> accelerationIncludingGravity = readAccelerationArgument(info[4], isolate);
+ RefPtrWillBeRawPtr<DeviceMotionData::RotationRate> rotationRate = readRotationRateArgument(info[5], isolate);
bool intervalProvided = !isUndefinedOrNull(info[6]);
double interval = info[6]->NumberValue();
- RefPtr<DeviceMotionData> deviceMotionData = DeviceMotionData::create(acceleration, accelerationIncludingGravity, rotationRate, intervalProvided, interval);
- imp->initDeviceMotionEvent(type, bubbles, cancelable, deviceMotionData.get());
+ RefPtrWillBeRawPtr<DeviceMotionData> deviceMotionData = DeviceMotionData::create(acceleration.release(), accelerationIncludingGravity.release(), rotationRate.release(), intervalProvided, interval);
+ impl->initDeviceMotionEvent(type, bubbles, cancelable, deviceMotionData.get());
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8DeviceOrientationEventCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8DeviceOrientationEventCustom.cpp
index ef2a0a92e48..c9d68ec2057 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8DeviceOrientationEventCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8DeviceOrientationEventCustom.cpp
@@ -24,7 +24,7 @@
*/
#include "config.h"
-#include "V8DeviceOrientationEvent.h"
+#include "bindings/modules/v8/V8DeviceOrientationEvent.h"
#include "bindings/v8/V8Binding.h"
#include "modules/device_orientation/DeviceOrientationData.h"
@@ -34,8 +34,8 @@ namespace WebCore {
void V8DeviceOrientationEvent::initDeviceOrientationEventMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
- DeviceOrientationEvent* imp = V8DeviceOrientationEvent::toNative(info.Holder());
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<>, type, info[0]);
+ DeviceOrientationEvent* impl = V8DeviceOrientationEvent::toNative(info.Holder());
+ TOSTRING_VOID(V8StringResource<>, type, info[0]);
bool bubbles = info[1]->BooleanValue();
bool cancelable = info[2]->BooleanValue();
// If alpha, beta, gamma or absolute are null or undefined, mark them as not provided.
@@ -48,8 +48,8 @@ void V8DeviceOrientationEvent::initDeviceOrientationEventMethodCustom(const v8::
double gamma = info[5]->NumberValue();
bool absoluteProvided = !isUndefinedOrNull(info[6]);
bool absolute = info[6]->BooleanValue();
- RefPtr<DeviceOrientationData> orientation = DeviceOrientationData::create(alphaProvided, alpha, betaProvided, beta, gammaProvided, gamma, absoluteProvided, absolute);
- imp->initDeviceOrientationEvent(type, bubbles, cancelable, orientation.get());
+ RefPtrWillBeRawPtr<DeviceOrientationData> orientation = DeviceOrientationData::create(alphaProvided, alpha, betaProvided, beta, gammaProvided, gamma, absoluteProvided, absolute);
+ impl->initDeviceOrientationEvent(type, bubbles, cancelable, orientation.get());
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8DocumentCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8DocumentCustom.cpp
index 94ed248cb90..930ba77f07d 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8DocumentCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8DocumentCustom.cpp
@@ -29,16 +29,16 @@
*/
#include "config.h"
-#include "V8Document.h"
+#include "bindings/core/v8/V8Document.h"
-#include "V8CanvasRenderingContext2D.h"
-#include "V8DOMImplementation.h"
-#include "V8Node.h"
-#include "V8Touch.h"
-#include "V8TouchList.h"
-#include "V8WebGLRenderingContext.h"
-#include "V8XPathNSResolver.h"
-#include "V8XPathResult.h"
+#include "bindings/core/v8/V8CanvasRenderingContext2D.h"
+#include "bindings/core/v8/V8DOMImplementation.h"
+#include "bindings/core/v8/V8Node.h"
+#include "bindings/core/v8/V8Touch.h"
+#include "bindings/core/v8/V8TouchList.h"
+#include "bindings/core/v8/V8WebGLRenderingContext.h"
+#include "bindings/core/v8/V8XPathNSResolver.h"
+#include "bindings/core/v8/V8XPathResult.h"
#include "bindings/v8/ExceptionMessages.h"
#include "bindings/v8/ExceptionState.h"
#include "bindings/v8/ScriptController.h"
@@ -49,8 +49,8 @@
#include "core/dom/ExceptionCode.h"
#include "core/dom/Node.h"
#include "core/dom/TouchList.h"
+#include "core/frame/LocalFrame.h"
#include "core/html/canvas/CanvasRenderingContext.h"
-#include "core/frame/Frame.h"
#include "core/xml/DocumentXPathEvaluator.h"
#include "core/xml/XPathNSResolver.h"
#include "core/xml/XPathResult.h"
@@ -60,27 +60,23 @@ namespace WebCore {
void V8Document::evaluateMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
- RefPtr<Document> document = V8Document::toNative(info.Holder());
+ RefPtrWillBeRawPtr<Document> document = V8Document::toNative(info.Holder());
+ ASSERT(document);
ExceptionState exceptionState(ExceptionState::ExecutionContext, "evaluate", "Document", info.Holder(), info.GetIsolate());
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<>, expression, info[0]);
- RefPtr<Node> contextNode;
- if (V8Node::hasInstance(info[1], info.GetIsolate(), worldType(info.GetIsolate())))
- contextNode = V8Node::toNative(v8::Handle<v8::Object>::Cast(info[1]));
+ TOSTRING_VOID(V8StringResource<>, expression, info[0]);
+ RefPtrWillBeRawPtr<Node> contextNode = V8Node::toNativeWithTypeCheck(info.GetIsolate(), info[1]);
const int resolverArgumentIndex = 2;
- RefPtr<XPathNSResolver> resolver = toXPathNSResolver(info[resolverArgumentIndex], info.GetIsolate());
+ RefPtrWillBeRawPtr<XPathNSResolver> resolver = toXPathNSResolver(info[resolverArgumentIndex], info.GetIsolate());
if (!resolver && !isUndefinedOrNull(info[resolverArgumentIndex])) {
- exceptionState.throwTypeError(ExceptionMessages::incorrectArgumentType(resolverArgumentIndex + 1, "is not a resolver function."));
+ exceptionState.throwTypeError(ExceptionMessages::argumentNullOrIncorrectType(resolverArgumentIndex + 1, "XPathNSResolver"));
exceptionState.throwIfNeeded();
return;
}
int type = toInt32(info[3]);
- RefPtr<XPathResult> inResult;
- if (V8XPathResult::hasInstance(info[4], info.GetIsolate(), worldType(info.GetIsolate())))
- inResult = V8XPathResult::toNative(v8::Handle<v8::Object>::Cast(info[4]));
-
- V8TRYCATCH_VOID(RefPtr<XPathResult>, result, DocumentXPathEvaluator::evaluate(document.get(), expression, contextNode.get(), resolver.release(), type, inResult.get(), exceptionState));
+ RefPtrWillBeRawPtr<XPathResult> inResult = V8XPathResult::toNativeWithTypeCheck(info.GetIsolate(), info[4]);
+ TONATIVE_VOID(RefPtrWillBeRawPtr<XPathResult>, result, DocumentXPathEvaluator::evaluate(*document, expression, contextNode.get(), resolver.release(), type, inResult.get(), exceptionState));
if (exceptionState.throwIfNeeded())
return;
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8ElementCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8ElementCustom.cpp
new file mode 100644
index 00000000000..0083ac9b055
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8ElementCustom.cpp
@@ -0,0 +1,236 @@
+/*
+ * Copyright (C) 2014 Google Inc. All rights reserved.
+ *
+ * Redistribution and use in source and binary forms, with or without
+ * modification, are permitted provided that the following conditions are
+ * met:
+ *
+ * * Redistributions of source code must retain the above copyright
+ * notice, this list of conditions and the following disclaimer.
+ * * Redistributions in binary form must reproduce the above
+ * copyright notice, this list of conditions and the following disclaimer
+ * in the documentation and/or other materials provided with the
+ * distribution.
+ * * Neither the name of Google Inc. nor the names of its
+ * contributors may be used to endorse or promote products derived from
+ * this software without specific prior written permission.
+ *
+ * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
+ * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
+ * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
+ * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
+ * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
+ * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
+ * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
+ * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
+ * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
+ * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
+ * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
+ */
+
+#include "config.h"
+#include "bindings/core/v8/V8Element.h"
+
+#include "bindings/core/v8/V8AnimationEffect.h"
+#include "bindings/core/v8/V8AnimationPlayer.h"
+#include "bindings/v8/Dictionary.h"
+#include "bindings/v8/ExceptionState.h"
+#include "bindings/v8/V8Binding.h"
+#include "bindings/v8/V8BindingMacros.h"
+#include "core/animation/ElementAnimation.h"
+#include "core/dom/Element.h"
+#include "core/frame/UseCounter.h"
+#include "platform/RuntimeEnabledFeatures.h"
+#include "wtf/GetPtr.h"
+
+namespace WebCore {
+
+void V8Element::scrollLeftAttributeSetterCustom(v8::Local<v8::Value> value, const v8::PropertyCallbackInfo<void>& info)
+{
+ ExceptionState exceptionState(ExceptionState::SetterContext, "scrollLeft", "Element", info.Holder(), info.GetIsolate());
+ Element* impl = V8Element::toNative(info.Holder());
+
+ if (RuntimeEnabledFeatures::cssomSmoothScrollEnabled() && value->IsObject()) {
+ TONATIVE_VOID(Dictionary, scrollOptionsHorizontal, Dictionary(value, info.GetIsolate()));
+ impl->setScrollLeft(scrollOptionsHorizontal, exceptionState);
+ exceptionState.throwIfNeeded();
+ return;
+ }
+
+ TONATIVE_VOID_EXCEPTIONSTATE(float, position, toInt32(value, exceptionState), exceptionState);
+ impl->setScrollLeft(position);
+}
+
+void V8Element::scrollTopAttributeSetterCustom(v8::Local<v8::Value> value, const v8::PropertyCallbackInfo<void>& info)
+{
+ ExceptionState exceptionState(ExceptionState::SetterContext, "scrollTop", "Element", info.Holder(), info.GetIsolate());
+ Element* impl = V8Element::toNative(info.Holder());
+
+ if (RuntimeEnabledFeatures::cssomSmoothScrollEnabled() && value->IsObject()) {
+ TONATIVE_VOID(Dictionary, scrollOptionsVertical, Dictionary(value, info.GetIsolate()));
+ impl->setScrollTop(scrollOptionsVertical, exceptionState);
+ exceptionState.throwIfNeeded();
+ return;
+ }
+
+ TONATIVE_VOID_EXCEPTIONSTATE(float, position, toInt32(value, exceptionState), exceptionState);
+ impl->setScrollTop(position);
+}
+
+////////////////////////////////////////////////////////////////////////////////
+// Overload resolution for animate()
+// FIXME: needs support for union types http://crbug.com/240176
+////////////////////////////////////////////////////////////////////////////////
+
+// AnimationPlayer animate(AnimationEffect? effect);
+void animate1Method(const v8::FunctionCallbackInfo<v8::Value>& info)
+{
+ Element* impl = V8Element::toNative(info.Holder());
+ TONATIVE_VOID(AnimationEffect*, effect, V8AnimationEffect::toNativeWithTypeCheck(info.GetIsolate(), info[0]));
+ v8SetReturnValueFast(info, WTF::getPtr(ElementAnimation::animate(*impl, effect)), impl);
+}
+
+// [RaisesException] AnimationPlayer animate(sequence<Dictionary> effect);
+void animate2Method(const v8::FunctionCallbackInfo<v8::Value>& info)
+{
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "animate", "Element", info.Holder(), info.GetIsolate());
+ Element* impl = V8Element::toNative(info.Holder());
+ TONATIVE_VOID(Vector<Dictionary>, keyframes, toNativeArray<Dictionary>(info[0], 1, info.GetIsolate()));
+ RefPtr<AnimationPlayer> result = ElementAnimation::animate(*impl, keyframes, exceptionState);
+ if (exceptionState.throwIfNeeded())
+ return;
+ v8SetReturnValueFast(info, WTF::getPtr(result.release()), impl);
+}
+
+// AnimationPlayer animate(AnimationEffect? effect, double timing);
+void animate3Method(const v8::FunctionCallbackInfo<v8::Value>& info)
+{
+ Element* impl = V8Element::toNative(info.Holder());
+ TONATIVE_VOID(AnimationEffect*, effect, V8AnimationEffect::toNativeWithTypeCheck(info.GetIsolate(), info[0]));
+ TONATIVE_VOID(double, duration, static_cast<double>(info[1]->NumberValue()));
+ v8SetReturnValueFast(info, WTF::getPtr(ElementAnimation::animate(*impl, effect, duration)), impl);
+}
+
+// AnimationPlayer animate(AnimationEffect? effect, Dictionary timing);
+void animate4Method(const v8::FunctionCallbackInfo<v8::Value>& info)
+{
+ Element* impl = V8Element::toNative(info.Holder());
+ TONATIVE_VOID(AnimationEffect*, effect, V8AnimationEffect::toNativeWithTypeCheck(info.GetIsolate(), info[0]));
+ TONATIVE_VOID(Dictionary, timingInput, Dictionary(info[1], info.GetIsolate()));
+ if (!timingInput.isUndefinedOrNull() && !timingInput.isObject()) {
+ throwTypeError(ExceptionMessages::failedToExecute("animate", "Element", "parameter 2 ('timingInput') is not an object."), info.GetIsolate());
+ return;
+ }
+ v8SetReturnValueFast(info, WTF::getPtr(ElementAnimation::animate(*impl, effect, timingInput)), impl);
+}
+
+// [RaisesException] AnimationPlayer animate(sequence<Dictionary> effect, double timing);
+void animate5Method(const v8::FunctionCallbackInfo<v8::Value>& info)
+{
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "animate", "Element", info.Holder(), info.GetIsolate());
+ Element* impl = V8Element::toNative(info.Holder());
+ TONATIVE_VOID(Vector<Dictionary>, keyframes, toNativeArray<Dictionary>(info[0], 1, info.GetIsolate()));
+ TONATIVE_VOID(double, duration, static_cast<double>(info[1]->NumberValue()));
+ RefPtr<AnimationPlayer> result = ElementAnimation::animate(*impl, keyframes, duration, exceptionState);
+ if (exceptionState.throwIfNeeded())
+ return;
+ v8SetReturnValueFast(info, WTF::getPtr(result.release()), impl);
+}
+
+// [RaisesException] AnimationPlayer animate(sequence<Dictionary> effect, Dictionary timing);
+void animate6Method(const v8::FunctionCallbackInfo<v8::Value>& info)
+{
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "animate", "Element", info.Holder(), info.GetIsolate());
+ Element* impl = V8Element::toNative(info.Holder());
+ TONATIVE_VOID(Vector<Dictionary>, keyframes, toNativeArray<Dictionary>(info[0], 1, info.GetIsolate()));
+ TONATIVE_VOID(Dictionary, timingInput, Dictionary(info[1], info.GetIsolate()));
+ if (!timingInput.isUndefinedOrNull() && !timingInput.isObject()) {
+ exceptionState.throwTypeError("parameter 2 ('timingInput') is not an object.");
+ exceptionState.throwIfNeeded();
+ return;
+ }
+ RefPtr<AnimationPlayer> result = ElementAnimation::animate(*impl, keyframes, timingInput, exceptionState);
+ if (exceptionState.throwIfNeeded())
+ return;
+ v8SetReturnValueFast(info, WTF::getPtr(result.release()), impl);
+}
+
+void V8Element::animateMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
+{
+ v8::Isolate* isolate = info.GetIsolate();
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "animate", "Element", info.Holder(), isolate);
+ // AnimationPlayer animate(
+ // (AnimationEffect or sequence<Dictionary>)? effect,
+ // optional (double or Dictionary) timing);
+ switch (info.Length()) {
+ case 1:
+ // null resolved as to AnimationEffect, as if the member were nullable:
+ // (AnimationEffect? or sequence<Dictionary>)
+ // instead of the *union* being nullable:
+ // (AnimationEffect or sequence<Dictionary>)?
+ // AnimationPlayer animate(AnimationEffect? effect);
+ if (info[0]->IsNull()) {
+ animate1Method(info);
+ return;
+ }
+ // AnimationPlayer animate(AnimationEffect effect);
+ if (V8AnimationEffect::hasInstance(info[0], isolate)) {
+ animate1Method(info);
+ return;
+ }
+ // [MeasureAs=ElementAnimateKeyframeListEffectNoTiming]
+ // AnimationPlayer animate(sequence<Dictionary> effect);
+ if (info[0]->IsArray()) {
+ UseCounter::count(callingExecutionContext(isolate), UseCounter::ElementAnimateKeyframeListEffectNoTiming);
+ animate2Method(info);
+ return;
+ }
+ break;
+ case 2:
+ // As above, null resolved to AnimationEffect
+ // AnimationPlayer animate(AnimationEffect? effect, Dictionary timing);
+ if (info[0]->IsNull() && info[1]->IsObject()) {
+ animate4Method(info);
+ return;
+ }
+ // AnimationPlayer animate(AnimationEffect? effect, double timing);
+ if (info[0]->IsNull()) {
+ animate3Method(info);
+ return;
+ }
+ // AnimationPlayer animate(AnimationEffect effect, Dictionary timing);
+ if (V8AnimationEffect::hasInstance(info[0], isolate)
+ && info[1]->IsObject()) {
+ animate4Method(info);
+ return;
+ }
+ // AnimationPlayer animate(AnimationEffect effect, double timing);
+ if (V8AnimationEffect::hasInstance(info[0], isolate)) {
+ animate3Method(info);
+ return;
+ }
+ // [MeasureAs=ElementAnimateKeyframeListEffectObjectTiming]
+ // AnimationPlayer animate(sequence<Dictionary> effect, Dictionary timing);
+ if (info[0]->IsArray() && info[1]->IsObject()) {
+ UseCounter::count(callingExecutionContext(isolate), UseCounter::ElementAnimateKeyframeListEffectObjectTiming);
+ animate6Method(info);
+ return;
+ }
+ // [MeasureAs=ElementAnimateKeyframeListEffectDoubleTiming]
+ // AnimationPlayer animate(sequence<Dictionary> effect, double timing);
+ if (info[0]->IsArray()) {
+ UseCounter::count(callingExecutionContext(isolate), UseCounter::ElementAnimateKeyframeListEffectDoubleTiming);
+ animate5Method(info);
+ return;
+ }
+ break;
+ default:
+ throwArityTypeError(exceptionState, "[1]", info.Length());
+ return;
+ break;
+ }
+ exceptionState.throwTypeError("No function was found that matched the signature provided.");
+ exceptionState.throwIfNeeded();
+}
+
+} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8EntryCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8EntryCustom.cpp
index 98fc46d1cbf..e74cf314240 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8EntryCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8EntryCustom.cpp
@@ -29,11 +29,11 @@
*/
#include "config.h"
-#include "V8Entry.h"
+#include "bindings/modules/v8/V8Entry.h"
-#include "V8Attr.h"
-#include "V8DirectoryEntry.h"
-#include "V8FileEntry.h"
+#include "bindings/core/v8/V8Attr.h"
+#include "bindings/modules/v8/V8DirectoryEntry.h"
+#include "bindings/modules/v8/V8FileEntry.h"
#include "bindings/v8/V8Binding.h"
#include "wtf/RefPtr.h"
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8EntrySyncCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8EntrySyncCustom.cpp
index 2ebd101e94f..b079b7699ad 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8EntrySyncCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8EntrySyncCustom.cpp
@@ -29,11 +29,11 @@
*/
#include "config.h"
-#include "V8EntrySync.h"
+#include "bindings/modules/v8/V8EntrySync.h"
-#include "V8Attr.h"
-#include "V8DirectoryEntrySync.h"
-#include "V8FileEntrySync.h"
+#include "bindings/core/v8/V8Attr.h"
+#include "bindings/modules/v8/V8DirectoryEntrySync.h"
+#include "bindings/modules/v8/V8FileEntrySync.h"
#include "bindings/v8/V8Binding.h"
#include "wtf/RefPtr.h"
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8ErrorEventCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8ErrorEventCustom.cpp
index 01ed71acdac..8021350dfbd 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8ErrorEventCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8ErrorEventCustom.cpp
@@ -29,25 +29,23 @@
*/
#include "config.h"
-#include "V8ErrorEvent.h"
+#include "bindings/core/v8/V8ErrorEvent.h"
-#include "RuntimeEnabledFeatures.h"
-#include "V8Event.h"
+#include "bindings/core/v8/V8Event.h"
#include "bindings/v8/DOMWrapperWorld.h"
#include "bindings/v8/Dictionary.h"
-#include "bindings/v8/ScriptState.h"
#include "bindings/v8/SerializedScriptValue.h"
#include "bindings/v8/V8Binding.h"
#include "bindings/v8/V8DOMWrapper.h"
-#include "bindings/v8/V8HiddenPropertyName.h"
+#include "bindings/v8/V8HiddenValue.h"
#include "core/dom/ContextFeatures.h"
+#include "platform/RuntimeEnabledFeatures.h"
namespace WebCore {
void V8ErrorEvent::errorAttributeGetterCustom(const v8::PropertyCallbackInfo<v8::Value>& info)
{
- v8::Handle<v8::Value> error = info.Holder()->GetHiddenValue(V8HiddenPropertyName::error(info.GetIsolate()));
-
+ v8::Handle<v8::Value> error = V8HiddenValue::getHiddenValue(info.GetIsolate(), info.Holder(), V8HiddenValue::error(info.GetIsolate()));
if (!error.IsEmpty()) {
v8SetReturnValue(info, error);
return;
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8EventCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8EventCustom.cpp
index d313239f485..86217c40a83 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8EventCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8EventCustom.cpp
@@ -29,16 +29,15 @@
*/
#include "config.h"
-#include "V8Event.h"
+#include "bindings/core/v8/V8Event.h"
-#include "EventHeaders.h"
-#include "EventInterfaces.h"
-#include "V8Clipboard.h"
+#include "EventModulesHeaders.h"
+#include "EventModulesInterfaces.h"
+#include "bindings/core/v8/V8DataTransfer.h"
#include "bindings/v8/V8Binding.h"
-#include "core/dom/Clipboard.h"
+#include "core/clipboard/Clipboard.h"
#include "core/events/ClipboardEvent.h"
#include "core/events/Event.h"
-#include "core/events/ThreadLocalEventNames.h"
namespace WebCore {
@@ -67,6 +66,7 @@ v8::Handle<v8::Object> wrap(Event* event, v8::Handle<v8::Object> creationContext
return V8Event::createWrapper(event, creationContext, isolate);
EVENT_INTERFACES_FOR_EACH(TRY_TO_WRAP_WITH_INTERFACE)
+ EVENT_MODULES_INTERFACES_FOR_EACH(TRY_TO_WRAP_WITH_INTERFACE)
return V8Event::createWrapper(event, creationContext, isolate);
}
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8EventTargetCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8EventTargetCustom.cpp
index 8bb41db3bcb..89e7b660449 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8EventTargetCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8EventTargetCustom.cpp
@@ -29,10 +29,12 @@
*/
#include "config.h"
-#include "V8EventTarget.h"
+#include "bindings/core/v8/V8EventTarget.h"
-#include "EventTargetHeaders.h"
-#include "EventTargetInterfaces.h"
+#include "core/EventTargetHeaders.h"
+#include "core/EventTargetInterfaces.h"
+#include "modules/EventTargetModulesHeaders.h"
+#include "modules/EventTargetModulesInterfaces.h"
namespace WebCore {
@@ -47,6 +49,7 @@ v8::Handle<v8::Value> toV8(EventTarget* impl, v8::Handle<v8::Object> creationCon
AtomicString desiredInterface = impl->interfaceName();
EVENT_TARGET_INTERFACES_FOR_EACH(TRY_TO_WRAP_WITH_INTERFACE)
+ EVENT_TARGET_MODULES_INTERFACES_FOR_EACH(TRY_TO_WRAP_WITH_INTERFACE)
ASSERT_NOT_REACHED();
return v8Undefined();
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8FileCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8FileCustom.cpp
index ecbb7815d46..d01acf369cc 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8FileCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8FileCustom.cpp
@@ -29,12 +29,11 @@
*/
#include "config.h"
-#include "V8File.h"
+#include "bindings/core/v8/V8File.h"
-#include "RuntimeEnabledFeatures.h"
#include "bindings/v8/ExceptionState.h"
#include "bindings/v8/custom/V8BlobCustomHelpers.h"
-#include "core/fileapi/BlobBuilder.h"
+#include "platform/RuntimeEnabledFeatures.h"
namespace WebCore {
@@ -66,7 +65,7 @@ void V8File::constructorCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
}
}
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<>, fileName, info[1]);
+ TOSTRING_VOID(V8StringResource<>, fileName, info[1]);
V8BlobCustomHelpers::ParsedProperties properties(true);
if (info.Length() > 2) {
@@ -84,12 +83,14 @@ void V8File::constructorCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
properties.setDefaultLastModified();
}
- BlobBuilder blobBuilder;
+ OwnPtr<BlobData> blobData = BlobData::create();
+ blobData->setContentType(properties.contentType());
v8::Local<v8::Object> blobParts = v8::Local<v8::Object>::Cast(info[0]);
- if (!V8BlobCustomHelpers::processBlobParts(blobParts, length, properties.endings(), blobBuilder, info.GetIsolate()))
+ if (!V8BlobCustomHelpers::processBlobParts(blobParts, length, properties.normalizeLineEndingsToNative(), *blobData, info.GetIsolate()))
return;
- RefPtr<File> file = blobBuilder.createFile(properties.contentType(), fileName, properties.lastModified());
+ long long fileSize = blobData->length();
+ RefPtrWillBeRawPtr<File> file = File::create(fileName, properties.lastModified(), BlobDataHandle::create(blobData.release(), fileSize));
v8SetReturnValue(info, file.release());
}
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8FileReaderCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8FileReaderCustom.cpp
index c6ee39e6f4b..333040712e5 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8FileReaderCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8FileReaderCustom.cpp
@@ -29,7 +29,7 @@
*/
#include "config.h"
-#include "V8FileReader.h"
+#include "bindings/core/v8/V8FileReader.h"
#include "bindings/v8/V8Binding.h"
#include "bindings/v8/custom/V8ArrayBufferCustom.h"
@@ -40,12 +40,12 @@ namespace WebCore {
void V8FileReader::resultAttributeGetterCustom(const v8::PropertyCallbackInfo<v8::Value>& info)
{
v8::Handle<v8::Object> holder = info.Holder();
- FileReader* imp = V8FileReader::toNative(holder);
- if (imp->readType() == FileReaderLoader::ReadAsArrayBuffer) {
- v8SetReturnValueFast(info, imp->arrayBufferResult(), imp);
+ FileReader* impl = V8FileReader::toNative(holder);
+ if (impl->readType() == FileReaderLoader::ReadAsArrayBuffer) {
+ v8SetReturnValueFast(info, impl->arrayBufferResult(), impl);
return;
}
- v8SetReturnValueStringOrNull(info, imp->stringResult(), info.GetIsolate());
+ v8SetReturnValueStringOrNull(info, impl->stringResult(), info.GetIsolate());
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8Float32ArrayCustom.h b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8Float32ArrayCustom.h
index 17ef9710e0a..3caa7d1da2a 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8Float32ArrayCustom.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8Float32ArrayCustom.h
@@ -59,10 +59,6 @@ public:
typedef V8TypedArray<Float32Array> V8Float32Array;
-template<>
-class WrapperTypeTraits<Float32Array> : public TypedArrayWrapperTraits<Float32Array> { };
-
-
inline v8::Handle<v8::Object> wrap(Float32Array* impl, v8::Handle<v8::Object> creationContext, v8::Isolate* isolate)
{
return V8TypedArray<Float32Array>::wrap(impl, creationContext, isolate);
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8Float64ArrayCustom.h b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8Float64ArrayCustom.h
index 30ec270d288..0e793b6525f 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8Float64ArrayCustom.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8Float64ArrayCustom.h
@@ -59,10 +59,6 @@ public:
typedef V8TypedArray<Float64Array> V8Float64Array;
-template<>
-class WrapperTypeTraits<Float64Array> : public TypedArrayWrapperTraits<Float64Array> { };
-
-
inline v8::Handle<v8::Object> wrap(Float64Array* impl, v8::Handle<v8::Object> creationContext, v8::Isolate* isolate)
{
return V8TypedArray<Float64Array>::wrap(impl, creationContext, isolate);
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8FormDataCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8FormDataCustom.cpp
deleted file mode 100644
index 890bf034789..00000000000
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8FormDataCustom.cpp
+++ /dev/null
@@ -1,71 +0,0 @@
-/*
- * Copyright (C) 2010 Google Inc. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions are
- * met:
- *
- * * Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * * Redistributions in binary form must reproduce the above
- * copyright notice, this list of conditions and the following disclaimer
- * in the documentation and/or other materials provided with the
- * distribution.
- * * Neither the name of Google Inc. nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
- * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
- * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
- * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
- * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
- * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
- * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
- * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
- * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-#include "config.h"
-#include "V8FormData.h"
-
-#include "V8Blob.h"
-#include "V8HTMLFormElement.h"
-#include "bindings/v8/V8Binding.h"
-#include "bindings/v8/V8Utilities.h"
-#include "core/html/DOMFormData.h"
-
-namespace WebCore {
-
-void V8FormData::appendMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
-{
- if (info.Length() < 2) {
- throwError(v8SyntaxError, "Not enough arguments", info.GetIsolate());
- return;
- }
-
- DOMFormData* domFormData = V8FormData::toNative(info.Holder());
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<WithNullCheck>, name, info[0]);
-
- v8::Handle<v8::Value> arg = info[1];
- if (V8Blob::hasInstance(arg, info.GetIsolate(), worldType(info.GetIsolate()))) {
- v8::Handle<v8::Object> object = v8::Handle<v8::Object>::Cast(arg);
- Blob* blob = V8Blob::toNative(object);
- ASSERT(blob);
-
- String filename;
- if (info.Length() >= 3) {
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<WithUndefinedOrNullCheck>, filenameResource, info[2]);
- filename = filenameResource;
- }
-
- domFormData->append(name, blob, filename);
- } else {
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<WithNullCheck>, argString, arg);
- domFormData->append(name, argString);
- }
-}
-
-} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8GeolocationCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8GeolocationCustom.cpp
index 3ce2878edde..e09d99c34bd 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8GeolocationCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8GeolocationCustom.cpp
@@ -24,31 +24,29 @@
*/
#include "config.h"
-#include "V8Geolocation.h"
+#include "bindings/modules/v8/V8Geolocation.h"
-#include "V8PositionCallback.h"
-#include "V8PositionErrorCallback.h"
+#include "bindings/modules/v8/V8PositionCallback.h"
+#include "bindings/modules/v8/V8PositionErrorCallback.h"
#include "bindings/v8/V8Binding.h"
#include "bindings/v8/V8Callback.h"
-#include "bindings/v8/V8Utilities.h"
#include "modules/geolocation/Geolocation.h"
-using namespace std;
using namespace WTF;
namespace WebCore {
-static PassRefPtr<PositionOptions> createPositionOptions(v8::Local<v8::Value> value, v8::Isolate* isolate, bool& succeeded)
+static PositionOptions* createPositionOptions(v8::Local<v8::Value> value, v8::Isolate* isolate, bool& succeeded, ExceptionState& exceptionState)
{
succeeded = true;
// Create default options.
- RefPtr<PositionOptions> options = PositionOptions::create();
+ PositionOptions* options = PositionOptions::create();
// Argument is optional (hence undefined is allowed), and null is allowed.
if (isUndefinedOrNull(value)) {
// Use default options.
- return options.release();
+ return options;
}
// Given the above test, this will always yield an object.
@@ -61,13 +59,13 @@ static PassRefPtr<PositionOptions> createPositionOptions(v8::Local<v8::Value> va
v8::Local<v8::Value> enableHighAccuracyValue = object->Get(v8AtomicString(isolate, "enableHighAccuracy"));
if (enableHighAccuracyValue.IsEmpty()) {
succeeded = false;
- return 0;
+ return nullptr;
}
if (!enableHighAccuracyValue->IsUndefined()) {
v8::Local<v8::Boolean> enableHighAccuracyBoolean = enableHighAccuracyValue->ToBoolean();
if (enableHighAccuracyBoolean.IsEmpty()) {
succeeded = false;
- return 0;
+ return nullptr;
}
options->setEnableHighAccuracy(enableHighAccuracyBoolean->Value());
}
@@ -75,100 +73,88 @@ static PassRefPtr<PositionOptions> createPositionOptions(v8::Local<v8::Value> va
v8::Local<v8::Value> timeoutValue = object->Get(v8AtomicString(isolate, "timeout"));
if (timeoutValue.IsEmpty()) {
succeeded = false;
- return 0;
+ return nullptr;
}
if (!timeoutValue->IsUndefined()) {
v8::Local<v8::Number> timeoutNumber = timeoutValue->ToNumber();
if (timeoutNumber.IsEmpty()) {
succeeded = false;
- return 0;
- }
- double timeoutDouble = timeoutNumber->Value();
- // If the value is positive infinity, there's nothing to do.
- if (!(std::isinf(timeoutDouble) && timeoutDouble > 0)) {
- v8::Local<v8::Int32> timeoutInt32 = timeoutValue->ToInt32();
- if (timeoutInt32.IsEmpty()) {
- succeeded = false;
- return 0;
- }
- // Wrap to int32 and force non-negative to match behavior of window.setTimeout.
- options->setTimeout(max(0, timeoutInt32->Value()));
+ return nullptr;
}
+ if (timeoutNumber->Value() <= 0)
+ options->setTimeout(0);
+ else
+ options->setTimeout(toUInt32(timeoutValue, Clamp, exceptionState));
}
v8::Local<v8::Value> maximumAgeValue = object->Get(v8AtomicString(isolate, "maximumAge"));
if (maximumAgeValue.IsEmpty()) {
succeeded = false;
- return 0;
+ return nullptr;
}
if (!maximumAgeValue->IsUndefined()) {
v8::Local<v8::Number> maximumAgeNumber = maximumAgeValue->ToNumber();
if (maximumAgeNumber.IsEmpty()) {
succeeded = false;
- return 0;
- }
- double maximumAgeDouble = maximumAgeNumber->Value();
- if (std::isinf(maximumAgeDouble) && maximumAgeDouble > 0) {
- // If the value is positive infinity, clear maximumAge.
- options->clearMaximumAge();
- } else {
- v8::Local<v8::Int32> maximumAgeInt32 = maximumAgeValue->ToInt32();
- if (maximumAgeInt32.IsEmpty()) {
- succeeded = false;
- return 0;
- }
- // Wrap to int32 and force non-negative to match behavior of window.setTimeout.
- options->setMaximumAge(max(0, maximumAgeInt32->Value()));
+ return nullptr;
}
+ if (maximumAgeNumber->Value() <= 0)
+ options->setMaximumAge(0);
+ else
+ options->setMaximumAge(toUInt32(maximumAgeValue, Clamp, exceptionState));
}
- return options.release();
+ return options;
}
void V8Geolocation::getCurrentPositionMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
bool succeeded = false;
- OwnPtr<PositionCallback> positionCallback = createFunctionOnlyCallback<V8PositionCallback>(info[0], succeeded, info.GetIsolate());
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "getCurrentPosition", "Geolocation", info.Holder(), info.GetIsolate());
+
+ OwnPtr<PositionCallback> positionCallback = createFunctionOnlyCallback<V8PositionCallback>(info[0], 1, succeeded, info.GetIsolate(), exceptionState);
if (!succeeded)
return;
ASSERT(positionCallback);
// Argument is optional (hence undefined is allowed), and null is allowed.
- OwnPtr<PositionErrorCallback> positionErrorCallback = createFunctionOnlyCallback<V8PositionErrorCallback>(info[1], succeeded, info.GetIsolate(), CallbackAllowUndefined | CallbackAllowNull);
+ OwnPtr<PositionErrorCallback> positionErrorCallback = createFunctionOnlyCallback<V8PositionErrorCallback>(info[1], 2, succeeded, info.GetIsolate(), exceptionState, CallbackAllowUndefined | CallbackAllowNull);
if (!succeeded)
return;
- RefPtr<PositionOptions> positionOptions = createPositionOptions(info[2], info.GetIsolate(), succeeded);
+ PositionOptions* positionOptions = createPositionOptions(info[2], info.GetIsolate(), succeeded, exceptionState);
if (!succeeded)
return;
ASSERT(positionOptions);
Geolocation* geolocation = V8Geolocation::toNative(info.Holder());
- geolocation->getCurrentPosition(positionCallback.release(), positionErrorCallback.release(), positionOptions.release());
+ geolocation->getCurrentPosition(positionCallback.release(), positionErrorCallback.release(), positionOptions);
}
void V8Geolocation::watchPositionMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
bool succeeded = false;
- OwnPtr<PositionCallback> positionCallback = createFunctionOnlyCallback<V8PositionCallback>(info[0], succeeded, info.GetIsolate());
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "watchCurrentPosition", "Geolocation", info.Holder(), info.GetIsolate());
+
+ OwnPtr<PositionCallback> positionCallback = createFunctionOnlyCallback<V8PositionCallback>(info[0], 1, succeeded, info.GetIsolate(), exceptionState);
if (!succeeded)
return;
ASSERT(positionCallback);
// Argument is optional (hence undefined is allowed), and null is allowed.
- OwnPtr<PositionErrorCallback> positionErrorCallback = createFunctionOnlyCallback<V8PositionErrorCallback>(info[1], succeeded, info.GetIsolate(), CallbackAllowUndefined | CallbackAllowNull);
+ OwnPtr<PositionErrorCallback> positionErrorCallback = createFunctionOnlyCallback<V8PositionErrorCallback>(info[1], 2, succeeded, info.GetIsolate(), exceptionState, CallbackAllowUndefined | CallbackAllowNull);
if (!succeeded)
return;
- RefPtr<PositionOptions> positionOptions = createPositionOptions(info[2], info.GetIsolate(), succeeded);
+ PositionOptions* positionOptions = createPositionOptions(info[2], info.GetIsolate(), succeeded, exceptionState);
if (!succeeded)
return;
ASSERT(positionOptions);
Geolocation* geolocation = V8Geolocation::toNative(info.Holder());
- int watchId = geolocation->watchPosition(positionCallback.release(), positionErrorCallback.release(), positionOptions.release());
+ int watchId = geolocation->watchPosition(positionCallback.release(), positionErrorCallback.release(), positionOptions);
v8SetReturnValue(info, watchId);
}
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8HTMLAllCollectionCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8HTMLAllCollectionCustom.cpp
index 670b36cbadd..c0383741326 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8HTMLAllCollectionCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8HTMLAllCollectionCustom.cpp
@@ -29,10 +29,10 @@
*/
#include "config.h"
-#include "V8HTMLAllCollection.h"
+#include "bindings/core/v8/V8HTMLAllCollection.h"
-#include "V8Node.h"
-#include "V8NodeList.h"
+#include "bindings/core/v8/V8Element.h"
+#include "bindings/core/v8/V8NodeList.h"
#include "bindings/v8/V8Binding.h"
#include "core/dom/NamedNodesCollection.h"
#include "core/html/HTMLAllCollection.h"
@@ -43,7 +43,7 @@ namespace WebCore {
template<class CallbackInfo>
static v8::Handle<v8::Value> getNamedItems(HTMLAllCollection* collection, AtomicString name, const CallbackInfo& info)
{
- Vector<RefPtr<Node> > namedItems;
+ WillBeHeapVector<RefPtrWillBeMember<Element> > namedItems;
collection->namedItems(name, namedItems);
if (!namedItems.size())
@@ -62,7 +62,7 @@ static v8::Handle<v8::Value> getItem(HTMLAllCollection* collection, v8::Handle<v
{
v8::Local<v8::Uint32> index = argument->ToArrayIndex();
if (index.IsEmpty()) {
- V8TRYCATCH_FOR_V8STRINGRESOURCE_RETURN(V8StringResource<>, name, argument, v8::Undefined(info.GetIsolate()));
+ TOSTRING_DEFAULT(V8StringResource<>, name, argument, v8::Undefined(info.GetIsolate()));
v8::Handle<v8::Value> result = getNamedItems(collection, name, info);
if (result.IsEmpty())
@@ -71,29 +71,14 @@ static v8::Handle<v8::Value> getItem(HTMLAllCollection* collection, v8::Handle<v
return result;
}
- RefPtr<Node> result = collection->item(index->Uint32Value());
+ RefPtrWillBeRawPtr<Element> result = collection->item(index->Uint32Value());
return toV8(result.release(), info.Holder(), info.GetIsolate());
}
void V8HTMLAllCollection::itemMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
- HTMLAllCollection* imp = V8HTMLAllCollection::toNative(info.Holder());
- v8SetReturnValue(info, getItem(imp, info[0], info));
-}
-
-void V8HTMLAllCollection::namedItemMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
-{
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<>, name, info[0]);
-
- HTMLAllCollection* imp = V8HTMLAllCollection::toNative(info.Holder());
- v8::Handle<v8::Value> result = getNamedItems(imp, name, info);
-
- if (result.IsEmpty()) {
- v8SetReturnValueNull(info);
- return;
- }
-
- v8SetReturnValue(info, result);
+ HTMLAllCollection* impl = V8HTMLAllCollection::toNative(info.Holder());
+ v8SetReturnValue(info, getItem(impl, info[0], info));
}
void V8HTMLAllCollection::legacyCallCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
@@ -101,25 +86,24 @@ void V8HTMLAllCollection::legacyCallCustom(const v8::FunctionCallbackInfo<v8::Va
if (info.Length() < 1)
return;
- HTMLAllCollection* imp = V8HTMLAllCollection::toNative(info.Holder());
- Node* ownerNode = imp->ownerNode();
- ASSERT(ownerNode);
+ HTMLAllCollection* impl = V8HTMLAllCollection::toNative(info.Holder());
+ Node& ownerNode = impl->ownerNode();
- UseCounter::count(ownerNode->document(), UseCounter::DocumentAllLegacyCall);
+ UseCounter::count(ownerNode.document(), UseCounter::DocumentAllLegacyCall);
if (info.Length() == 1) {
- v8SetReturnValue(info, getItem(imp, info[0], info));
+ v8SetReturnValue(info, getItem(impl, info[0], info));
return;
}
// If there is a second argument it is the index of the item we want.
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<>, name, info[0]);
+ TOSTRING_VOID(V8StringResource<>, name, info[0]);
v8::Local<v8::Uint32> index = info[1]->ToArrayIndex();
if (index.IsEmpty())
return;
- if (Node* node = imp->namedItemWithIndex(name, index->Uint32Value())) {
- v8SetReturnValueFast(info, node, imp);
+ if (Node* node = impl->namedItemWithIndex(name, index->Uint32Value())) {
+ v8SetReturnValueFast(info, node, impl);
return;
}
}
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8HTMLCanvasElementCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8HTMLCanvasElementCustom.cpp
index c69cbdde418..46a15946f72 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8HTMLCanvasElementCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8HTMLCanvasElementCustom.cpp
@@ -30,13 +30,12 @@
*/
#include "config.h"
-#include "V8HTMLCanvasElement.h"
+#include "bindings/core/v8/V8HTMLCanvasElement.h"
-#include "V8CanvasRenderingContext2D.h"
-#include "V8Node.h"
-#include "V8WebGLRenderingContext.h"
+#include "bindings/core/v8/V8CanvasRenderingContext2D.h"
+#include "bindings/core/v8/V8Node.h"
+#include "bindings/core/v8/V8WebGLRenderingContext.h"
#include "bindings/v8/ExceptionState.h"
-#include "bindings/v8/ScriptState.h"
#include "bindings/v8/V8Binding.h"
#include "core/html/HTMLCanvasElement.h"
#include "core/html/canvas/Canvas2DContextAttributes.h"
@@ -52,34 +51,34 @@ void V8HTMLCanvasElement::getContextMethodCustom(const v8::FunctionCallbackInfo<
{
v8::Handle<v8::Object> holder = info.Holder();
v8::Isolate* isolate = info.GetIsolate();
- HTMLCanvasElement* imp = V8HTMLCanvasElement::toNative(holder);
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<>, contextIdResource, info[0]);
+ HTMLCanvasElement* impl = V8HTMLCanvasElement::toNative(holder);
+ TOSTRING_VOID(V8StringResource<>, contextIdResource, info[0]);
String contextId = contextIdResource;
RefPtr<CanvasContextAttributes> attributes;
- if (contextId == "webgl" || contextId == "experimental-webgl" || contextId == "webkit-3d") {
+ if (contextId == "webgl" || contextId == "experimental-webgl") {
RefPtr<WebGLContextAttributes> webGLAttributes = WebGLContextAttributes::create();
if (info.Length() > 1 && info[1]->IsObject()) {
v8::Handle<v8::Object> jsAttributes = info[1]->ToObject();
v8::Handle<v8::String> alpha = v8AtomicString(isolate, "alpha");
- if (jsAttributes->Has(alpha))
+ if (jsAttributes->Has(alpha) && !isUndefinedOrNull(jsAttributes->Get(alpha)))
webGLAttributes->setAlpha(jsAttributes->Get(alpha)->BooleanValue());
v8::Handle<v8::String> depth = v8AtomicString(isolate, "depth");
- if (jsAttributes->Has(depth))
+ if (jsAttributes->Has(depth) && !isUndefinedOrNull(jsAttributes->Get(depth)))
webGLAttributes->setDepth(jsAttributes->Get(depth)->BooleanValue());
v8::Handle<v8::String> stencil = v8AtomicString(isolate, "stencil");
- if (jsAttributes->Has(stencil))
+ if (jsAttributes->Has(stencil) && !isUndefinedOrNull(jsAttributes->Get(stencil)))
webGLAttributes->setStencil(jsAttributes->Get(stencil)->BooleanValue());
v8::Handle<v8::String> antialias = v8AtomicString(isolate, "antialias");
- if (jsAttributes->Has(antialias))
+ if (jsAttributes->Has(antialias) && !isUndefinedOrNull(jsAttributes->Get(antialias)))
webGLAttributes->setAntialias(jsAttributes->Get(antialias)->BooleanValue());
v8::Handle<v8::String> premultipliedAlpha = v8AtomicString(isolate, "premultipliedAlpha");
- if (jsAttributes->Has(premultipliedAlpha))
+ if (jsAttributes->Has(premultipliedAlpha) && !isUndefinedOrNull(jsAttributes->Get(premultipliedAlpha)))
webGLAttributes->setPremultipliedAlpha(jsAttributes->Get(premultipliedAlpha)->BooleanValue());
v8::Handle<v8::String> preserveDrawingBuffer = v8AtomicString(isolate, "preserveDrawingBuffer");
- if (jsAttributes->Has(preserveDrawingBuffer))
+ if (jsAttributes->Has(preserveDrawingBuffer) && !isUndefinedOrNull(jsAttributes->Get(preserveDrawingBuffer)))
webGLAttributes->setPreserveDrawingBuffer(jsAttributes->Get(preserveDrawingBuffer)->BooleanValue());
v8::Handle<v8::String> failIfMajorPerformanceCaveat = v8AtomicString(isolate, "failIfMajorPerformanceCaveat");
- if (jsAttributes->Has(failIfMajorPerformanceCaveat))
+ if (jsAttributes->Has(failIfMajorPerformanceCaveat) && !isUndefinedOrNull(jsAttributes->Get(failIfMajorPerformanceCaveat)))
webGLAttributes->setFailIfMajorPerformanceCaveat(jsAttributes->Get(failIfMajorPerformanceCaveat)->BooleanValue());
}
attributes = webGLAttributes;
@@ -88,23 +87,23 @@ void V8HTMLCanvasElement::getContextMethodCustom(const v8::FunctionCallbackInfo<
if (info.Length() > 1 && info[1]->IsObject()) {
v8::Handle<v8::Object> jsAttributes = info[1]->ToObject();
v8::Handle<v8::String> alpha = v8AtomicString(isolate, "alpha");
- if (jsAttributes->Has(alpha))
+ if (jsAttributes->Has(alpha) && !isUndefinedOrNull(jsAttributes->Get(alpha)))
canvas2DAttributes->setAlpha(jsAttributes->Get(alpha)->BooleanValue());
}
attributes = canvas2DAttributes;
}
- CanvasRenderingContext* result = imp->getContext(contextId, attributes.get());
+ CanvasRenderingContext* result = impl->getContext(contextId, attributes.get());
if (!result) {
v8SetReturnValueNull(info);
return;
}
if (result->is2d()) {
v8::Handle<v8::Value> v8Result = toV8(toCanvasRenderingContext2D(result), info.Holder(), info.GetIsolate());
- if (InspectorInstrumentation::canvasAgentEnabled(&imp->document())) {
- ScriptState* scriptState = ScriptState::forContext(isolate->GetCurrentContext());
- ScriptObject context(scriptState, v8::Handle<v8::Object>::Cast(v8Result));
- ScriptObject wrapped = InspectorInstrumentation::wrapCanvas2DRenderingContextForInstrumentation(&imp->document(), context);
- if (!wrapped.hasNoValue()) {
+ if (InspectorInstrumentation::canvasAgentEnabled(&impl->document())) {
+ ScriptState* scriptState = ScriptState::current(isolate);
+ ScriptValue context(scriptState, v8Result);
+ ScriptValue wrapped = InspectorInstrumentation::wrapCanvas2DRenderingContextForInstrumentation(&impl->document(), context);
+ if (!wrapped.isEmpty()) {
v8SetReturnValue(info, wrapped.v8Value());
return;
}
@@ -114,11 +113,11 @@ void V8HTMLCanvasElement::getContextMethodCustom(const v8::FunctionCallbackInfo<
}
if (result->is3d()) {
v8::Handle<v8::Value> v8Result = toV8(toWebGLRenderingContext(result), info.Holder(), info.GetIsolate());
- if (InspectorInstrumentation::canvasAgentEnabled(&imp->document())) {
- ScriptState* scriptState = ScriptState::forContext(isolate->GetCurrentContext());
- ScriptObject glContext(scriptState, v8::Handle<v8::Object>::Cast(v8Result));
- ScriptObject wrapped = InspectorInstrumentation::wrapWebGLRenderingContextForInstrumentation(&imp->document(), glContext);
- if (!wrapped.hasNoValue()) {
+ if (InspectorInstrumentation::canvasAgentEnabled(&impl->document())) {
+ ScriptState* scriptState = ScriptState::current(isolate);
+ ScriptValue glContext(scriptState, v8Result);
+ ScriptValue wrapped = InspectorInstrumentation::wrapWebGLRenderingContextForInstrumentation(&impl->document(), glContext);
+ if (!wrapped.isEmpty()) {
v8SetReturnValue(info, wrapped.v8Value());
return;
}
@@ -136,7 +135,7 @@ void V8HTMLCanvasElement::toDataURLMethodCustom(const v8::FunctionCallbackInfo<v
HTMLCanvasElement* canvas = V8HTMLCanvasElement::toNative(holder);
ExceptionState exceptionState(ExceptionState::ExecutionContext, "toDataURL", "HTMLCanvasElement", info.Holder(), info.GetIsolate());
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<>, type, info[0]);
+ TOSTRING_VOID(V8StringResource<>, type, info[0]);
double quality;
double* qualityPtr = 0;
if (info.Length() > 1 && info[1]->IsNumber()) {
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8HTMLCollectionCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8HTMLCollectionCustom.cpp
index 33fd4ca1d38..05883e60cee 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8HTMLCollectionCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8HTMLCollectionCustom.cpp
@@ -29,12 +29,12 @@
*/
#include "config.h"
-#include "V8HTMLCollection.h"
+#include "bindings/core/v8/V8HTMLCollection.h"
-#include "V8HTMLAllCollection.h"
-#include "V8HTMLFormControlsCollection.h"
-#include "V8HTMLOptionsCollection.h"
-#include "V8Node.h"
+#include "bindings/core/v8/V8HTMLAllCollection.h"
+#include "bindings/core/v8/V8HTMLFormControlsCollection.h"
+#include "bindings/core/v8/V8HTMLOptionsCollection.h"
+#include "bindings/core/v8/V8Node.h"
#include "bindings/v8/V8Binding.h"
#include "core/html/HTMLCollection.h"
@@ -45,11 +45,11 @@ v8::Handle<v8::Object> wrap(HTMLCollection* impl, v8::Handle<v8::Object> creatio
ASSERT(impl);
switch (impl->type()) {
case FormControls:
- return wrap(static_cast<HTMLFormControlsCollection*>(impl), creationContext, isolate);
+ return wrap(toHTMLFormControlsCollection(impl), creationContext, isolate);
case SelectOptions:
- return wrap(static_cast<HTMLOptionsCollection*>(impl), creationContext, isolate);
+ return wrap(toHTMLOptionsCollection(impl), creationContext, isolate);
case DocAll:
- return wrap(static_cast<HTMLAllCollection*>(impl), creationContext, isolate);
+ return wrap(toHTMLAllCollection(impl), creationContext, isolate);
default:
break;
}
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8HTMLDocumentCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8HTMLDocumentCustom.cpp
index 49f76e73080..1f1a99bf49f 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8HTMLDocumentCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8HTMLDocumentCustom.cpp
@@ -29,20 +29,20 @@
*/
#include "config.h"
-#include "V8HTMLDocument.h"
+#include "bindings/core/v8/V8HTMLDocument.h"
-#include "HTMLNames.h"
-#include "V8HTMLAllCollection.h"
-#include "V8HTMLCollection.h"
-#include "V8Node.h"
-#include "V8Window.h"
+#include "bindings/core/v8/V8HTMLAllCollection.h"
+#include "bindings/core/v8/V8HTMLCollection.h"
+#include "bindings/core/v8/V8Node.h"
+#include "bindings/core/v8/V8Window.h"
#include "bindings/v8/ScriptController.h"
#include "bindings/v8/V8Binding.h"
+#include "core/HTMLNames.h"
+#include "core/frame/LocalFrame.h"
#include "core/html/HTMLAllCollection.h"
#include "core/html/HTMLCollection.h"
#include "core/html/HTMLDocument.h"
#include "core/html/HTMLIFrameElement.h"
-#include "core/frame/Frame.h"
#include "wtf/OwnPtr.h"
#include "wtf/RefPtr.h"
#include "wtf/StdLibExtras.h"
@@ -56,15 +56,18 @@ void V8HTMLDocument::openMethodCustom(const v8::FunctionCallbackInfo<v8::Value>&
HTMLDocument* htmlDocument = V8HTMLDocument::toNative(info.Holder());
if (info.Length() > 2) {
- if (RefPtr<Frame> frame = htmlDocument->frame()) {
+ if (RefPtr<LocalFrame> frame = htmlDocument->frame()) {
// Fetch the global object for the frame.
- v8::Local<v8::Context> context = frame->script().currentWorldContext();
+ v8::Local<v8::Context> context = toV8Context(frame.get(), DOMWrapperWorld::current(info.GetIsolate()));
// Bail out if we cannot get the context.
if (context.IsEmpty())
return;
v8::Local<v8::Object> global = context->Global();
// Get the open property of the global object.
v8::Local<v8::Value> function = global->Get(v8AtomicString(info.GetIsolate(), "open"));
+ // Failed; return without throwing (new) exception.
+ if (function.IsEmpty())
+ return;
// If the open property is not a function throw a type error.
if (!function->IsFunction()) {
throwTypeError("open is not a function", info.GetIsolate());
@@ -80,7 +83,11 @@ void V8HTMLDocument::openMethodCustom(const v8::FunctionCallbackInfo<v8::Value>&
}
}
- htmlDocument->open(activeDOMWindow()->document());
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "open", "Document", info.Holder(), info.GetIsolate());
+ htmlDocument->open(callingDOMWindow(info.GetIsolate())->document(), exceptionState);
+ if (exceptionState.throwIfNeeded())
+ return;
+
v8SetReturnValue(info, info.Holder());
}
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8HTMLElementCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8HTMLElementCustom.cpp
index dae4512d1dc..78706afe722 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8HTMLElementCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8HTMLElementCustom.cpp
@@ -29,9 +29,9 @@
*/
#include "config.h"
-#include "V8HTMLElement.h"
+#include "bindings/core/v8/V8HTMLElement.h"
-#include "V8HTMLElementWrapperFactory.h"
+#include "core/V8HTMLElementWrapperFactory.h" // FIXME: should be bindings/core/v8
namespace WebCore {
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8HTMLFormControlsCollectionCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8HTMLFormControlsCollectionCustom.cpp
deleted file mode 100644
index ab84454965f..00000000000
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8HTMLFormControlsCollectionCustom.cpp
+++ /dev/null
@@ -1,71 +0,0 @@
-/*
- * Copyright (C) 2009 Google Inc. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions are
- * met:
- *
- * * Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * * Redistributions in binary form must reproduce the above
- * copyright notice, this list of conditions and the following disclaimer
- * in the documentation and/or other materials provided with the
- * distribution.
- * * Neither the name of Google Inc. nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
- * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
- * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
- * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
- * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
- * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
- * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
- * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
- * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-#include "config.h"
-#include "V8HTMLFormControlsCollection.h"
-
-#include "V8Node.h"
-#include "V8RadioNodeList.h"
-#include "bindings/v8/V8Binding.h"
-#include "core/html/HTMLCollection.h"
-#include "core/html/RadioNodeList.h"
-
-namespace WebCore {
-
-template<typename CallbackInfo>
-static v8::Handle<v8::Value> getNamedItems(HTMLFormControlsCollection* collection, const AtomicString& name, const CallbackInfo& info)
-{
- Vector<RefPtr<Node> > namedItems;
- collection->namedItems(name, namedItems);
-
- if (!namedItems.size())
- return v8Undefined();
-
- if (namedItems.size() == 1)
- return toV8(namedItems.at(0).release(), info.Holder(), info.GetIsolate());
-
- return toV8(collection->ownerNode()->radioNodeList(name).get(), info.Holder(), info.GetIsolate());
-}
-
-void V8HTMLFormControlsCollection::namedItemMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
-{
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<>, name, info[0]);
- HTMLFormControlsCollection* imp = V8HTMLFormControlsCollection::toNative(info.Holder());
- v8::Handle<v8::Value> result = getNamedItems(imp, name, info);
-
- if (result.IsEmpty()) {
- v8SetReturnValueNull(info);
- return;
- }
-
- v8SetReturnValue(info, result);
-}
-
-} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8HTMLFrameElementCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8HTMLFrameElementCustom.cpp
deleted file mode 100644
index 8c011d0d922..00000000000
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8HTMLFrameElementCustom.cpp
+++ /dev/null
@@ -1,59 +0,0 @@
-/*
- * Copyright (C) 2007-2009 Google Inc. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions are
- * met:
- *
- * * Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * * Redistributions in binary form must reproduce the above
- * copyright notice, this list of conditions and the following disclaimer
- * in the documentation and/or other materials provided with the
- * distribution.
- * * Neither the name of Google Inc. nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
- * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
- * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
- * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
- * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
- * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
- * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
- * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
- * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-#include "config.h"
-#include "V8HTMLFrameElement.h"
-
-#include "HTMLNames.h"
-#include "bindings/v8/BindingSecurity.h"
-#include "bindings/v8/ExceptionState.h"
-#include "bindings/v8/V8Binding.h"
-#include "core/html/HTMLFrameElement.h"
-#include "core/html/parser/HTMLParserIdioms.h"
-
-namespace WebCore {
-
-using namespace HTMLNames;
-
-void V8HTMLFrameElement::locationAttributeSetterCustom(v8::Local<v8::Value> value, const v8::PropertyCallbackInfo<void>& info)
-{
- HTMLFrameElement* frame = V8HTMLFrameElement::toNative(info.Holder());
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<WithNullCheck>, locationValue, value);
-
- ExceptionState exceptionState(info.Holder(), info.GetIsolate());
- if (protocolIsJavaScript(stripLeadingAndTrailingHTMLSpaces(locationValue)) && !BindingSecurity::shouldAllowAccessToFrame(frame->contentFrame(), exceptionState)) {
- exceptionState.throwIfNeeded();
- return;
- }
-
- frame->setLocation(locationValue);
-}
-
-} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8HTMLOptionsCollectionCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8HTMLOptionsCollectionCustom.cpp
index 094bf4acc8b..08ffb16adbd 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8HTMLOptionsCollectionCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8HTMLOptionsCollectionCustom.cpp
@@ -29,12 +29,11 @@
*/
#include "config.h"
-#include "V8HTMLOptionsCollection.h"
+#include "bindings/core/v8/V8HTMLOptionsCollection.h"
-#include "V8HTMLOptionElement.h"
-#include "V8Node.h"
-#include "V8NodeList.h"
-#include "bindings/v8/ExceptionMessages.h"
+#include "bindings/core/v8/V8HTMLOptionElement.h"
+#include "bindings/core/v8/V8Node.h"
+#include "bindings/core/v8/V8NodeList.h"
#include "bindings/v8/ExceptionState.h"
#include "bindings/v8/V8Binding.h"
#include "core/dom/ExceptionCode.h"
@@ -45,50 +44,23 @@
namespace WebCore {
-template<typename CallbackInfo>
-static void getNamedItems(HTMLOptionsCollection* collection, const AtomicString& name, const CallbackInfo& info)
-{
- Vector<RefPtr<Node> > namedItems;
- collection->namedItems(name, namedItems);
-
- if (!namedItems.size()) {
- v8SetReturnValueNull(info);
- return;
- }
-
- if (namedItems.size() == 1) {
- v8SetReturnValueFast(info, namedItems.at(0).release(), collection);
- return;
- }
-
- v8SetReturnValueFast(info, NamedNodesCollection::create(namedItems), collection);
-}
-
-void V8HTMLOptionsCollection::namedItemMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
-{
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<>, name, info[0]);
- HTMLOptionsCollection* imp = V8HTMLOptionsCollection::toNative(info.Holder());
- getNamedItems(imp, name, info);
-}
-
void V8HTMLOptionsCollection::addMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
ExceptionState exceptionState(ExceptionState::ExecutionContext, "add", "HTMLOptionsCollection", info.Holder(), info.GetIsolate());
- if (!V8HTMLOptionElement::hasInstance(info[0], info.GetIsolate(), worldType(info.GetIsolate()))) {
+ if (!V8HTMLOptionElement::hasInstance(info[0], info.GetIsolate())) {
exceptionState.throwTypeError("The element provided was not an HTMLOptionElement.");
} else {
- HTMLOptionsCollection* imp = V8HTMLOptionsCollection::toNative(info.Holder());
+ HTMLOptionsCollection* impl = V8HTMLOptionsCollection::toNative(info.Holder());
HTMLOptionElement* option = V8HTMLOptionElement::toNative(v8::Handle<v8::Object>(v8::Handle<v8::Object>::Cast(info[0])));
if (info.Length() < 2) {
- imp->add(option, exceptionState);
+ impl->add(option, exceptionState);
} else {
- bool ok;
- V8TRYCATCH_VOID(int, index, toInt32(info[1], ok));
- if (!ok)
- exceptionState.throwTypeError("The index provided could not be interpreted as an integer.");
- else
- imp->add(option, index, exceptionState);
+ int index = toInt32(info[1], exceptionState);
+ if (exceptionState.throwIfNeeded())
+ return;
+
+ impl->add(option, index, exceptionState);
}
}
@@ -97,7 +69,7 @@ void V8HTMLOptionsCollection::addMethodCustom(const v8::FunctionCallbackInfo<v8:
void V8HTMLOptionsCollection::lengthAttributeSetterCustom(v8::Local<v8::Value> value, const v8::PropertyCallbackInfo<void>& info)
{
- HTMLOptionsCollection* imp = V8HTMLOptionsCollection::toNative(info.Holder());
+ HTMLOptionsCollection* impl = V8HTMLOptionsCollection::toNative(info.Holder());
double v = value->NumberValue();
unsigned newLength = 0;
ExceptionState exceptionState(ExceptionState::SetterContext, "length", "HTMLOptionsCollection", info.Holder(), info.GetIsolate());
@@ -113,7 +85,7 @@ void V8HTMLOptionsCollection::lengthAttributeSetterCustom(v8::Local<v8::Value> v
if (exceptionState.throwIfNeeded())
return;
- imp->setLength(newLength, exceptionState);
+ impl->setLength(newLength, exceptionState);
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8HTMLPlugInElementCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8HTMLPlugInElementCustom.cpp
index d29360ac3cb..ac4f4cde34c 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8HTMLPlugInElementCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8HTMLPlugInElementCustom.cpp
@@ -30,9 +30,9 @@
#include "config.h"
-#include "V8HTMLAppletElement.h"
-#include "V8HTMLEmbedElement.h"
-#include "V8HTMLObjectElement.h"
+#include "bindings/core/v8/V8HTMLAppletElement.h"
+#include "bindings/core/v8/V8HTMLEmbedElement.h"
+#include "bindings/core/v8/V8HTMLObjectElement.h"
#include "bindings/v8/SharedPersistent.h"
#include "bindings/v8/V8Binding.h"
#include "bindings/v8/V8NPObject.h"
@@ -46,8 +46,8 @@ namespace WebCore {
template <class C>
static void npObjectNamedGetter(v8::Local<v8::String> name, const v8::PropertyCallbackInfo<v8::Value>& info)
{
- HTMLPlugInElement* imp = C::toNative(info.Holder());
- RefPtr<SharedPersistent<v8::Object> > wrapper = imp->pluginWrapper();
+ HTMLPlugInElement* impl = C::toNative(info.Holder());
+ RefPtr<SharedPersistent<v8::Object> > wrapper = impl->pluginWrapper();
if (!wrapper)
return;
@@ -61,8 +61,8 @@ static void npObjectNamedGetter(v8::Local<v8::String> name, const v8::PropertyCa
template <class C>
static void npObjectNamedSetter(v8::Local<v8::String> name, v8::Local<v8::Value> value, const v8::PropertyCallbackInfo<v8::Value>& info)
{
- HTMLPlugInElement* imp = C::toNative(info.Holder());
- RefPtr<SharedPersistent<v8::Object> > wrapper = imp->pluginWrapper();
+ HTMLPlugInElement* impl = C::toNative(info.Holder());
+ RefPtr<SharedPersistent<v8::Object> > wrapper = impl->pluginWrapper();
if (!wrapper)
return;
@@ -105,30 +105,30 @@ void V8HTMLObjectElement::namedPropertySetterCustom(v8::Local<v8::String> name,
void V8HTMLAppletElement::legacyCallCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
- HTMLPlugInElement* imp = V8HTMLAppletElement::toNative(info.Holder());
- UseCounter::count(imp->document(), UseCounter::HTMLAppletElementLegacyCall);
+ HTMLPlugInElement* impl = V8HTMLAppletElement::toNative(info.Holder());
+ UseCounter::count(impl->document(), UseCounter::HTMLAppletElementLegacyCall);
npObjectInvokeDefaultHandler(info);
}
void V8HTMLEmbedElement::legacyCallCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
- HTMLPlugInElement* imp = V8HTMLEmbedElement::toNative(info.Holder());
- UseCounter::count(imp->document(), UseCounter::HTMLEmbedElementLegacyCall);
+ HTMLPlugInElement* impl = V8HTMLEmbedElement::toNative(info.Holder());
+ UseCounter::count(impl->document(), UseCounter::HTMLEmbedElementLegacyCall);
npObjectInvokeDefaultHandler(info);
}
void V8HTMLObjectElement::legacyCallCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
- HTMLPlugInElement* imp = V8HTMLObjectElement::toNative(info.Holder());
- UseCounter::count(imp->document(), UseCounter::HTMLObjectElementLegacyCall);
+ HTMLPlugInElement* impl = V8HTMLObjectElement::toNative(info.Holder());
+ UseCounter::count(impl->document(), UseCounter::HTMLObjectElementLegacyCall);
npObjectInvokeDefaultHandler(info);
}
template <class C>
void npObjectIndexedGetter(uint32_t index, const v8::PropertyCallbackInfo<v8::Value>& info)
{
- HTMLPlugInElement* imp = C::toNative(info.Holder());
- RefPtr<SharedPersistent<v8::Object> > wrapper = imp->pluginWrapper();
+ HTMLPlugInElement* impl = C::toNative(info.Holder());
+ RefPtr<SharedPersistent<v8::Object> > wrapper = impl->pluginWrapper();
if (!wrapper)
return;
@@ -142,8 +142,8 @@ void npObjectIndexedGetter(uint32_t index, const v8::PropertyCallbackInfo<v8::Va
template <class C>
void npObjectIndexedSetter(uint32_t index, v8::Local<v8::Value> value, const v8::PropertyCallbackInfo<v8::Value>& info)
{
- HTMLPlugInElement* imp = C::toNative(info.Holder());
- RefPtr<SharedPersistent<v8::Object> > wrapper = imp->pluginWrapper();
+ HTMLPlugInElement* impl = C::toNative(info.Holder());
+ RefPtr<SharedPersistent<v8::Object> > wrapper = impl->pluginWrapper();
if (!wrapper)
return;
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8HistoryCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8HistoryCustom.cpp
index 427e8776532..ec963bf1204 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8HistoryCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8HistoryCustom.cpp
@@ -29,13 +29,13 @@
*/
#include "config.h"
-#include "V8History.h"
+#include "bindings/core/v8/V8History.h"
-#include "V8Window.h"
+#include "bindings/core/v8/V8Window.h"
#include "bindings/v8/ExceptionState.h"
#include "bindings/v8/SerializedScriptValue.h"
#include "bindings/v8/V8Binding.h"
-#include "bindings/v8/V8HiddenPropertyName.h"
+#include "bindings/v8/V8HiddenValue.h"
#include "core/dom/ExceptionCode.h"
#include "core/frame/History.h"
@@ -45,7 +45,7 @@ void V8History::stateAttributeGetterCustom(const v8::PropertyCallbackInfo<v8::Va
{
History* history = V8History::toNative(info.Holder());
- v8::Handle<v8::Value> value = info.Holder()->GetHiddenValue(V8HiddenPropertyName::state(info.GetIsolate()));
+ v8::Handle<v8::Value> value = V8HiddenValue::getHiddenValue(info.GetIsolate(), info.Holder(), V8HiddenValue::state(info.GetIsolate()));
if (!value.IsEmpty() && !history->stateChanged()) {
v8SetReturnValue(info, value);
@@ -54,42 +54,40 @@ void V8History::stateAttributeGetterCustom(const v8::PropertyCallbackInfo<v8::Va
RefPtr<SerializedScriptValue> serialized = history->state();
value = serialized ? serialized->deserialize(info.GetIsolate()) : v8::Handle<v8::Value>(v8::Null(info.GetIsolate()));
- info.Holder()->SetHiddenValue(V8HiddenPropertyName::state(info.GetIsolate()), value);
+ V8HiddenValue::setHiddenValue(info.GetIsolate(), info.Holder(), V8HiddenValue::state(info.GetIsolate()), value);
v8SetReturnValue(info, value);
}
void V8History::pushStateMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
- bool didThrow = false;
- RefPtr<SerializedScriptValue> historyState = SerializedScriptValue::create(info[0], 0, 0, didThrow, info.GetIsolate());
- if (didThrow)
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "pushState", "History", info.Holder(), info.GetIsolate());
+ RefPtr<SerializedScriptValue> historyState = SerializedScriptValue::create(info[0], 0, 0, exceptionState, info.GetIsolate());
+ if (exceptionState.throwIfNeeded())
return;
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<WithUndefinedOrNullCheck>, title, info[1]);
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<WithUndefinedOrNullCheck>, url, argumentOrNull(info, 2));
+ TOSTRING_VOID(V8StringResource<WithUndefinedOrNullCheck>, title, info[1]);
+ TOSTRING_VOID(V8StringResource<WithUndefinedOrNullCheck>, url, argumentOrNull(info, 2));
- ExceptionState exceptionState(info.Holder(), info.GetIsolate());
History* history = V8History::toNative(info.Holder());
- history->stateObjectAdded(historyState.release(), title, url, SameDocumentNavigationPushState, exceptionState);
- info.Holder()->DeleteHiddenValue(V8HiddenPropertyName::state(info.GetIsolate()));
+ history->stateObjectAdded(historyState.release(), title, url, FrameLoadTypeStandard, exceptionState);
+ V8HiddenValue::deleteHiddenValue(info.GetIsolate(), info.Holder(), V8HiddenValue::state(info.GetIsolate()));
exceptionState.throwIfNeeded();
}
void V8History::replaceStateMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
- bool didThrow = false;
- RefPtr<SerializedScriptValue> historyState = SerializedScriptValue::create(info[0], 0, 0, didThrow, info.GetIsolate());
- if (didThrow)
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "replaceState", "History", info.Holder(), info.GetIsolate());
+ RefPtr<SerializedScriptValue> historyState = SerializedScriptValue::create(info[0], 0, 0, exceptionState, info.GetIsolate());
+ if (exceptionState.throwIfNeeded())
return;
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<WithUndefinedOrNullCheck>, title, info[1]);
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<WithUndefinedOrNullCheck>, url, argumentOrNull(info, 2));
+ TOSTRING_VOID(V8StringResource<WithUndefinedOrNullCheck>, title, info[1]);
+ TOSTRING_VOID(V8StringResource<WithUndefinedOrNullCheck>, url, argumentOrNull(info, 2));
- ExceptionState exceptionState(info.Holder(), info.GetIsolate());
History* history = V8History::toNative(info.Holder());
- history->stateObjectAdded(historyState.release(), title, url, SameDocumentNavigationReplaceState, exceptionState);
- info.Holder()->DeleteHiddenValue(V8HiddenPropertyName::state(info.GetIsolate()));
+ history->stateObjectAdded(historyState.release(), title, url, FrameLoadTypeRedirectWithLockedBackForwardList, exceptionState);
+ V8HiddenValue::deleteHiddenValue(info.GetIsolate(), info.Holder(), V8HiddenValue::state(info.GetIsolate()));
exceptionState.throwIfNeeded();
}
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8ImageDataCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8ImageDataCustom.cpp
index 813731456ec..c940c7c44f8 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8ImageDataCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8ImageDataCustom.cpp
@@ -29,7 +29,7 @@
*/
#include "config.h"
-#include "V8ImageData.h"
+#include "bindings/core/v8/V8ImageData.h"
#include "bindings/v8/custom/V8Uint8ClampedArrayCustom.h"
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8InjectedScriptHostCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8InjectedScriptHostCustom.cpp
index cb545e6e3a3..772649e1bfb 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8InjectedScriptHostCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8InjectedScriptHostCustom.cpp
@@ -29,21 +29,21 @@
*/
#include "config.h"
-#include "V8InjectedScriptHost.h"
-
-#include "V8Database.h"
-#include "V8HTMLAllCollection.h"
-#include "V8HTMLCollection.h"
-#include "V8Node.h"
-#include "V8NodeList.h"
-#include "V8Storage.h"
+#include "bindings/core/v8/V8InjectedScriptHost.h"
+
+#include "bindings/core/v8/V8EventTarget.h"
+#include "bindings/core/v8/V8HTMLAllCollection.h"
+#include "bindings/core/v8/V8HTMLCollection.h"
+#include "bindings/core/v8/V8Node.h"
+#include "bindings/core/v8/V8NodeList.h"
+#include "bindings/core/v8/V8Storage.h"
+#include "bindings/modules/v8/V8Database.h"
#include "bindings/v8/BindingSecurity.h"
#include "bindings/v8/ExceptionState.h"
#include "bindings/v8/ScriptDebugServer.h"
#include "bindings/v8/ScriptValue.h"
#include "bindings/v8/V8AbstractEventListener.h"
#include "bindings/v8/V8Binding.h"
-#include "bindings/v8/V8HiddenPropertyName.h"
#include "bindings/v8/V8ScriptRunner.h"
#include "bindings/v8/custom/V8Float32ArrayCustom.h"
#include "bindings/v8/custom/V8Float64ArrayCustom.h"
@@ -54,6 +54,8 @@
#include "bindings/v8/custom/V8Uint32ArrayCustom.h"
#include "bindings/v8/custom/V8Uint8ArrayCustom.h"
#include "bindings/v8/custom/V8Uint8ClampedArrayCustom.h"
+#include "core/events/EventTarget.h"
+#include "core/frame/LocalDOMWindow.h"
#include "core/inspector/InjectedScript.h"
#include "core/inspector/InjectedScriptHost.h"
#include "core/inspector/InspectorDOMAgent.h"
@@ -62,25 +64,22 @@
namespace WebCore {
-Node* InjectedScriptHost::scriptValueAsNode(ScriptValue value)
+Node* InjectedScriptHost::scriptValueAsNode(ScriptState* scriptState, ScriptValue value)
{
- v8::HandleScope scope(value.isolate());
+ ScriptState::Scope scope(scriptState);
if (!value.isObject() || value.isNull())
return 0;
return V8Node::toNative(v8::Handle<v8::Object>::Cast(value.v8Value()));
}
-ScriptValue InjectedScriptHost::nodeAsScriptValue(ScriptState* state, Node* node)
+ScriptValue InjectedScriptHost::nodeAsScriptValue(ScriptState* scriptState, Node* node)
{
- v8::Isolate* isolate = state->isolate();
- v8::HandleScope scope(isolate);
- v8::Local<v8::Context> context = state->context();
- v8::Context::Scope contextScope(context);
-
- ExceptionState exceptionState(v8::Handle<v8::Object>(), isolate);
- if (!BindingSecurity::shouldAllowAccessToNode(node, exceptionState))
- return ScriptValue(v8::Null(isolate), isolate);
- return ScriptValue(toV8(node, v8::Handle<v8::Object>(), isolate), isolate);
+ ScriptState::Scope scope(scriptState);
+ v8::Isolate* isolate = scriptState->isolate();
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "nodeAsScriptValue", "InjectedScriptHost", scriptState->context()->Global(), isolate);
+ if (!BindingSecurity::shouldAllowAccessToNode(isolate, node, exceptionState))
+ return ScriptValue(scriptState, v8::Null(isolate));
+ return ScriptValue(scriptState, toV8(node, scriptState->context()->Global(), isolate));
}
void V8InjectedScriptHost::inspectedObjectMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
@@ -95,7 +94,7 @@ void V8InjectedScriptHost::inspectedObjectMethodCustom(const v8::FunctionCallbac
InjectedScriptHost* host = V8InjectedScriptHost::toNative(info.Holder());
InjectedScriptHost::InspectableObject* object = host->inspectedObject(info[0]->ToInt32()->Value());
- v8SetReturnValue(info, object->get(ScriptState::current()).v8Value());
+ v8SetReturnValue(info, object->get(ScriptState::current(info.GetIsolate())).v8Value());
}
void V8InjectedScriptHost::internalConstructorNameMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
@@ -119,7 +118,7 @@ void V8InjectedScriptHost::isHTMLAllCollectionMethodCustom(const v8::FunctionCal
return;
}
- v8SetReturnValue(info, V8HTMLAllCollection::hasInstance(info[0], info.GetIsolate(), worldType(info.GetIsolate())));
+ v8SetReturnValue(info, V8HTMLAllCollection::hasInstance(info[0], info.GetIsolate()));
}
void V8InjectedScriptHost::typeMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
@@ -153,32 +152,31 @@ void V8InjectedScriptHost::typeMethodCustom(const v8::FunctionCallbackInfo<v8::V
v8SetReturnValue(info, v8AtomicString(isolate, "regexp"));
return;
}
- WrapperWorldType currentWorldType = worldType(isolate);
- if (V8Node::hasInstance(value, isolate, currentWorldType)) {
+ if (V8Node::hasInstance(value, isolate)) {
v8SetReturnValue(info, v8AtomicString(isolate, "node"));
return;
}
- if (V8NodeList::hasInstance(value, isolate, currentWorldType)) {
+ if (V8NodeList::hasInstance(value, isolate)) {
v8SetReturnValue(info, v8AtomicString(isolate, "array"));
return;
}
- if (V8HTMLCollection::hasInstance(value, isolate, currentWorldType)) {
+ if (V8HTMLCollection::hasInstance(value, isolate)) {
v8SetReturnValue(info, v8AtomicString(isolate, "array"));
return;
}
- if (V8Int8Array::hasInstance(value, isolate, currentWorldType) || V8Int16Array::hasInstance(value, isolate, currentWorldType) || V8Int32Array::hasInstance(value, isolate, currentWorldType)) {
+ if (V8Int8Array::hasInstance(value, isolate) || V8Int16Array::hasInstance(value, isolate) || V8Int32Array::hasInstance(value, isolate)) {
v8SetReturnValue(info, v8AtomicString(isolate, "array"));
return;
}
- if (V8Uint8Array::hasInstance(value, isolate, currentWorldType) || V8Uint16Array::hasInstance(value, isolate, currentWorldType) || V8Uint32Array::hasInstance(value, isolate, currentWorldType)) {
+ if (V8Uint8Array::hasInstance(value, isolate) || V8Uint16Array::hasInstance(value, isolate) || V8Uint32Array::hasInstance(value, isolate)) {
v8SetReturnValue(info, v8AtomicString(isolate, "array"));
return;
}
- if (V8Float32Array::hasInstance(value, isolate, currentWorldType) || V8Float64Array::hasInstance(value, isolate, currentWorldType)) {
+ if (V8Float32Array::hasInstance(value, isolate) || V8Float64Array::hasInstance(value, isolate)) {
v8SetReturnValue(info, v8AtomicString(isolate, "array"));
return;
}
- if (V8Uint8ClampedArray::hasInstance(value, isolate, currentWorldType)) {
+ if (V8Uint8ClampedArray::hasInstance(value, isolate)) {
v8SetReturnValue(info, v8AtomicString(isolate, "array"));
return;
}
@@ -207,12 +205,12 @@ void V8InjectedScriptHost::functionDetailsMethodCustom(const v8::FunctionCallbac
int lineNumber = function->GetScriptLineNumber();
int columnNumber = function->GetScriptColumnNumber();
- v8::Local<v8::Object> location = v8::Object::New();
- location->Set(v8AtomicString(isolate, "lineNumber"), v8::Integer::New(lineNumber, isolate));
- location->Set(v8AtomicString(isolate, "columnNumber"), v8::Integer::New(columnNumber, isolate));
- location->Set(v8AtomicString(isolate, "scriptId"), v8::Integer::New(function->ScriptId(), isolate)->ToString());
+ v8::Local<v8::Object> location = v8::Object::New(isolate);
+ location->Set(v8AtomicString(isolate, "lineNumber"), v8::Integer::New(isolate, lineNumber));
+ location->Set(v8AtomicString(isolate, "columnNumber"), v8::Integer::New(isolate, columnNumber));
+ location->Set(v8AtomicString(isolate, "scriptId"), v8::Integer::New(isolate, function->ScriptId())->ToString());
- v8::Local<v8::Object> result = v8::Object::New();
+ v8::Local<v8::Object> result = v8::Object::New(isolate);
result->Set(v8AtomicString(isolate, "location"), location);
if (!setFunctionName(result, function->GetDisplayName(), isolate)
@@ -241,7 +239,7 @@ void V8InjectedScriptHost::getInternalPropertiesMethodCustom(const v8::FunctionC
v8SetReturnValue(info, debugServer.getInternalProperties(object));
}
-static v8::Handle<v8::Array> getJSListenerFunctions(Document* document, const EventListenerInfo& listenerInfo, v8::Isolate* isolate)
+static v8::Handle<v8::Array> getJSListenerFunctions(ExecutionContext* executionContext, const EventListenerInfo& listenerInfo, v8::Isolate* isolate)
{
v8::Local<v8::Array> result = v8::Array::New(isolate);
size_t handlersCount = listenerInfo.eventListenerVector.size();
@@ -252,7 +250,7 @@ static v8::Handle<v8::Array> getJSListenerFunctions(Document* document, const Ev
continue;
}
V8AbstractEventListener* v8Listener = static_cast<V8AbstractEventListener*>(listener.get());
- v8::Local<v8::Context> context = toV8Context(document, v8Listener->world());
+ v8::Local<v8::Context> context = toV8Context(executionContext, v8Listener->world());
// Hide listeners from other contexts.
if (context != isolate->GetCurrentContext())
continue;
@@ -260,12 +258,12 @@ static v8::Handle<v8::Array> getJSListenerFunctions(Document* document, const Ev
{
// getListenerObject() may cause JS in the event attribute to get compiled, potentially unsuccessfully.
v8::TryCatch block;
- function = v8Listener->getListenerObject(document);
+ function = v8Listener->getListenerObject(executionContext);
if (block.HasCaught())
continue;
}
ASSERT(!function.IsEmpty());
- v8::Local<v8::Object> listenerEntry = v8::Object::New();
+ v8::Local<v8::Object> listenerEntry = v8::Object::New(isolate);
listenerEntry->Set(v8AtomicString(isolate, "listener"), function);
listenerEntry->Set(v8AtomicString(isolate, "useCapture"), v8::Boolean::New(isolate, listenerInfo.eventListenerVector[i].useCapture));
result->Set(v8::Number::New(isolate, outputIndex++), listenerEntry);
@@ -278,20 +276,24 @@ void V8InjectedScriptHost::getEventListenersMethodCustom(const v8::FunctionCallb
if (info.Length() < 1)
return;
+
v8::Local<v8::Value> value = info[0];
- if (!V8Node::hasInstance(value, info.GetIsolate(), worldType(info.GetIsolate())))
- return;
- Node* node = V8Node::toNative(value->ToObject());
- if (!node)
+ EventTarget* target = V8EventTarget::toNativeWithTypeCheck(info.GetIsolate(), value);
+
+ // We need to handle a LocalDOMWindow specially, because a LocalDOMWindow wrapper exists on a prototype chain.
+ if (!target)
+ target = toDOMWindow(value, info.GetIsolate());
+
+ if (!target || !target->executionContext())
return;
InjectedScriptHost* host = V8InjectedScriptHost::toNative(info.Holder());
Vector<EventListenerInfo> listenersArray;
- host->getEventListenersImpl(node, listenersArray);
+ host->getEventListenersImpl(target, listenersArray);
- v8::Local<v8::Object> result = v8::Object::New();
+ v8::Local<v8::Object> result = v8::Object::New(info.GetIsolate());
for (size_t i = 0; i < listenersArray.size(); ++i) {
- v8::Handle<v8::Array> listeners = getJSListenerFunctions(&node->document(), listenersArray[i], info.GetIsolate());
+ v8::Handle<v8::Array> listeners = getJSListenerFunctions(target->executionContext(), listenersArray[i], info.GetIsolate());
if (!listeners->Length())
continue;
AtomicString eventType = listenersArray[i].eventType;
@@ -307,34 +309,10 @@ void V8InjectedScriptHost::inspectMethodCustom(const v8::FunctionCallbackInfo<v8
return;
InjectedScriptHost* host = V8InjectedScriptHost::toNative(info.Holder());
- ScriptValue object(info[0], info.GetIsolate());
- ScriptValue hints(info[1], info.GetIsolate());
- host->inspectImpl(object.toJSONValue(ScriptState::current()), hints.toJSONValue(ScriptState::current()));
-}
-
-void V8InjectedScriptHost::databaseIdMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
-{
- if (info.Length() > 0 && V8Database::hasInstance(info[0], info.GetIsolate(), worldType(info.GetIsolate()))) {
- Database* database = V8Database::toNative(v8::Handle<v8::Object>::Cast(info[0]));
- if (database) {
- InjectedScriptHost* host = V8InjectedScriptHost::toNative(info.Holder()); {
- v8SetReturnValueStringOrUndefined(info, host->databaseIdImpl(database), info.GetIsolate());
- return;
- }
- }
- }
-}
-
-void V8InjectedScriptHost::storageIdMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
-{
- if (info.Length() > 0 && V8Storage::hasInstance(info[0], info.GetIsolate(), worldType(info.GetIsolate()))) {
- Storage* storage = V8Storage::toNative(v8::Handle<v8::Object>::Cast(info[0]));
- if (storage) {
- InjectedScriptHost* host = V8InjectedScriptHost::toNative(info.Holder());
- v8SetReturnValueStringOrUndefined(info, host->storageIdImpl(storage), info.GetIsolate());
- return;
- }
- }
+ ScriptState* scriptState = ScriptState::current(info.GetIsolate());
+ ScriptValue object(scriptState, info[0]);
+ ScriptValue hints(scriptState, info[1]);
+ host->inspectImpl(object.toJSONValue(scriptState), hints.toJSONValue(scriptState));
}
void V8InjectedScriptHost::evaluateMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
@@ -351,7 +329,7 @@ void V8InjectedScriptHost::evaluateMethodCustom(const v8::FunctionCallbackInfo<v
return;
}
- ASSERT(!isolate->GetCurrentContext().IsEmpty());
+ ASSERT(isolate->InContext());
v8::TryCatch tryCatch;
v8::Handle<v8::Value> result = V8ScriptRunner::compileAndRunInternalScript(expression, info.GetIsolate());
if (tryCatch.HasCaught()) {
@@ -445,4 +423,25 @@ void V8InjectedScriptHost::unmonitorFunctionMethodCustom(const v8::FunctionCallb
host->unmonitorFunction(scriptId, lineNumber, columnNumber);
}
+void V8InjectedScriptHost::suppressWarningsAndCallMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
+{
+ if (info.Length() < 2 || !info[0]->IsObject() || !info[1]->IsFunction())
+ return;
+
+ InjectedScriptHost* host = V8InjectedScriptHost::toNative(info.Holder());
+ ScriptDebugServer& debugServer = host->scriptDebugServer();
+ debugServer.muteWarningsAndDeprecations();
+
+ v8::Handle<v8::Object> receiver = v8::Handle<v8::Object>::Cast(info[0]);
+ v8::Handle<v8::Function> function = v8::Handle<v8::Function>::Cast(info[1]);
+ size_t argc = info.Length() - 2;
+ OwnPtr<v8::Handle<v8::Value>[]> argv = adoptArrayPtr(new v8::Handle<v8::Value>[argc]);
+ for (size_t i = 0; i < argc; ++i)
+ argv[i] = info[i + 2];
+
+ v8::Local<v8::Value> result = function->Call(receiver, argc, argv.get());
+ debugServer.unmuteWarningsAndDeprecations();
+ v8SetReturnValue(info, result);
+}
+
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8InjectedScriptManager.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8InjectedScriptManager.cpp
index fbe5295d1af..fbeffc2fc2a 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8InjectedScriptManager.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8InjectedScriptManager.cpp
@@ -31,17 +31,17 @@
#include "config.h"
#include "core/inspector/InjectedScriptManager.h"
-#include "V8InjectedScriptHost.h"
-#include "V8Window.h"
+#include "bindings/core/v8/V8InjectedScriptHost.h"
+#include "bindings/core/v8/V8Window.h"
#include "bindings/v8/BindingSecurity.h"
#include "bindings/v8/ScopedPersistent.h"
#include "bindings/v8/ScriptDebugServer.h"
-#include "bindings/v8/ScriptObject.h"
+#include "bindings/v8/ScriptValue.h"
#include "bindings/v8/V8Binding.h"
#include "bindings/v8/V8ObjectConstructor.h"
#include "bindings/v8/V8ScriptRunner.h"
#include "core/inspector/InjectedScriptHost.h"
-#include "core/frame/DOMWindow.h"
+#include "core/frame/LocalDOMWindow.h"
#include "wtf/RefPtr.h"
namespace WebCore {
@@ -53,12 +53,12 @@ struct InjectedScriptManager::CallbackData {
static v8::Local<v8::Object> createInjectedScriptHostV8Wrapper(InjectedScriptHost* host, v8::Isolate* isolate)
{
- v8::Local<v8::Function> function = V8InjectedScriptHost::domTemplate(isolate, MainWorld)->GetFunction();
+ v8::Local<v8::Function> function = V8InjectedScriptHost::domTemplate(isolate)->GetFunction();
if (function.IsEmpty()) {
// Return if allocation failed.
return v8::Local<v8::Object>();
}
- v8::Local<v8::Object> instanceTemplate = V8ObjectConstructor::newInstance(function);
+ v8::Local<v8::Object> instanceTemplate = V8ObjectConstructor::newInstance(isolate, function);
if (instanceTemplate.IsEmpty()) {
// Avoid setting the wrapper if allocation failed.
return v8::Local<v8::Object>();
@@ -73,21 +73,18 @@ static v8::Local<v8::Object> createInjectedScriptHostV8Wrapper(InjectedScriptHos
return instanceTemplate;
}
-ScriptObject InjectedScriptManager::createInjectedScript(const String& scriptSource, ScriptState* inspectedScriptState, int id)
+ScriptValue InjectedScriptManager::createInjectedScript(const String& scriptSource, ScriptState* inspectedScriptState, int id)
{
v8::Isolate* isolate = inspectedScriptState->isolate();
- v8::HandleScope handleScope(isolate);
-
- v8::Local<v8::Context> inspectedContext = inspectedScriptState->context();
- v8::Context::Scope contextScope(inspectedContext);
+ ScriptState::Scope scope(inspectedScriptState);
// Call custom code to create InjectedScripHost wrapper specific for the context
// instead of calling toV8() that would create the
// wrapper in the current context.
// FIXME: make it possible to use generic bindings factory for InjectedScriptHost.
- v8::Local<v8::Object> scriptHostWrapper = createInjectedScriptHostV8Wrapper(m_injectedScriptHost.get(), inspectedContext->GetIsolate());
+ v8::Local<v8::Object> scriptHostWrapper = createInjectedScriptHostV8Wrapper(m_injectedScriptHost.get(), inspectedScriptState->isolate());
if (scriptHostWrapper.IsEmpty())
- return ScriptObject();
+ return ScriptValue();
// Inject javascript into the context. The compiled script is supposed to evaluate into
// a single anonymous function(it's anonymous to avoid cluttering the global object with
@@ -98,28 +95,24 @@ ScriptObject InjectedScriptManager::createInjectedScript(const String& scriptSou
ASSERT(!value.IsEmpty());
ASSERT(value->IsFunction());
- v8::Local<v8::Object> windowGlobal = inspectedContext->Global();
- v8::Handle<v8::Value> info[] = { scriptHostWrapper, windowGlobal, v8::Number::New(inspectedContext->GetIsolate(), id) };
- v8::Local<v8::Value> injectedScriptValue = V8ScriptRunner::callInternalFunction(v8::Local<v8::Function>::Cast(value), windowGlobal, WTF_ARRAY_LENGTH(info), info, inspectedContext->GetIsolate());
- return ScriptObject(inspectedScriptState, v8::Handle<v8::Object>::Cast(injectedScriptValue));
+ v8::Local<v8::Object> windowGlobal = inspectedScriptState->context()->Global();
+ v8::Handle<v8::Value> info[] = { scriptHostWrapper, windowGlobal, v8::Number::New(inspectedScriptState->isolate(), id) };
+ v8::Local<v8::Value> injectedScriptValue = V8ScriptRunner::callInternalFunction(v8::Local<v8::Function>::Cast(value), windowGlobal, WTF_ARRAY_LENGTH(info), info, inspectedScriptState->isolate());
+ return ScriptValue(inspectedScriptState, injectedScriptValue);
}
bool InjectedScriptManager::canAccessInspectedWindow(ScriptState* scriptState)
{
- v8::HandleScope handleScope(scriptState->isolate());
- v8::Local<v8::Context> context = scriptState->context();
- v8::Local<v8::Object> global = context->Global();
+ ScriptState::Scope scope(scriptState);
+ v8::Local<v8::Object> global = scriptState->context()->Global();
if (global.IsEmpty())
return false;
- v8::Handle<v8::Object> holder = global->FindInstanceInPrototypeChain(V8Window::domTemplate(context->GetIsolate(), MainWorld));
- if (holder.IsEmpty())
- holder = global->FindInstanceInPrototypeChain(V8Window::domTemplate(context->GetIsolate(), IsolatedWorld));
+ v8::Handle<v8::Object> holder = V8Window::findInstanceInPrototypeChain(global, scriptState->isolate());
if (holder.IsEmpty())
return false;
- Frame* frame = V8Window::toNative(holder)->frame();
+ LocalFrame* frame = V8Window::toNative(holder)->frame();
- v8::Context::Scope contextScope(context);
- return BindingSecurity::shouldAllowAccessToFrame(frame, DoNotReportSecurityError);
+ return BindingSecurity::shouldAllowAccessToFrame(scriptState->isolate(), frame, DoNotReportSecurityError);
}
void InjectedScriptManager::setWeakCallback(const v8::WeakCallbackData<v8::Object, InjectedScriptManager::CallbackData>& data)
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8InspectorFrontendHostCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8InspectorFrontendHostCustom.cpp
index 6fef29ec312..439e9347ee3 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8InspectorFrontendHostCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8InspectorFrontendHostCustom.cpp
@@ -29,9 +29,9 @@
*/
#include "config.h"
-#include "V8InspectorFrontendHost.h"
+#include "bindings/core/v8/V8InspectorFrontendHost.h"
-#include "V8MouseEvent.h"
+#include "bindings/core/v8/V8MouseEvent.h"
#include "bindings/v8/V8Binding.h"
#include "core/inspector/InspectorController.h"
#include "core/inspector/InspectorFrontendClient.h"
@@ -80,7 +80,7 @@ static bool populateContextMenuItems(v8::Local<v8::Array>& itemArray, ContextMen
v8::Local<v8::Array> subItemsArray = v8::Local<v8::Array>::Cast(subItems);
if (!populateContextMenuItems(subItemsArray, subMenu, isolate))
return false;
- V8TRYCATCH_FOR_V8STRINGRESOURCE_RETURN(V8StringResource<WithNullCheck>, labelString, label, false);
+ TOSTRING_DEFAULT(V8StringResource<WithNullCheck>, labelString, label, false);
ContextMenuItem item(SubmenuType,
ContextMenuItemCustomTagNoAction,
labelString,
@@ -88,7 +88,7 @@ static bool populateContextMenuItems(v8::Local<v8::Array>& itemArray, ContextMen
menu.appendItem(item);
} else {
ContextMenuAction typedId = static_cast<ContextMenuAction>(ContextMenuItemBaseCustomTag + id->ToInt32()->Value());
- V8TRYCATCH_FOR_V8STRINGRESOURCE_RETURN(V8StringResource<WithNullCheck>, labelString, label, false);
+ TOSTRING_DEFAULT(V8StringResource<WithNullCheck>, labelString, label, false);
ContextMenuItem menuItem((typeString == "checkbox" ? CheckableActionType : ActionType), typedId, labelString);
if (checked->IsBoolean())
menuItem.setChecked(checked->ToBoolean()->Value());
@@ -143,10 +143,5 @@ void V8InspectorFrontendHost::recordPanelShownMethodCustom(const v8::FunctionCal
histogramEnumeration("DevTools.PanelShown", info, 20);
}
-void V8InspectorFrontendHost::recordSettingChangedMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
-{
- histogramEnumeration("DevTools.SettingChanged", info, 100);
-}
-
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8Int16ArrayCustom.h b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8Int16ArrayCustom.h
index 30f5f5864d4..58aab8bb3ae 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8Int16ArrayCustom.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8Int16ArrayCustom.h
@@ -59,10 +59,6 @@ public:
typedef V8TypedArray<Int16Array> V8Int16Array;
-template<>
-class WrapperTypeTraits<Int16Array> : public TypedArrayWrapperTraits<Int16Array> { };
-
-
inline v8::Handle<v8::Object> wrap(Int16Array* impl, v8::Handle<v8::Object> creationContext, v8::Isolate* isolate)
{
return V8TypedArray<Int16Array>::wrap(impl, creationContext, isolate);
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8Int32ArrayCustom.h b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8Int32ArrayCustom.h
index bbb4aafc94d..6c29dca3988 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8Int32ArrayCustom.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8Int32ArrayCustom.h
@@ -59,10 +59,6 @@ public:
typedef V8TypedArray<Int32Array> V8Int32Array;
-template<>
-class WrapperTypeTraits<Int32Array> : public TypedArrayWrapperTraits<Int32Array> { };
-
-
inline v8::Handle<v8::Object> wrap(Int32Array* impl, v8::Handle<v8::Object> creationContext, v8::Isolate* isolate)
{
return V8TypedArray<Int32Array>::wrap(impl, creationContext, isolate);
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8Int8ArrayCustom.h b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8Int8ArrayCustom.h
index 31a9e356ea4..e8783171357 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8Int8ArrayCustom.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8Int8ArrayCustom.h
@@ -59,10 +59,6 @@ public:
typedef V8TypedArray<Int8Array> V8Int8Array;
-template<>
-class WrapperTypeTraits<Int8Array> : public TypedArrayWrapperTraits<Int8Array> { };
-
-
inline v8::Handle<v8::Object> wrap(Int8Array* impl, v8::Handle<v8::Object> creationContext, v8::Isolate* isolate)
{
return V8TypedArray<Int8Array>::wrap(impl, creationContext, isolate);
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8JavaScriptCallFrameCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8JavaScriptCallFrameCustom.cpp
index 0f1a60ad709..c379d9a50dc 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8JavaScriptCallFrameCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8JavaScriptCallFrameCustom.cpp
@@ -29,7 +29,7 @@
*/
#include "config.h"
-#include "V8JavaScriptCallFrame.h"
+#include "bindings/core/v8/V8JavaScriptCallFrame.h"
#include "bindings/v8/V8Binding.h"
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8LocationCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8LocationCustom.cpp
index a9009c9f335..58835d5f127 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8LocationCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8LocationCustom.cpp
@@ -29,7 +29,7 @@
*/
#include "config.h"
-#include "V8Location.h"
+#include "bindings/core/v8/V8Location.h"
namespace WebCore {
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8MIDIInputCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8MIDIInputCustom.cpp
deleted file mode 100644
index 6ad179c447f..00000000000
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8MIDIInputCustom.cpp
+++ /dev/null
@@ -1,52 +0,0 @@
-/*
- * Copyright (C) 2013 Google Inc. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions are
- * met:
- *
- * * Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * * Redistributions in binary form must reproduce the above
- * copyright notice, this list of conditions and the following disclaimer
- * in the documentation and/or other materials provided with the
- * distribution.
- * * Neither the name of Google Inc. nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
- * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
- * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
- * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
- * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
- * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
- * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
- * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
- * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-#include "config.h"
-#include "V8MIDIInput.h"
-
-#include "V8MIDIAccess.h"
-#include "bindings/v8/V8HiddenPropertyName.h"
-
-namespace WebCore {
-
-v8::Handle<v8::Object> wrap(MIDIInput* input, v8::Handle<v8::Object> creationContext, v8::Isolate* isolate)
-{
- ASSERT(input);
- ASSERT(!DOMDataStore::containsWrapper<V8MIDIInput>(input, isolate));
-
- v8::Handle<v8::Object> wrapper = V8MIDIInput::createWrapper(input, creationContext, isolate);
-
- if (input->midiAccess())
- V8HiddenPropertyName::setNamedHiddenReference(wrapper, "access", toV8(input->midiAccess(), creationContext, isolate));
-
- return wrapper;
-}
-
-} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8MessageChannelCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8MessageChannelCustom.cpp
index 67ec60fbd92..d39c588710d 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8MessageChannelCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8MessageChannelCustom.cpp
@@ -29,12 +29,11 @@
*/
#include "config.h"
-#include "V8MessageChannel.h"
+#include "bindings/core/v8/V8MessageChannel.h"
-#include "V8MessagePort.h"
+#include "bindings/core/v8/V8MessagePort.h"
#include "bindings/v8/V8Binding.h"
-#include "bindings/v8/V8HiddenPropertyName.h"
-#include "bindings/v8/V8Utilities.h"
+#include "bindings/v8/V8HiddenValue.h"
#include "core/dom/MessageChannel.h"
#include "core/workers/WorkerGlobalScope.h"
#include "wtf/RefPtr.h"
@@ -43,17 +42,17 @@ namespace WebCore {
void V8MessageChannel::constructorCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
- ExecutionContext* context = getExecutionContext();
+ ExecutionContext* context = currentExecutionContext(info.GetIsolate());
- RefPtr<MessageChannel> obj = MessageChannel::create(context);
+ RefPtrWillBeRawPtr<MessageChannel> obj = MessageChannel::create(context);
v8::Local<v8::Object> wrapper = info.Holder();
// Create references from the MessageChannel wrapper to the two
// MessagePort wrappers to make sure that the MessagePort wrappers
// stay alive as long as the MessageChannel wrapper is around.
- V8HiddenPropertyName::setNamedHiddenReference(wrapper, "port1", toV8(obj->port1(), info.Holder(), info.GetIsolate()));
- V8HiddenPropertyName::setNamedHiddenReference(wrapper, "port2", toV8(obj->port2(), info.Holder(), info.GetIsolate()));
+ V8HiddenValue::setHiddenValue(info.GetIsolate(), wrapper, V8HiddenValue::port1(info.GetIsolate()), toV8(obj->port1(), info.Holder(), info.GetIsolate()));
+ V8HiddenValue::setHiddenValue(info.GetIsolate(), wrapper, V8HiddenValue::port2(info.GetIsolate()), toV8(obj->port2(), info.Holder(), info.GetIsolate()));
V8DOMWrapper::associateObjectWithWrapper<V8MessageChannel>(obj.release(), &wrapperTypeInfo, wrapper, info.GetIsolate(), WrapperConfiguration::Dependent);
info.GetReturnValue().Set(wrapper);
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8MessageEventCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8MessageEventCustom.cpp
index 9060e643728..145af08fab3 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8MessageEventCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8MessageEventCustom.cpp
@@ -29,19 +29,50 @@
*/
#include "config.h"
-#include "V8MessageEvent.h"
+#include "bindings/core/v8/V8MessageEvent.h"
-#include "V8Blob.h"
-#include "V8MessagePort.h"
-#include "V8Window.h"
+#include "bindings/core/v8/V8Blob.h"
+#include "bindings/core/v8/V8MessagePort.h"
+#include "bindings/core/v8/V8Window.h"
#include "bindings/v8/SerializedScriptValue.h"
#include "bindings/v8/V8Binding.h"
-#include "bindings/v8/V8HiddenPropertyName.h"
+#include "bindings/v8/V8HiddenValue.h"
#include "bindings/v8/custom/V8ArrayBufferCustom.h"
#include "core/events/MessageEvent.h"
namespace WebCore {
+// Ensures a wrapper is created for the data to return now so that V8 knows how
+// much memory is used via the wrapper. To keep the wrapper alive, it's set to
+// the wrapper of the MessageEvent as a hidden value.
+static void ensureWrapperCreatedAndAssociated(MessageEvent* eventImpl, v8::Handle<v8::Object> eventWrapper, v8::Isolate* isolate)
+{
+ switch (eventImpl->dataType()) {
+ case MessageEvent::DataTypeScriptValue:
+ case MessageEvent::DataTypeSerializedScriptValue:
+ break;
+ case MessageEvent::DataTypeString: {
+ String stringValue = eventImpl->dataAsString();
+ V8HiddenValue::setHiddenValue(isolate, eventWrapper, V8HiddenValue::stringData(isolate), v8String(isolate, stringValue));
+ break;
+ }
+ case MessageEvent::DataTypeBlob:
+ break;
+ case MessageEvent::DataTypeArrayBuffer:
+ V8HiddenValue::setHiddenValue(isolate, eventWrapper, V8HiddenValue::arrayBufferData(isolate), toV8(eventImpl->dataAsArrayBuffer(), eventWrapper, isolate));
+ break;
+ }
+}
+
+v8::Handle<v8::Object> wrap(MessageEvent* impl, v8::Handle<v8::Object> creationContext, v8::Isolate* isolate)
+{
+ ASSERT(impl);
+ ASSERT(!DOMDataStore::containsWrapper<V8MessageEvent>(impl, isolate));
+ v8::Handle<v8::Object> wrapper = V8MessageEvent::createWrapper(impl, creationContext, isolate);
+ ensureWrapperCreatedAndAssociated(impl, wrapper, isolate);
+ return wrapper;
+}
+
void V8MessageEvent::dataAttributeGetterCustom(const v8::PropertyCallbackInfo<v8::Value>& info)
{
MessageEvent* event = V8MessageEvent::toNative(info.Holder());
@@ -49,12 +80,12 @@ void V8MessageEvent::dataAttributeGetterCustom(const v8::PropertyCallbackInfo<v8
v8::Handle<v8::Value> result;
switch (event->dataType()) {
case MessageEvent::DataTypeScriptValue: {
- result = info.Holder()->GetHiddenValue(V8HiddenPropertyName::data(info.GetIsolate()));
+ result = V8HiddenValue::getHiddenValue(info.GetIsolate(), info.Holder(), V8HiddenValue::data(info.GetIsolate()));
if (result.IsEmpty()) {
if (!event->dataAsSerializedScriptValue()) {
// If we're in an isolated world and the event was created in the main world,
// we need to find the 'data' property on the main world wrapper and clone it.
- v8::Local<v8::Value> mainWorldData = getHiddenValueFromMainWorldWrapper(info.GetIsolate(), event, V8HiddenPropertyName::data(info.GetIsolate()));
+ v8::Local<v8::Value> mainWorldData = V8HiddenValue::getHiddenValueFromMainWorldWrapper(info.GetIsolate(), event, V8HiddenValue::data(info.GetIsolate()));
if (!mainWorldData.IsEmpty())
event->setSerializedData(SerializedScriptValue::createAndSwallowExceptions(mainWorldData, info.GetIsolate()));
}
@@ -76,8 +107,11 @@ void V8MessageEvent::dataAttributeGetterCustom(const v8::PropertyCallbackInfo<v8
break;
case MessageEvent::DataTypeString: {
- String stringValue = event->dataAsString();
- result = v8String(info.GetIsolate(), stringValue);
+ result = V8HiddenValue::getHiddenValue(info.GetIsolate(), info.Holder(), V8HiddenValue::stringData(info.GetIsolate()));
+ if (result.IsEmpty()) {
+ String stringValue = event->dataAsString();
+ result = v8String(info.GetIsolate(), stringValue);
+ }
break;
}
@@ -86,12 +120,14 @@ void V8MessageEvent::dataAttributeGetterCustom(const v8::PropertyCallbackInfo<v8
break;
case MessageEvent::DataTypeArrayBuffer:
- result = toV8(event->dataAsArrayBuffer(), info.Holder(), info.GetIsolate());
+ result = V8HiddenValue::getHiddenValue(info.GetIsolate(), info.Holder(), V8HiddenValue::arrayBufferData(info.GetIsolate()));
+ if (result.IsEmpty())
+ result = toV8(event->dataAsArrayBuffer(), info.Holder(), info.GetIsolate());
break;
}
// Overwrite the data attribute so it returns the cached result in future invocations.
- // This custom handler (dataAccessGetter) will not be called again.
+ // This custom getter handler will not be called again.
v8::PropertyAttribute dataAttr = static_cast<v8::PropertyAttribute>(v8::DontDelete | v8::ReadOnly);
info.Holder()->ForceSet(v8AtomicString(info.GetIsolate(), "data"), result, dataAttr);
v8SetReturnValue(info, result);
@@ -100,41 +136,29 @@ void V8MessageEvent::dataAttributeGetterCustom(const v8::PropertyCallbackInfo<v8
void V8MessageEvent::initMessageEventMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
MessageEvent* event = V8MessageEvent::toNative(info.Holder());
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<>, typeArg, info[0]);
- V8TRYCATCH_VOID(bool, canBubbleArg, info[1]->BooleanValue());
- V8TRYCATCH_VOID(bool, cancelableArg, info[2]->BooleanValue());
+ TOSTRING_VOID(V8StringResource<>, typeArg, info[0]);
+ TONATIVE_VOID(bool, canBubbleArg, info[1]->BooleanValue());
+ TONATIVE_VOID(bool, cancelableArg, info[2]->BooleanValue());
v8::Handle<v8::Value> dataArg = info[3];
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<>, originArg, info[4]);
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<>, lastEventIdArg, info[5]);
-
- DOMWindow* sourceArg = 0;
- if (info[6]->IsObject()) {
- v8::Handle<v8::Object> wrapper = v8::Handle<v8::Object>::Cast(info[6]);
- v8::Handle<v8::Object> window = wrapper->FindInstanceInPrototypeChain(V8Window::domTemplate(info.GetIsolate(), worldTypeInMainThread(info.GetIsolate())));
- if (!window.IsEmpty())
- sourceArg = V8Window::toNative(window);
- }
+ TOSTRING_VOID(V8StringResource<>, originArg, info[4]);
+ TOSTRING_VOID(V8StringResource<>, lastEventIdArg, info[5]);
+ LocalDOMWindow* sourceArg = toDOMWindow(info[6], info.GetIsolate());
OwnPtr<MessagePortArray> portArray;
-
const int portArrayIndex = 7;
if (!isUndefinedOrNull(info[portArrayIndex])) {
portArray = adoptPtr(new MessagePortArray);
- if (!getMessagePortArray(info[portArrayIndex], portArrayIndex + 1, *portArray, info.GetIsolate()))
+ bool success = false;
+ *portArray = toRefPtrNativeArray<MessagePort, V8MessagePort>(info[portArrayIndex], portArrayIndex + 1, info.GetIsolate(), &success);
+ if (!success)
return;
}
event->initMessageEvent(typeArg, canBubbleArg, cancelableArg, originArg, lastEventIdArg, sourceArg, portArray.release());
if (!dataArg.IsEmpty()) {
- info.Holder()->SetHiddenValue(V8HiddenPropertyName::data(info.GetIsolate()), dataArg);
- if (isolatedWorldForIsolate(info.GetIsolate()))
+ V8HiddenValue::setHiddenValue(info.GetIsolate(), info.Holder(), V8HiddenValue::data(info.GetIsolate()), dataArg);
+ if (DOMWrapperWorld::current(info.GetIsolate()).isIsolatedWorld())
event->setSerializedData(SerializedScriptValue::createAndSwallowExceptions(dataArg, info.GetIsolate()));
}
}
-void V8MessageEvent::webkitInitMessageEventMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
-{
- initMessageEventMethodCustom(info);
-}
-
-
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8MessagePortCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8MessagePortCustom.cpp
index f8eb9df2abd..d368989ba93 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8MessagePortCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8MessagePortCustom.cpp
@@ -29,13 +29,12 @@
*/
#include "config.h"
-#include "V8MessagePort.h"
+#include "bindings/core/v8/V8MessagePort.h"
#include "bindings/v8/ExceptionMessages.h"
#include "bindings/v8/ExceptionState.h"
#include "bindings/v8/SerializedScriptValue.h"
#include "bindings/v8/V8Binding.h"
-#include "bindings/v8/V8Utilities.h"
#include "core/dom/MessagePort.h"
#include "wtf/ArrayBuffer.h"
@@ -48,19 +47,14 @@ void V8MessagePort::postMessageMethodCustom(const v8::FunctionCallbackInfo<v8::V
MessagePortArray portArray;
ArrayBufferArray arrayBufferArray;
if (info.Length() > 1) {
- bool notASequence = false;
const int transferablesArgIndex = 1;
- if (!extractTransferables(info[transferablesArgIndex], portArray, arrayBufferArray, notASequence, info.GetIsolate())) {
- if (notASequence) {
- exceptionState.throwTypeError(ExceptionMessages::notAnArrayTypeArgumentOrValue(transferablesArgIndex + 1));
- exceptionState.throwIfNeeded();
- }
+ if (!SerializedScriptValue::extractTransferables(info[transferablesArgIndex], transferablesArgIndex, portArray, arrayBufferArray, exceptionState, info.GetIsolate())) {
+ exceptionState.throwIfNeeded();
return;
}
}
- bool didThrow = false;
- RefPtr<SerializedScriptValue> message = SerializedScriptValue::create(info[0], &portArray, &arrayBufferArray, didThrow, info.GetIsolate());
- if (didThrow)
+ RefPtr<SerializedScriptValue> message = SerializedScriptValue::create(info[0], &portArray, &arrayBufferArray, exceptionState, info.GetIsolate());
+ if (exceptionState.throwIfNeeded())
return;
messagePort->postMessage(message.release(), &portArray, exceptionState);
exceptionState.throwIfNeeded();
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8MutationObserverCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8MutationObserverCustom.cpp
index f19d3eb52ff..f2e62908d48 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8MutationObserverCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8MutationObserverCustom.cpp
@@ -29,14 +29,14 @@
*/
#include "config.h"
-#include "V8MutationObserver.h"
+#include "bindings/core/v8/V8MutationObserver.h"
#include "bindings/v8/ExceptionMessages.h"
#include "bindings/v8/ExceptionState.h"
#include "bindings/v8/V8Binding.h"
#include "bindings/v8/V8DOMWrapper.h"
+#include "bindings/v8/V8GCController.h"
#include "bindings/v8/V8MutationCallback.h"
-#include "bindings/v8/V8Utilities.h"
#include "core/dom/MutationObserver.h"
namespace WebCore {
@@ -57,14 +57,23 @@ void V8MutationObserver::constructorCustom(const v8::FunctionCallbackInfo<v8::Va
return;
}
- ExecutionContext* context = getExecutionContext();
v8::Handle<v8::Object> wrapper = info.Holder();
- OwnPtr<MutationCallback> callback = V8MutationCallback::create(v8::Handle<v8::Function>::Cast(arg), context, wrapper, info.GetIsolate());
- RefPtr<MutationObserver> observer = MutationObserver::create(callback.release());
+ OwnPtr<MutationCallback> callback = V8MutationCallback::create(v8::Handle<v8::Function>::Cast(arg), wrapper, ScriptState::current(info.GetIsolate()));
+ RefPtrWillBeRawPtr<MutationObserver> observer = MutationObserver::create(callback.release());
V8DOMWrapper::associateObjectWithWrapper<V8MutationObserver>(observer.release(), &wrapperTypeInfo, wrapper, info.GetIsolate(), WrapperConfiguration::Dependent);
info.GetReturnValue().Set(wrapper);
}
+void V8MutationObserver::visitDOMWrapper(void* object, const v8::Persistent<v8::Object>& wrapper, v8::Isolate* isolate)
+{
+ MutationObserver* observer = static_cast<MutationObserver*>(object);
+ HashSet<Node*> observedNodes = observer->getObservedNodes();
+ for (HashSet<Node*>::iterator it = observedNodes.begin(); it != observedNodes.end(); ++it) {
+ v8::UniqueId id(reinterpret_cast<intptr_t>(V8GCController::opaqueRootForGC(*it, isolate)));
+ isolate->SetReferenceFromGroup(id, wrapper);
+ }
+}
+
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8NodeCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8NodeCustom.cpp
index 854eb42b1e3..159b31e303b 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8NodeCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8NodeCustom.cpp
@@ -29,22 +29,21 @@
*/
#include "config.h"
-#include "V8Node.h"
-
-#include "V8Attr.h"
-#include "V8CDATASection.h"
-#include "V8Comment.h"
-#include "V8Document.h"
-#include "V8DocumentFragment.h"
-#include "V8DocumentType.h"
-#include "V8Element.h"
-#include "V8Entity.h"
-#include "V8HTMLElement.h"
-#include "V8Notation.h"
-#include "V8ProcessingInstruction.h"
-#include "V8SVGElement.h"
-#include "V8ShadowRoot.h"
-#include "V8Text.h"
+#include "bindings/core/v8/V8Node.h"
+
+#include "bindings/core/v8/V8Attr.h"
+#include "bindings/core/v8/V8CDATASection.h"
+#include "bindings/core/v8/V8Comment.h"
+#include "bindings/core/v8/V8Document.h"
+#include "bindings/core/v8/V8DocumentFragment.h"
+#include "bindings/core/v8/V8DocumentType.h"
+#include "bindings/core/v8/V8Element.h"
+#include "bindings/core/v8/V8HTMLElement.h"
+#include "bindings/core/v8/V8Notation.h"
+#include "bindings/core/v8/V8ProcessingInstruction.h"
+#include "bindings/core/v8/V8SVGElement.h"
+#include "bindings/core/v8/V8ShadowRoot.h"
+#include "bindings/core/v8/V8Text.h"
#include "bindings/v8/ExceptionState.h"
#include "bindings/v8/V8AbstractEventListener.h"
#include "bindings/v8/V8Binding.h"
@@ -62,14 +61,14 @@ namespace WebCore {
void V8Node::insertBeforeMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
v8::Handle<v8::Object> holder = info.Holder();
- Node* imp = V8Node::toNative(holder);
+ Node* impl = V8Node::toNative(holder);
CustomElementCallbackDispatcher::CallbackDeliveryScope deliveryScope;
ExceptionState exceptionState(ExceptionState::ExecutionContext, "insertBefore", "Node", info.Holder(), info.GetIsolate());
- Node* newChild = V8Node::hasInstance(info[0], info.GetIsolate(), worldType(info.GetIsolate())) ? V8Node::toNative(v8::Handle<v8::Object>::Cast(info[0])) : 0;
- Node* refChild = V8Node::hasInstance(info[1], info.GetIsolate(), worldType(info.GetIsolate())) ? V8Node::toNative(v8::Handle<v8::Object>::Cast(info[1])) : 0;
- imp->insertBefore(newChild, refChild, exceptionState);
+ Node* newChild = V8Node::toNativeWithTypeCheck(info.GetIsolate(), info[0]);
+ Node* refChild = V8Node::toNativeWithTypeCheck(info.GetIsolate(), info[1]);
+ impl->insertBefore(newChild, refChild, exceptionState);
if (exceptionState.throwIfNeeded())
return;
v8SetReturnValue(info, info[0]);
@@ -78,14 +77,14 @@ void V8Node::insertBeforeMethodCustom(const v8::FunctionCallbackInfo<v8::Value>&
void V8Node::replaceChildMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
v8::Handle<v8::Object> holder = info.Holder();
- Node* imp = V8Node::toNative(holder);
+ Node* impl = V8Node::toNative(holder);
CustomElementCallbackDispatcher::CallbackDeliveryScope deliveryScope;
ExceptionState exceptionState(ExceptionState::ExecutionContext, "replaceChild", "Node", info.Holder(), info.GetIsolate());
- Node* newChild = V8Node::hasInstance(info[0], info.GetIsolate(), worldType(info.GetIsolate())) ? V8Node::toNative(v8::Handle<v8::Object>::Cast(info[0])) : 0;
- Node* oldChild = V8Node::hasInstance(info[1], info.GetIsolate(), worldType(info.GetIsolate())) ? V8Node::toNative(v8::Handle<v8::Object>::Cast(info[1])) : 0;
- imp->replaceChild(newChild, oldChild, exceptionState);
+ Node* newChild = V8Node::toNativeWithTypeCheck(info.GetIsolate(), info[0]);
+ Node* oldChild = V8Node::toNativeWithTypeCheck(info.GetIsolate(), info[1]);
+ impl->replaceChild(newChild, oldChild, exceptionState);
if (exceptionState.throwIfNeeded())
return;
v8SetReturnValue(info, info[1]);
@@ -94,13 +93,13 @@ void V8Node::replaceChildMethodCustom(const v8::FunctionCallbackInfo<v8::Value>&
void V8Node::removeChildMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
v8::Handle<v8::Object> holder = info.Holder();
- Node* imp = V8Node::toNative(holder);
+ Node* impl = V8Node::toNative(holder);
CustomElementCallbackDispatcher::CallbackDeliveryScope deliveryScope;
ExceptionState exceptionState(ExceptionState::ExecutionContext, "removeChild", "Node", info.Holder(), info.GetIsolate());
- Node* oldChild = V8Node::hasInstance(info[0], info.GetIsolate(), worldType(info.GetIsolate())) ? V8Node::toNative(v8::Handle<v8::Object>::Cast(info[0])) : 0;
- imp->removeChild(oldChild, exceptionState);
+ Node* oldChild = V8Node::toNativeWithTypeCheck(info.GetIsolate(), info[0]);
+ impl->removeChild(oldChild, exceptionState);
if (exceptionState.throwIfNeeded())
return;
v8SetReturnValue(info, info[0]);
@@ -109,13 +108,13 @@ void V8Node::removeChildMethodCustom(const v8::FunctionCallbackInfo<v8::Value>&
void V8Node::appendChildMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
v8::Handle<v8::Object> holder = info.Holder();
- Node* imp = V8Node::toNative(holder);
+ Node* impl = V8Node::toNative(holder);
CustomElementCallbackDispatcher::CallbackDeliveryScope deliveryScope;
ExceptionState exceptionState(ExceptionState::ExecutionContext, "appendChild", "Node", info.Holder(), info.GetIsolate());
- Node* newChild = V8Node::hasInstance(info[0], info.GetIsolate(), worldType(info.GetIsolate())) ? V8Node::toNative(v8::Handle<v8::Object>::Cast(info[0])) : 0;
- imp->appendChild(newChild, exceptionState);
+ Node* newChild = V8Node::toNativeWithTypeCheck(info.GetIsolate(), info[0]);
+ impl->appendChild(newChild, exceptionState);
if (exceptionState.throwIfNeeded())
return;
v8SetReturnValue(info, info[0]);
@@ -150,14 +149,8 @@ v8::Handle<v8::Object> wrap(Node* impl, v8::Handle<v8::Object> creationContext,
if (impl->isShadowRoot())
return wrap(toShadowRoot(impl), creationContext, isolate);
return wrap(toDocumentFragment(impl), creationContext, isolate);
- case Node::ENTITY_NODE:
- case Node::NOTATION_NODE:
- // We never create objects of Entity and Notation.
- ASSERT_NOT_REACHED();
- break;
- default:
- break; // ENTITY_REFERENCE_NODE or XPATH_NAMESPACE_NODE
}
+ ASSERT_NOT_REACHED();
return V8Node::createWrapper(impl, creationContext, isolate);
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8OscillatorNodeCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8OscillatorNodeCustom.cpp
deleted file mode 100644
index 7216a8ec56b..00000000000
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8OscillatorNodeCustom.cpp
+++ /dev/null
@@ -1,60 +0,0 @@
-/*
- * Copyright (C) 2012, Google Inc. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- * 1. Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * 2. Redistributions in binary form must reproduce the above copyright
- * notice, this list of conditions and the following disclaimer in the
- * documentation and/or other materials provided with the distribution.
- *
- * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS'' AND ANY
- * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
- * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
- * DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS BE LIABLE FOR ANY
- * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
- * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
- * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
- * ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
- * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-#include "config.h"
-#if ENABLE(WEB_AUDIO)
-#include "V8OscillatorNode.h"
-
-#include "bindings/v8/V8Binding.h"
-#include "modules/webaudio/OscillatorNode.h"
-
-namespace WebCore {
-
-void V8OscillatorNode::typeAttributeSetterCustom(v8::Local<v8::Value> value, const v8::PropertyCallbackInfo<void>& info)
-{
- v8::Handle<v8::Object> holder = info.Holder();
- OscillatorNode* imp = V8OscillatorNode::toNative(holder);
-
- if (value->IsNumber()) {
- bool ok = false;
- uint32_t type = toUInt32(value, ok);
- if (!ok || !imp->setType(type))
- throwTypeError("Illegal OscillatorNode type", info.GetIsolate());
- return;
- }
-
- if (value->IsString()) {
- String type = toCoreString(value.As<v8::String>());
- if (type == "sine" || type == "square" || type == "sawtooth" || type == "triangle") {
- imp->setType(type);
- return;
- }
- }
-
- throwTypeError("Illegal OscillatorNode type", info.GetIsolate());
-}
-
-} // namespace WebCore
-
-#endif // ENABLE(WEB_AUDIO)
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8PannerNodeCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8PannerNodeCustom.cpp
deleted file mode 100644
index 5e10fda34cf..00000000000
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8PannerNodeCustom.cpp
+++ /dev/null
@@ -1,84 +0,0 @@
-/*
- * Copyright (C) 2012, Google Inc. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- * 1. Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * 2. Redistributions in binary form must reproduce the above copyright
- * notice, this list of conditions and the following disclaimer in the
- * documentation and/or other materials provided with the distribution.
- *
- * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS'' AND ANY
- * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
- * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
- * DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS BE LIABLE FOR ANY
- * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
- * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
- * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
- * ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
- * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-#include "config.h"
-#if ENABLE(WEB_AUDIO)
-#include "V8PannerNode.h"
-
-#include "bindings/v8/V8Binding.h"
-#include "modules/webaudio/PannerNode.h"
-
-namespace WebCore {
-
-void V8PannerNode::panningModelAttributeSetterCustom(v8::Local<v8::Value> value, const v8::PropertyCallbackInfo<void>& info)
-{
- PannerNode* imp = V8PannerNode::toNative(info.Holder());
-
- if (value->IsNumber()) {
- bool ok = false;
- uint32_t model = toUInt32(value, ok);
- ASSERT(ok);
- if (!imp->setPanningModel(model))
- throwTypeError("Illegal panningModel", info.GetIsolate());
- return;
- }
-
- if (value->IsString()) {
- String model = toCoreString(value.As<v8::String>());
- if (model == "equalpower" || model == "HRTF" || model == "soundfield") {
- imp->setPanningModel(model);
- return;
- }
- }
-
- throwTypeError("Illegal panningModel", info.GetIsolate());
-}
-
-void V8PannerNode::distanceModelAttributeSetterCustom(v8::Local<v8::Value> value, const v8::PropertyCallbackInfo<void>& info)
-{
- PannerNode* imp = V8PannerNode::toNative(info.Holder());
-
- if (value->IsNumber()) {
- bool ok = false;
- uint32_t model = toUInt32(value, ok);
- ASSERT(ok);
- if (!imp->setDistanceModel(model))
- throwTypeError("Illegal distanceModel", info.GetIsolate());
- return;
- }
-
- if (value->IsString()) {
- String model = toCoreString(value.As<v8::String>());
- if (model == "linear" || model == "inverse" || model == "exponential") {
- imp->setDistanceModel(model);
- return;
- }
- }
-
- throwTypeError("Illegal distanceModel", info.GetIsolate());
-}
-
-} // namespace WebCore
-
-#endif // ENABLE(WEB_AUDIO)
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8PerformanceEntryCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8PerformanceEntryCustom.cpp
index 15197329bae..6e1d54e0b68 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8PerformanceEntryCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8PerformanceEntryCustom.cpp
@@ -29,11 +29,11 @@
*/
#include "config.h"
-#include "V8PerformanceEntry.h"
+#include "bindings/core/v8/V8PerformanceEntry.h"
-#include "V8PerformanceMark.h"
-#include "V8PerformanceMeasure.h"
-#include "V8PerformanceResourceTiming.h"
+#include "bindings/core/v8/V8PerformanceMark.h"
+#include "bindings/core/v8/V8PerformanceMeasure.h"
+#include "bindings/core/v8/V8PerformanceResourceTiming.h"
#include "core/timing/Performance.h"
#include "core/timing/PerformanceMark.h"
#include "core/timing/PerformanceMeasure.h"
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8PopStateEventCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8PopStateEventCustom.cpp
index 8a7b790822c..83385ca297f 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8PopStateEventCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8PopStateEventCustom.cpp
@@ -29,11 +29,11 @@
*/
#include "config.h"
-#include "V8PopStateEvent.h"
+#include "bindings/core/v8/V8PopStateEvent.h"
-#include "V8History.h"
+#include "bindings/core/v8/V8History.h"
#include "bindings/v8/SerializedScriptValue.h"
-#include "bindings/v8/V8HiddenPropertyName.h"
+#include "bindings/v8/V8HiddenValue.h"
#include "core/events/PopStateEvent.h"
#include "core/frame/History.h"
@@ -42,13 +42,13 @@ namespace WebCore {
// Save the state value to a hidden attribute in the V8PopStateEvent, and return it, for convenience.
static v8::Handle<v8::Value> cacheState(v8::Handle<v8::Object> popStateEvent, v8::Handle<v8::Value> state, v8::Isolate* isolate)
{
- popStateEvent->SetHiddenValue(V8HiddenPropertyName::state(isolate), state);
+ V8HiddenValue::setHiddenValue(isolate, popStateEvent, V8HiddenValue::state(isolate), state);
return state;
}
void V8PopStateEvent::stateAttributeGetterCustom(const v8::PropertyCallbackInfo<v8::Value>& info)
{
- v8::Handle<v8::Value> result = info.Holder()->GetHiddenValue(V8HiddenPropertyName::state(info.GetIsolate()));
+ v8::Handle<v8::Value> result = V8HiddenValue::getHiddenValue(info.GetIsolate(), info.Holder(), V8HiddenValue::state(info.GetIsolate()));
if (!result.IsEmpty()) {
v8SetReturnValue(info, result);
@@ -61,7 +61,7 @@ void V8PopStateEvent::stateAttributeGetterCustom(const v8::PropertyCallbackInfo<
if (!event->serializedState()) {
// If we're in an isolated world and the event was created in the main world,
// we need to find the 'state' property on the main world wrapper and clone it.
- v8::Local<v8::Value> mainWorldState = getHiddenValueFromMainWorldWrapper(info.GetIsolate(), event, V8HiddenPropertyName::state(info.GetIsolate()));
+ v8::Local<v8::Value> mainWorldState = V8HiddenValue::getHiddenValueFromMainWorldWrapper(info.GetIsolate(), event, V8HiddenValue::state(info.GetIsolate()));
if (!mainWorldState.IsEmpty())
event->setSerializedState(SerializedScriptValue::createAndSwallowExceptions(mainWorldState, info.GetIsolate()));
}
@@ -84,14 +84,14 @@ void V8PopStateEvent::stateAttributeGetterCustom(const v8::PropertyCallbackInfo<
if (isSameState) {
v8::Handle<v8::Object> v8History = toV8(history, info.Holder(), info.GetIsolate()).As<v8::Object>();
if (!history->stateChanged()) {
- result = v8History->GetHiddenValue(V8HiddenPropertyName::state(info.GetIsolate()));
+ result = V8HiddenValue::getHiddenValue(info.GetIsolate(), v8History, V8HiddenValue::state(info.GetIsolate()));
if (!result.IsEmpty()) {
v8SetReturnValue(info, cacheState(info.Holder(), result, info.GetIsolate()));
return;
}
}
result = event->serializedState()->deserialize(info.GetIsolate());
- v8History->SetHiddenValue(V8HiddenPropertyName::state(info.GetIsolate()), result);
+ V8HiddenValue::setHiddenValue(info.GetIsolate(), v8History, V8HiddenValue::state(info.GetIsolate()), result);
} else {
result = event->serializedState()->deserialize(info.GetIsolate());
}
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8PromiseCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8PromiseCustom.cpp
deleted file mode 100644
index 22580d70da8..00000000000
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8PromiseCustom.cpp
+++ /dev/null
@@ -1,794 +0,0 @@
-/*
- * Copyright (C) 2013 Google Inc. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions are
- * met:
- *
- * * Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * * Redistributions in binary form must reproduce the above
- * copyright notice, this list of conditions and the following disclaimer
- * in the documentation and/or other materials provided with the
- * distribution.
- * * Neither the name of Google Inc. nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
- * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
- * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
- * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
- * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
- * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
- * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
- * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
- * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-#include "config.h"
-#include "bindings/v8/custom/V8PromiseCustom.h"
-
-#include <v8.h>
-#include "V8Promise.h"
-#include "bindings/v8/DOMRequestState.h"
-#include "bindings/v8/ScopedPersistent.h"
-#include "bindings/v8/ScriptFunctionCall.h"
-#include "bindings/v8/ScriptState.h"
-#include "bindings/v8/V8Binding.h"
-#include "bindings/v8/V8HiddenPropertyName.h"
-#include "bindings/v8/V8PerIsolateData.h"
-#include "bindings/v8/V8ScriptRunner.h"
-#include "bindings/v8/WrapperTypeInfo.h"
-#include "core/dom/Document.h"
-#include "core/dom/ExecutionContextTask.h"
-#include "core/frame/DOMWindow.h"
-#include "core/workers/WorkerGlobalScope.h"
-#include "platform/Task.h"
-#include "wtf/Deque.h"
-#include "wtf/Functional.h"
-#include "wtf/Noncopyable.h"
-#include "wtf/PassOwnPtr.h"
-
-namespace WebCore {
-
-namespace {
-
-v8::Local<v8::ObjectTemplate> cachedObjectTemplate(void* privateTemplateUniqueKey, int internalFieldCount, v8::Isolate* isolate)
-{
- V8PerIsolateData* data = V8PerIsolateData::from(isolate);
- WrapperWorldType currentWorldType = worldType(isolate);
- v8::Handle<v8::FunctionTemplate> functionDescriptor = data->privateTemplateIfExists(currentWorldType, privateTemplateUniqueKey);
- if (!functionDescriptor.IsEmpty())
- return functionDescriptor->InstanceTemplate();
-
- functionDescriptor = v8::FunctionTemplate::New(isolate);
- v8::Local<v8::ObjectTemplate> instanceTemplate = functionDescriptor->InstanceTemplate();
- instanceTemplate->SetInternalFieldCount(internalFieldCount);
- data->setPrivateTemplate(currentWorldType, privateTemplateUniqueKey, functionDescriptor);
- return instanceTemplate;
-}
-
-v8::Local<v8::ObjectTemplate> promiseAllEnvironmentObjectTemplate(v8::Isolate* isolate)
-{
- // This is only for getting a unique pointer which we can pass to privateTemplate.
- static int privateTemplateUniqueKey;
- return cachedObjectTemplate(&privateTemplateUniqueKey, V8PromiseCustom::PromiseAllEnvironmentFieldCount, isolate);
-}
-
-v8::Local<v8::ObjectTemplate> primitiveWrapperObjectTemplate(v8::Isolate* isolate)
-{
- // This is only for getting a unique pointer which we can pass to privateTemplate.
- static int privateTemplateUniqueKey;
- return cachedObjectTemplate(&privateTemplateUniqueKey, V8PromiseCustom::PrimitiveWrapperFieldCount, isolate);
-}
-
-v8::Local<v8::ObjectTemplate> internalObjectTemplate(v8::Isolate* isolate)
-{
- // This is only for getting a unique pointer which we can pass to privateTemplate.
- static int privateTemplateUniqueKey;
- return cachedObjectTemplate(&privateTemplateUniqueKey, V8PromiseCustom::InternalFieldCount, isolate);
-}
-
-void promiseResolveCallback(const v8::FunctionCallbackInfo<v8::Value>& info)
-{
- ASSERT(!info.Data().IsEmpty());
- v8::Local<v8::Object> promise = info.Data().As<v8::Object>();
- v8::Local<v8::Value> result = v8::Undefined(info.GetIsolate());
- if (info.Length() > 0)
- result = info[0];
-
- V8PromiseCustom::resolve(promise, result, info.GetIsolate());
-}
-
-void promiseRejectCallback(const v8::FunctionCallbackInfo<v8::Value>& info)
-{
- ASSERT(!info.Data().IsEmpty());
- v8::Local<v8::Object> promise = info.Data().As<v8::Object>();
- v8::Local<v8::Value> result = v8::Undefined(info.GetIsolate());
- if (info.Length() > 0)
- result = info[0];
-
- V8PromiseCustom::reject(promise, result, info.GetIsolate());
-}
-
-void promiseAllFulfillCallback(const v8::FunctionCallbackInfo<v8::Value>& info)
-{
- v8::Isolate* isolate = info.GetIsolate();
- ASSERT(!info.Data().IsEmpty());
- v8::Local<v8::Object> environment = info.Data().As<v8::Object>();
- v8::Local<v8::Value> result = v8::Undefined(isolate);
- if (info.Length() > 0)
- result = info[0];
-
- v8::Local<v8::Object> promise = environment->GetInternalField(V8PromiseCustom::PromiseAllEnvironmentPromiseIndex).As<v8::Object>();
- v8::Local<v8::Object> countdownWrapper = environment->GetInternalField(V8PromiseCustom::PromiseAllEnvironmentCountdownIndex).As<v8::Object>();
- v8::Local<v8::Integer> index = environment->GetInternalField(V8PromiseCustom::PromiseAllEnvironmentIndexIndex).As<v8::Integer>();
- v8::Local<v8::Array> results = environment->GetInternalField(V8PromiseCustom::PromiseAllEnvironmentResultsIndex).As<v8::Array>();
-
- results->Set(index->Value(), result);
-
- v8::Local<v8::Integer> countdown = countdownWrapper->GetInternalField(V8PromiseCustom::PrimitiveWrapperPrimitiveIndex).As<v8::Integer>();
- ASSERT(countdown->Value() >= 1);
- if (countdown->Value() == 1) {
- V8PromiseCustom::resolve(promise, results, isolate);
- return;
- }
- countdownWrapper->SetInternalField(V8PromiseCustom::PrimitiveWrapperPrimitiveIndex, v8::Integer::New(countdown->Value() - 1, isolate));
-}
-
-v8::Local<v8::Object> promiseAllEnvironment(v8::Handle<v8::Object> promise, v8::Handle<v8::Object> countdownWrapper, int index, v8::Handle<v8::Array> results, v8::Isolate* isolate)
-{
- v8::Local<v8::ObjectTemplate> objectTemplate = promiseAllEnvironmentObjectTemplate(isolate);
- v8::Local<v8::Object> environment = objectTemplate->NewInstance();
-
- environment->SetInternalField(V8PromiseCustom::PromiseAllEnvironmentPromiseIndex, promise);
- environment->SetInternalField(V8PromiseCustom::PromiseAllEnvironmentCountdownIndex, countdownWrapper);
- environment->SetInternalField(V8PromiseCustom::PromiseAllEnvironmentIndexIndex, v8::Integer::New(index, isolate));
- environment->SetInternalField(V8PromiseCustom::PromiseAllEnvironmentResultsIndex, results);
- return environment;
-}
-
-// Clear |internal|'s derived array.
-void clearDerived(v8::Handle<v8::Object> internal, v8::Isolate* isolate)
-{
- internal->SetInternalField(V8PromiseCustom::InternalFulfillCallbackIndex, v8::Array::New(isolate));
- internal->SetInternalField(V8PromiseCustom::InternalRejectCallbackIndex, v8::Array::New(isolate));
- internal->SetInternalField(V8PromiseCustom::InternalDerivedPromiseIndex, v8::Array::New(isolate));
-}
-
-// Add a tuple (|derivedPromise|, |onFulfilled|, |onRejected|) to
-// |internal|'s derived array.
-// |internal| must be a Promise internal object.
-// |derivedPromise| must be a Promise instance.
-// |onFulfilled| and |onRejected| can be an empty value respectively.
-void addToDerived(v8::Handle<v8::Object> internal, v8::Handle<v8::Object> derivedPromise, v8::Handle<v8::Function> onFulfilled, v8::Handle<v8::Function> onRejected, v8::Isolate* isolate)
-{
- v8::Local<v8::Array> fulfillCallbacks = internal->GetInternalField(V8PromiseCustom::InternalFulfillCallbackIndex).As<v8::Array>();
- v8::Local<v8::Array> rejectCallbacks = internal->GetInternalField(V8PromiseCustom::InternalRejectCallbackIndex).As<v8::Array>();
- v8::Local<v8::Array> derivedPromises = internal->GetInternalField(V8PromiseCustom::InternalDerivedPromiseIndex).As<v8::Array>();
-
- if (onFulfilled.IsEmpty()) {
- fulfillCallbacks->Set(fulfillCallbacks->Length(), v8::Undefined(isolate));
- } else {
- fulfillCallbacks->Set(fulfillCallbacks->Length(), onFulfilled);
- }
-
- if (onRejected.IsEmpty()) {
- rejectCallbacks->Set(rejectCallbacks->Length(), v8::Undefined(isolate));
- } else {
- rejectCallbacks->Set(rejectCallbacks->Length(), onRejected);
- }
-
- ASSERT(!derivedPromise.IsEmpty());
- derivedPromises->Set(derivedPromises->Length(), derivedPromise);
-
- // Since they are treated as a tuple,
- // we need to guaranteed that the length of these arrays are same.
- ASSERT(fulfillCallbacks->Length() == rejectCallbacks->Length() && rejectCallbacks->Length() == derivedPromises->Length());
-}
-
-class CallHandlerTask : public ExecutionContextTask {
-public:
- CallHandlerTask(v8::Handle<v8::Object> promise, v8::Handle<v8::Function> handler, v8::Handle<v8::Value> argument, v8::Isolate* isolate, ExecutionContext* context)
- : m_promise(isolate, promise)
- , m_handler(isolate, handler)
- , m_argument(isolate, argument)
- , m_requestState(context)
- {
- ASSERT(!m_promise.isEmpty());
- ASSERT(!m_handler.isEmpty());
- ASSERT(!m_argument.isEmpty());
- }
- virtual ~CallHandlerTask() { }
-
- virtual void performTask(ExecutionContext*) OVERRIDE;
-
-private:
- ScopedPersistent<v8::Object> m_promise;
- ScopedPersistent<v8::Function> m_handler;
- ScopedPersistent<v8::Value> m_argument;
- DOMRequestState m_requestState;
-};
-
-void CallHandlerTask::performTask(ExecutionContext* context)
-{
- ASSERT(context);
- if (context->activeDOMObjectsAreStopped())
- return;
-
- DOMRequestState::Scope scope(m_requestState);
- v8::Isolate* isolate = m_requestState.isolate();
- v8::Handle<v8::Value> info[] = { m_argument.newLocal(isolate) };
- v8::TryCatch trycatch;
- v8::Local<v8::Value> value = V8ScriptRunner::callFunction(m_handler.newLocal(isolate), context, v8::Undefined(isolate), WTF_ARRAY_LENGTH(info), info, isolate);
- if (value.IsEmpty()) {
- V8PromiseCustom::reject(m_promise.newLocal(isolate), trycatch.Exception(), isolate);
- } else {
- V8PromiseCustom::resolve(m_promise.newLocal(isolate), value, isolate);
- }
-}
-
-class UpdateDerivedTask : public ExecutionContextTask {
-public:
- UpdateDerivedTask(v8::Handle<v8::Object> promise, v8::Handle<v8::Function> onFulfilled, v8::Handle<v8::Function> onRejected, v8::Handle<v8::Object> originatorValueObject, v8::Isolate* isolate, ExecutionContext* context)
- : m_promise(isolate, promise)
- , m_onFulfilled(isolate, onFulfilled)
- , m_onRejected(isolate, onRejected)
- , m_originatorValueObject(isolate, originatorValueObject)
- , m_requestState(context)
- {
- ASSERT(!m_promise.isEmpty());
- ASSERT(!m_originatorValueObject.isEmpty());
- }
- virtual ~UpdateDerivedTask() { }
-
- virtual void performTask(ExecutionContext*) OVERRIDE;
-
-private:
- ScopedPersistent<v8::Object> m_promise;
- ScopedPersistent<v8::Function> m_onFulfilled;
- ScopedPersistent<v8::Function> m_onRejected;
- ScopedPersistent<v8::Object> m_originatorValueObject;
- DOMRequestState m_requestState;
-};
-
-void UpdateDerivedTask::performTask(ExecutionContext* context)
-{
- ASSERT(context);
- if (context->activeDOMObjectsAreStopped())
- return;
-
- DOMRequestState::Scope scope(m_requestState);
- v8::Isolate* isolate = m_requestState.isolate();
- v8::Local<v8::Object> originatorValueObject = m_originatorValueObject.newLocal(isolate);
- v8::Local<v8::Value> coercedAlready = originatorValueObject->GetHiddenValue(V8HiddenPropertyName::thenableHiddenPromise(isolate));
- if (!coercedAlready.IsEmpty() && coercedAlready->IsObject()) {
- ASSERT(V8PromiseCustom::isPromise(coercedAlready.As<v8::Object>(), isolate));
- V8PromiseCustom::updateDerivedFromPromise(m_promise.newLocal(isolate), m_onFulfilled.newLocal(isolate), m_onRejected.newLocal(isolate), coercedAlready.As<v8::Object>(), isolate);
- return;
- }
-
- v8::Local<v8::Value> then;
- v8::TryCatch trycatch;
- then = originatorValueObject->Get(v8AtomicString(isolate, "then"));
- if (then.IsEmpty()) {
- // If calling the [[Get]] internal method threw an exception, catch it and run updateDerivedFromReason.
- V8PromiseCustom::updateDerivedFromReason(m_promise.newLocal(isolate), m_onRejected.newLocal(isolate), trycatch.Exception(), isolate);
- return;
- }
-
- if (then->IsFunction()) {
- ASSERT(then->IsObject());
- v8::Local<v8::Object> coerced = V8PromiseCustom::coerceThenable(originatorValueObject, then.As<v8::Function>(), isolate);
- V8PromiseCustom::updateDerivedFromPromise(m_promise.newLocal(isolate), m_onFulfilled.newLocal(isolate), m_onRejected.newLocal(isolate), coerced, isolate);
- return;
- }
-
- V8PromiseCustom::updateDerivedFromValue(m_promise.newLocal(isolate), m_onFulfilled.newLocal(isolate), originatorValueObject, isolate);
-}
-
-// Since Promises state propagation routines are executed recursively, they cause
-// stack overflow.
-// (e.g. UpdateDerived -> UpdateDerivedFromValue -> SetValue ->
-// PropagateToDerived -> UpdateDerived)
-//
-// To fix that, we introduce PromisePropagator. It holds the stack. When
-// propagating the result to the derived tuples, we append the derived tuples
-// to the stack. After that, we drain the stack to propagate the result to
-// the stored tuples.
-//
-// PromisePropagator should be held on the stack and should not be held
-// as other object's member. PromisePropagator holds Derived tuples. Since
-// Derived tuples hold persistent handles to JS objects, retaining
-// PromisePropagator in the heap causes memory leaks.
-//
-class PromisePropagator {
- WTF_MAKE_NONCOPYABLE(PromisePropagator);
-public:
- PromisePropagator() { }
-
- void performPropagation(v8::Isolate*);
-
- void setValue(v8::Handle<v8::Object> promise, v8::Handle<v8::Value>, v8::Isolate*);
- void setReason(v8::Handle<v8::Object> promise, v8::Handle<v8::Value>, v8::Isolate*);
- void propagateToDerived(v8::Handle<v8::Object> promise, v8::Isolate*);
- void updateDerived(v8::Handle<v8::Object> derivedPromise, v8::Handle<v8::Function> onFulfilled, v8::Handle<v8::Function> onRejected, v8::Handle<v8::Object> originator, v8::Isolate*);
- void updateDerivedFromValue(v8::Handle<v8::Object> derivedPromise, v8::Handle<v8::Function> onFulfilled, v8::Handle<v8::Value>, v8::Isolate*);
- void updateDerivedFromReason(v8::Handle<v8::Object> derivedPromise, v8::Handle<v8::Function> onRejected, v8::Handle<v8::Value>, v8::Isolate*);
- void updateDerivedFromPromise(v8::Handle<v8::Object> derivedPromise, v8::Handle<v8::Function> onFulfilled, v8::Handle<v8::Function> onRejected, v8::Handle<v8::Object> promise, v8::Isolate*);
-
-private:
- class Derived {
- WTF_MAKE_NONCOPYABLE(Derived);
- public:
- Derived(v8::Handle<v8::Object> promise, v8::Handle<v8::Function> onFulfilled, v8::Handle<v8::Function> onRejected, v8::Handle<v8::Object> originator, v8::Isolate* isolate)
- : m_promise(isolate, promise)
- , m_onFulfilled(isolate, onFulfilled)
- , m_onRejected(isolate, onRejected)
- , m_originator(isolate, originator)
- {
- ASSERT(!m_promise.isEmpty());
- ASSERT(!m_originator.isEmpty());
- }
-
- static PassOwnPtr<Derived> create(v8::Handle<v8::Object> promise, v8::Handle<v8::Function> onFulfilled, v8::Handle<v8::Function> onRejected, v8::Handle<v8::Object> originator, v8::Isolate* isolate)
- {
- return adoptPtr(new Derived(promise, onFulfilled, onRejected, originator, isolate));
- }
-
- v8::Local<v8::Object> promise(v8::Isolate* isolate) const { return m_promise.newLocal(isolate); }
- v8::Local<v8::Function> onFulfilled(v8::Isolate* isolate) const { return m_onFulfilled.newLocal(isolate); }
- v8::Local<v8::Function> onRejected(v8::Isolate* isolate) const { return m_onRejected.newLocal(isolate); }
- v8::Local<v8::Object> originator(v8::Isolate* isolate) const { return m_originator.newLocal(isolate); }
-
- private:
- ScopedPersistent<v8::Object> m_promise;
- ScopedPersistent<v8::Function> m_onFulfilled;
- ScopedPersistent<v8::Function> m_onRejected;
- ScopedPersistent<v8::Object> m_originator;
- };
-
- Deque<OwnPtr<Derived> > m_derivedStack;
-};
-
-void PromisePropagator::performPropagation(v8::Isolate* isolate)
-{
- while (!m_derivedStack.isEmpty()) {
- v8::HandleScope handleScope(isolate);
- OwnPtr<Derived> derived = m_derivedStack.takeLast();
- updateDerived(derived->promise(isolate), derived->onFulfilled(isolate), derived->onRejected(isolate), derived->originator(isolate), isolate);
- }
-}
-
-void PromisePropagator::setValue(v8::Handle<v8::Object> promise, v8::Handle<v8::Value> value, v8::Isolate* isolate)
-{
- v8::Local<v8::Object> internal = V8PromiseCustom::getInternal(promise);
- ASSERT(V8PromiseCustom::getState(internal) != V8PromiseCustom::Fulfilled && V8PromiseCustom::getState(internal) != V8PromiseCustom::Rejected);
- V8PromiseCustom::setState(internal, V8PromiseCustom::Fulfilled, value, isolate);
- propagateToDerived(promise, isolate);
-}
-
-void PromisePropagator::setReason(v8::Handle<v8::Object> promise, v8::Handle<v8::Value> reason, v8::Isolate* isolate)
-{
- v8::Local<v8::Object> internal = V8PromiseCustom::getInternal(promise);
- ASSERT(V8PromiseCustom::getState(internal) != V8PromiseCustom::Fulfilled && V8PromiseCustom::getState(internal) != V8PromiseCustom::Rejected);
- V8PromiseCustom::setState(internal, V8PromiseCustom::Rejected, reason, isolate);
- propagateToDerived(promise, isolate);
-}
-
-void PromisePropagator::propagateToDerived(v8::Handle<v8::Object> promise, v8::Isolate* isolate)
-{
- v8::Local<v8::Object> internal = V8PromiseCustom::getInternal(promise);
- ASSERT(V8PromiseCustom::getState(internal) == V8PromiseCustom::Fulfilled || V8PromiseCustom::getState(internal) == V8PromiseCustom::Rejected);
- v8::Local<v8::Array> fulfillCallbacks = internal->GetInternalField(V8PromiseCustom::InternalFulfillCallbackIndex).As<v8::Array>();
- v8::Local<v8::Array> rejectCallbacks = internal->GetInternalField(V8PromiseCustom::InternalRejectCallbackIndex).As<v8::Array>();
- v8::Local<v8::Array> derivedPromises = internal->GetInternalField(V8PromiseCustom::InternalDerivedPromiseIndex).As<v8::Array>();
- // Since they are treated as a tuple,
- // we need to guaranteed that the length of these arrays are same.
- ASSERT(fulfillCallbacks->Length() == rejectCallbacks->Length() && rejectCallbacks->Length() == derivedPromises->Length());
-
- // Append Derived tuple to the stack in reverse order.
- for (uint32_t count = 0, length = derivedPromises->Length(); count < length; ++count) {
- uint32_t i = length - count - 1;
- v8::Local<v8::Object> derivedPromise = derivedPromises->Get(i).As<v8::Object>();
-
- v8::Local<v8::Function> onFulfilled, onRejected;
- v8::Local<v8::Value> onFulfilledValue = fulfillCallbacks->Get(i);
- if (onFulfilledValue->IsFunction()) {
- onFulfilled = onFulfilledValue.As<v8::Function>();
- }
- v8::Local<v8::Value> onRejectedValue = rejectCallbacks->Get(i);
- if (onRejectedValue->IsFunction()) {
- onRejected = onRejectedValue.As<v8::Function>();
- }
-
- m_derivedStack.append(Derived::create(derivedPromise, onFulfilled, onRejected, promise, isolate));
- }
- clearDerived(internal, isolate);
-}
-
-void PromisePropagator::updateDerivedFromValue(v8::Handle<v8::Object> derivedPromise, v8::Handle<v8::Function> onFulfilled, v8::Handle<v8::Value> value, v8::Isolate* isolate)
-{
- if (!onFulfilled.IsEmpty()) {
- V8PromiseCustom::callHandler(derivedPromise, onFulfilled, value, isolate);
- } else {
- setValue(derivedPromise, value, isolate);
- }
-}
-
-void PromisePropagator::updateDerivedFromReason(v8::Handle<v8::Object> derivedPromise, v8::Handle<v8::Function> onRejected, v8::Handle<v8::Value> reason, v8::Isolate* isolate)
-{
- if (!onRejected.IsEmpty()) {
- V8PromiseCustom::callHandler(derivedPromise, onRejected, reason, isolate);
- } else {
- setReason(derivedPromise, reason, isolate);
- }
-}
-
-void PromisePropagator::updateDerived(v8::Handle<v8::Object> derivedPromise, v8::Handle<v8::Function> onFulfilled, v8::Handle<v8::Function> onRejected, v8::Handle<v8::Object> originator, v8::Isolate* isolate)
-{
- v8::Local<v8::Object> originatorInternal = V8PromiseCustom::getInternal(originator);
- V8PromiseCustom::PromiseState originatorState = V8PromiseCustom::getState(originatorInternal);
- ASSERT(originatorState == V8PromiseCustom::Fulfilled || originatorState == V8PromiseCustom::Rejected);
- v8::Local<v8::Value> originatorValue = originatorInternal->GetInternalField(V8PromiseCustom::InternalResultIndex);
- if (originatorState == V8PromiseCustom::Fulfilled) {
- if (originatorValue->IsObject()) {
- ExecutionContext* executionContext = getExecutionContext();
- ASSERT(executionContext && executionContext->isContextThread());
- executionContext->postTask(adoptPtr(new UpdateDerivedTask(derivedPromise, onFulfilled, onRejected, originatorValue.As<v8::Object>(), isolate, executionContext)));
- } else {
- updateDerivedFromValue(derivedPromise, onFulfilled, originatorValue, isolate);
- }
- } else {
- updateDerivedFromReason(derivedPromise, onRejected, originatorValue, isolate);
- }
-}
-
-void PromisePropagator::updateDerivedFromPromise(v8::Handle<v8::Object> derivedPromise, v8::Handle<v8::Function> onFulfilled, v8::Handle<v8::Function> onRejected, v8::Handle<v8::Object> promise, v8::Isolate* isolate)
-{
- v8::Local<v8::Object> internal = V8PromiseCustom::getInternal(promise);
- V8PromiseCustom::PromiseState state = V8PromiseCustom::getState(internal);
- if (state == V8PromiseCustom::Fulfilled || state == V8PromiseCustom::Rejected) {
- updateDerived(derivedPromise, onFulfilled, onRejected, promise, isolate);
- } else {
- addToDerived(internal, derivedPromise, onFulfilled, onRejected, isolate);
- }
-}
-
-} // namespace
-
-void V8Promise::constructorCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
-{
- v8SetReturnValue(info, v8::Local<v8::Value>());
- v8::Isolate* isolate = info.GetIsolate();
- if (!info.Length() || !info[0]->IsFunction()) {
- throwTypeError("Promise constructor takes a function argument", isolate);
- return;
- }
- v8::Local<v8::Function> init = info[0].As<v8::Function>();
- v8::Local<v8::Object> promise = V8PromiseCustom::createPromise(info.Holder(), isolate);
- v8::Handle<v8::Value> argv[] = {
- createClosure(promiseResolveCallback, promise, isolate),
- createClosure(promiseRejectCallback, promise, isolate)
- };
- v8::TryCatch trycatch;
- if (V8ScriptRunner::callFunction(init, getExecutionContext(), v8::Undefined(isolate), WTF_ARRAY_LENGTH(argv), argv, isolate).IsEmpty()) {
- // An exception is thrown. Reject the promise if its resolved flag is unset.
- V8PromiseCustom::reject(promise, trycatch.Exception(), isolate);
- }
- v8SetReturnValue(info, promise);
- return;
-}
-
-void V8Promise::thenMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
-{
- v8::Isolate* isolate = info.GetIsolate();
- v8::Local<v8::Function> onFulfilled, onRejected;
- if (info.Length() > 0 && info[0]->IsFunction())
- onFulfilled = info[0].As<v8::Function>();
- if (info.Length() > 1 && info[1]->IsFunction())
- onRejected = info[1].As<v8::Function>();
- v8SetReturnValue(info, V8PromiseCustom::then(info.Holder(), onFulfilled, onRejected, isolate));
-}
-
-void V8Promise::castMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
-{
- v8::Isolate* isolate = info.GetIsolate();
- v8::Local<v8::Value> result = v8::Undefined(isolate);
- if (info.Length() > 0)
- result = info[0];
-
- v8SetReturnValue(info, V8PromiseCustom::toPromise(result, isolate));
-}
-
-void V8Promise::catchMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
-{
- v8::Isolate* isolate = info.GetIsolate();
- v8::Local<v8::Function> onFulfilled, onRejected;
-
- if (info.Length() > 0 && !info[0]->IsUndefined()) {
- if (!info[0]->IsFunction()) {
- v8SetReturnValue(info, throwTypeError("onRejected must be a function or undefined", isolate));
- return;
- }
- onRejected = info[0].As<v8::Function>();
- }
- v8SetReturnValue(info, V8PromiseCustom::then(info.Holder(), onFulfilled, onRejected, isolate));
-}
-
-void V8Promise::resolveMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
-{
- v8::Isolate* isolate = info.GetIsolate();
- v8::Local<v8::Value> result = v8::Undefined(isolate);
- if (info.Length() > 0)
- result = info[0];
-
- v8::Local<v8::Object> promise = V8PromiseCustom::createPromise(info.Holder(), isolate);
- V8PromiseCustom::resolve(promise, result, isolate);
- v8SetReturnValue(info, promise);
-}
-
-void V8Promise::rejectMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
-{
- v8::Isolate* isolate = info.GetIsolate();
- v8::Local<v8::Value> result = v8::Undefined(isolate);
- if (info.Length() > 0)
- result = info[0];
-
- v8::Local<v8::Object> promise = V8PromiseCustom::createPromise(info.Holder(), isolate);
- V8PromiseCustom::reject(promise, result, isolate);
- v8SetReturnValue(info, promise);
-}
-
-void V8Promise::raceMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
-{
- v8::Isolate* isolate = info.GetIsolate();
- v8::Local<v8::Object> promise = V8PromiseCustom::createPromise(info.Holder(), isolate);
-
- if (!info.Length() || !info[0]->IsArray()) {
- v8SetReturnValue(info, promise);
- return;
- }
-
- // FIXME: Now we limit the iterable type to the Array type.
- v8::Local<v8::Array> iterable = info[0].As<v8::Array>();
- v8::Local<v8::Function> onFulfilled = createClosure(promiseResolveCallback, promise, isolate);
- v8::Local<v8::Function> onRejected = createClosure(promiseRejectCallback, promise, isolate);
-
- for (unsigned i = 0, length = iterable->Length(); i < length; ++i) {
- // Array-holes should not be skipped by for-of iteration semantics.
- V8TRYCATCH_VOID(v8::Local<v8::Value>, nextValue, iterable->Get(i));
- v8::Local<v8::Object> nextPromise = V8PromiseCustom::toPromise(nextValue, isolate);
- V8PromiseCustom::then(nextPromise, onFulfilled, onRejected, isolate);
- }
- v8SetReturnValue(info, promise);
-}
-
-void V8Promise::allMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
-{
- v8::Isolate* isolate = info.GetIsolate();
- v8::Local<v8::Object> promise = V8PromiseCustom::createPromise(info.Holder(), isolate);
- v8::Local<v8::Array> results = v8::Array::New(info.GetIsolate());
-
- if (!info.Length() || !info[0]->IsArray()) {
- V8PromiseCustom::resolve(promise, results, isolate);
- v8SetReturnValue(info, promise);
- return;
- }
-
- // FIXME: Now we limit the iterable type to the Array type.
- v8::Local<v8::Array> iterable = info[0].As<v8::Array>();
-
- if (!iterable->Length()) {
- V8PromiseCustom::resolve(promise, results, isolate);
- v8SetReturnValue(info, promise);
- return;
- }
-
- v8::Local<v8::ObjectTemplate> objectTemplate = primitiveWrapperObjectTemplate(isolate);
- v8::Local<v8::Object> countdownWrapper = objectTemplate->NewInstance();
- countdownWrapper->SetInternalField(V8PromiseCustom::PrimitiveWrapperPrimitiveIndex, v8::Integer::New(iterable->Length(), isolate));
-
- v8::Local<v8::Function> onRejected = createClosure(promiseRejectCallback, promise, isolate);
- for (unsigned i = 0, length = iterable->Length(); i < length; ++i) {
- // Array-holes should not be skipped by for-of iteration semantics.
- v8::Local<v8::Object> environment = promiseAllEnvironment(promise, countdownWrapper, i, results, isolate);
- v8::Local<v8::Function> onFulfilled = createClosure(promiseAllFulfillCallback, environment, isolate);
- V8TRYCATCH_VOID(v8::Local<v8::Value>, nextValue, iterable->Get(i));
- v8::Local<v8::Object> nextPromise = V8PromiseCustom::toPromise(nextValue, isolate);
- V8PromiseCustom::then(nextPromise, onFulfilled, onRejected, isolate);
- }
- v8SetReturnValue(info, promise);
-}
-
-//
-// -- V8PromiseCustom --
-v8::Local<v8::Object> V8PromiseCustom::createPromise(v8::Handle<v8::Object> creationContext, v8::Isolate* isolate)
-{
- v8::Local<v8::ObjectTemplate> internalTemplate = internalObjectTemplate(isolate);
- v8::Local<v8::Object> internal = internalTemplate->NewInstance();
- v8::Local<v8::Object> promise = V8DOMWrapper::createWrapper(creationContext, &V8Promise::wrapperTypeInfo, 0, isolate);
-
- clearDerived(internal, isolate);
- setState(internal, Pending, v8::Undefined(isolate), isolate);
-
- promise->SetInternalField(v8DOMWrapperObjectIndex, internal);
- return promise;
-}
-
-v8::Local<v8::Object> V8PromiseCustom::getInternal(v8::Handle<v8::Object> promise)
-{
- v8::Local<v8::Value> value = promise->GetInternalField(v8DOMWrapperObjectIndex);
- return value.As<v8::Object>();
-}
-
-V8PromiseCustom::PromiseState V8PromiseCustom::getState(v8::Handle<v8::Object> internal)
-{
- v8::Handle<v8::Value> value = internal->GetInternalField(V8PromiseCustom::InternalStateIndex);
- bool ok = false;
- uint32_t number = toInt32(value, ok);
- ASSERT(ok && (number == Pending || number == Fulfilled || number == Rejected || number == Following));
- return static_cast<PromiseState>(number);
-}
-
-void V8PromiseCustom::setState(v8::Handle<v8::Object> internal, PromiseState state, v8::Handle<v8::Value> value, v8::Isolate* isolate)
-{
- ASSERT(!value.IsEmpty());
- ASSERT(state == Pending || state == Fulfilled || state == Rejected || state == Following);
- internal->SetInternalField(InternalStateIndex, v8::Integer::New(state, isolate));
- internal->SetInternalField(InternalResultIndex, value);
-}
-
-bool V8PromiseCustom::isPromise(v8::Handle<v8::Value> maybePromise, v8::Isolate* isolate)
-{
- WrapperWorldType currentWorldType = worldType(isolate);
- return V8Promise::domTemplate(isolate, currentWorldType)->HasInstance(maybePromise);
-}
-
-v8::Local<v8::Object> V8PromiseCustom::toPromise(v8::Handle<v8::Value> maybePromise, v8::Isolate* isolate)
-{
- // FIXME: Currently we don't check [[PromiseConstructor]] since we limit
- // the creation of the promise objects only from the Blink Promise
- // constructor.
- if (isPromise(maybePromise, isolate))
- return maybePromise.As<v8::Object>();
-
- v8::Local<v8::Object> promise = createPromise(v8::Handle<v8::Object>(), isolate);
- resolve(promise, maybePromise, isolate);
- return promise;
-}
-
-void V8PromiseCustom::resolve(v8::Handle<v8::Object> promise, v8::Handle<v8::Value> result, v8::Isolate* isolate)
-{
- ASSERT(!result.IsEmpty());
- v8::Local<v8::Object> internal = getInternal(promise);
- PromiseState state = getState(internal);
- if (state != Pending)
- return;
-
- if (isPromise(result, isolate)) {
- v8::Local<v8::Object> valuePromise = result.As<v8::Object>();
- v8::Local<v8::Object> valueInternal = getInternal(valuePromise);
- PromiseState valueState = getState(valueInternal);
- if (promise->SameValue(valuePromise)) {
- v8::Local<v8::Value> reason = V8ThrowException::createTypeError("Resolve a promise with itself", isolate);
- setReason(promise, reason, isolate);
- } else if (valueState == Following) {
- v8::Local<v8::Object> valuePromiseFollowing = valueInternal->GetInternalField(InternalResultIndex).As<v8::Object>();
- setState(internal, Following, valuePromiseFollowing, isolate);
- addToDerived(getInternal(valuePromiseFollowing), promise, v8::Handle<v8::Function>(), v8::Handle<v8::Function>(), isolate);
- } else if (valueState == Fulfilled) {
- setValue(promise, valueInternal->GetInternalField(InternalResultIndex), isolate);
- } else if (valueState == Rejected) {
- setReason(promise, valueInternal->GetInternalField(InternalResultIndex), isolate);
- } else {
- ASSERT(valueState == Pending);
- setState(internal, Following, valuePromise, isolate);
- addToDerived(valueInternal, promise, v8::Handle<v8::Function>(), v8::Handle<v8::Function>(), isolate);
- }
- } else {
- setValue(promise, result, isolate);
- }
-}
-
-void V8PromiseCustom::reject(v8::Handle<v8::Object> promise, v8::Handle<v8::Value> reason, v8::Isolate* isolate)
-{
- v8::Local<v8::Object> internal = getInternal(promise);
- PromiseState state = getState(internal);
- if (state != Pending)
- return;
- setReason(promise, reason, isolate);
-}
-
-v8::Local<v8::Object> V8PromiseCustom::then(v8::Handle<v8::Object> promise, v8::Handle<v8::Function> onFulfilled, v8::Handle<v8::Function> onRejected, v8::Isolate* isolate)
-{
- v8::Handle<v8::Object> internal = getInternal(promise);
- while (getState(internal) == Following) {
- promise = internal->GetInternalField(InternalResultIndex).As<v8::Object>();
- internal = getInternal(promise);
- }
- // FIXME: Currently we don't lookup "constructor" property since we limit
- // the creation of the promise objects only from the Blink Promise
- // constructor.
- v8::Local<v8::Object> derivedPromise = createPromise(v8::Handle<v8::Object>(), isolate);
- updateDerivedFromPromise(derivedPromise, onFulfilled, onRejected, promise, isolate);
- return derivedPromise;
-}
-
-void V8PromiseCustom::setValue(v8::Handle<v8::Object> promise, v8::Handle<v8::Value> value, v8::Isolate* isolate)
-{
- PromisePropagator propagator;
- propagator.setValue(promise, value, isolate);
- propagator.performPropagation(isolate);
-}
-
-void V8PromiseCustom::setReason(v8::Handle<v8::Object> promise, v8::Handle<v8::Value> reason, v8::Isolate* isolate)
-{
- PromisePropagator propagator;
- propagator.setReason(promise, reason, isolate);
- propagator.performPropagation(isolate);
-}
-
-void V8PromiseCustom::propagateToDerived(v8::Handle<v8::Object> promise, v8::Isolate* isolate)
-{
- PromisePropagator propagator;
- propagator.propagateToDerived(promise, isolate);
- propagator.performPropagation(isolate);
-}
-
-void V8PromiseCustom::updateDerived(v8::Handle<v8::Object> derivedPromise, v8::Handle<v8::Function> onFulfilled, v8::Handle<v8::Function> onRejected, v8::Handle<v8::Object> originator, v8::Isolate* isolate)
-{
- PromisePropagator propagator;
- propagator.updateDerived(derivedPromise, onFulfilled, onRejected, originator, isolate);
- propagator.performPropagation(isolate);
-}
-
-void V8PromiseCustom::updateDerivedFromValue(v8::Handle<v8::Object> derivedPromise, v8::Handle<v8::Function> onFulfilled, v8::Handle<v8::Value> value, v8::Isolate* isolate)
-{
- PromisePropagator propagator;
- propagator.updateDerivedFromValue(derivedPromise, onFulfilled, value, isolate);
- propagator.performPropagation(isolate);
-}
-
-void V8PromiseCustom::updateDerivedFromReason(v8::Handle<v8::Object> derivedPromise, v8::Handle<v8::Function> onRejected, v8::Handle<v8::Value> reason, v8::Isolate* isolate)
-{
- PromisePropagator propagator;
- propagator.updateDerivedFromReason(derivedPromise, onRejected, reason, isolate);
- propagator.performPropagation(isolate);
-}
-
-void V8PromiseCustom::updateDerivedFromPromise(v8::Handle<v8::Object> derivedPromise, v8::Handle<v8::Function> onFulfilled, v8::Handle<v8::Function> onRejected, v8::Handle<v8::Object> promise, v8::Isolate* isolate)
-{
- PromisePropagator propagator;
- propagator.updateDerivedFromPromise(derivedPromise, onFulfilled, onRejected, promise, isolate);
- propagator.performPropagation(isolate);
-}
-
-v8::Local<v8::Object> V8PromiseCustom::coerceThenable(v8::Handle<v8::Object> thenable, v8::Handle<v8::Function> then, v8::Isolate* isolate)
-{
- ASSERT(!thenable.IsEmpty());
- ASSERT(!then.IsEmpty());
- v8::Local<v8::Object> promise = createPromise(v8::Handle<v8::Object>(), isolate);
- v8::Handle<v8::Value> argv[] = {
- createClosure(promiseResolveCallback, promise, isolate),
- createClosure(promiseRejectCallback, promise, isolate)
- };
- v8::TryCatch trycatch;
- if (V8ScriptRunner::callFunction(then, getExecutionContext(), thenable, WTF_ARRAY_LENGTH(argv), argv, isolate).IsEmpty()) {
- reject(promise, trycatch.Exception(), isolate);
- }
- thenable->SetHiddenValue(V8HiddenPropertyName::thenableHiddenPromise(isolate), promise);
- return promise;
-}
-
-void V8PromiseCustom::callHandler(v8::Handle<v8::Object> promise, v8::Handle<v8::Function> handler, v8::Handle<v8::Value> argument, v8::Isolate* isolate)
-{
- ExecutionContext* executionContext = getExecutionContext();
- ASSERT(executionContext && executionContext->isContextThread());
- executionContext->postTask(adoptPtr(new CallHandlerTask(promise, handler, argument, isolate, executionContext)));
-}
-
-} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8PromiseCustom.h b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8PromiseCustom.h
deleted file mode 100644
index 1751c1e4ae3..00000000000
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8PromiseCustom.h
+++ /dev/null
@@ -1,136 +0,0 @@
-/*
- * Copyright (C) 2013, Google Inc. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions
- * are met:
- * 1. Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * 2. Redistributions in binary form must reproduce the above copyright
- * notice, this list of conditions and the following disclaimer in the
- * documentation and/or other materials provided with the distribution.
- *
- * THIS SOFTWARE IS PROVIDED BY APPLE INC. AND ITS CONTRIBUTORS ``AS IS'' AND ANY
- * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE IMPLIED
- * WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE ARE
- * DISCLAIMED. IN NO EVENT SHALL APPLE INC. OR ITS CONTRIBUTORS BE LIABLE FOR ANY
- * DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES
- * (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES;
- * LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON
- * ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE OF THIS
- * SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-#ifndef V8PromiseCustom_h
-#define V8PromiseCustom_h
-
-#include "bindings/v8/WrapperTypeInfo.h"
-
-#include <v8.h>
-
-namespace WebCore {
-
-class V8PromiseCustom {
-public:
- enum InternalFieldIndex {
- InternalStateIndex,
- InternalResultIndex,
- InternalFulfillCallbackIndex,
- InternalRejectCallbackIndex,
- InternalDerivedPromiseIndex,
- InternalFieldCount, // This entry must always be at the bottom.
- };
-
- enum PromiseAllEnvironmentFieldIndex {
- PromiseAllEnvironmentPromiseIndex,
- PromiseAllEnvironmentCountdownIndex,
- PromiseAllEnvironmentIndexIndex,
- PromiseAllEnvironmentResultsIndex,
- PromiseAllEnvironmentFieldCount, // This entry must always be at the bottom.
- };
-
- enum PrimitiveWrapperFieldIndex {
- PrimitiveWrapperPrimitiveIndex,
- PrimitiveWrapperFieldCount, // This entry must always be at the bottom.
- };
-
- enum PromiseState {
- Pending,
- Fulfilled,
- Rejected,
- Following,
- };
-
- static v8::Local<v8::Object> createPromise(v8::Handle<v8::Object> creationContext, v8::Isolate*);
-
- // |promise| must be a Promise instance.
- static v8::Local<v8::Object> getInternal(v8::Handle<v8::Object> promise);
-
- // |internal| must be a Promise internal object.
- static PromiseState getState(v8::Handle<v8::Object> internal);
-
- // |internal| must be a Promise internal object.
- // Set a |promise|'s state and result that correspond to the state.
- static void setState(v8::Handle<v8::Object> internal, PromiseState, v8::Handle<v8::Value>, v8::Isolate*);
-
- // Return true if |maybePromise| is a Promise instance.
- static bool isPromise(v8::Handle<v8::Value> maybePromise, v8::Isolate*);
-
- // Coerces |maybePromise| to a Promise instance.
- static v8::Local<v8::Object> toPromise(v8::Handle<v8::Value> maybePromise, v8::Isolate*);
-
- // |promise| must be a Promise instance.
- static void resolve(v8::Handle<v8::Object> promise, v8::Handle<v8::Value> result, v8::Isolate*);
-
- // |promise| must be a Promise instance.
- static void reject(v8::Handle<v8::Object> promise, v8::Handle<v8::Value> result, v8::Isolate*);
-
- // |promise| must be a Promise instance.
- // |onFulfilled| and |onRejected| can be an empty value respectively.
- // Appends |onFulfilled| and/or |onRejected| handlers to |promise|.
- static v8::Local<v8::Object> then(v8::Handle<v8::Object> promise, v8::Handle<v8::Function> onFulfilled, v8::Handle<v8::Function> onRejected, v8::Isolate*);
-
- // |promise| must be a Promise instance.
- // Set a |promise|'s value and propagate it to derived promises.
- static void setValue(v8::Handle<v8::Object> promise, v8::Handle<v8::Value>, v8::Isolate*);
-
- // |promise| must be a Promise instance.
- // Set a |promise|'s failure reason and propagate it to derived promises.
- static void setReason(v8::Handle<v8::Object> promise, v8::Handle<v8::Value>, v8::Isolate*);
-
- // |promise| must be a Promise instance.
- // Propagate a |promise|'s value or reason to all of its derived promies.
- static void propagateToDerived(v8::Handle<v8::Object> promise, v8::Isolate*);
-
- // |derivedPromise| and |originator| must be a Promise instance.
- // |onFulfilled| and |onRejected| can be an empty value respectively.
- // Propagate |originator|'s state to |derivedPromise|.
- static void updateDerived(v8::Handle<v8::Object> derivedPromise, v8::Handle<v8::Function> onFulfilled, v8::Handle<v8::Function> onRejected, v8::Handle<v8::Object> originator, v8::Isolate*);
-
- // |derivedPromise| must be a Promise instance.
- // Propagate a value to |derivedPromise|.
- static void updateDerivedFromValue(v8::Handle<v8::Object> derivedPromise, v8::Handle<v8::Function> onFulfilled, v8::Handle<v8::Value>, v8::Isolate*);
-
- // |derivedPromise| must be a Promise instance.
- // Propagate a failure reason to |derivedPromise|.
- static void updateDerivedFromReason(v8::Handle<v8::Object> derivedPromise, v8::Handle<v8::Function> onRejected, v8::Handle<v8::Value>, v8::Isolate*);
-
- // |derivedPromise| and |promise| must be a Promise instance.
- // |onFulfilled| and |onRejected| can be an empty value respectively.
- // Propagate |promise|'s state to |derivedPromise|.
- static void updateDerivedFromPromise(v8::Handle<v8::Object> derivedPromise, v8::Handle<v8::Function> onFulfilled, v8::Handle<v8::Function> onRejected, v8::Handle<v8::Object> promise, v8::Isolate*);
-
- // Returns a Promise instance that will be fulfilled or rejected by
- // |thenable|'s result.
- static v8::Local<v8::Object> coerceThenable(v8::Handle<v8::Object> thenable, v8::Handle<v8::Function> then, v8::Isolate*);
-
- // |promise| must be a Promise instance.
- // Applies a transformation to an argument and use it to update derived
- // promies.
- static void callHandler(v8::Handle<v8::Object> promise, v8::Handle<v8::Function> handler, v8::Handle<v8::Value> argument, v8::Isolate*);
-};
-
-} // namespace WebCore
-
-#endif // V8PromiseCustom_h
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8SQLResultSetRowListCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8SQLResultSetRowListCustom.cpp
index 3c41cb7b9a6..a6fed441759 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8SQLResultSetRowListCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8SQLResultSetRowListCustom.cpp
@@ -29,22 +29,28 @@
*/
#include "config.h"
-#include "V8SQLResultSetRowList.h"
+#include "bindings/modules/v8/V8SQLResultSetRowList.h"
+#include "bindings/v8/ExceptionMessages.h"
+#include "bindings/v8/ExceptionState.h"
#include "bindings/v8/V8Binding.h"
+#include "core/dom/ExceptionCode.h"
#include "modules/webdatabase/SQLResultSetRowList.h"
namespace WebCore {
void V8SQLResultSetRowList::itemMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "item", "SQLResultSetRowList", info.Holder(), info.GetIsolate());
if (!info.Length()) {
- throwError(v8SyntaxError, "Item index is required.", info.GetIsolate());
+ exceptionState.throwDOMException(SyntaxError, ExceptionMessages::notEnoughArguments(1, 0));
+ exceptionState.throwIfNeeded();
return;
}
if (!info[0]->IsNumber()) {
- throwTypeError("Item index must be a number.", info.GetIsolate());
+ exceptionState.throwTypeError("The index provided is not a number.");
+ exceptionState.throwIfNeeded();
return;
}
@@ -52,11 +58,12 @@ void V8SQLResultSetRowList::itemMethodCustom(const v8::FunctionCallbackInfo<v8::
unsigned long index = info[0]->IntegerValue();
if (index >= rowList->length()) {
- throwError(v8RangeError, "Item index is out of range.", info.GetIsolate());
+ exceptionState.throwDOMException(IndexSizeError, ExceptionMessages::indexExceedsMaximumBound<unsigned>("index", index, rowList->length()));
+ exceptionState.throwIfNeeded();
return;
}
- v8::Local<v8::Object> item = v8::Object::New();
+ v8::Local<v8::Object> item = v8::Object::New(info.GetIsolate());
unsigned numColumns = rowList->columnNames().size();
unsigned valuesIndex = index * numColumns;
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8SQLTransactionCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8SQLTransactionCustom.cpp
index 9a314b5f666..45a764ce042 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8SQLTransactionCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8SQLTransactionCustom.cpp
@@ -29,10 +29,11 @@
*/
#include "config.h"
-#include "V8SQLTransaction.h"
+#include "bindings/modules/v8/V8SQLTransaction.h"
-#include "V8SQLStatementCallback.h"
-#include "V8SQLStatementErrorCallback.h"
+#include "bindings/modules/v8/V8SQLStatementCallback.h"
+#include "bindings/modules/v8/V8SQLStatementErrorCallback.h"
+#include "bindings/v8/ExceptionMessages.h"
#include "bindings/v8/ExceptionState.h"
#include "bindings/v8/V8Binding.h"
#include "core/dom/ExceptionCode.h"
@@ -46,69 +47,70 @@ namespace WebCore {
void V8SQLTransaction::executeSqlMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "executeSql", "SQLTransaction", info.Holder(), info.GetIsolate());
if (!info.Length()) {
- setDOMException(SyntaxError, info.GetIsolate());
+ exceptionState.throwDOMException(SyntaxError, ExceptionMessages::notEnoughArguments(1, 0));
+ exceptionState.throwIfNeeded();
return;
}
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<>, statement, info[0]);
+ TOSTRING_VOID(V8StringResource<>, statement, info[0]);
Vector<SQLValue> sqlValues;
if (info.Length() > 1 && !isUndefinedOrNull(info[1])) {
if (!info[1]->IsObject()) {
- setDOMException(TypeMismatchError, info.GetIsolate());
+ exceptionState.throwDOMException(TypeMismatchError, "The 'arguments' (2nd) argument provided is not an object.");
+ exceptionState.throwIfNeeded();
return;
}
uint32_t sqlArgsLength = 0;
v8::Local<v8::Object> sqlArgsObject = info[1]->ToObject();
- V8TRYCATCH_VOID(v8::Local<v8::Value>, length, sqlArgsObject->Get(v8AtomicString(info.GetIsolate(), "length")));
+ TONATIVE_VOID(v8::Local<v8::Value>, length, sqlArgsObject->Get(v8AtomicString(info.GetIsolate(), "length")));
if (isUndefinedOrNull(length))
sqlArgsLength = sqlArgsObject->GetPropertyNames()->Length();
else
sqlArgsLength = length->Uint32Value();
- for (unsigned int i = 0; i < sqlArgsLength; ++i) {
- v8::Handle<v8::Integer> key = v8::Integer::New(i, info.GetIsolate());
- V8TRYCATCH_VOID(v8::Local<v8::Value>, value, sqlArgsObject->Get(key));
+ for (unsigned i = 0; i < sqlArgsLength; ++i) {
+ v8::Handle<v8::Integer> key = v8::Integer::New(info.GetIsolate(), i);
+ TONATIVE_VOID(v8::Local<v8::Value>, value, sqlArgsObject->Get(key));
if (value.IsEmpty() || value->IsNull())
sqlValues.append(SQLValue());
else if (value->IsNumber()) {
- V8TRYCATCH_VOID(double, sqlValue, value->NumberValue());
+ TONATIVE_VOID(double, sqlValue, value->NumberValue());
sqlValues.append(SQLValue(sqlValue));
} else {
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<>, sqlValue, value);
+ TOSTRING_VOID(V8StringResource<>, sqlValue, value);
sqlValues.append(SQLValue(sqlValue));
}
}
}
SQLTransaction* transaction = V8SQLTransaction::toNative(info.Holder());
-
- ExecutionContext* executionContext = getExecutionContext();
-
OwnPtr<SQLStatementCallback> callback;
if (info.Length() > 2 && !isUndefinedOrNull(info[2])) {
if (!info[2]->IsFunction()) {
- setDOMException(TypeMismatchError, info.GetIsolate());
+ exceptionState.throwDOMException(TypeMismatchError, "The 'callback' (2nd) argument provided is not a function.");
+ exceptionState.throwIfNeeded();
return;
}
- callback = V8SQLStatementCallback::create(v8::Handle<v8::Function>::Cast(info[2]), executionContext);
+ callback = V8SQLStatementCallback::create(v8::Handle<v8::Function>::Cast(info[2]), ScriptState::current(info.GetIsolate()));
}
OwnPtr<SQLStatementErrorCallback> errorCallback;
if (info.Length() > 3 && !isUndefinedOrNull(info[3])) {
if (!info[3]->IsFunction()) {
- setDOMException(TypeMismatchError, info.GetIsolate());
+ exceptionState.throwDOMException(TypeMismatchError, "The 'errorCallback' (3rd) argument provided is not a function.");
+ exceptionState.throwIfNeeded();
return;
}
- errorCallback = V8SQLStatementErrorCallback::create(v8::Handle<v8::Function>::Cast(info[3]), executionContext);
+ errorCallback = V8SQLStatementErrorCallback::create(v8::Handle<v8::Function>::Cast(info[3]), ScriptState::current(info.GetIsolate()));
}
- ExceptionState exceptionState(info.Holder(), info.GetIsolate());
transaction->executeSQL(statement, sqlValues, callback.release(), errorCallback.release(), exceptionState);
exceptionState.throwIfNeeded();
}
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8SQLTransactionSyncCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8SQLTransactionSyncCustom.cpp
index eaffffa0ca5..9b24721fa41 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8SQLTransactionSyncCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8SQLTransactionSyncCustom.cpp
@@ -29,9 +29,9 @@
*/
#include "config.h"
-#include "V8SQLTransactionSync.h"
+#include "bindings/modules/v8/V8SQLTransactionSync.h"
-#include "V8SQLResultSet.h"
+#include "bindings/modules/v8/V8SQLResultSet.h"
#include "bindings/v8/ExceptionState.h"
#include "bindings/v8/V8Binding.h"
#include "core/dom/ExceptionCode.h"
@@ -46,41 +46,44 @@ namespace WebCore {
void V8SQLTransactionSync::executeSqlMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "executeSql", "SQLTransactionSync", info.Holder(), info.GetIsolate());
if (!info.Length()) {
- setDOMException(SyntaxError, info.GetIsolate());
+ exceptionState.throwDOMException(SyntaxError, ExceptionMessages::notEnoughArguments(1, 0));
+ exceptionState.throwIfNeeded();
return;
}
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<>, statement, info[0]);
+ TOSTRING_VOID(V8StringResource<>, statement, info[0]);
Vector<SQLValue> sqlValues;
if (info.Length() > 1 && !isUndefinedOrNull(info[1])) {
if (!info[1]->IsObject()) {
- setDOMException(TypeMismatchError, info.GetIsolate());
+ exceptionState.throwDOMException(TypeMismatchError, ExceptionMessages::argumentNullOrIncorrectType(1, "DOMString"));
+ exceptionState.throwIfNeeded();
return;
}
uint32_t sqlArgsLength = 0;
v8::Local<v8::Object> sqlArgsObject = info[1]->ToObject();
- V8TRYCATCH_VOID(v8::Local<v8::Value>, length, sqlArgsObject->Get(v8AtomicString(info.GetIsolate(), "length")));
+ TONATIVE_VOID(v8::Local<v8::Value>, length, sqlArgsObject->Get(v8AtomicString(info.GetIsolate(), "length")));
if (isUndefinedOrNull(length))
sqlArgsLength = sqlArgsObject->GetPropertyNames()->Length();
else
sqlArgsLength = length->Uint32Value();
- for (unsigned int i = 0; i < sqlArgsLength; ++i) {
- v8::Handle<v8::Integer> key = v8::Integer::New(i, info.GetIsolate());
- V8TRYCATCH_VOID(v8::Local<v8::Value>, value, sqlArgsObject->Get(key));
+ for (unsigned i = 0; i < sqlArgsLength; ++i) {
+ v8::Handle<v8::Integer> key = v8::Integer::New(info.GetIsolate(), i);
+ TONATIVE_VOID(v8::Local<v8::Value>, value, sqlArgsObject->Get(key));
if (value.IsEmpty() || value->IsNull())
sqlValues.append(SQLValue());
else if (value->IsNumber()) {
- V8TRYCATCH_VOID(double, sqlValue, value->NumberValue());
+ TONATIVE_VOID(double, sqlValue, value->NumberValue());
sqlValues.append(SQLValue(sqlValue));
} else {
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<>, sqlValue, value);
+ TOSTRING_VOID(V8StringResource<>, sqlValue, value);
sqlValues.append(SQLValue(sqlValue));
}
}
@@ -88,7 +91,6 @@ void V8SQLTransactionSync::executeSqlMethodCustom(const v8::FunctionCallbackInfo
SQLTransactionSync* transaction = V8SQLTransactionSync::toNative(info.Holder());
- ExceptionState exceptionState(info.Holder(), info.GetIsolate());
v8::Handle<v8::Value> result = toV8(transaction->executeSQL(statement, sqlValues, exceptionState), info.Holder(), info.GetIsolate());
if (exceptionState.throwIfNeeded())
return;
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8SVGElementCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8SVGElementCustom.cpp
index c21247e4d9a..abe89461fad 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8SVGElementCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8SVGElementCustom.cpp
@@ -29,9 +29,9 @@
*/
#include "config.h"
-#include "V8SVGElement.h"
+#include "bindings/core/v8/V8SVGElement.h"
-#include "V8SVGElementWrapperFactory.h"
+#include "core/V8SVGElementWrapperFactory.h" // FIXME: should be bindings/core/v8
namespace WebCore {
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8SVGLengthCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8SVGLengthCustom.cpp
deleted file mode 100644
index a5a1cfef55b..00000000000
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8SVGLengthCustom.cpp
+++ /dev/null
@@ -1,102 +0,0 @@
-/*
- * Copyright (C) 2009 Google Inc. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions are
- * met:
- *
- * * Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * * Redistributions in binary form must reproduce the above
- * copyright notice, this list of conditions and the following disclaimer
- * in the documentation and/or other materials provided with the
- * distribution.
- * * Neither the name of Google Inc. nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
- * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
- * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
- * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
- * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
- * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
- * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
- * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
- * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-#include "config.h"
-#include "V8SVGLength.h"
-
-#include "bindings/v8/ExceptionMessages.h"
-#include "bindings/v8/ExceptionState.h"
-#include "bindings/v8/V8Binding.h"
-#include "core/dom/ExceptionCode.h"
-#include "core/svg/SVGLengthContext.h"
-#include "core/svg/properties/SVGPropertyTearOff.h"
-
-namespace WebCore {
-
-void V8SVGLength::valueAttributeGetterCustom(const v8::PropertyCallbackInfo<v8::Value>& info)
-{
- SVGPropertyTearOff<SVGLength>* wrapper = V8SVGLength::toNative(info.Holder());
- SVGLength& imp = wrapper->propertyReference();
- ExceptionState exceptionState(info.Holder(), info.GetIsolate());
- SVGLengthContext lengthContext(wrapper->contextElement());
- float value = imp.value(lengthContext, exceptionState);
- if (exceptionState.throwIfNeeded())
- return;
- v8SetReturnValue(info, value);
-}
-
-void V8SVGLength::valueAttributeSetterCustom(v8::Local<v8::Value> value, const v8::PropertyCallbackInfo<void>& info)
-{
- SVGPropertyTearOff<SVGLength>* wrapper = V8SVGLength::toNative(info.Holder());
- if (wrapper->isReadOnly()) {
- setDOMException(NoModificationAllowedError, info.GetIsolate());
- return;
- }
-
- if (!isUndefinedOrNull(value) && !value->IsNumber() && !value->IsBoolean()) {
- throwUninformativeAndGenericTypeError(info.GetIsolate());
- return;
- }
-
- SVGLength& imp = wrapper->propertyReference();
- ExceptionState exceptionState(info.Holder(), info.GetIsolate());
- SVGLengthContext lengthContext(wrapper->contextElement());
- imp.setValue(static_cast<float>(value->NumberValue()), lengthContext, exceptionState);
- if (exceptionState.throwIfNeeded())
- return;
- wrapper->commitChange();
-}
-
-void V8SVGLength::convertToSpecifiedUnitsMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
-{
- ExceptionState exceptionState(ExceptionState::ExecutionContext, "convertToSpecifiedUnits", "SVGLength", info.Holder(), info.GetIsolate());
- SVGPropertyTearOff<SVGLength>* wrapper = V8SVGLength::toNative(info.Holder());
- if (wrapper->isReadOnly()) {
- exceptionState.throwDOMException(NoModificationAllowedError, "The length is read only.");
- exceptionState.throwIfNeeded();
- return;
- }
-
- if (info.Length() < 1) {
- exceptionState.throwTypeError(ExceptionMessages::notEnoughArguments(1, info.Length()));
- exceptionState.throwIfNeeded();
- return;
- }
-
- SVGLength& imp = wrapper->propertyReference();
- V8TRYCATCH_VOID(int, unitType, toUInt32(info[0]));
- SVGLengthContext lengthContext(wrapper->contextElement());
- imp.convertToSpecifiedUnits(unitType, lengthContext, exceptionState);
- if (exceptionState.throwIfNeeded())
- return;
- wrapper->commitChange();
-}
-
-} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8SVGPathSegCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8SVGPathSegCustom.cpp
index 77bf679d4f8..8d159757c06 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8SVGPathSegCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8SVGPathSegCustom.cpp
@@ -29,28 +29,28 @@
*/
#include "config.h"
-#include "V8SVGPathSeg.h"
+#include "bindings/core/v8/V8SVGPathSeg.h"
-#include "V8SVGPathSegArcAbs.h"
-#include "V8SVGPathSegArcRel.h"
-#include "V8SVGPathSegClosePath.h"
-#include "V8SVGPathSegCurvetoCubicAbs.h"
-#include "V8SVGPathSegCurvetoCubicRel.h"
-#include "V8SVGPathSegCurvetoCubicSmoothAbs.h"
-#include "V8SVGPathSegCurvetoCubicSmoothRel.h"
-#include "V8SVGPathSegCurvetoQuadraticAbs.h"
-#include "V8SVGPathSegCurvetoQuadraticRel.h"
-#include "V8SVGPathSegCurvetoQuadraticSmoothAbs.h"
-#include "V8SVGPathSegCurvetoQuadraticSmoothRel.h"
-#include "V8SVGPathSegLinetoAbs.h"
-#include "V8SVGPathSegLinetoHorizontalAbs.h"
-#include "V8SVGPathSegLinetoHorizontalRel.h"
-#include "V8SVGPathSegLinetoRel.h"
-#include "V8SVGPathSegLinetoVerticalAbs.h"
-#include "V8SVGPathSegLinetoVerticalRel.h"
-#include "V8SVGPathSegMovetoAbs.h"
-#include "V8SVGPathSegMovetoRel.h"
-#include "V8Window.h"
+#include "bindings/core/v8/V8SVGPathSegArcAbs.h"
+#include "bindings/core/v8/V8SVGPathSegArcRel.h"
+#include "bindings/core/v8/V8SVGPathSegClosePath.h"
+#include "bindings/core/v8/V8SVGPathSegCurvetoCubicAbs.h"
+#include "bindings/core/v8/V8SVGPathSegCurvetoCubicRel.h"
+#include "bindings/core/v8/V8SVGPathSegCurvetoCubicSmoothAbs.h"
+#include "bindings/core/v8/V8SVGPathSegCurvetoCubicSmoothRel.h"
+#include "bindings/core/v8/V8SVGPathSegCurvetoQuadraticAbs.h"
+#include "bindings/core/v8/V8SVGPathSegCurvetoQuadraticRel.h"
+#include "bindings/core/v8/V8SVGPathSegCurvetoQuadraticSmoothAbs.h"
+#include "bindings/core/v8/V8SVGPathSegCurvetoQuadraticSmoothRel.h"
+#include "bindings/core/v8/V8SVGPathSegLinetoAbs.h"
+#include "bindings/core/v8/V8SVGPathSegLinetoHorizontalAbs.h"
+#include "bindings/core/v8/V8SVGPathSegLinetoHorizontalRel.h"
+#include "bindings/core/v8/V8SVGPathSegLinetoRel.h"
+#include "bindings/core/v8/V8SVGPathSegLinetoVerticalAbs.h"
+#include "bindings/core/v8/V8SVGPathSegLinetoVerticalRel.h"
+#include "bindings/core/v8/V8SVGPathSegMovetoAbs.h"
+#include "bindings/core/v8/V8SVGPathSegMovetoRel.h"
+#include "bindings/core/v8/V8Window.h"
#include "bindings/v8/V8DOMWrapper.h"
namespace WebCore {
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8ServiceWorkerCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8ServiceWorkerCustom.cpp
new file mode 100644
index 00000000000..21337b4f437
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8ServiceWorkerCustom.cpp
@@ -0,0 +1,38 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "config.h"
+#include "bindings/modules/v8/V8ServiceWorker.h"
+
+#include "bindings/v8/ExceptionMessages.h"
+#include "bindings/v8/ExceptionState.h"
+#include "bindings/v8/SerializedScriptValue.h"
+#include "bindings/v8/V8Binding.h"
+#include "core/dom/MessagePort.h"
+#include "modules/serviceworkers/ServiceWorker.h"
+#include "wtf/ArrayBuffer.h"
+
+namespace WebCore {
+
+void V8ServiceWorker::postMessageMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
+{
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "postMessage", "ServiceWorker", info.Holder(), info.GetIsolate());
+ ServiceWorker* worker = V8ServiceWorker::toNative(info.Holder());
+ MessagePortArray ports;
+ ArrayBufferArray arrayBuffers;
+ if (info.Length() > 1) {
+ const int transferablesArgIndex = 1;
+ if (!SerializedScriptValue::extractTransferables(info[transferablesArgIndex], transferablesArgIndex, ports, arrayBuffers, exceptionState, info.GetIsolate())) {
+ exceptionState.throwIfNeeded();
+ return;
+ }
+ }
+ RefPtr<SerializedScriptValue> message = SerializedScriptValue::create(info[0], &ports, &arrayBuffers, exceptionState, info.GetIsolate());
+ if (exceptionState.throwIfNeeded())
+ return;
+ worker->postMessage(message.release(), &ports, exceptionState);
+ exceptionState.throwIfNeeded();
+}
+
+} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8StyleSheetCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8StyleSheetCustom.cpp
index 39d28a800c6..8705d0783be 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8StyleSheetCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8StyleSheetCustom.cpp
@@ -29,10 +29,10 @@
*/
#include "config.h"
-#include "V8StyleSheet.h"
+#include "bindings/core/v8/V8StyleSheet.h"
-#include "V8CSSStyleSheet.h"
-#include "V8Node.h"
+#include "bindings/core/v8/V8CSSStyleSheet.h"
+#include "bindings/core/v8/V8Node.h"
#include "bindings/v8/V8DOMWrapper.h"
namespace WebCore {
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8SubtleCryptoCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8SubtleCryptoCustom.cpp
new file mode 100644
index 00000000000..943ad7666a0
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8SubtleCryptoCustom.cpp
@@ -0,0 +1,125 @@
+// Copyright 2014 The Chromium Authors. All rights reserved.
+// Use of this source code is governed by a BSD-style license that can be
+// found in the LICENSE file.
+
+#include "config.h"
+#include "bindings/modules/v8/V8SubtleCrypto.h"
+
+#include "bindings/modules/v8/V8Key.h"
+#include "bindings/v8/Dictionary.h"
+#include "bindings/v8/custom/V8ArrayBufferCustom.h"
+#include "bindings/v8/custom/V8ArrayBufferViewCustom.h"
+
+namespace WebCore {
+
+////////////////////////////////////////////////////////////////////////////////
+// Overload resolution for verify()
+// FIXME: needs support for union types http://crbug.com/240176
+////////////////////////////////////////////////////////////////////////////////
+
+// Promise verify(Dictionary algorithm, Key key, ArrayBuffer signature, ArrayBuffer data);
+void verify1Method(const v8::FunctionCallbackInfo<v8::Value>& info)
+{
+ SubtleCrypto* impl = V8SubtleCrypto::toNative(info.Holder());
+ TONATIVE_VOID(Dictionary, algorithm, Dictionary(info[0], info.GetIsolate()));
+ if (!algorithm.isUndefinedOrNull() && !algorithm.isObject()) {
+ throwTypeError(ExceptionMessages::failedToExecute("verify", "SubtleCrypto", "parameter 1 ('algorithm') is not an object."), info.GetIsolate());
+ return;
+ }
+ TONATIVE_VOID(Key*, key, V8Key::toNativeWithTypeCheck(info.GetIsolate(), info[1]));
+ TONATIVE_VOID(ArrayBuffer*, signature, info[2]->IsArrayBuffer() ? V8ArrayBuffer::toNative(v8::Handle<v8::ArrayBuffer>::Cast(info[2])) : 0);
+ TONATIVE_VOID(ArrayBuffer*, data, info[3]->IsArrayBuffer() ? V8ArrayBuffer::toNative(v8::Handle<v8::ArrayBuffer>::Cast(info[3])) : 0);
+ v8SetReturnValue(info, impl->verifySignature(ScriptState::current(info.GetIsolate()), algorithm, key, signature, data).v8Value());
+}
+
+// Promise verify(Dictionary algorithm, Key key, ArrayBuffer signature, ArrayBufferView data);
+void verify2Method(const v8::FunctionCallbackInfo<v8::Value>& info)
+{
+ SubtleCrypto* impl = V8SubtleCrypto::toNative(info.Holder());
+ TONATIVE_VOID(Dictionary, algorithm, Dictionary(info[0], info.GetIsolate()));
+ if (!algorithm.isUndefinedOrNull() && !algorithm.isObject()) {
+ throwTypeError(ExceptionMessages::failedToExecute("verify", "SubtleCrypto", "parameter 1 ('algorithm') is not an object."), info.GetIsolate());
+ return;
+ }
+ TONATIVE_VOID(Key*, key, V8Key::toNativeWithTypeCheck(info.GetIsolate(), info[1]));
+ TONATIVE_VOID(ArrayBuffer*, signature, info[2]->IsArrayBuffer() ? V8ArrayBuffer::toNative(v8::Handle<v8::ArrayBuffer>::Cast(info[2])) : 0);
+ TONATIVE_VOID(ArrayBufferView*, data, info[3]->IsArrayBufferView() ? V8ArrayBufferView::toNative(v8::Handle<v8::ArrayBufferView>::Cast(info[3])) : 0);
+ v8SetReturnValue(info, impl->verifySignature(ScriptState::current(info.GetIsolate()), algorithm, key, signature, data).v8Value());
+}
+
+// Promise verify(Dictionary algorithm, Key key, ArrayBufferView signature, ArrayBuffer data);
+void verify3Method(const v8::FunctionCallbackInfo<v8::Value>& info)
+{
+ SubtleCrypto* impl = V8SubtleCrypto::toNative(info.Holder());
+ TONATIVE_VOID(Dictionary, algorithm, Dictionary(info[0], info.GetIsolate()));
+ if (!algorithm.isUndefinedOrNull() && !algorithm.isObject()) {
+ throwTypeError(ExceptionMessages::failedToExecute("verify", "SubtleCrypto", "parameter 1 ('algorithm') is not an object."), info.GetIsolate());
+ return;
+ }
+ TONATIVE_VOID(Key*, key, V8Key::toNativeWithTypeCheck(info.GetIsolate(), info[1]));
+ TONATIVE_VOID(ArrayBufferView*, signature, info[2]->IsArrayBufferView() ? V8ArrayBufferView::toNative(v8::Handle<v8::ArrayBufferView>::Cast(info[2])) : 0);
+ TONATIVE_VOID(ArrayBuffer*, data, info[3]->IsArrayBuffer() ? V8ArrayBuffer::toNative(v8::Handle<v8::ArrayBuffer>::Cast(info[3])) : 0);
+ v8SetReturnValue(info, impl->verifySignature(ScriptState::current(info.GetIsolate()), algorithm, key, signature, data).v8Value());
+}
+
+// Promise verify(Dictionary algorithm, Key key, ArrayBufferView signature, ArrayBufferView data);
+void verify4Method(const v8::FunctionCallbackInfo<v8::Value>& info)
+{
+ SubtleCrypto* impl = V8SubtleCrypto::toNative(info.Holder());
+ TONATIVE_VOID(Dictionary, algorithm, Dictionary(info[0], info.GetIsolate()));
+ if (!algorithm.isUndefinedOrNull() && !algorithm.isObject()) {
+ throwTypeError(ExceptionMessages::failedToExecute("verify", "SubtleCrypto", "parameter 1 ('algorithm') is not an object."), info.GetIsolate());
+ return;
+ }
+ TONATIVE_VOID(Key*, key, V8Key::toNativeWithTypeCheck(info.GetIsolate(), info[1]));
+ TONATIVE_VOID(ArrayBufferView*, signature, info[2]->IsArrayBufferView() ? V8ArrayBufferView::toNative(v8::Handle<v8::ArrayBufferView>::Cast(info[2])) : 0);
+ TONATIVE_VOID(ArrayBufferView*, data, info[3]->IsArrayBufferView() ? V8ArrayBufferView::toNative(v8::Handle<v8::ArrayBufferView>::Cast(info[3])) : 0);
+ v8SetReturnValue(info, impl->verifySignature(ScriptState::current(info.GetIsolate()), algorithm, key, signature, data).v8Value());
+}
+
+void V8SubtleCrypto::verifyMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
+{
+ v8::Isolate* isolate = info.GetIsolate();
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "verify", "SubtleCrypto", info.Holder(), isolate);
+ // typedef (ArrayBuffer or ArrayBufferView) CryptoOperationData;
+ //
+ // Promise verify(Dictionary algorithm, Key key,
+ // CryptoOperationData signature,
+ // CryptoOperationData data);
+ switch (info.Length()) {
+ case 4:
+ // Promise verify(Dictionary algorithm, Key key, ArrayBuffer signature, ArrayBuffer data);
+ if (V8ArrayBuffer::hasInstance(info[2], isolate)
+ && V8ArrayBuffer::hasInstance(info[3], isolate)) {
+ verify1Method(info);
+ return;
+ }
+ // Promise verify(Dictionary algorithm, Key key, ArrayBuffer signature, ArrayBufferView data);
+ if (V8ArrayBuffer::hasInstance(info[2], isolate)
+ && V8ArrayBufferView::hasInstance(info[3], isolate)) {
+ verify2Method(info);
+ return;
+ }
+ // Promise verify(Dictionary algorithm, Key key, ArrayBufferView signature, ArrayBuffer data);
+ if (V8ArrayBufferView::hasInstance(info[2], isolate)
+ && V8ArrayBuffer::hasInstance(info[3], isolate)) {
+ verify3Method(info);
+ return;
+ }
+ // Promise verify(Dictionary algorithm, Key key, ArrayBufferView signature, ArrayBufferView data);
+ if (V8ArrayBufferView::hasInstance(info[2], isolate)
+ && V8ArrayBufferView::hasInstance(info[3], isolate)) {
+ verify4Method(info);
+ return;
+ }
+ break;
+ default:
+ throwArityTypeError(exceptionState, "[4]", info.Length());
+ return;
+ break;
+ }
+ exceptionState.throwTypeError("No function was found that matched the signature provided.");
+ exceptionState.throwIfNeeded();
+}
+
+} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8TextCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8TextCustom.cpp
index 478537c3b9f..4ffbadc0d3d 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8TextCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8TextCustom.cpp
@@ -29,9 +29,9 @@
*/
#include "config.h"
-#include "V8Text.h"
+#include "bindings/core/v8/V8Text.h"
-#include "V8CDATASection.h"
+#include "bindings/core/v8/V8CDATASection.h"
#include "core/dom/Node.h"
#include "core/dom/Text.h"
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8TextTrackCueCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8TextTrackCueCustom.cpp
index 3adef38297e..8d078eb91e9 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8TextTrackCueCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8TextTrackCueCustom.cpp
@@ -28,13 +28,9 @@
*/
#include "config.h"
-#include "V8TextTrackCue.h"
+#include "bindings/core/v8/V8TextTrackCue.h"
-#include "V8VTTCue.h"
-
-#include "bindings/v8/ExceptionMessages.h"
-#include "bindings/v8/ExceptionState.h"
-#include "core/frame/UseCounter.h"
+#include "bindings/core/v8/V8VTTCue.h"
namespace WebCore {
@@ -43,27 +39,4 @@ v8::Handle<v8::Value> toV8(TextTrackCue* impl, v8::Handle<v8::Object> creationCo
return toV8(toVTTCue(impl), creationContext, isolate);
}
-// Custom constructor to make new TextTrackCue(...) return a VTTCue. This is legacy
-// compat, not per spec, and should be removed at the earliest opportunity.
-void V8TextTrackCue::constructorCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
-{
- ExceptionState exceptionState(ExceptionState::ConstructionContext, "TextTrackCue", info.Holder(), info.GetIsolate());
- if (UNLIKELY(info.Length() < 3)) {
- exceptionState.throwTypeError(ExceptionMessages::notEnoughArguments(3, info.Length()));
- exceptionState.throwIfNeeded();
- return;
- }
- V8TRYCATCH_VOID(double, startTime, static_cast<double>(info[0]->NumberValue()));
- V8TRYCATCH_VOID(double, endTime, static_cast<double>(info[1]->NumberValue()));
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<>, text, info[2]);
-
- Document& document = *toDocument(getExecutionContext());
- UseCounter::count(document, UseCounter::TextTrackCueConstructor);
-
- RefPtr<VTTCue> impl = VTTCue::create(document, startTime, endTime, text);
- v8::Handle<v8::Object> wrapper = wrap(impl.get(), info.Holder(), info.GetIsolate());
-
- v8SetReturnValue(info, wrapper);
-}
-
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8TrackEventCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8TrackEventCustom.cpp
index aa76cc2c3fd..9c2b04e3c31 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8TrackEventCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8TrackEventCustom.cpp
@@ -29,9 +29,11 @@
*/
#include "config.h"
-#include "V8TrackEvent.h"
+#include "bindings/core/v8/V8TrackEvent.h"
-#include "V8TextTrack.h"
+#include "bindings/core/v8/V8AudioTrack.h"
+#include "bindings/core/v8/V8TextTrack.h"
+#include "bindings/core/v8/V8VideoTrack.h"
#include "core/html/track/TrackBase.h"
#include "core/html/track/TrackEvent.h"
@@ -53,10 +55,12 @@ void V8TrackEvent::trackAttributeGetterCustom(const v8::PropertyCallbackInfo<v8:
return;
case TrackBase::AudioTrack:
+ v8SetReturnValueFast(info, static_cast<AudioTrack*>(track), trackEvent);
+ return;
+
case TrackBase::VideoTrack:
- // This should not happen until VideoTrack and AudioTrack are implemented.
- ASSERT_NOT_REACHED();
- break;
+ v8SetReturnValueFast(info, static_cast<VideoTrack*>(track), trackEvent);
+ return;
}
v8SetReturnValueNull(info);
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8TypedArrayCustom.h b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8TypedArrayCustom.h
index f64f457f2f5..fac7a110e5e 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8TypedArrayCustom.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8TypedArrayCustom.h
@@ -47,17 +47,13 @@ class TypedArrayTraits
template<typename TypedArray>
class V8TypedArray {
public:
- static bool hasInstance(v8::Handle<v8::Value> value, v8::Isolate*, WrapperWorldType)
- {
- return TypedArrayTraits<TypedArray>::IsInstance(value);
- }
-
- static bool hasInstanceInAnyWorld(v8::Handle<v8::Value> value, v8::Isolate*)
+ static bool hasInstance(v8::Handle<v8::Value> value, v8::Isolate*)
{
return TypedArrayTraits<TypedArray>::IsInstance(value);
}
static TypedArray* toNative(v8::Handle<v8::Object>);
+ static TypedArray* toNativeWithTypeCheck(v8::Isolate*, v8::Handle<v8::Value>);
static void derefObject(void*);
static const WrapperTypeInfo wrapperTypeInfo;
static const int internalFieldCount = v8DefaultWrapperInternalFieldCount;
@@ -95,7 +91,7 @@ public:
template<typename CallbackInfo>
static void v8SetReturnValueForMainWorld(const CallbackInfo& info, TypedArray* impl)
{
- ASSERT(worldType(info.GetIsolate()) == MainWorld);
+ ASSERT(DOMWrapperWorld::current(info.GetIsolate()).isMainWorld());
if (UNLIKELY(!impl)) {
v8SetReturnValueNull(info);
return;
@@ -174,12 +170,17 @@ TypedArray* V8TypedArray<TypedArray>::toNative(v8::Handle<v8::Object> object)
return reinterpret_cast<TypedArray*>(typedarrayPtr);
}
+template <typename TypedArray>
+TypedArray* V8TypedArray<TypedArray>::toNativeWithTypeCheck(v8::Isolate* isolate, v8::Handle<v8::Value> value)
+{
+ return V8TypedArray<TypedArray>::hasInstance(value, isolate) ? V8TypedArray<TypedArray>::toNative(v8::Handle<v8::Object>::Cast(value)) : 0;
+}
template <typename TypedArray>
const WrapperTypeInfo V8TypedArray<TypedArray>::wrapperTypeInfo = {
gin::kEmbedderBlink,
0, V8TypedArray<TypedArray>::derefObject,
- 0, 0, 0, 0, 0, WrapperTypeObjectPrototype
+ 0, 0, 0, 0, 0, WrapperTypeObjectPrototype, RefCountedObject
};
template <typename TypedArray>
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8Uint16ArrayCustom.h b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8Uint16ArrayCustom.h
index e692a9cb979..d819d228ece 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8Uint16ArrayCustom.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8Uint16ArrayCustom.h
@@ -59,10 +59,6 @@ public:
typedef V8TypedArray<Uint16Array> V8Uint16Array;
-template<>
-class WrapperTypeTraits<Uint16Array> : public TypedArrayWrapperTraits<Uint16Array> { };
-
-
inline v8::Handle<v8::Object> wrap(Uint16Array* impl, v8::Handle<v8::Object> creationContext, v8::Isolate* isolate)
{
return V8TypedArray<Uint16Array>::wrap(impl, creationContext, isolate);
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8Uint32ArrayCustom.h b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8Uint32ArrayCustom.h
index 09ee5e990ec..9218135ef73 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8Uint32ArrayCustom.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8Uint32ArrayCustom.h
@@ -59,10 +59,6 @@ public:
typedef V8TypedArray<Uint32Array> V8Uint32Array;
-template<>
-class WrapperTypeTraits<Uint32Array> : public TypedArrayWrapperTraits<Uint32Array> { };
-
-
inline v8::Handle<v8::Object> wrap(Uint32Array* impl, v8::Handle<v8::Object> creationContext, v8::Isolate* isolate)
{
return V8TypedArray<Uint32Array>::wrap(impl, creationContext, isolate);
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8Uint8ArrayCustom.h b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8Uint8ArrayCustom.h
index 5bcf0045731..7a37501dc64 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8Uint8ArrayCustom.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8Uint8ArrayCustom.h
@@ -59,10 +59,6 @@ public:
typedef V8TypedArray<Uint8Array> V8Uint8Array;
-template<>
-class WrapperTypeTraits<Uint8Array> : public TypedArrayWrapperTraits<Uint8Array> { };
-
-
inline v8::Handle<v8::Object> wrap(Uint8Array* impl, v8::Handle<v8::Object> creationContext, v8::Isolate* isolate)
{
return V8TypedArray<Uint8Array>::wrap(impl, creationContext, isolate);
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8Uint8ClampedArrayCustom.h b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8Uint8ClampedArrayCustom.h
index 53d938ad4d4..7f936669b8d 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8Uint8ClampedArrayCustom.h
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8Uint8ClampedArrayCustom.h
@@ -59,10 +59,6 @@ public:
typedef V8TypedArray<Uint8ClampedArray> V8Uint8ClampedArray;
-template<>
-class WrapperTypeTraits<Uint8ClampedArray> : public TypedArrayWrapperTraits<Uint8ClampedArray> { };
-
-
inline v8::Handle<v8::Object> wrap(Uint8ClampedArray* impl, v8::Handle<v8::Object> creationContext, v8::Isolate* isolate)
{
return V8TypedArray<Uint8ClampedArray>::wrap(impl, creationContext, isolate);
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8WebGLRenderingContextCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8WebGLRenderingContextCustom.cpp
index 8eb86e9ba86..faa45a3ce42 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8WebGLRenderingContextCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8WebGLRenderingContextCustom.cpp
@@ -29,41 +29,44 @@
*/
#include "config.h"
-#include "V8WebGLRenderingContext.h"
-
-#include "V8ANGLEInstancedArrays.h"
-#include "V8EXTFragDepth.h"
-#include "V8EXTTextureFilterAnisotropic.h"
-#include "V8HTMLCanvasElement.h"
-#include "V8HTMLImageElement.h"
-#include "V8HTMLVideoElement.h"
-#include "V8ImageData.h"
-#include "V8OESElementIndexUint.h"
-#include "V8OESStandardDerivatives.h"
-#include "V8OESTextureFloat.h"
-#include "V8OESTextureFloatLinear.h"
-#include "V8OESTextureHalfFloat.h"
-#include "V8OESTextureHalfFloatLinear.h"
-#include "V8OESVertexArrayObject.h"
-#include "V8WebGLBuffer.h"
-#include "V8WebGLCompressedTextureATC.h"
-#include "V8WebGLCompressedTexturePVRTC.h"
-#include "V8WebGLCompressedTextureS3TC.h"
-#include "V8WebGLDebugRendererInfo.h"
-#include "V8WebGLDebugShaders.h"
-#include "V8WebGLDepthTexture.h"
-#include "V8WebGLDrawBuffers.h"
-#include "V8WebGLFramebuffer.h"
-#include "V8WebGLLoseContext.h"
-#include "V8WebGLProgram.h"
-#include "V8WebGLRenderbuffer.h"
-#include "V8WebGLShader.h"
-#include "V8WebGLTexture.h"
-#include "V8WebGLUniformLocation.h"
-#include "V8WebGLVertexArrayObjectOES.h"
+#include "bindings/core/v8/V8WebGLRenderingContext.h"
+
+#include "bindings/core/v8/V8ANGLEInstancedArrays.h"
+#include "bindings/core/v8/V8EXTBlendMinMax.h"
+#include "bindings/core/v8/V8EXTFragDepth.h"
+#include "bindings/core/v8/V8EXTShaderTextureLOD.h"
+#include "bindings/core/v8/V8EXTTextureFilterAnisotropic.h"
+#include "bindings/core/v8/V8HTMLCanvasElement.h"
+#include "bindings/core/v8/V8HTMLImageElement.h"
+#include "bindings/core/v8/V8HTMLVideoElement.h"
+#include "bindings/core/v8/V8ImageData.h"
+#include "bindings/core/v8/V8OESElementIndexUint.h"
+#include "bindings/core/v8/V8OESStandardDerivatives.h"
+#include "bindings/core/v8/V8OESTextureFloat.h"
+#include "bindings/core/v8/V8OESTextureFloatLinear.h"
+#include "bindings/core/v8/V8OESTextureHalfFloat.h"
+#include "bindings/core/v8/V8OESTextureHalfFloatLinear.h"
+#include "bindings/core/v8/V8OESVertexArrayObject.h"
+#include "bindings/core/v8/V8WebGLBuffer.h"
+#include "bindings/core/v8/V8WebGLCompressedTextureATC.h"
+#include "bindings/core/v8/V8WebGLCompressedTextureETC1.h"
+#include "bindings/core/v8/V8WebGLCompressedTexturePVRTC.h"
+#include "bindings/core/v8/V8WebGLCompressedTextureS3TC.h"
+#include "bindings/core/v8/V8WebGLDebugRendererInfo.h"
+#include "bindings/core/v8/V8WebGLDebugShaders.h"
+#include "bindings/core/v8/V8WebGLDepthTexture.h"
+#include "bindings/core/v8/V8WebGLDrawBuffers.h"
+#include "bindings/core/v8/V8WebGLFramebuffer.h"
+#include "bindings/core/v8/V8WebGLLoseContext.h"
+#include "bindings/core/v8/V8WebGLProgram.h"
+#include "bindings/core/v8/V8WebGLRenderbuffer.h"
+#include "bindings/core/v8/V8WebGLShader.h"
+#include "bindings/core/v8/V8WebGLTexture.h"
+#include "bindings/core/v8/V8WebGLUniformLocation.h"
+#include "bindings/core/v8/V8WebGLVertexArrayObjectOES.h"
#include "bindings/v8/ExceptionMessages.h"
#include "bindings/v8/V8Binding.h"
-#include "bindings/v8/V8HiddenPropertyName.h"
+#include "bindings/v8/V8HiddenValue.h"
#include "bindings/v8/custom/V8ArrayBufferViewCustom.h"
#include "bindings/v8/custom/V8Float32ArrayCustom.h"
#include "bindings/v8/custom/V8Int16ArrayCustom.h"
@@ -81,39 +84,43 @@
namespace WebCore {
// Allocates new storage via fastMalloc.
-// Returns NULL if array failed to convert for any reason.
-static float* jsArrayToFloatArray(v8::Handle<v8::Array> array, uint32_t len)
+// Returns 0 if array failed to convert for any reason.
+static float* jsArrayToFloatArray(v8::Handle<v8::Array> array, uint32_t len, ExceptionState& exceptionState)
{
// Convert the data element-by-element.
- if (len > std::numeric_limits<uint32_t>::max() / sizeof(float))
+ if (len > std::numeric_limits<uint32_t>::max() / sizeof(float)) {
+ exceptionState.throwTypeError("Array length exceeds supported limit.");
return 0;
+ }
float* data = static_cast<float*>(fastMalloc(len * sizeof(float)));
for (uint32_t i = 0; i < len; i++) {
v8::Local<v8::Value> val = array->Get(i);
- if (!val->IsNumber()) {
+ float value = toFloat(val, exceptionState);
+ if (exceptionState.hadException()) {
fastFree(data);
return 0;
}
- data[i] = toFloat(val);
+ data[i] = value;
}
return data;
}
// Allocates new storage via fastMalloc.
-// Returns NULL if array failed to convert for any reason.
-static int* jsArrayToIntArray(v8::Handle<v8::Array> array, uint32_t len)
+// Returns 0 if array failed to convert for any reason.
+static int* jsArrayToIntArray(v8::Handle<v8::Array> array, uint32_t len, ExceptionState& exceptionState)
{
// Convert the data element-by-element.
- if (len > std::numeric_limits<uint32_t>::max() / sizeof(int))
+ if (len > std::numeric_limits<uint32_t>::max() / sizeof(int)) {
+ exceptionState.throwTypeError("Array length exceeds supported limit.");
return 0;
+ }
int* data = static_cast<int*>(fastMalloc(len * sizeof(int)));
for (uint32_t i = 0; i < len; i++) {
v8::Local<v8::Value> val = array->Get(i);
- bool ok;
- int ival = toInt32(val, ok);
- if (!ok) {
+ int ival = toInt32(val, exceptionState);
+ if (exceptionState.hadException()) {
fastFree(data);
return 0;
}
@@ -131,19 +138,19 @@ static v8::Handle<v8::Value> toV8Object(const WebGLGetInfo& args, v8::Handle<v8:
const Vector<bool>& value = args.getBoolArray();
v8::Local<v8::Array> array = v8::Array::New(isolate, value.size());
for (size_t ii = 0; ii < value.size(); ++ii)
- array->Set(v8::Integer::New(ii, isolate), v8Boolean(value[ii], isolate));
+ array->Set(v8::Integer::New(isolate, ii), v8Boolean(value[ii], isolate));
return array;
}
case WebGLGetInfo::kTypeFloat:
return v8::Number::New(isolate, args.getFloat());
case WebGLGetInfo::kTypeInt:
- return v8::Integer::New(args.getInt(), isolate);
+ return v8::Integer::New(isolate, args.getInt());
case WebGLGetInfo::kTypeNull:
return v8::Null(isolate);
case WebGLGetInfo::kTypeString:
return v8String(isolate, args.getString());
case WebGLGetInfo::kTypeUnsignedInt:
- return v8::Integer::NewFromUnsigned(args.getUnsignedInt(), isolate);
+ return v8::Integer::NewFromUnsigned(isolate, args.getUnsignedInt());
case WebGLGetInfo::kTypeWebGLBuffer:
return toV8(args.getWebGLBuffer(), creationContext, isolate);
case WebGLGetInfo::kTypeWebGLFloatArray:
@@ -179,81 +186,96 @@ static v8::Handle<v8::Value> toV8Object(WebGLExtension* extension, v8::Handle<v8
v8::Handle<v8::Value> extensionObject;
const char* referenceName = 0;
switch (extension->name()) {
- case WebGLExtension::ANGLEInstancedArraysName:
+ case ANGLEInstancedArraysName:
extensionObject = toV8(static_cast<ANGLEInstancedArrays*>(extension), contextObject, isolate);
referenceName = "angleInstancedArraysName";
break;
- case WebGLExtension::EXTFragDepthName:
+ case EXTBlendMinMaxName:
+ extensionObject = toV8(static_cast<EXTBlendMinMax*>(extension), contextObject, isolate);
+ referenceName = "extBlendMinMaxName";
+ break;
+ case EXTFragDepthName:
extensionObject = toV8(static_cast<EXTFragDepth*>(extension), contextObject, isolate);
referenceName = "extFragDepthName";
break;
- case WebGLExtension::EXTTextureFilterAnisotropicName:
+ case EXTShaderTextureLODName:
+ extensionObject = toV8(static_cast<EXTShaderTextureLOD*>(extension), contextObject, isolate);
+ referenceName = "extShaderTextureLODName";
+ break;
+ case EXTTextureFilterAnisotropicName:
extensionObject = toV8(static_cast<EXTTextureFilterAnisotropic*>(extension), contextObject, isolate);
referenceName = "extTextureFilterAnisotropicName";
break;
- case WebGLExtension::OESElementIndexUintName:
+ case OESElementIndexUintName:
extensionObject = toV8(static_cast<OESElementIndexUint*>(extension), contextObject, isolate);
referenceName = "oesElementIndexUintName";
break;
- case WebGLExtension::OESStandardDerivativesName:
+ case OESStandardDerivativesName:
extensionObject = toV8(static_cast<OESStandardDerivatives*>(extension), contextObject, isolate);
referenceName = "oesStandardDerivativesName";
break;
- case WebGLExtension::OESTextureFloatName:
+ case OESTextureFloatName:
extensionObject = toV8(static_cast<OESTextureFloat*>(extension), contextObject, isolate);
referenceName = "oesTextureFloatName";
break;
- case WebGLExtension::OESTextureFloatLinearName:
+ case OESTextureFloatLinearName:
extensionObject = toV8(static_cast<OESTextureFloatLinear*>(extension), contextObject, isolate);
referenceName = "oesTextureFloatLinearName";
break;
- case WebGLExtension::OESTextureHalfFloatName:
+ case OESTextureHalfFloatName:
extensionObject = toV8(static_cast<OESTextureHalfFloat*>(extension), contextObject, isolate);
referenceName = "oesTextureHalfFloatName";
break;
- case WebGLExtension::OESTextureHalfFloatLinearName:
+ case OESTextureHalfFloatLinearName:
extensionObject = toV8(static_cast<OESTextureHalfFloatLinear*>(extension), contextObject, isolate);
referenceName = "oesTextureHalfFloatLinearName";
break;
- case WebGLExtension::OESVertexArrayObjectName:
+ case OESVertexArrayObjectName:
extensionObject = toV8(static_cast<OESVertexArrayObject*>(extension), contextObject, isolate);
referenceName = "oesVertexArrayObjectName";
break;
- case WebGLExtension::WebGLCompressedTextureATCName:
+ case WebGLCompressedTextureATCName:
extensionObject = toV8(static_cast<WebGLCompressedTextureATC*>(extension), contextObject, isolate);
referenceName = "webGLCompressedTextureATCName";
break;
- case WebGLExtension::WebGLCompressedTexturePVRTCName:
+ case WebGLCompressedTextureETC1Name:
+ extensionObject = toV8(static_cast<WebGLCompressedTextureETC1*>(extension), contextObject, isolate);
+ referenceName = "webGLCompressedTextureETC1Name";
+ break;
+ case WebGLCompressedTexturePVRTCName:
extensionObject = toV8(static_cast<WebGLCompressedTexturePVRTC*>(extension), contextObject, isolate);
referenceName = "webGLCompressedTexturePVRTCName";
break;
- case WebGLExtension::WebGLCompressedTextureS3TCName:
+ case WebGLCompressedTextureS3TCName:
extensionObject = toV8(static_cast<WebGLCompressedTextureS3TC*>(extension), contextObject, isolate);
referenceName = "webGLCompressedTextureS3TCName";
break;
- case WebGLExtension::WebGLDebugRendererInfoName:
+ case WebGLDebugRendererInfoName:
extensionObject = toV8(static_cast<WebGLDebugRendererInfo*>(extension), contextObject, isolate);
referenceName = "webGLDebugRendererInfoName";
break;
- case WebGLExtension::WebGLDebugShadersName:
+ case WebGLDebugShadersName:
extensionObject = toV8(static_cast<WebGLDebugShaders*>(extension), contextObject, isolate);
referenceName = "webGLDebugShadersName";
break;
- case WebGLExtension::WebGLDepthTextureName:
+ case WebGLDepthTextureName:
extensionObject = toV8(static_cast<WebGLDepthTexture*>(extension), contextObject, isolate);
referenceName = "webGLDepthTextureName";
break;
- case WebGLExtension::WebGLDrawBuffersName:
+ case WebGLDrawBuffersName:
extensionObject = toV8(static_cast<WebGLDrawBuffers*>(extension), contextObject, isolate);
referenceName = "webGLDrawBuffersName";
break;
- case WebGLExtension::WebGLLoseContextName:
+ case WebGLLoseContextName:
extensionObject = toV8(static_cast<WebGLLoseContext*>(extension), contextObject, isolate);
referenceName = "webGLLoseContextName";
break;
+ case WebGLExtensionNameCount:
+ notImplemented();
+ return v8::Undefined(isolate);
}
ASSERT(!extensionObject.IsEmpty());
- V8HiddenPropertyName::setNamedHiddenReference(contextObject, referenceName, extensionObject);
+ V8HiddenValue::setHiddenValue(isolate, contextObject, v8AtomicString(isolate, referenceName), extensionObject);
return extensionObject;
}
@@ -261,16 +283,21 @@ enum ObjectType {
kBuffer, kRenderbuffer, kTexture, kVertexAttrib
};
-static void getObjectParameter(const v8::FunctionCallbackInfo<v8::Value>& info, ObjectType objectType, const char* method)
+static void getObjectParameter(const v8::FunctionCallbackInfo<v8::Value>& info, ObjectType objectType, ExceptionState& exceptionState)
{
if (info.Length() != 2) {
- throwTypeError(ExceptionMessages::failedToExecute(method, "WebGLRenderingContext", ExceptionMessages::notEnoughArguments(2, info.Length())), info.GetIsolate());
+ exceptionState.throwTypeError(ExceptionMessages::notEnoughArguments(2, info.Length()));
+ exceptionState.throwIfNeeded();
return;
}
WebGLRenderingContext* context = V8WebGLRenderingContext::toNative(info.Holder());
- unsigned target = toInt32(info[0]);
- unsigned pname = toInt32(info[1]);
+ unsigned target = toInt32(info[0], exceptionState);
+ if (exceptionState.throwIfNeeded())
+ return;
+ unsigned pname = toInt32(info[1], exceptionState);
+ if (exceptionState.throwIfNeeded())
+ return;
WebGLGetInfo args;
switch (objectType) {
case kBuffer:
@@ -293,15 +320,9 @@ static void getObjectParameter(const v8::FunctionCallbackInfo<v8::Value>& info,
v8SetReturnValue(info, toV8Object(args, info.Holder(), info.GetIsolate()));
}
-static WebGLUniformLocation* toWebGLUniformLocation(v8::Handle<v8::Value> value, bool& ok, v8::Isolate* isolate)
+static WebGLUniformLocation* toWebGLUniformLocation(v8::Handle<v8::Value> value, v8::Isolate* isolate)
{
- ok = false;
- WebGLUniformLocation* location = 0;
- if (V8WebGLUniformLocation::hasInstance(value, isolate, worldType(isolate))) {
- location = V8WebGLUniformLocation::toNative(value->ToObject());
- ok = true;
- }
- return location;
+ return V8WebGLUniformLocation::toNativeWithTypeCheck(isolate, value);
}
enum WhichProgramCall {
@@ -310,17 +331,21 @@ enum WhichProgramCall {
void V8WebGLRenderingContext::getAttachedShadersMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "getAttachedShaders", "WebGLRenderingContext", info.Holder(), info.GetIsolate());
if (info.Length() < 1) {
- throwTypeError(ExceptionMessages::failedToExecute("getAttachedShaders", "WebGLRenderingContext", ExceptionMessages::notEnoughArguments(1, info.Length())), info.GetIsolate());
+ exceptionState.throwTypeError(ExceptionMessages::notEnoughArguments(1, info.Length()));
+ exceptionState.throwIfNeeded();
return;
}
+ const int programArgumentIndex = 0;
WebGLRenderingContext* context = V8WebGLRenderingContext::toNative(info.Holder());
- if (info.Length() > 0 && !isUndefinedOrNull(info[0]) && !V8WebGLProgram::hasInstance(info[0], info.GetIsolate(), worldType(info.GetIsolate()))) {
- throwUninformativeAndGenericTypeError(info.GetIsolate());
+ if (info.Length() > 0 && !isUndefinedOrNull(info[programArgumentIndex]) && !V8WebGLProgram::hasInstance(info[programArgumentIndex], info.GetIsolate())) {
+ exceptionState.throwTypeError(ExceptionMessages::argumentNullOrIncorrectType(programArgumentIndex + 1, "WebGLProgram"));
+ exceptionState.throwIfNeeded();
return;
}
- WebGLProgram* program = V8WebGLProgram::hasInstance(info[0], info.GetIsolate(), worldType(info.GetIsolate())) ? V8WebGLProgram::toNative(v8::Handle<v8::Object>::Cast(info[0])) : 0;
+ WebGLProgram* program = V8WebGLProgram::toNativeWithTypeCheck(info.GetIsolate(), info[programArgumentIndex]);
Vector<RefPtr<WebGLShader> > shaders;
bool succeed = context->getAttachedShaders(program, shaders);
if (!succeed) {
@@ -329,136 +354,169 @@ void V8WebGLRenderingContext::getAttachedShadersMethodCustom(const v8::FunctionC
}
v8::Local<v8::Array> array = v8::Array::New(info.GetIsolate(), shaders.size());
for (size_t ii = 0; ii < shaders.size(); ++ii)
- array->Set(v8::Integer::New(ii, info.GetIsolate()), toV8(shaders[ii].get(), info.Holder(), info.GetIsolate()));
+ array->Set(v8::Integer::New(info.GetIsolate(), ii), toV8(shaders[ii].get(), info.Holder(), info.GetIsolate()));
v8SetReturnValue(info, array);
}
void V8WebGLRenderingContext::getBufferParameterMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
- getObjectParameter(info, kBuffer, "getBufferParameter");
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "getBufferParameter", "WebGLRenderingContext", info.Holder(), info.GetIsolate());
+ getObjectParameter(info, kBuffer, exceptionState);
}
void V8WebGLRenderingContext::getExtensionMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
- WebGLRenderingContext* imp = V8WebGLRenderingContext::toNative(info.Holder());
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "getExtension", "WebGLRenderingContext", info.Holder(), info.GetIsolate());
+ WebGLRenderingContext* impl = V8WebGLRenderingContext::toNative(info.Holder());
if (info.Length() < 1) {
- throwTypeError(ExceptionMessages::failedToExecute("getExtension", "WebGLRenderingContext", ExceptionMessages::notEnoughArguments(1, info.Length())), info.GetIsolate());
+ exceptionState.throwTypeError(ExceptionMessages::notEnoughArguments(1, info.Length()));
+ exceptionState.throwIfNeeded();
return;
}
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<>, name, info[0]);
- RefPtr<WebGLExtension> extension(imp->getExtension(name));
+ TOSTRING_VOID(V8StringResource<>, name, info[0]);
+ RefPtr<WebGLExtension> extension(impl->getExtension(name));
v8SetReturnValue(info, toV8Object(extension.get(), info.Holder(), info.GetIsolate()));
}
void V8WebGLRenderingContext::getFramebufferAttachmentParameterMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "getFramebufferAttachmentParameter", "WebGLRenderingContext", info.Holder(), info.GetIsolate());
if (info.Length() != 3) {
- throwTypeError(ExceptionMessages::failedToExecute("getFramebufferAttachmentParameter", "WebGLRenderingContext", ExceptionMessages::notEnoughArguments(3, info.Length())), info.GetIsolate());
+ exceptionState.throwTypeError(ExceptionMessages::notEnoughArguments(3, info.Length()));
+ exceptionState.throwIfNeeded();
return;
}
WebGLRenderingContext* context = V8WebGLRenderingContext::toNative(info.Holder());
unsigned target = toInt32(info[0]);
- unsigned attachment = toInt32(info[1]);
- unsigned pname = toInt32(info[2]);
+ unsigned attachment = toInt32(info[1], exceptionState);
+ if (exceptionState.throwIfNeeded())
+ return;
+ unsigned pname = toInt32(info[2], exceptionState);
+ if (exceptionState.throwIfNeeded())
+ return;
WebGLGetInfo args = context->getFramebufferAttachmentParameter(target, attachment, pname);
v8SetReturnValue(info, toV8Object(args, info.Holder(), info.GetIsolate()));
}
void V8WebGLRenderingContext::getParameterMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "getParameter", "WebGLRenderingContext", info.Holder(), info.GetIsolate());
if (info.Length() != 1) {
- throwTypeError(ExceptionMessages::failedToExecute("getParameter", "WebGLRenderingContext", ExceptionMessages::notEnoughArguments(1, info.Length())), info.GetIsolate());
+ exceptionState.throwTypeError(ExceptionMessages::notEnoughArguments(1, info.Length()));
+ exceptionState.throwIfNeeded();
return;
}
WebGLRenderingContext* context = V8WebGLRenderingContext::toNative(info.Holder());
- unsigned pname = toInt32(info[0]);
+ unsigned pname = toInt32(info[0], exceptionState);
+ if (exceptionState.throwIfNeeded())
+ return;
WebGLGetInfo args = context->getParameter(pname);
v8SetReturnValue(info, toV8Object(args, info.Holder(), info.GetIsolate()));
}
void V8WebGLRenderingContext::getProgramParameterMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "getProgramParameter", "WebGLRenderingContext", info.Holder(), info.GetIsolate());
if (info.Length() != 2) {
- throwTypeError(ExceptionMessages::failedToExecute("getProgramParameter", "WebGLRenderingContext", ExceptionMessages::notEnoughArguments(2, info.Length())), info.GetIsolate());
+ exceptionState.throwTypeError(ExceptionMessages::notEnoughArguments(2, info.Length()));
+ exceptionState.throwIfNeeded();
return;
}
+ const int programArgumentIndex = 0;
WebGLRenderingContext* context = V8WebGLRenderingContext::toNative(info.Holder());
- if (info.Length() > 0 && !isUndefinedOrNull(info[0]) && !V8WebGLProgram::hasInstance(info[0], info.GetIsolate(), worldType(info.GetIsolate()))) {
- throwUninformativeAndGenericTypeError(info.GetIsolate());
+ if (info.Length() > 0 && !isUndefinedOrNull(info[programArgumentIndex]) && !V8WebGLProgram::hasInstance(info[programArgumentIndex], info.GetIsolate())) {
+ exceptionState.throwTypeError(ExceptionMessages::argumentNullOrIncorrectType(programArgumentIndex + 1, "WebGLProgram"));
+ exceptionState.throwIfNeeded();
return;
}
- WebGLProgram* program = V8WebGLProgram::hasInstance(info[0], info.GetIsolate(), worldType(info.GetIsolate())) ? V8WebGLProgram::toNative(v8::Handle<v8::Object>::Cast(info[0])) : 0;
- unsigned pname = toInt32(info[1]);
+ WebGLProgram* program = V8WebGLProgram::toNativeWithTypeCheck(info.GetIsolate(), info[programArgumentIndex]);
+ unsigned pname = toInt32(info[1], exceptionState);
+ if (exceptionState.throwIfNeeded())
+ return;
WebGLGetInfo args = context->getProgramParameter(program, pname);
v8SetReturnValue(info, toV8Object(args, info.Holder(), info.GetIsolate()));
}
void V8WebGLRenderingContext::getRenderbufferParameterMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
- getObjectParameter(info, kRenderbuffer, "getRenderbufferParameter");
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "getRenderbufferParameter", "WebGLRenderingContext", info.Holder(), info.GetIsolate());
+ getObjectParameter(info, kRenderbuffer, exceptionState);
}
void V8WebGLRenderingContext::getShaderParameterMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "getShaderParameter", "WebGLRenderingContext", info.Holder(), info.GetIsolate());
if (info.Length() != 2) {
- throwTypeError(ExceptionMessages::failedToExecute("getShaderParameter", "WebGLRenderingContext", ExceptionMessages::notEnoughArguments(2, info.Length())), info.GetIsolate());
+ exceptionState.throwTypeError(ExceptionMessages::notEnoughArguments(2, info.Length()));
+ exceptionState.throwIfNeeded();
return;
}
+ const int shaderArgumentIndex = 0;
WebGLRenderingContext* context = V8WebGLRenderingContext::toNative(info.Holder());
- if (info.Length() > 0 && !isUndefinedOrNull(info[0]) && !V8WebGLShader::hasInstance(info[0], info.GetIsolate(), worldType(info.GetIsolate()))) {
- throwUninformativeAndGenericTypeError(info.GetIsolate());
+ if (info.Length() > 0 && !isUndefinedOrNull(info[shaderArgumentIndex]) && !V8WebGLShader::hasInstance(info[shaderArgumentIndex], info.GetIsolate())) {
+ exceptionState.throwTypeError(ExceptionMessages::argumentNullOrIncorrectType(shaderArgumentIndex + 1, "WebGLShader"));
+ exceptionState.throwIfNeeded();
return;
}
- WebGLShader* shader = V8WebGLShader::hasInstance(info[0], info.GetIsolate(), worldType(info.GetIsolate())) ? V8WebGLShader::toNative(v8::Handle<v8::Object>::Cast(info[0])) : 0;
- unsigned pname = toInt32(info[1]);
+ WebGLShader* shader = V8WebGLShader::toNativeWithTypeCheck(info.GetIsolate(), info[shaderArgumentIndex]);
+ unsigned pname = toInt32(info[1], exceptionState);
+ if (exceptionState.throwIfNeeded())
+ return;
WebGLGetInfo args = context->getShaderParameter(shader, pname);
v8SetReturnValue(info, toV8Object(args, info.Holder(), info.GetIsolate()));
}
void V8WebGLRenderingContext::getSupportedExtensionsMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
- WebGLRenderingContext* imp = V8WebGLRenderingContext::toNative(info.Holder());
- if (imp->isContextLost()) {
+ WebGLRenderingContext* impl = V8WebGLRenderingContext::toNative(info.Holder());
+ if (impl->isContextLost()) {
v8SetReturnValueNull(info);
return;
}
- Vector<String> value = imp->getSupportedExtensions();
+ Vector<String> value = impl->getSupportedExtensions();
v8::Local<v8::Array> array = v8::Array::New(info.GetIsolate(), value.size());
for (size_t ii = 0; ii < value.size(); ++ii)
- array->Set(v8::Integer::New(ii, info.GetIsolate()), v8String(info.GetIsolate(), value[ii]));
+ array->Set(v8::Integer::New(info.GetIsolate(), ii), v8String(info.GetIsolate(), value[ii]));
v8SetReturnValue(info, array);
}
void V8WebGLRenderingContext::getTexParameterMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
- getObjectParameter(info, kTexture, "getTexParameter");
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "getTexParameter", "WebGLRenderingContext", info.Holder(), info.GetIsolate());
+ getObjectParameter(info, kTexture, exceptionState);
}
void V8WebGLRenderingContext::getUniformMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "getUniform", "WebGLRenderingContext", info.Holder(), info.GetIsolate());
if (info.Length() != 2) {
- throwTypeError(ExceptionMessages::failedToExecute("getUniform", "WebGLRenderingContext", ExceptionMessages::notEnoughArguments(2, info.Length())), info.GetIsolate());
+ exceptionState.throwTypeError(ExceptionMessages::notEnoughArguments(2, info.Length()));
+ exceptionState.throwIfNeeded();
return;
}
+ const int programArgumentIndex = 0;
WebGLRenderingContext* context = V8WebGLRenderingContext::toNative(info.Holder());
- if (info.Length() > 0 && !isUndefinedOrNull(info[0]) && !V8WebGLProgram::hasInstance(info[0], info.GetIsolate(), worldType(info.GetIsolate()))) {
- throwUninformativeAndGenericTypeError(info.GetIsolate());
+ if (info.Length() > 0 && !isUndefinedOrNull(info[programArgumentIndex]) && !V8WebGLProgram::hasInstance(info[programArgumentIndex], info.GetIsolate())) {
+ exceptionState.throwTypeError(ExceptionMessages::argumentNullOrIncorrectType(programArgumentIndex + 1, "WebGLProgram"));
+ exceptionState.throwIfNeeded();
return;
}
- WebGLProgram* program = V8WebGLProgram::hasInstance(info[0], info.GetIsolate(), worldType(info.GetIsolate())) ? V8WebGLProgram::toNative(v8::Handle<v8::Object>::Cast(info[0])) : 0;
+ WebGLProgram* program = V8WebGLProgram::toNativeWithTypeCheck(info.GetIsolate(), info[programArgumentIndex]);
- if (info.Length() > 1 && !isUndefinedOrNull(info[1]) && !V8WebGLUniformLocation::hasInstance(info[1], info.GetIsolate(), worldType(info.GetIsolate()))) {
- throwUninformativeAndGenericTypeError(info.GetIsolate());
+ const int uniformArgumentIndex = 1;
+ if (info.Length() > 1 && !isUndefinedOrNull(info[uniformArgumentIndex]) && !V8WebGLUniformLocation::hasInstance(info[uniformArgumentIndex], info.GetIsolate())) {
+ exceptionState.throwTypeError(ExceptionMessages::argumentNullOrIncorrectType(uniformArgumentIndex + 1, "WebGLUniformLocation"));
+ exceptionState.throwIfNeeded();
return;
}
- bool ok = false;
- WebGLUniformLocation* location = toWebGLUniformLocation(info[1], ok, info.GetIsolate());
+ const int uniformLocationArgumentIndex = 1;
+ WebGLUniformLocation* location = toWebGLUniformLocation(info[uniformLocationArgumentIndex], info.GetIsolate());
WebGLGetInfo args = context->getUniform(program, location);
v8SetReturnValue(info, toV8Object(args, info.Holder(), info.GetIsolate()));
@@ -466,7 +524,8 @@ void V8WebGLRenderingContext::getUniformMethodCustom(const v8::FunctionCallbackI
void V8WebGLRenderingContext::getVertexAttribMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
- getObjectParameter(info, kVertexAttrib, "getVertexAttrib");
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "getVertexAttrib", "WebGLRenderingContext", info.Holder(), info.GetIsolate());
+ getObjectParameter(info, kVertexAttrib, exceptionState);
}
enum FunctionToCall {
@@ -488,7 +547,7 @@ bool isFunctionToCallForAttribute(FunctionToCall functionToCall)
return false;
}
-static void vertexAttribAndUniformHelperf(const v8::FunctionCallbackInfo<v8::Value>& info, FunctionToCall functionToCall, const char* method)
+static void vertexAttribAndUniformHelperf(const v8::FunctionCallbackInfo<v8::Value>& info, FunctionToCall functionToCall, ExceptionState& exceptionState)
{
// Forms:
// * glUniform1fv(WebGLUniformLocation location, Array data);
@@ -509,29 +568,34 @@ static void vertexAttribAndUniformHelperf(const v8::FunctionCallbackInfo<v8::Val
// * glVertexAttrib4fv(GLint index, Float32Array data);
if (info.Length() != 2) {
- throwTypeError(ExceptionMessages::failedToExecute(method, "WebGLRenderingContext", ExceptionMessages::notEnoughArguments(2, info.Length())), info.GetIsolate());
+ exceptionState.throwTypeError(ExceptionMessages::notEnoughArguments(2, info.Length()));
+ exceptionState.throwIfNeeded();
return;
}
- bool ok = false;
int index = -1;
WebGLUniformLocation* location = 0;
- if (isFunctionToCallForAttribute(functionToCall))
- index = toInt32(info[0]);
- else {
- if (info.Length() > 0 && !isUndefinedOrNull(info[0]) && !V8WebGLUniformLocation::hasInstance(info[0], info.GetIsolate(), worldType(info.GetIsolate()))) {
- throwUninformativeAndGenericTypeError(info.GetIsolate());
+ if (isFunctionToCallForAttribute(functionToCall)) {
+ index = toInt32(info[0], exceptionState);
+ if (exceptionState.throwIfNeeded())
+ return;
+ } else {
+ const int uniformLocationArgumentIndex = 0;
+ if (info.Length() > 0 && !isUndefinedOrNull(info[uniformLocationArgumentIndex]) && !V8WebGLUniformLocation::hasInstance(info[uniformLocationArgumentIndex], info.GetIsolate())) {
+ exceptionState.throwTypeError(ExceptionMessages::argumentNullOrIncorrectType(uniformLocationArgumentIndex + 1, "WebGLUniformLocation"));
+ exceptionState.throwIfNeeded();
return;
}
- location = toWebGLUniformLocation(info[0], ok, info.GetIsolate());
+ location = toWebGLUniformLocation(info[uniformLocationArgumentIndex], info.GetIsolate());
}
WebGLRenderingContext* context = V8WebGLRenderingContext::toNative(info.Holder());
- if (V8Float32Array::hasInstance(info[1], info.GetIsolate(), worldType(info.GetIsolate()))) {
- Float32Array* array = V8Float32Array::toNative(info[1]->ToObject());
- ASSERT(array != NULL);
+ const int indexArrayArgument = 1;
+ if (V8Float32Array::hasInstance(info[indexArrayArgument], info.GetIsolate())) {
+ Float32Array* array = V8Float32Array::toNative(info[indexArrayArgument]->ToObject());
+ ASSERT(array);
switch (functionToCall) {
case kUniform1v: context->uniform1fv(location, array); break;
case kUniform2v: context->uniform2fv(location, array); break;
@@ -546,16 +610,20 @@ static void vertexAttribAndUniformHelperf(const v8::FunctionCallbackInfo<v8::Val
return;
}
- if (info[1].IsEmpty() || !info[1]->IsArray()) {
- throwUninformativeAndGenericTypeError(info.GetIsolate());
+ if (info[indexArrayArgument].IsEmpty() || !info[indexArrayArgument]->IsArray()) {
+ exceptionState.throwTypeError(ExceptionMessages::argumentNullOrIncorrectType(indexArrayArgument + 1, "Array"));
+ exceptionState.throwIfNeeded();
return;
}
v8::Handle<v8::Array> array = v8::Local<v8::Array>::Cast(info[1]);
uint32_t len = array->Length();
- float* data = jsArrayToFloatArray(array, len);
+ float* data = jsArrayToFloatArray(array, len, exceptionState);
+ if (exceptionState.throwIfNeeded())
+ return;
if (!data) {
// FIXME: consider different / better exception type.
- setDOMException(SyntaxError, info.GetIsolate());
+ exceptionState.throwDOMException(SyntaxError, "Failed to convert array argument");
+ exceptionState.throwIfNeeded();
return;
}
switch (functionToCall) {
@@ -572,7 +640,7 @@ static void vertexAttribAndUniformHelperf(const v8::FunctionCallbackInfo<v8::Val
fastFree(data);
}
-static void uniformHelperi(const v8::FunctionCallbackInfo<v8::Value>& info, FunctionToCall functionToCall, const char* method)
+static void uniformHelperi(const v8::FunctionCallbackInfo<v8::Value>& info, FunctionToCall functionToCall, ExceptionState& exceptionState)
{
// Forms:
// * glUniform1iv(GLUniformLocation location, Array data);
@@ -585,21 +653,24 @@ static void uniformHelperi(const v8::FunctionCallbackInfo<v8::Value>& info, Func
// * glUniform4iv(GLUniformLocation location, Int32Array data);
if (info.Length() != 2) {
- throwTypeError(ExceptionMessages::failedToExecute(method, "WebGLRenderingContext", ExceptionMessages::notEnoughArguments(2, info.Length())), info.GetIsolate());
+ exceptionState.throwTypeError(ExceptionMessages::notEnoughArguments(2, info.Length()));
+ exceptionState.throwIfNeeded();
return;
}
+ const int uniformLocationArgumentIndex = 0;
WebGLRenderingContext* context = V8WebGLRenderingContext::toNative(info.Holder());
- if (info.Length() > 0 && !isUndefinedOrNull(info[0]) && !V8WebGLUniformLocation::hasInstance(info[0], info.GetIsolate(), worldType(info.GetIsolate()))) {
- throwUninformativeAndGenericTypeError(info.GetIsolate());
+ if (info.Length() > 0 && !isUndefinedOrNull(info[uniformLocationArgumentIndex]) && !V8WebGLUniformLocation::hasInstance(info[uniformLocationArgumentIndex], info.GetIsolate())) {
+ exceptionState.throwTypeError(ExceptionMessages::argumentNullOrIncorrectType(uniformLocationArgumentIndex + 1, "WebGLUniformLocation"));
+ exceptionState.throwIfNeeded();
return;
}
- bool ok = false;
- WebGLUniformLocation* location = toWebGLUniformLocation(info[0], ok, info.GetIsolate());
+ WebGLUniformLocation* location = toWebGLUniformLocation(info[uniformLocationArgumentIndex], info.GetIsolate());
- if (V8Int32Array::hasInstance(info[1], info.GetIsolate(), worldType(info.GetIsolate()))) {
- Int32Array* array = V8Int32Array::toNative(info[1]->ToObject());
- ASSERT(array != NULL);
+ const int indexArrayArgumentIndex = 1;
+ if (V8Int32Array::hasInstance(info[indexArrayArgumentIndex], info.GetIsolate())) {
+ Int32Array* array = V8Int32Array::toNative(info[indexArrayArgumentIndex]->ToObject());
+ ASSERT(array);
switch (functionToCall) {
case kUniform1v: context->uniform1iv(location, array); break;
case kUniform2v: context->uniform2iv(location, array); break;
@@ -610,16 +681,20 @@ static void uniformHelperi(const v8::FunctionCallbackInfo<v8::Value>& info, Func
return;
}
- if (info[1].IsEmpty() || !info[1]->IsArray()) {
- throwUninformativeAndGenericTypeError(info.GetIsolate());
+ if (info[indexArrayArgumentIndex].IsEmpty() || !info[indexArrayArgumentIndex]->IsArray()) {
+ exceptionState.throwTypeError(ExceptionMessages::argumentNullOrIncorrectType(indexArrayArgumentIndex + 1, "Array"));
+ exceptionState.throwIfNeeded();
return;
}
- v8::Handle<v8::Array> array = v8::Local<v8::Array>::Cast(info[1]);
+ v8::Handle<v8::Array> array = v8::Local<v8::Array>::Cast(info[indexArrayArgumentIndex]);
uint32_t len = array->Length();
- int* data = jsArrayToIntArray(array, len);
+ int* data = jsArrayToIntArray(array, len, exceptionState);
+ if (exceptionState.throwIfNeeded())
+ return;
if (!data) {
// FIXME: consider different / better exception type.
- setDOMException(SyntaxError, info.GetIsolate());
+ exceptionState.throwDOMException(SyntaxError, "Failed to convert array argument");
+ exceptionState.throwIfNeeded();
return;
}
switch (functionToCall) {
@@ -634,45 +709,53 @@ static void uniformHelperi(const v8::FunctionCallbackInfo<v8::Value>& info, Func
void V8WebGLRenderingContext::uniform1fvMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
- vertexAttribAndUniformHelperf(info, kUniform1v, "uniform1fv");
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "uniform1fv", "WebGLRenderingContext", info.Holder(), info.GetIsolate());
+ vertexAttribAndUniformHelperf(info, kUniform1v, exceptionState);
}
void V8WebGLRenderingContext::uniform1ivMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
- uniformHelperi(info, kUniform1v, "uniform1iv");
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "uniform1iv", "WebGLRenderingContext", info.Holder(), info.GetIsolate());
+ uniformHelperi(info, kUniform1v, exceptionState);
}
void V8WebGLRenderingContext::uniform2fvMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
- vertexAttribAndUniformHelperf(info, kUniform2v, "uniform2fv");
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "uniform2fv", "WebGLRenderingContext", info.Holder(), info.GetIsolate());
+ vertexAttribAndUniformHelperf(info, kUniform2v, exceptionState);
}
void V8WebGLRenderingContext::uniform2ivMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
- uniformHelperi(info, kUniform2v, "uniform2iv");
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "uniform2iv", "WebGLRenderingContext", info.Holder(), info.GetIsolate());
+ uniformHelperi(info, kUniform2v, exceptionState);
}
void V8WebGLRenderingContext::uniform3fvMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
- vertexAttribAndUniformHelperf(info, kUniform3v, "uniform3fv");
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "uniform3fv", "WebGLRenderingContext", info.Holder(), info.GetIsolate());
+ vertexAttribAndUniformHelperf(info, kUniform3v, exceptionState);
}
void V8WebGLRenderingContext::uniform3ivMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
- uniformHelperi(info, kUniform3v, "uniform3iv");
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "uniform3iv", "WebGLRenderingContext", info.Holder(), info.GetIsolate());
+ uniformHelperi(info, kUniform3v, exceptionState);
}
void V8WebGLRenderingContext::uniform4fvMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
- vertexAttribAndUniformHelperf(info, kUniform4v, "uniform4fv");
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "uniform4fv", "WebGLRenderingContext", info.Holder(), info.GetIsolate());
+ vertexAttribAndUniformHelperf(info, kUniform4v, exceptionState);
}
void V8WebGLRenderingContext::uniform4ivMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
- uniformHelperi(info, kUniform4v, "uniform4iv");
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "uniform4iv", "WebGLRenderingContext", info.Holder(), info.GetIsolate());
+ uniformHelperi(info, kUniform4v, exceptionState);
}
-static void uniformMatrixHelper(const v8::FunctionCallbackInfo<v8::Value>& info, int matrixSize, const char* method)
+static void uniformMatrixHelper(const v8::FunctionCallbackInfo<v8::Value>& info, int matrixSize, ExceptionState& exceptionState)
{
// Forms:
// * glUniformMatrix2fv(GLint location, GLboolean transpose, Array data);
@@ -684,23 +767,26 @@ static void uniformMatrixHelper(const v8::FunctionCallbackInfo<v8::Value>& info,
//
// FIXME: need to change to accept Float32Array as well.
if (info.Length() != 3) {
- throwTypeError(ExceptionMessages::failedToExecute(method, "WebGLRenderingContext", ExceptionMessages::notEnoughArguments(3, info.Length())), info.GetIsolate());
+ exceptionState.throwTypeError(ExceptionMessages::notEnoughArguments(3, info.Length()));
+ exceptionState.throwIfNeeded();
return;
}
WebGLRenderingContext* context = V8WebGLRenderingContext::toNative(info.Holder());
- if (info.Length() > 0 && !isUndefinedOrNull(info[0]) && !V8WebGLUniformLocation::hasInstance(info[0], info.GetIsolate(), worldType(info.GetIsolate()))) {
- throwUninformativeAndGenericTypeError(info.GetIsolate());
+ const int uniformLocationArgumentIndex = 0;
+ if (info.Length() > 0 && !isUndefinedOrNull(info[uniformLocationArgumentIndex]) && !V8WebGLUniformLocation::hasInstance(info[uniformLocationArgumentIndex], info.GetIsolate())) {
+ exceptionState.throwTypeError(ExceptionMessages::argumentNullOrIncorrectType(uniformLocationArgumentIndex + 1, "WebGLUniformLocation"));
+ exceptionState.throwIfNeeded();
return;
}
- bool ok = false;
- WebGLUniformLocation* location = toWebGLUniformLocation(info[0], ok, info.GetIsolate());
+ WebGLUniformLocation* location = toWebGLUniformLocation(info[uniformLocationArgumentIndex], info.GetIsolate());
bool transpose = info[1]->BooleanValue();
- if (V8Float32Array::hasInstance(info[2], info.GetIsolate(), worldType(info.GetIsolate()))) {
- Float32Array* array = V8Float32Array::toNative(info[2]->ToObject());
- ASSERT(array != NULL);
+ const int arrayArgumentIndex = 2;
+ if (V8Float32Array::hasInstance(info[arrayArgumentIndex], info.GetIsolate())) {
+ Float32Array* array = V8Float32Array::toNative(info[arrayArgumentIndex]->ToObject());
+ ASSERT(array);
switch (matrixSize) {
case 2: context->uniformMatrix2fv(location, transpose, array); break;
case 3: context->uniformMatrix3fv(location, transpose, array); break;
@@ -710,16 +796,20 @@ static void uniformMatrixHelper(const v8::FunctionCallbackInfo<v8::Value>& info,
return;
}
- if (info[2].IsEmpty() || !info[2]->IsArray()) {
- throwUninformativeAndGenericTypeError(info.GetIsolate());
+ if (info[arrayArgumentIndex].IsEmpty() || !info[arrayArgumentIndex]->IsArray()) {
+ exceptionState.throwTypeError(ExceptionMessages::argumentNullOrIncorrectType(arrayArgumentIndex + 1, "Array"));
+ exceptionState.throwIfNeeded();
return;
}
v8::Handle<v8::Array> array = v8::Local<v8::Array>::Cast(info[2]);
uint32_t len = array->Length();
- float* data = jsArrayToFloatArray(array, len);
+ float* data = jsArrayToFloatArray(array, len, exceptionState);
+ if (exceptionState.throwIfNeeded())
+ return;
if (!data) {
// FIXME: consider different / better exception type.
- setDOMException(SyntaxError, info.GetIsolate());
+ exceptionState.throwDOMException(SyntaxError, "failed to convert Array value");
+ exceptionState.throwIfNeeded();
return;
}
switch (matrixSize) {
@@ -733,37 +823,44 @@ static void uniformMatrixHelper(const v8::FunctionCallbackInfo<v8::Value>& info,
void V8WebGLRenderingContext::uniformMatrix2fvMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
- uniformMatrixHelper(info, 2, "uniformMatrix2fv");
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "uniformMatrix2fv", "WebGLRenderingContext", info.Holder(), info.GetIsolate());
+ uniformMatrixHelper(info, 2, exceptionState);
}
void V8WebGLRenderingContext::uniformMatrix3fvMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
- uniformMatrixHelper(info, 3, "uniformMatrix3fv");
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "uniformMatrix3fv", "WebGLRenderingContext", info.Holder(), info.GetIsolate());
+ uniformMatrixHelper(info, 3, exceptionState);
}
void V8WebGLRenderingContext::uniformMatrix4fvMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
- uniformMatrixHelper(info, 4, "uniformMatrix4fv");
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "uniformMatrix4fv", "WebGLRenderingContext", info.Holder(), info.GetIsolate());
+ uniformMatrixHelper(info, 4, exceptionState);
}
void V8WebGLRenderingContext::vertexAttrib1fvMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
- vertexAttribAndUniformHelperf(info, kVertexAttrib1v, "vertexAttrib1fv");
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "vertexAttrib1fv", "WebGLRenderingContext", info.Holder(), info.GetIsolate());
+ vertexAttribAndUniformHelperf(info, kVertexAttrib1v, exceptionState);
}
void V8WebGLRenderingContext::vertexAttrib2fvMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
- vertexAttribAndUniformHelperf(info, kVertexAttrib2v, "vertexAttrib2fv");
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "vertexAttrib2fv", "WebGLRenderingContext", info.Holder(), info.GetIsolate());
+ vertexAttribAndUniformHelperf(info, kVertexAttrib2v, exceptionState);
}
void V8WebGLRenderingContext::vertexAttrib3fvMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
- vertexAttribAndUniformHelperf(info, kVertexAttrib3v, "vertexAttrib3fv");
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "vertexAttrib3fv", "WebGLRenderingContext", info.Holder(), info.GetIsolate());
+ vertexAttribAndUniformHelperf(info, kVertexAttrib3v, exceptionState);
}
void V8WebGLRenderingContext::vertexAttrib4fvMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
- vertexAttribAndUniformHelperf(info, kVertexAttrib4v, "vertexAttrib4fv");
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "vertexAttrib4fv", "WebGLRenderingContext", info.Holder(), info.GetIsolate());
+ vertexAttribAndUniformHelperf(info, kVertexAttrib4v, exceptionState);
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8WebKitPointCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8WebKitPointCustom.cpp
index 35429f91ffd..e87549ec81f 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8WebKitPointCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8WebKitPointCustom.cpp
@@ -29,7 +29,7 @@
*/
#include "config.h"
-#include "V8WebKitPoint.h"
+#include "bindings/core/v8/V8WebKitPoint.h"
#include "bindings/v8/V8Binding.h"
#include "bindings/v8/V8DOMWrapper.h"
@@ -54,7 +54,7 @@ void V8WebKitPoint::constructorCustom(const v8::FunctionCallbackInfo<v8::Value>&
y = 0;
}
}
- RefPtr<DOMPoint> point = DOMPoint::create(x, y);
+ RefPtrWillBeRawPtr<DOMPoint> point = DOMPoint::create(x, y);
v8::Handle<v8::Object> wrapper = info.Holder();
V8DOMWrapper::associateObjectWithWrapper<V8WebKitPoint>(point.release(), &wrapperTypeInfo, wrapper, info.GetIsolate(), WrapperConfiguration::Dependent);
info.GetReturnValue().Set(wrapper);
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8WindowCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8WindowCustom.cpp
index 24f19e4fd10..7ab9e529d00 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8WindowCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8WindowCustom.cpp
@@ -29,10 +29,10 @@
*/
#include "config.h"
-#include "V8Window.h"
+#include "bindings/core/v8/V8Window.h"
-#include "V8HTMLCollection.h"
-#include "V8Node.h"
+#include "bindings/core/v8/V8HTMLCollection.h"
+#include "bindings/core/v8/V8Node.h"
#include "bindings/v8/BindingSecurity.h"
#include "bindings/v8/ExceptionMessages.h"
#include "bindings/v8/ExceptionState.h"
@@ -44,8 +44,7 @@
#include "bindings/v8/V8EventListener.h"
#include "bindings/v8/V8EventListenerList.h"
#include "bindings/v8/V8GCForContextDispose.h"
-#include "bindings/v8/V8HiddenPropertyName.h"
-#include "bindings/v8/V8Utilities.h"
+#include "bindings/v8/V8HiddenValue.h"
#include "core/dom/ExceptionCode.h"
#include "core/dom/MessagePort.h"
#include "core/html/HTMLCollection.h"
@@ -53,13 +52,13 @@
#include "core/inspector/ScriptCallStack.h"
#include "core/loader/FrameLoadRequest.h"
#include "core/loader/FrameLoader.h"
-#include "core/frame/ContentSecurityPolicy.h"
#include "core/frame/DOMTimer.h"
-#include "core/frame/DOMWindow.h"
+#include "core/frame/LocalDOMWindow.h"
#include "core/frame/DOMWindowTimers.h"
-#include "core/frame/Frame.h"
#include "core/frame/FrameView.h"
+#include "core/frame/LocalFrame.h"
#include "core/frame/Settings.h"
+#include "core/frame/csp/ContentSecurityPolicy.h"
#include "core/storage/Storage.h"
#include "platform/PlatformScreen.h"
#include "platform/graphics/media/MediaPlayer.h"
@@ -71,19 +70,19 @@ namespace WebCore {
// FIXME: There is a lot of duplication with SetTimeoutOrInterval() in V8WorkerGlobalScopeCustom.cpp.
// We should refactor this.
-void WindowSetTimeoutImpl(const v8::FunctionCallbackInfo<v8::Value>& info, bool singleShot, ExceptionState& exceptionState)
+static void windowSetTimeoutImpl(const v8::FunctionCallbackInfo<v8::Value>& info, bool singleShot, ExceptionState& exceptionState)
{
int argumentCount = info.Length();
if (argumentCount < 1)
return;
- DOMWindow* imp = V8Window::toNative(info.Holder());
- if (!imp->document()) {
+ LocalDOMWindow* impl = V8Window::toNative(info.Holder());
+ if (!impl->frame() || !impl->document()) {
exceptionState.throwDOMException(InvalidAccessError, "No script context is available in which to execute the script.");
return;
}
-
+ ScriptState* scriptState = ScriptState::current(info.GetIsolate());
v8::Handle<v8::Value> function = info[0];
String functionString;
if (!function->IsFunction()) {
@@ -105,7 +104,7 @@ void WindowSetTimeoutImpl(const v8::FunctionCallbackInfo<v8::Value>& info, bool
return;
}
- if (!BindingSecurity::shouldAllowAccessToFrame(imp->frame(), exceptionState))
+ if (!BindingSecurity::shouldAllowAccessToFrame(info.GetIsolate(), impl->frame(), exceptionState))
return;
OwnPtr<ScheduledAction> action;
@@ -121,23 +120,23 @@ void WindowSetTimeoutImpl(const v8::FunctionCallbackInfo<v8::Value>& info, bool
}
// params is passed to action, and released in action's destructor
- ASSERT(imp->frame());
- action = adoptPtr(new ScheduledAction(imp->frame()->script().currentWorldContext(), v8::Handle<v8::Function>::Cast(function), paramCount, params.get(), info.GetIsolate()));
+ ASSERT(impl->frame());
+ action = adoptPtr(new ScheduledAction(scriptState, v8::Handle<v8::Function>::Cast(function), paramCount, params.get(), info.GetIsolate()));
} else {
- if (imp->document() && !imp->document()->contentSecurityPolicy()->allowEval()) {
+ if (impl->document() && !impl->document()->contentSecurityPolicy()->allowEval()) {
v8SetReturnValue(info, 0);
return;
}
- ASSERT(imp->frame());
- action = adoptPtr(new ScheduledAction(imp->frame()->script().currentWorldContext(), functionString, KURL(), info.GetIsolate()));
+ ASSERT(impl->frame());
+ action = adoptPtr(new ScheduledAction(scriptState, functionString, KURL(), info.GetIsolate()));
}
int32_t timeout = argumentCount >= 2 ? info[1]->Int32Value() : 0;
int timerId;
if (singleShot)
- timerId = DOMWindowTimers::setTimeout(imp, action.release(), timeout);
+ timerId = DOMWindowTimers::setTimeout(*impl, action.release(), timeout);
else
- timerId = DOMWindowTimers::setInterval(imp, action.release(), timeout);
+ timerId = DOMWindowTimers::setInterval(*impl, action.release(), timeout);
// Try to do the idle notification before the timeout expires to get better
// use of any idle time. Aim for the middle of the interval for simplicity.
@@ -151,24 +150,14 @@ void WindowSetTimeoutImpl(const v8::FunctionCallbackInfo<v8::Value>& info, bool
void V8Window::eventAttributeGetterCustom(const v8::PropertyCallbackInfo<v8::Value>& info)
{
- v8::Handle<v8::Object> holder = info.This()->FindInstanceInPrototypeChain(V8Window::domTemplate(info.GetIsolate(), worldTypeInMainThread(info.GetIsolate())));
- if (holder.IsEmpty())
- return;
-
- Frame* frame = V8Window::toNative(holder)->frame();
+ LocalFrame* frame = V8Window::toNative(info.Holder())->frame();
ExceptionState exceptionState(ExceptionState::GetterContext, "event", "Window", info.Holder(), info.GetIsolate());
- if (!BindingSecurity::shouldAllowAccessToFrame(frame, exceptionState)) {
+ if (!BindingSecurity::shouldAllowAccessToFrame(info.GetIsolate(), frame, exceptionState)) {
exceptionState.throwIfNeeded();
return;
}
- ASSERT(frame);
- v8::Local<v8::Context> context = frame->script().currentWorldContext();
- if (context.IsEmpty())
- return;
-
- v8::Handle<v8::String> eventSymbol = V8HiddenPropertyName::event(info.GetIsolate());
- v8::Handle<v8::Value> jsEvent = context->Global()->GetHiddenValue(eventSymbol);
+ v8::Handle<v8::Value> jsEvent = V8HiddenValue::getHiddenValue(info.GetIsolate(), info.Holder()->CreationContext()->Global(), V8HiddenValue::event(info.GetIsolate()));
if (jsEvent.IsEmpty())
return;
v8SetReturnValue(info, jsEvent);
@@ -176,31 +165,21 @@ void V8Window::eventAttributeGetterCustom(const v8::PropertyCallbackInfo<v8::Val
void V8Window::eventAttributeSetterCustom(v8::Local<v8::Value> value, const v8::PropertyCallbackInfo<void>& info)
{
- v8::Handle<v8::Object> holder = info.This()->FindInstanceInPrototypeChain(V8Window::domTemplate(info.GetIsolate(), worldTypeInMainThread(info.GetIsolate())));
- if (holder.IsEmpty())
- return;
-
- Frame* frame = V8Window::toNative(holder)->frame();
+ LocalFrame* frame = V8Window::toNative(info.Holder())->frame();
ExceptionState exceptionState(ExceptionState::SetterContext, "event", "Window", info.Holder(), info.GetIsolate());
- if (!BindingSecurity::shouldAllowAccessToFrame(frame, exceptionState)) {
+ if (!BindingSecurity::shouldAllowAccessToFrame(info.GetIsolate(), frame, exceptionState)) {
exceptionState.throwIfNeeded();
return;
}
- ASSERT(frame);
- v8::Local<v8::Context> context = frame->script().currentWorldContext();
- if (context.IsEmpty())
- return;
-
- v8::Handle<v8::String> eventSymbol = V8HiddenPropertyName::event(info.GetIsolate());
- context->Global()->SetHiddenValue(eventSymbol, value);
+ V8HiddenValue::setHiddenValue(info.GetIsolate(), info.Holder()->CreationContext()->Global(), V8HiddenValue::event(info.GetIsolate()), value);
}
void V8Window::frameElementAttributeGetterCustom(const v8::PropertyCallbackInfo<v8::Value>& info)
{
- DOMWindow* imp = V8Window::toNative(info.Holder());
+ LocalDOMWindow* impl = V8Window::toNative(info.Holder());
ExceptionState exceptionState(ExceptionState::GetterContext, "frame", "Window", info.Holder(), info.GetIsolate());
- if (!BindingSecurity::shouldAllowAccessToNode(imp->frameElement(), exceptionState)) {
+ if (!BindingSecurity::shouldAllowAccessToNode(info.GetIsolate(), impl->frameElement(), exceptionState)) {
v8SetReturnValueNull(info);
exceptionState.throwIfNeeded();
return;
@@ -208,17 +187,17 @@ void V8Window::frameElementAttributeGetterCustom(const v8::PropertyCallbackInfo<
// The wrapper for an <iframe> should get its prototype from the context of the frame it's in, rather than its own frame.
// So, use its containing document as the creation context when wrapping.
- v8::Handle<v8::Value> creationContext = toV8(&imp->frameElement()->document(), v8::Handle<v8::Object>(), info.GetIsolate());
+ v8::Handle<v8::Value> creationContext = toV8(&impl->frameElement()->document(), info.Holder(), info.GetIsolate());
RELEASE_ASSERT(!creationContext.IsEmpty());
- v8::Handle<v8::Value> wrapper = toV8(imp->frameElement(), v8::Handle<v8::Object>::Cast(creationContext), info.GetIsolate());
+ v8::Handle<v8::Value> wrapper = toV8(impl->frameElement(), v8::Handle<v8::Object>::Cast(creationContext), info.GetIsolate());
v8SetReturnValue(info, wrapper);
}
void V8Window::openerAttributeSetterCustom(v8::Local<v8::Value> value, const v8::PropertyCallbackInfo<void>& info)
{
- DOMWindow* imp = V8Window::toNative(info.Holder());
+ LocalDOMWindow* impl = V8Window::toNative(info.Holder());
ExceptionState exceptionState(ExceptionState::SetterContext, "opener", "Window", info.Holder(), info.GetIsolate());
- if (!BindingSecurity::shouldAllowAccessToFrame(imp->frame(), exceptionState)) {
+ if (!BindingSecurity::shouldAllowAccessToFrame(info.GetIsolate(), impl->frame(), exceptionState)) {
exceptionState.throwIfNeeded();
return;
}
@@ -227,17 +206,18 @@ void V8Window::openerAttributeSetterCustom(v8::Local<v8::Value> value, const v8:
// Have a special handling of null value to behave
// like Firefox. See bug http://b/1224887 & http://b/791706.
if (value->IsNull()) {
- // imp->frame() cannot be null,
+ // impl->frame() cannot be null,
// otherwise, SameOrigin check would have failed.
- ASSERT(imp->frame());
- imp->frame()->loader().setOpener(0);
+ ASSERT(impl->frame());
+ impl->frame()->loader().setOpener(0);
}
// Delete the accessor from this object.
info.Holder()->Delete(v8AtomicString(info.GetIsolate(), "opener"));
// Put property on the front (this) object.
- info.This()->Set(v8AtomicString(info.GetIsolate(), "opener"), value);
+ if (info.This()->IsObject())
+ v8::Handle<v8::Object>::Cast(info.This())->Set(v8AtomicString(info.GetIsolate(), "opener"), value);
}
static bool isLegacyTargetOriginDesignation(v8::Handle<v8::Value> value)
@@ -252,12 +232,15 @@ void V8Window::postMessageMethodCustom(const v8::FunctionCallbackInfo<v8::Value>
{
// None of these need to be RefPtr because info and context are guaranteed
// to hold on to them.
- DOMWindow* window = V8Window::toNative(info.Holder());
- DOMWindow* source = activeDOMWindow();
+ LocalDOMWindow* window = V8Window::toNative(info.Holder());
+ LocalDOMWindow* source = callingDOMWindow(info.GetIsolate());
+
+ ExceptionState exceptionState(ExceptionState::ExecutionContext, "postMessage", "Window", info.Holder(), info.GetIsolate());
// If called directly by WebCore we don't have a calling context.
if (!source) {
- throwUninformativeAndGenericTypeError(info.GetIsolate());
+ exceptionState.throwTypeError("No active calling context exists.");
+ exceptionState.throwIfNeeded();
return;
}
@@ -276,22 +259,17 @@ void V8Window::postMessageMethodCustom(const v8::FunctionCallbackInfo<v8::Value>
targetOriginArgIndex = 2;
transferablesArgIndex = 1;
}
- bool notASequence = false;
- if (!extractTransferables(info[transferablesArgIndex], portArray, arrayBufferArray, notASequence, info.GetIsolate())) {
- if (notASequence)
- throwTypeError(ExceptionMessages::failedToExecute("postMessage", "Window", ExceptionMessages::notAnArrayTypeArgumentOrValue(transferablesArgIndex + 1)), info.GetIsolate());
+ if (!SerializedScriptValue::extractTransferables(info[transferablesArgIndex], transferablesArgIndex, portArray, arrayBufferArray, exceptionState, info.GetIsolate())) {
+ exceptionState.throwIfNeeded();
return;
}
}
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<WithUndefinedOrNullCheck>, targetOrigin, info[targetOriginArgIndex]);
+ TOSTRING_VOID(V8StringResource<WithUndefinedOrNullCheck>, targetOrigin, info[targetOriginArgIndex]);
- bool didThrow = false;
- RefPtr<SerializedScriptValue> message =
- SerializedScriptValue::create(info[0], &portArray, &arrayBufferArray, didThrow, info.GetIsolate());
- if (didThrow)
+ RefPtr<SerializedScriptValue> message = SerializedScriptValue::create(info[0], &portArray, &arrayBufferArray, exceptionState, info.GetIsolate());
+ if (exceptionState.throwIfNeeded())
return;
- ExceptionState exceptionState(ExceptionState::ExecutionContext, "postMessage", "Window", info.Holder(), info.GetIsolate());
window->postMessage(message.release(), &portArray, targetOrigin, source, exceptionState);
exceptionState.throwIfNeeded();
}
@@ -302,7 +280,7 @@ void V8Window::postMessageMethodCustom(const v8::FunctionCallbackInfo<v8::Value>
// switching context of receiver. I consider it is dangerous.
void V8Window::toStringMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
- v8::Handle<v8::Object> domWrapper = info.This()->FindInstanceInPrototypeChain(V8Window::domTemplate(info.GetIsolate(), worldTypeInMainThread(info.GetIsolate())));
+ v8::Handle<v8::Object> domWrapper = V8Window::findInstanceInPrototypeChain(info.This(), info.GetIsolate());
if (domWrapper.IsEmpty()) {
v8SetReturnValue(info, info.This()->ObjectProtoToString());
return;
@@ -312,84 +290,92 @@ void V8Window::toStringMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& i
class DialogHandler {
public:
- explicit DialogHandler(v8::Handle<v8::Value> dialogArguments)
- : m_dialogArguments(dialogArguments)
+ explicit DialogHandler(v8::Handle<v8::Value> dialogArguments, ScriptState* scriptState)
+ : m_scriptState(scriptState)
+ , m_dialogArguments(dialogArguments)
{
}
- void dialogCreated(DOMWindow*, v8::Isolate*);
- v8::Handle<v8::Value> returnValue(v8::Isolate*) const;
+ void dialogCreated(LocalDOMWindow*);
+ v8::Handle<v8::Value> returnValue() const;
private:
+ RefPtr<ScriptState> m_scriptState;
+ RefPtr<ScriptState> m_scriptStateForDialogFrame;
v8::Handle<v8::Value> m_dialogArguments;
- v8::Handle<v8::Context> m_dialogContext;
};
-inline void DialogHandler::dialogCreated(DOMWindow* dialogFrame, v8::Isolate* isolate)
+void DialogHandler::dialogCreated(LocalDOMWindow* dialogFrame)
{
- m_dialogContext = dialogFrame->frame() ? dialogFrame->frame()->script().currentWorldContext() : v8::Local<v8::Context>();
- if (m_dialogContext.IsEmpty())
- return;
if (m_dialogArguments.IsEmpty())
return;
- v8::Context::Scope scope(m_dialogContext);
- m_dialogContext->Global()->Set(v8AtomicString(isolate, "dialogArguments"), m_dialogArguments);
+ v8::Handle<v8::Context> context = toV8Context(dialogFrame->frame(), m_scriptState->world());
+ if (context.IsEmpty())
+ return;
+ m_scriptStateForDialogFrame = ScriptState::from(context);
+
+ ScriptState::Scope scope(m_scriptStateForDialogFrame.get());
+ m_scriptStateForDialogFrame->context()->Global()->Set(v8AtomicString(m_scriptState->isolate(), "dialogArguments"), m_dialogArguments);
}
-inline v8::Handle<v8::Value> DialogHandler::returnValue(v8::Isolate* isolate) const
+v8::Handle<v8::Value> DialogHandler::returnValue() const
{
- if (m_dialogContext.IsEmpty())
- return v8::Undefined(isolate);
- v8::Context::Scope scope(m_dialogContext);
- v8::Handle<v8::Value> returnValue = m_dialogContext->Global()->Get(v8AtomicString(isolate, "returnValue"));
+ if (!m_scriptStateForDialogFrame)
+ return v8Undefined();
+ ASSERT(!m_scriptStateForDialogFrame->contextIsEmpty());
+
+ v8::Isolate* isolate = m_scriptStateForDialogFrame->isolate();
+ v8::EscapableHandleScope handleScope(isolate);
+ ScriptState::Scope scope(m_scriptStateForDialogFrame.get());
+ v8::Local<v8::Value> returnValue = m_scriptStateForDialogFrame->context()->Global()->Get(v8AtomicString(isolate, "returnValue"));
if (returnValue.IsEmpty())
- return v8::Undefined(isolate);
- return returnValue;
+ return v8Undefined();
+ return handleScope.Escape(returnValue);
}
-static void setUpDialog(DOMWindow* dialog, void* handler)
+static void setUpDialog(LocalDOMWindow* dialog, void* handler)
{
- static_cast<DialogHandler*>(handler)->dialogCreated(dialog, v8::Isolate::GetCurrent());
+ static_cast<DialogHandler*>(handler)->dialogCreated(dialog);
}
void V8Window::showModalDialogMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
- DOMWindow* impl = V8Window::toNative(info.Holder());
+ LocalDOMWindow* impl = V8Window::toNative(info.Holder());
ExceptionState exceptionState(ExceptionState::ExecutionContext, "showModalDialog", "Window", info.Holder(), info.GetIsolate());
- if (!BindingSecurity::shouldAllowAccessToFrame(impl->frame(), exceptionState)) {
+ if (!BindingSecurity::shouldAllowAccessToFrame(info.GetIsolate(), impl->frame(), exceptionState)) {
exceptionState.throwIfNeeded();
return;
}
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<WithUndefinedOrNullCheck>, urlString, info[0]);
- DialogHandler handler(info[1]);
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<WithUndefinedOrNullCheck>, dialogFeaturesString, info[2]);
+ TOSTRING_VOID(V8StringResource<WithUndefinedOrNullCheck>, urlString, info[0]);
+ DialogHandler handler(info[1], ScriptState::current(info.GetIsolate()));
+ TOSTRING_VOID(V8StringResource<WithUndefinedOrNullCheck>, dialogFeaturesString, info[2]);
- impl->showModalDialog(urlString, dialogFeaturesString, activeDOMWindow(), firstDOMWindow(), setUpDialog, &handler);
+ impl->showModalDialog(urlString, dialogFeaturesString, callingDOMWindow(info.GetIsolate()), enteredDOMWindow(info.GetIsolate()), setUpDialog, &handler);
- v8SetReturnValue(info, handler.returnValue(info.GetIsolate()));
+ v8SetReturnValue(info, handler.returnValue());
}
void V8Window::openMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
- DOMWindow* impl = V8Window::toNative(info.Holder());
+ LocalDOMWindow* impl = V8Window::toNative(info.Holder());
ExceptionState exceptionState(ExceptionState::ExecutionContext, "open", "Window", info.Holder(), info.GetIsolate());
- if (!BindingSecurity::shouldAllowAccessToFrame(impl->frame(), exceptionState)) {
+ if (!BindingSecurity::shouldAllowAccessToFrame(info.GetIsolate(), impl->frame(), exceptionState)) {
exceptionState.throwIfNeeded();
return;
}
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<WithUndefinedOrNullCheck>, urlString, info[0]);
+ TOSTRING_VOID(V8StringResource<WithUndefinedOrNullCheck>, urlString, info[0]);
AtomicString frameName;
if (info[1]->IsUndefined() || info[1]->IsNull()) {
frameName = "_blank";
} else {
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<>, frameNameResource, info[1]);
+ TOSTRING_VOID(V8StringResource<>, frameNameResource, info[1]);
frameName = frameNameResource;
}
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<WithUndefinedOrNullCheck>, windowFeaturesString, info[2]);
+ TOSTRING_VOID(V8StringResource<WithUndefinedOrNullCheck>, windowFeaturesString, info[2]);
- RefPtr<DOMWindow> openedWindow = impl->open(urlString, frameName, windowFeaturesString, activeDOMWindow(), firstDOMWindow());
+ RefPtrWillBeRawPtr<LocalDOMWindow> openedWindow = impl->open(urlString, frameName, windowFeaturesString, callingDOMWindow(info.GetIsolate()), enteredDOMWindow(info.GetIsolate()));
if (!openedWindow)
return;
@@ -399,11 +385,11 @@ void V8Window::openMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
void V8Window::namedPropertyGetterCustom(v8::Local<v8::String> name, const v8::PropertyCallbackInfo<v8::Value>& info)
{
- DOMWindow* window = V8Window::toNative(info.Holder());
+ LocalDOMWindow* window = V8Window::toNative(info.Holder());
if (!window)
return;
- Frame* frame = window->frame();
+ LocalFrame* frame = window->frame();
// window is detached from a frame.
if (!frame)
return;
@@ -425,7 +411,7 @@ void V8Window::namedPropertyGetterCustom(v8::Local<v8::String> name, const v8::P
if (doc && doc->isHTMLDocument()) {
if (toHTMLDocument(doc)->hasNamedItem(propName) || doc->hasElementWithId(propName.impl())) {
- RefPtr<HTMLCollection> items = doc->windowNamedItems(propName);
+ RefPtrWillBeRawPtr<HTMLCollection> items = doc->windowNamedItems(propName);
if (!items->isEmpty()) {
if (items->hasExactlyOneItem()) {
v8SetReturnValueFast(info, items->item(0), window);
@@ -442,7 +428,7 @@ void V8Window::namedPropertyGetterCustom(v8::Local<v8::String> name, const v8::P
void V8Window::setTimeoutMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
ExceptionState exceptionState(ExceptionState::ExecutionContext, "setTimeout", "Window", info.Holder(), info.GetIsolate());
- WindowSetTimeoutImpl(info, true, exceptionState);
+ windowSetTimeoutImpl(info, true, exceptionState);
exceptionState.throwIfNeeded();
}
@@ -450,22 +436,22 @@ void V8Window::setTimeoutMethodCustom(const v8::FunctionCallbackInfo<v8::Value>&
void V8Window::setIntervalMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
ExceptionState exceptionState(ExceptionState::ExecutionContext, "setInterval", "Window", info.Holder(), info.GetIsolate());
- WindowSetTimeoutImpl(info, false, exceptionState);
+ windowSetTimeoutImpl(info, false, exceptionState);
exceptionState.throwIfNeeded();
}
bool V8Window::namedSecurityCheckCustom(v8::Local<v8::Object> host, v8::Local<v8::Value> key, v8::AccessType type, v8::Local<v8::Value>)
{
v8::Isolate* isolate = v8::Isolate::GetCurrent();
- v8::Handle<v8::Object> window = host->FindInstanceInPrototypeChain(V8Window::domTemplate(isolate, worldTypeInMainThread(isolate)));
+ v8::Handle<v8::Object> window = V8Window::findInstanceInPrototypeChain(host, isolate);
if (window.IsEmpty())
return false; // the frame is gone.
- DOMWindow* targetWindow = V8Window::toNative(window);
+ LocalDOMWindow* targetWindow = V8Window::toNative(window);
ASSERT(targetWindow);
- Frame* target = targetWindow->frame();
+ LocalFrame* target = targetWindow->frame();
if (!target)
return false;
@@ -494,21 +480,21 @@ bool V8Window::namedSecurityCheckCustom(v8::Local<v8::Object> host, v8::Local<v8
return true;
}
- return BindingSecurity::shouldAllowAccessToFrame(target, DoNotReportSecurityError);
+ return BindingSecurity::shouldAllowAccessToFrame(isolate, target, DoNotReportSecurityError);
}
bool V8Window::indexedSecurityCheckCustom(v8::Local<v8::Object> host, uint32_t index, v8::AccessType type, v8::Local<v8::Value>)
{
v8::Isolate* isolate = v8::Isolate::GetCurrent();
- v8::Handle<v8::Object> window = host->FindInstanceInPrototypeChain(V8Window::domTemplate(isolate, worldTypeInMainThread(isolate)));
+ v8::Handle<v8::Object> window = V8Window::findInstanceInPrototypeChain(host, isolate);
if (window.IsEmpty())
return false;
- DOMWindow* targetWindow = V8Window::toNative(window);
+ LocalDOMWindow* targetWindow = V8Window::toNative(window);
ASSERT(targetWindow);
- Frame* target = targetWindow->frame();
+ LocalFrame* target = targetWindow->frame();
if (!target)
return false;
@@ -516,7 +502,7 @@ bool V8Window::indexedSecurityCheckCustom(v8::Local<v8::Object> host, uint32_t i
if (target->loader().stateMachine()->isDisplayingInitialEmptyDocument())
target->loader().didAccessInitialDocument();
- Frame* childFrame = target->tree().scopedChild(index);
+ Frame* childFrame = target->tree().scopedChild(index);
// Notice that we can't call HasRealNamedProperty for ACCESS_HAS
// because that would generate infinite recursion.
@@ -528,36 +514,22 @@ bool V8Window::indexedSecurityCheckCustom(v8::Local<v8::Object> host, uint32_t i
&& !window->HasRealIndexedProperty(index))
return true;
- return BindingSecurity::shouldAllowAccessToFrame(target, DoNotReportSecurityError);
+ return BindingSecurity::shouldAllowAccessToFrame(isolate, target, DoNotReportSecurityError);
}
-v8::Handle<v8::Value> toV8(DOMWindow* window, v8::Handle<v8::Object> creationContext, v8::Isolate* isolate)
+v8::Handle<v8::Value> toV8(LocalDOMWindow* window, v8::Handle<v8::Object> creationContext, v8::Isolate* isolate)
{
- // Notice that we explicitly ignore creationContext because the DOMWindow is its own creationContext.
+ // Notice that we explicitly ignore creationContext because the LocalDOMWindow is its own creationContext.
if (!window)
return v8::Null(isolate);
// Initializes environment of a frame, and return the global object
// of the frame.
- Frame* frame = window->frame();
+ LocalFrame* frame = window->frame();
if (!frame)
return v8Undefined();
- // Special case: Because of executeScriptInIsolatedWorld() one DOMWindow can have
- // multiple contexts and multiple global objects associated with it. When
- // code running in one of those contexts accesses the window object, we
- // want to return the global object associated with that context, not
- // necessarily the first global object associated with that DOMWindow.
- v8::Handle<v8::Context> currentContext = isolate->GetCurrentContext();
- v8::Handle<v8::Object> currentGlobal = currentContext->Global();
- v8::Handle<v8::Object> windowWrapper = currentGlobal->FindInstanceInPrototypeChain(V8Window::domTemplate(isolate, worldTypeInMainThread(isolate)));
- if (!windowWrapper.IsEmpty()) {
- if (V8Window::toNative(windowWrapper) == window)
- return currentGlobal;
- }
-
- // Otherwise, return the global object associated with this frame.
- v8::Handle<v8::Context> context = frame->script().currentWorldContext();
+ v8::Handle<v8::Context> context = toV8Context(frame, DOMWrapperWorld::current(isolate));
if (context.IsEmpty())
return v8Undefined();
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8WorkerCryptoCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8WorkerCryptoCustom.cpp
deleted file mode 100644
index acf7a114d5a..00000000000
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8WorkerCryptoCustom.cpp
+++ /dev/null
@@ -1,43 +0,0 @@
-/*
- * Copyright (C) 2013 Google Inc. All rights reserved.
- *
- * Redistribution and use in source and binary forms, with or without
- * modification, are permitted provided that the following conditions are
- * met:
- *
- * * Redistributions of source code must retain the above copyright
- * notice, this list of conditions and the following disclaimer.
- * * Redistributions in binary form must reproduce the above
- * copyright notice, this list of conditions and the following disclaimer
- * in the documentation and/or other materials provided with the
- * distribution.
- * * Neither the name of Google Inc. nor the names of its
- * contributors may be used to endorse or promote products derived from
- * this software without specific prior written permission.
- *
- * THIS SOFTWARE IS PROVIDED BY THE COPYRIGHT HOLDERS AND CONTRIBUTORS
- * "AS IS" AND ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT
- * LIMITED TO, THE IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR
- * A PARTICULAR PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL THE COPYRIGHT
- * OWNER OR CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL,
- * SPECIAL, EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT
- * LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE,
- * DATA, OR PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY
- * THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT
- * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE
- * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE.
- */
-
-#include "config.h"
-#include "V8WorkerCrypto.h"
-
-#include "V8Crypto.h"
-
-namespace WebCore {
-
-void V8WorkerCrypto::getRandomValuesMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
-{
- V8Crypto::getRandomValuesMethodCustom(info);
-}
-
-} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8WorkerCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8WorkerCustom.cpp
index 19440578be3..01a4a822546 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8WorkerCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8WorkerCustom.cpp
@@ -29,13 +29,12 @@
*/
#include "config.h"
-#include "V8Worker.h"
+#include "bindings/core/v8/V8Worker.h"
#include "bindings/v8/ExceptionMessages.h"
#include "bindings/v8/ExceptionState.h"
#include "bindings/v8/SerializedScriptValue.h"
#include "bindings/v8/V8Binding.h"
-#include "bindings/v8/V8Utilities.h"
#include "core/workers/Worker.h"
#include "core/workers/WorkerGlobalScope.h"
#include "wtf/ArrayBuffer.h"
@@ -50,18 +49,13 @@ void V8Worker::postMessageMethodCustom(const v8::FunctionCallbackInfo<v8::Value>
ArrayBufferArray arrayBuffers;
if (info.Length() > 1) {
const int transferablesArgIndex = 1;
- bool notASequence = false;
- if (!extractTransferables(info[transferablesArgIndex], ports, arrayBuffers, notASequence, info.GetIsolate())) {
- if (notASequence) {
- exceptionState.throwTypeError(ExceptionMessages::notAnArrayTypeArgumentOrValue(transferablesArgIndex + 1));
- exceptionState.throwIfNeeded();
- }
+ if (!SerializedScriptValue::extractTransferables(info[transferablesArgIndex], transferablesArgIndex, ports, arrayBuffers, exceptionState, info.GetIsolate())) {
+ exceptionState.throwIfNeeded();
return;
}
}
- bool didThrow = false;
- RefPtr<SerializedScriptValue> message = SerializedScriptValue::create(info[0], &ports, &arrayBuffers, didThrow, info.GetIsolate());
- if (didThrow)
+ RefPtr<SerializedScriptValue> message = SerializedScriptValue::create(info[0], &ports, &arrayBuffers, exceptionState, info.GetIsolate());
+ if (exceptionState.throwIfNeeded())
return;
worker->postMessage(message.release(), &ports, exceptionState);
exceptionState.throwIfNeeded();
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8WorkerGlobalScopeCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8WorkerGlobalScopeCustom.cpp
index 1863af5992c..ca43934106b 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8WorkerGlobalScopeCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8WorkerGlobalScopeCustom.cpp
@@ -29,27 +29,27 @@
*/
#include "config.h"
-#include "V8WorkerGlobalScope.h"
+#include "bindings/core/v8/V8WorkerGlobalScope.h"
#include "bindings/v8/ExceptionState.h"
#include "bindings/v8/ScheduledAction.h"
#include "bindings/v8/V8Binding.h"
-#include "bindings/v8/V8Utilities.h"
#include "bindings/v8/V8WorkerGlobalScopeEventListener.h"
#include "bindings/v8/WorkerScriptController.h"
#include "core/inspector/ScriptCallStack.h"
-#include "core/frame/ContentSecurityPolicy.h"
#include "core/frame/DOMTimer.h"
#include "core/frame/DOMWindowTimers.h"
+#include "core/frame/csp/ContentSecurityPolicy.h"
#include "core/workers/WorkerGlobalScope.h"
#include "modules/websockets/WebSocket.h"
#include "wtf/OwnPtr.h"
namespace WebCore {
-void SetTimeoutOrInterval(const v8::FunctionCallbackInfo<v8::Value>& info, bool singleShot)
+static void setTimeoutOrInterval(const v8::FunctionCallbackInfo<v8::Value>& info, bool singleShot)
{
WorkerGlobalScope* workerGlobalScope = V8WorkerGlobalScope::toNative(info.Holder());
+ ASSERT(workerGlobalScope);
int argumentCount = info.Length();
if (argumentCount < 1)
@@ -61,8 +61,8 @@ void SetTimeoutOrInterval(const v8::FunctionCallbackInfo<v8::Value>& info, bool
if (!script)
return;
+ ScriptState* scriptState = ScriptState::current(info.GetIsolate());
OwnPtr<ScheduledAction> action;
- v8::Handle<v8::Context> v8Context = script->context();
if (function->IsString()) {
if (ContentSecurityPolicy* policy = workerGlobalScope->contentSecurityPolicy()) {
if (!policy->allowEval()) {
@@ -70,7 +70,7 @@ void SetTimeoutOrInterval(const v8::FunctionCallbackInfo<v8::Value>& info, bool
return;
}
}
- action = adoptPtr(new ScheduledAction(v8Context, toCoreString(function.As<v8::String>()), workerGlobalScope->url(), info.GetIsolate()));
+ action = adoptPtr(new ScheduledAction(scriptState, toCoreString(function.As<v8::String>()), workerGlobalScope->url(), info.GetIsolate()));
} else if (function->IsFunction()) {
size_t paramCount = argumentCount >= 2 ? argumentCount - 2 : 0;
OwnPtr<v8::Local<v8::Value>[]> params;
@@ -80,28 +80,28 @@ void SetTimeoutOrInterval(const v8::FunctionCallbackInfo<v8::Value>& info, bool
params[i] = info[i+2];
}
// ScheduledAction takes ownership of actual params and releases them in its destructor.
- action = adoptPtr(new ScheduledAction(v8Context, v8::Handle<v8::Function>::Cast(function), paramCount, params.get(), info.GetIsolate()));
+ action = adoptPtr(new ScheduledAction(scriptState, v8::Handle<v8::Function>::Cast(function), paramCount, params.get(), info.GetIsolate()));
} else
return;
int32_t timeout = argumentCount >= 2 ? info[1]->Int32Value() : 0;
int timerId;
if (singleShot)
- timerId = DOMWindowTimers::setTimeout(workerGlobalScope, action.release(), timeout);
+ timerId = DOMWindowTimers::setTimeout(*workerGlobalScope, action.release(), timeout);
else
- timerId = DOMWindowTimers::setInterval(workerGlobalScope, action.release(), timeout);
+ timerId = DOMWindowTimers::setInterval(*workerGlobalScope, action.release(), timeout);
v8SetReturnValue(info, timerId);
}
void V8WorkerGlobalScope::setTimeoutMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
- return SetTimeoutOrInterval(info, true);
+ return setTimeoutOrInterval(info, true);
}
void V8WorkerGlobalScope::setIntervalMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
- return SetTimeoutOrInterval(info, false);
+ return setTimeoutOrInterval(info, false);
}
v8::Handle<v8::Value> toV8(WorkerGlobalScope* impl, v8::Handle<v8::Object> creationContext, v8::Isolate* isolate)
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8XMLHttpRequestCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8XMLHttpRequestCustom.cpp
index 855f64e16bf..8659b65bcff 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8XMLHttpRequestCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8XMLHttpRequestCustom.cpp
@@ -29,17 +29,16 @@
*/
#include "config.h"
-#include "V8XMLHttpRequest.h"
+#include "bindings/core/v8/V8XMLHttpRequest.h"
-#include "V8Blob.h"
-#include "V8Document.h"
-#include "V8FormData.h"
-#include "V8HTMLDocument.h"
-#include "V8Stream.h"
+#include "bindings/core/v8/V8Blob.h"
+#include "bindings/core/v8/V8Document.h"
+#include "bindings/core/v8/V8FormData.h"
+#include "bindings/core/v8/V8HTMLDocument.h"
+#include "bindings/core/v8/V8Stream.h"
#include "bindings/v8/ExceptionMessages.h"
#include "bindings/v8/ExceptionState.h"
#include "bindings/v8/V8Binding.h"
-#include "bindings/v8/V8Utilities.h"
#include "bindings/v8/custom/V8ArrayBufferCustom.h"
#include "bindings/v8/custom/V8ArrayBufferViewCustom.h"
#include "core/dom/Document.h"
@@ -54,15 +53,16 @@ namespace WebCore {
void V8XMLHttpRequest::constructorCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
{
- ExecutionContext* context = getExecutionContext();
+ ExecutionContext* context = currentExecutionContext(info.GetIsolate());
RefPtr<SecurityOrigin> securityOrigin;
if (context->isDocument()) {
- if (DOMWrapperWorld* world = isolatedWorldForEnteredContext(info.GetIsolate()))
- securityOrigin = world->isolatedWorldSecurityOrigin();
+ DOMWrapperWorld& world = DOMWrapperWorld::current(info.GetIsolate());
+ if (world.isIsolatedWorld())
+ securityOrigin = world.isolatedWorldSecurityOrigin();
}
- RefPtr<XMLHttpRequest> xmlHttpRequest = XMLHttpRequest::create(context, securityOrigin);
+ RefPtrWillBeRawPtr<XMLHttpRequest> xmlHttpRequest = XMLHttpRequest::create(context, securityOrigin);
v8::Handle<v8::Object> wrapper = info.Holder();
V8DOMWrapper::associateObjectWithWrapper<V8XMLHttpRequest>(xmlHttpRequest.release(), &wrapperTypeInfo, wrapper, info.GetIsolate(), WrapperConfiguration::Dependent);
@@ -73,10 +73,10 @@ void V8XMLHttpRequest::responseTextAttributeGetterCustom(const v8::PropertyCallb
{
XMLHttpRequest* xmlHttpRequest = V8XMLHttpRequest::toNative(info.Holder());
ExceptionState exceptionState(ExceptionState::GetterContext, "responseText", "XMLHttpRequest", info.Holder(), info.GetIsolate());
- ScriptValue text = xmlHttpRequest->responseText(exceptionState);
+ ScriptString text = xmlHttpRequest->responseText(exceptionState);
if (exceptionState.throwIfNeeded())
return;
- if (text.hasNoValue()) {
+ if (text.isEmpty()) {
v8SetReturnValueString(info, emptyString(), info.GetIsolate());
return;
}
@@ -98,21 +98,18 @@ void V8XMLHttpRequest::responseAttributeGetterCustom(const v8::PropertyCallbackI
v8::Isolate* isolate = info.GetIsolate();
ScriptString jsonSource = xmlHttpRequest->responseJSONSource();
- if (jsonSource.hasNoValue() || !jsonSource.v8Value()->IsString()) {
+ if (jsonSource.isEmpty()) {
v8SetReturnValue(info, v8::Null(isolate));
return;
}
// Catch syntax error.
v8::TryCatch exceptionCatcher;
-
- v8::Handle<v8::Value> json = v8::JSON::Parse(jsonSource.v8Value().As<v8::String>());
-
+ v8::Handle<v8::Value> json = v8::JSON::Parse(jsonSource.v8Value());
if (exceptionCatcher.HasCaught() || json.IsEmpty())
v8SetReturnValue(info, v8::Null(isolate));
else
v8SetReturnValue(info, json);
-
return;
}
@@ -170,20 +167,20 @@ void V8XMLHttpRequest::openMethodCustom(const v8::FunctionCallbackInfo<v8::Value
XMLHttpRequest* xmlHttpRequest = V8XMLHttpRequest::toNative(info.Holder());
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<>, method, info[0]);
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<>, urlstring, info[1]);
+ TOSTRING_VOID(V8StringResource<>, method, info[0]);
+ TOSTRING_VOID(V8StringResource<>, urlstring, info[1]);
- ExecutionContext* context = getExecutionContext();
+ ExecutionContext* context = currentExecutionContext(info.GetIsolate());
KURL url = context->completeURL(urlstring);
if (info.Length() >= 3) {
bool async = info[2]->BooleanValue();
if (info.Length() >= 4 && !info[3]->IsUndefined()) {
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<WithNullCheck>, user, info[3]);
+ TOSTRING_VOID(V8StringResource<WithNullCheck>, user, info[3]);
if (info.Length() >= 5 && !info[4]->IsUndefined()) {
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<WithNullCheck>, password, info[4]);
+ TOSTRING_VOID(V8StringResource<WithNullCheck>, password, info[4]);
xmlHttpRequest->open(method, url, async, user, password, exceptionState);
} else {
xmlHttpRequest->open(method, url, async, user, exceptionState);
@@ -198,10 +195,10 @@ void V8XMLHttpRequest::openMethodCustom(const v8::FunctionCallbackInfo<v8::Value
exceptionState.throwIfNeeded();
}
-static bool isDocumentType(v8::Handle<v8::Value> value, v8::Isolate* isolate, WrapperWorldType currentWorldType)
+static bool isDocumentType(v8::Handle<v8::Value> value, v8::Isolate* isolate)
{
// FIXME: add other document types.
- return V8Document::hasInstance(value, isolate, currentWorldType) || V8HTMLDocument::hasInstance(value, isolate, currentWorldType);
+ return V8Document::hasInstance(value, isolate) || V8HTMLDocument::hasInstance(value, isolate);
}
void V8XMLHttpRequest::sendMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
@@ -215,36 +212,35 @@ void V8XMLHttpRequest::sendMethodCustom(const v8::FunctionCallbackInfo<v8::Value
xmlHttpRequest->send(exceptionState);
else {
v8::Handle<v8::Value> arg = info[0];
- WrapperWorldType currentWorldType = worldType(info.GetIsolate());
if (isUndefinedOrNull(arg)) {
xmlHttpRequest->send(exceptionState);
- } else if (isDocumentType(arg, info.GetIsolate(), currentWorldType)) {
+ } else if (isDocumentType(arg, info.GetIsolate())) {
v8::Handle<v8::Object> object = v8::Handle<v8::Object>::Cast(arg);
Document* document = V8Document::toNative(object);
ASSERT(document);
xmlHttpRequest->send(document, exceptionState);
- } else if (V8Blob::hasInstance(arg, info.GetIsolate(), currentWorldType)) {
+ } else if (V8Blob::hasInstance(arg, info.GetIsolate())) {
v8::Handle<v8::Object> object = v8::Handle<v8::Object>::Cast(arg);
Blob* blob = V8Blob::toNative(object);
ASSERT(blob);
xmlHttpRequest->send(blob, exceptionState);
- } else if (V8FormData::hasInstance(arg, info.GetIsolate(), currentWorldType)) {
+ } else if (V8FormData::hasInstance(arg, info.GetIsolate())) {
v8::Handle<v8::Object> object = v8::Handle<v8::Object>::Cast(arg);
DOMFormData* domFormData = V8FormData::toNative(object);
ASSERT(domFormData);
xmlHttpRequest->send(domFormData, exceptionState);
- } else if (V8ArrayBuffer::hasInstance(arg, info.GetIsolate(), currentWorldType)) {
+ } else if (V8ArrayBuffer::hasInstance(arg, info.GetIsolate())) {
v8::Handle<v8::Object> object = v8::Handle<v8::Object>::Cast(arg);
ArrayBuffer* arrayBuffer = V8ArrayBuffer::toNative(object);
ASSERT(arrayBuffer);
xmlHttpRequest->send(arrayBuffer, exceptionState);
- } else if (V8ArrayBufferView::hasInstance(arg, info.GetIsolate(), currentWorldType)) {
+ } else if (V8ArrayBufferView::hasInstance(arg, info.GetIsolate())) {
v8::Handle<v8::Object> object = v8::Handle<v8::Object>::Cast(arg);
ArrayBufferView* arrayBufferView = V8ArrayBufferView::toNative(object);
ASSERT(arrayBufferView);
xmlHttpRequest->send(arrayBufferView, exceptionState);
} else {
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<WithNullCheck>, argString, arg);
+ TOSTRING_VOID(V8StringResource<WithNullCheck>, argString, arg);
xmlHttpRequest->send(argString, exceptionState);
}
}
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8XSLTProcessorCustom.cpp b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8XSLTProcessorCustom.cpp
index 7835310a652..2c7591f1dde 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/custom/V8XSLTProcessorCustom.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/V8XSLTProcessorCustom.cpp
@@ -29,11 +29,11 @@
*/
#include "config.h"
-#include "V8XSLTProcessor.h"
+#include "bindings/core/v8/V8XSLTProcessor.h"
-#include "V8Document.h"
-#include "V8DocumentFragment.h"
-#include "V8Node.h"
+#include "bindings/core/v8/V8Document.h"
+#include "bindings/core/v8/V8DocumentFragment.h"
+#include "bindings/core/v8/V8Node.h"
#include "bindings/v8/V8Binding.h"
#include "core/dom/Document.h"
#include "core/dom/DocumentFragment.h"
@@ -48,12 +48,12 @@ void V8XSLTProcessor::setParameterMethodCustom(const v8::FunctionCallbackInfo<v8
if (isUndefinedOrNull(info[1]) || isUndefinedOrNull(info[2]))
return;
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<>, namespaceURI, info[0]);
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<>, localName, info[1]);
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<>, value, info[2]);
+ TOSTRING_VOID(V8StringResource<>, namespaceURI, info[0]);
+ TOSTRING_VOID(V8StringResource<>, localName, info[1]);
+ TOSTRING_VOID(V8StringResource<>, value, info[2]);
- XSLTProcessor* imp = V8XSLTProcessor::toNative(info.Holder());
- imp->setParameter(namespaceURI, localName, value);
+ XSLTProcessor* impl = V8XSLTProcessor::toNative(info.Holder());
+ impl->setParameter(namespaceURI, localName, value);
}
void V8XSLTProcessor::getParameterMethodCustom(const v8::FunctionCallbackInfo<v8::Value>& info)
@@ -61,11 +61,11 @@ void V8XSLTProcessor::getParameterMethodCustom(const v8::FunctionCallbackInfo<v8
if (isUndefinedOrNull(info[1]))
return;
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<>, namespaceURI, info[0]);
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<>, localName, info[1]);
+ TOSTRING_VOID(V8StringResource<>, namespaceURI, info[0]);
+ TOSTRING_VOID(V8StringResource<>, localName, info[1]);
- XSLTProcessor* imp = V8XSLTProcessor::toNative(info.Holder());
- String result = imp->getParameter(namespaceURI, localName);
+ XSLTProcessor* impl = V8XSLTProcessor::toNative(info.Holder());
+ String result = impl->getParameter(namespaceURI, localName);
if (result.isNull())
return;
@@ -77,11 +77,11 @@ void V8XSLTProcessor::removeParameterMethodCustom(const v8::FunctionCallbackInfo
if (isUndefinedOrNull(info[1]))
return;
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<>, namespaceURI, info[0]);
- V8TRYCATCH_FOR_V8STRINGRESOURCE_VOID(V8StringResource<>, localName, info[1]);
+ TOSTRING_VOID(V8StringResource<>, namespaceURI, info[0]);
+ TOSTRING_VOID(V8StringResource<>, localName, info[1]);
- XSLTProcessor* imp = V8XSLTProcessor::toNative(info.Holder());
- imp->removeParameter(namespaceURI, localName);
+ XSLTProcessor* impl = V8XSLTProcessor::toNative(info.Holder());
+ impl->removeParameter(namespaceURI, localName);
}
} // namespace WebCore
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/custom/custom.gypi b/chromium/third_party/WebKit/Source/bindings/v8/custom/custom.gypi
new file mode 100644
index 00000000000..9d76a6e41ad
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/bindings/v8/custom/custom.gypi
@@ -0,0 +1,92 @@
+# Copyright 2014 The Chromium Authors. All rights reserved.
+# Use of this source code is governed by a BSD-style license that can be
+# found in the LICENSE file.
+
+{
+ 'variables': {
+ 'bindings_v8_custom_files': [
+ 'V8ArrayBufferCustom.cpp',
+ 'V8ArrayBufferCustom.h',
+ 'V8ArrayBufferViewCustom.cpp',
+ 'V8ArrayBufferViewCustom.h',
+ 'V8AudioNodeCustom.cpp',
+ 'V8BlobCustom.cpp',
+ 'V8BlobCustomHelpers.cpp',
+ 'V8BlobCustomHelpers.h',
+ 'V8CSSRuleCustom.cpp',
+ 'V8CSSStyleDeclarationCustom.cpp',
+ 'V8CSSValueCustom.cpp',
+ 'V8CanvasRenderingContext2DCustom.cpp',
+ 'V8ClientCustom.cpp',
+ 'V8CryptoCustom.cpp',
+ 'V8CustomEventCustom.cpp',
+ 'V8CustomSQLStatementErrorCallback.cpp',
+ 'V8CustomXPathNSResolver.cpp',
+ 'V8CustomXPathNSResolver.h',
+ 'V8DataViewCustom.cpp',
+ 'V8DataViewCustom.h',
+ 'V8DedicatedWorkerGlobalScopeCustom.cpp',
+ 'V8DeviceMotionEventCustom.cpp',
+ 'V8DeviceOrientationEventCustom.cpp',
+ 'V8DocumentCustom.cpp',
+ 'V8ElementCustom.cpp',
+ 'V8EntryCustom.cpp',
+ 'V8EntrySyncCustom.cpp',
+ 'V8ErrorEventCustom.cpp',
+ 'V8EventCustom.cpp',
+ 'V8EventTargetCustom.cpp',
+ 'V8FileCustom.cpp',
+ 'V8FileReaderCustom.cpp',
+ 'V8Float32ArrayCustom.h',
+ 'V8Float64ArrayCustom.h',
+ 'V8GeolocationCustom.cpp',
+ 'V8HTMLAllCollectionCustom.cpp',
+ 'V8HTMLCanvasElementCustom.cpp',
+ 'V8HTMLCollectionCustom.cpp',
+ 'V8HTMLDocumentCustom.cpp',
+ 'V8HTMLElementCustom.cpp',
+ 'V8HTMLOptionsCollectionCustom.cpp',
+ 'V8HTMLPlugInElementCustom.cpp',
+ 'V8HistoryCustom.cpp',
+ 'V8ImageDataCustom.cpp',
+ 'V8InjectedScriptHostCustom.cpp',
+ 'V8InjectedScriptManager.cpp',
+ 'V8InspectorFrontendHostCustom.cpp',
+ 'V8Int16ArrayCustom.h',
+ 'V8Int32ArrayCustom.h',
+ 'V8Int8ArrayCustom.h',
+ 'V8JavaScriptCallFrameCustom.cpp',
+ 'V8LocationCustom.cpp',
+ 'V8MessageChannelCustom.cpp',
+ 'V8MessageEventCustom.cpp',
+ 'V8MessagePortCustom.cpp',
+ 'V8MutationObserverCustom.cpp',
+ 'V8NodeCustom.cpp',
+ 'V8PerformanceEntryCustom.cpp',
+ 'V8PopStateEventCustom.cpp',
+ 'V8SQLResultSetRowListCustom.cpp',
+ 'V8SQLTransactionCustom.cpp',
+ 'V8SQLTransactionSyncCustom.cpp',
+ 'V8SVGElementCustom.cpp',
+ 'V8SVGPathSegCustom.cpp',
+ 'V8ServiceWorkerCustom.cpp',
+ 'V8StyleSheetCustom.cpp',
+ 'V8SubtleCryptoCustom.cpp',
+ 'V8TextCustom.cpp',
+ 'V8TextTrackCueCustom.cpp',
+ 'V8TrackEventCustom.cpp',
+ 'V8TypedArrayCustom.h',
+ 'V8Uint16ArrayCustom.h',
+ 'V8Uint32ArrayCustom.h',
+ 'V8Uint8ArrayCustom.h',
+ 'V8Uint8ClampedArrayCustom.h',
+ 'V8WebGLRenderingContextCustom.cpp',
+ 'V8WebKitPointCustom.cpp',
+ 'V8WindowCustom.cpp',
+ 'V8WorkerCustom.cpp',
+ 'V8WorkerGlobalScopeCustom.cpp',
+ 'V8XMLHttpRequestCustom.cpp',
+ 'V8XSLTProcessorCustom.cpp',
+ ],
+ },
+}
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/npruntime.cpp b/chromium/third_party/WebKit/Source/bindings/v8/npruntime.cpp
index d3e1755f100..182845e8810 100644
--- a/chromium/third_party/WebKit/Source/bindings/v8/npruntime.cpp
+++ b/chromium/third_party/WebKit/Source/bindings/v8/npruntime.cpp
@@ -352,7 +352,7 @@ void _NPN_InitializeVariantWithStringCopy(NPVariant* variant, const NPString* va
// The rootObjectMap is a hash table of root objects to a set of
// objects that should be deactivated in sync with the root. A
// root is defined as a top-level owner object. This is used on
-// Frame teardown to deactivate all objects associated
+// LocalFrame teardown to deactivate all objects associated
// with a particular plugin.
typedef WTF::HashSet<NPObject*> NPObjectSet;
@@ -432,7 +432,7 @@ void _NPN_UnregisterObject(NPObject* npObject)
set->remove(sub_object);
liveObjectMap().remove(sub_object);
- // Script objects hold a refernce to their DOMWindow*, which is going away if
+ // Script objects hold a refernce to their LocalDOMWindow*, which is going away if
// we're unregistering the associated owner NPObject. Clear it out.
if (V8NPObject* v8npObject = npObjectToV8NPObject(sub_object))
v8npObject->rootObject = 0;
diff --git a/chromium/third_party/WebKit/Source/bindings/v8/v8.gypi b/chromium/third_party/WebKit/Source/bindings/v8/v8.gypi
new file mode 100644
index 00000000000..a220a63087e
--- /dev/null
+++ b/chromium/third_party/WebKit/Source/bindings/v8/v8.gypi
@@ -0,0 +1,165 @@
+# Copyright 2014 The Chromium Authors. All rights reserved.
+# Use of this source code is governed by a BSD-style license that can be
+# found in the LICENSE file.
+
+{
+ 'includes': [
+ 'custom/custom.gypi',
+ ],
+ 'variables': {
+ 'bindings_v8_dir': '.',
+ 'bindings_v8_files': [
+ '<@(bindings_v8_custom_files)',
+ 'ActiveDOMCallback.cpp',
+ 'ActiveDOMCallback.h',
+ 'ArrayValue.cpp',
+ 'ArrayValue.h',
+ 'BindingSecurity.cpp',
+ 'BindingSecurity.h',
+ 'CallbackPromiseAdapter.h',
+ 'CustomElementBinding.cpp',
+ 'CustomElementBinding.h',
+ 'CustomElementConstructorBuilder.cpp',
+ 'CustomElementConstructorBuilder.h',
+ 'CustomElementWrapper.cpp',
+ 'CustomElementWrapper.h',
+ 'DOMDataStore.cpp',
+ 'DOMDataStore.h',
+ 'DOMWrapperMap.h',
+ 'DOMWrapperWorld.cpp',
+ 'DOMWrapperWorld.h',
+ 'Dictionary.cpp',
+ 'Dictionary.h',
+ 'ExceptionMessages.cpp',
+ 'ExceptionMessages.h',
+ 'ExceptionState.cpp',
+ 'ExceptionState.h',
+ 'ExceptionStatePlaceholder.cpp',
+ 'ExceptionStatePlaceholder.h',
+ 'IDBBindingUtilities.cpp',
+ 'IDBBindingUtilities.h',
+ 'NPV8Object.cpp',
+ 'NPV8Object.h',
+ 'Nullable.h',
+ 'PageScriptDebugServer.cpp',
+ 'PageScriptDebugServer.h',
+ 'RetainedDOMInfo.cpp',
+ 'RetainedDOMInfo.h',
+ 'RetainedObjectInfo.h',
+ 'ScheduledAction.cpp',
+ 'ScheduledAction.h',
+ 'ScopedPersistent.h',
+ 'ScriptCallStackFactory.cpp',
+ 'ScriptCallStackFactory.h',
+ 'ScriptController.cpp',
+ 'ScriptController.h',
+ 'ScriptDebugServer.cpp',
+ 'ScriptDebugServer.h',
+ 'ScriptEventListener.cpp',
+ 'ScriptEventListener.h',
+ 'ScriptFunction.cpp',
+ 'ScriptFunction.h',
+ 'ScriptFunctionCall.cpp',
+ 'ScriptFunctionCall.h',
+ 'ScriptGCEvent.cpp',
+ 'ScriptGCEvent.h',
+ 'ScriptHeapSnapshot.cpp',
+ 'ScriptHeapSnapshot.h',
+ 'ScriptPreprocessor.cpp',
+ 'ScriptPreprocessor.h',
+ 'ScriptProfiler.cpp',
+ 'ScriptProfiler.h',
+ 'ScriptPromise.cpp',
+ 'ScriptPromise.h',
+ 'ScriptPromiseResolver.cpp',
+ 'ScriptPromiseResolver.h',
+ 'ScriptPromiseResolverWithContext.cpp',
+ 'ScriptPromiseResolverWithContext.h',
+ 'ScriptRegexp.cpp',
+ 'ScriptRegexp.h',
+ 'ScriptSourceCode.h',
+ 'ScriptState.cpp',
+ 'ScriptState.h',
+ 'ScriptString.cpp',
+ 'ScriptString.h',
+ 'ScriptValue.cpp',
+ 'ScriptValue.h',
+ 'ScriptWrappable.h',
+ 'SerializedScriptValue.cpp',
+ 'SerializedScriptValue.h',
+ 'SharedPersistent.h',
+ 'V8AbstractEventListener.cpp',
+ 'V8AbstractEventListener.h',
+ 'V8Binding.cpp',
+ 'V8Binding.h',
+ 'V8BindingMacros.h',
+ 'V8Callback.cpp',
+ 'V8Callback.h',
+ 'V8CustomElementLifecycleCallbacks.cpp',
+ 'V8CustomElementLifecycleCallbacks.h',
+ 'V8DOMActivityLogger.cpp',
+ 'V8DOMActivityLogger.h',
+ 'V8DOMConfiguration.cpp',
+ 'V8DOMConfiguration.h',
+ 'V8DOMWrapper.cpp',
+ 'V8DOMWrapper.h',
+ 'V8ErrorHandler.cpp',
+ 'V8ErrorHandler.h',
+ 'V8EventListener.cpp',
+ 'V8EventListener.h',
+ 'V8EventListenerList.cpp',
+ 'V8EventListenerList.h',
+ 'V8GCController.cpp',
+ 'V8GCController.h',
+ 'V8GCForContextDispose.cpp',
+ 'V8GCForContextDispose.h',
+ 'V8HiddenValue.cpp',
+ 'V8HiddenValue.h',
+ 'V8Initializer.cpp',
+ 'V8Initializer.h',
+ 'V8LazyEventListener.cpp',
+ 'V8LazyEventListener.h',
+ 'V8MutationCallback.cpp',
+ 'V8MutationCallback.h',
+ 'V8NPObject.cpp',
+ 'V8NPObject.h',
+ 'V8NPUtils.cpp',
+ 'V8NPUtils.h',
+ 'V8NodeFilterCondition.cpp',
+ 'V8NodeFilterCondition.h',
+ 'V8ObjectConstructor.cpp',
+ 'V8ObjectConstructor.h',
+ 'V8PerContextData.cpp',
+ 'V8PerContextData.h',
+ 'V8PerIsolateData.cpp',
+ 'V8PerIsolateData.h',
+ 'V8RecursionScope.cpp',
+ 'V8RecursionScope.h',
+ 'V8ScriptRunner.cpp',
+ 'V8ScriptRunner.h',
+ 'V8StringResource.cpp',
+ 'V8StringResource.h',
+ 'V8ThrowException.cpp',
+ 'V8ThrowException.h',
+ 'V8ValueCache.cpp',
+ 'V8ValueCache.h',
+ 'V8WindowShell.cpp',
+ 'V8WindowShell.h',
+ 'V8WorkerGlobalScopeEventListener.cpp',
+ 'V8WorkerGlobalScopeEventListener.h',
+ 'WorkerScriptController.cpp',
+ 'WorkerScriptController.h',
+ 'WorkerScriptDebugServer.cpp',
+ 'WorkerScriptDebugServer.h',
+ 'WrapperTypeInfo.h',
+ 'npruntime.cpp',
+ 'npruntime_impl.h',
+ 'npruntime_priv.h',
+ ],
+ 'bindings_v8_unittest_files': [
+ 'IDBBindingUtilitiesTest.cpp',
+ 'ScriptPromiseResolverTest.cpp',
+ 'ScriptPromiseTest.cpp',
+ ],
+ },
+}