commit-queue@webkit.org | 2620909 | 2017-08-30 00:39:26 +0000 | [diff] [blame] | 1 | /* |
mark.lam@apple.com | 6452c9d | 2020-07-03 05:51:58 +0000 | [diff] [blame] | 2 | * Copyright (C) 2017-2020 Apple Inc. All rights reserved. |
commit-queue@webkit.org | 2620909 | 2017-08-30 00:39:26 +0000 | [diff] [blame] | 3 | * |
| 4 | * Redistribution and use in source and binary forms, with or without |
| 5 | * modification, are permitted provided that the following conditions |
| 6 | * are met: |
| 7 | * 1. Redistributions of source code must retain the above copyright |
| 8 | * notice, this list of conditions and the following disclaimer. |
| 9 | * 2. Redistributions in binary form must reproduce the above copyright |
| 10 | * notice, this list of conditions and the following disclaimer in the |
| 11 | * documentation and/or other materials provided with the distribution. |
| 12 | * |
| 13 | * THIS SOFTWARE IS PROVIDED BY CANON INC. ``AS IS'' AND ANY |
| 14 | * EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE |
| 15 | * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR |
| 16 | * PURPOSE ARE DISCLAIMED. IN NO EVENT SHALL CANON INC. OR |
| 17 | * CONTRIBUTORS BE LIABLE FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, |
| 18 | * EXEMPLARY, OR CONSEQUENTIAL DAMAGES (INCLUDING, BUT NOT LIMITED TO, |
| 19 | * PROCUREMENT OF SUBSTITUTE GOODS OR SERVICES; LOSS OF USE, DATA, OR |
| 20 | * PROFITS; OR BUSINESS INTERRUPTION) HOWEVER CAUSED AND ON ANY THEORY |
| 21 | * OF LIABILITY, WHETHER IN CONTRACT, STRICT LIABILITY, OR TORT |
| 22 | * (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY OUT OF THE USE |
| 23 | * OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF SUCH DAMAGE. |
| 24 | */ |
| 25 | |
| 26 | #include "config.h" |
| 27 | #include "ReadableStream.h" |
| 28 | |
mark.lam@apple.com | 6452c9d | 2020-07-03 05:51:58 +0000 | [diff] [blame] | 29 | #include "Exception.h" |
| 30 | #include "ExceptionCode.h" |
commit-queue@webkit.org | a57234a | 2017-08-31 20:03:42 +0000 | [diff] [blame] | 31 | #include "JSDOMConvertSequences.h" |
commit-queue@webkit.org | 48672fa | 2017-09-01 22:53:23 +0000 | [diff] [blame] | 32 | #include "JSReadableStreamSink.h" |
commit-queue@webkit.org | 2620909 | 2017-08-30 00:39:26 +0000 | [diff] [blame] | 33 | #include "JSReadableStreamSource.h" |
| 34 | #include "WebCoreJSClientData.h" |
| 35 | |
commit-queue@webkit.org | 2620909 | 2017-08-30 00:39:26 +0000 | [diff] [blame] | 36 | |
| 37 | namespace WebCore { |
keith_miller@apple.com | ce64b73 | 2017-10-17 07:10:58 +0000 | [diff] [blame] | 38 | using namespace JSC; |
commit-queue@webkit.org | 2620909 | 2017-08-30 00:39:26 +0000 | [diff] [blame] | 39 | |
mark.lam@apple.com | 6452c9d | 2020-07-03 05:51:58 +0000 | [diff] [blame] | 40 | ExceptionOr<Ref<ReadableStream>> ReadableStream::create(JSC::JSGlobalObject& lexicalGlobalObject, RefPtr<ReadableStreamSource>&& source) |
commit-queue@webkit.org | 2620909 | 2017-08-30 00:39:26 +0000 | [diff] [blame] | 41 | { |
ysuzuki@apple.com | 52e98bb | 2019-10-22 09:24:48 +0000 | [diff] [blame] | 42 | VM& vm = lexicalGlobalObject.vm(); |
mark.lam@apple.com | 6452c9d | 2020-07-03 05:51:58 +0000 | [diff] [blame] | 43 | auto scope = DECLARE_THROW_SCOPE(vm); |
commit-queue@webkit.org | 47214d9 | 2017-09-07 23:23:57 +0000 | [diff] [blame] | 44 | |
commit-queue@webkit.org | 2620909 | 2017-08-30 00:39:26 +0000 | [diff] [blame] | 45 | auto& clientData = *static_cast<JSVMClientData*>(vm.clientData); |
ysuzuki@apple.com | 52e98bb | 2019-10-22 09:24:48 +0000 | [diff] [blame] | 46 | auto& globalObject = *JSC::jsCast<JSDOMGlobalObject*>(&lexicalGlobalObject); |
commit-queue@webkit.org | 2620909 | 2017-08-30 00:39:26 +0000 | [diff] [blame] | 47 | |
ysuzuki@apple.com | 52e98bb | 2019-10-22 09:24:48 +0000 | [diff] [blame] | 48 | auto* constructor = JSC::asObject(globalObject.get(&lexicalGlobalObject, clientData.builtinNames().ReadableStreamPrivateName())); |
commit-queue@webkit.org | 2620909 | 2017-08-30 00:39:26 +0000 | [diff] [blame] | 49 | |
ross.kirsling@sony.com | 924e750 | 2020-04-27 09:09:32 +0000 | [diff] [blame] | 50 | auto constructData = getConstructData(vm, constructor); |
| 51 | ASSERT(constructData.type != CallData::Type::None); |
commit-queue@webkit.org | 2620909 | 2017-08-30 00:39:26 +0000 | [diff] [blame] | 52 | |
| 53 | MarkedArgumentBuffer args; |
ysuzuki@apple.com | 52e98bb | 2019-10-22 09:24:48 +0000 | [diff] [blame] | 54 | args.append(source ? toJSNewlyCreated(&lexicalGlobalObject, &globalObject, source.releaseNonNull()) : JSC::jsUndefined()); |
mark.lam@apple.com | aad2231 | 2017-11-02 01:54:43 +0000 | [diff] [blame] | 55 | ASSERT(!args.hasOverflowed()); |
commit-queue@webkit.org | 2620909 | 2017-08-30 00:39:26 +0000 | [diff] [blame] | 56 | |
mark.lam@apple.com | 6452c9d | 2020-07-03 05:51:58 +0000 | [diff] [blame] | 57 | JSObject* object = JSC::construct(&lexicalGlobalObject, constructor, constructData, args); |
| 58 | ASSERT(!!scope.exception() == !object); |
| 59 | RETURN_IF_EXCEPTION(scope, Exception { ExistingExceptionError }); |
commit-queue@webkit.org | 2620909 | 2017-08-30 00:39:26 +0000 | [diff] [blame] | 60 | |
mark.lam@apple.com | 6452c9d | 2020-07-03 05:51:58 +0000 | [diff] [blame] | 61 | return create(globalObject, *jsCast<JSReadableStream*>(object)); |
commit-queue@webkit.org | 2620909 | 2017-08-30 00:39:26 +0000 | [diff] [blame] | 62 | } |
| 63 | |
keith_miller@apple.com | ce64b73 | 2017-10-17 07:10:58 +0000 | [diff] [blame] | 64 | namespace ReadableStreamInternal { |
ysuzuki@apple.com | 52e98bb | 2019-10-22 09:24:48 +0000 | [diff] [blame] | 65 | static inline JSC::JSValue callFunction(JSC::JSGlobalObject& lexicalGlobalObject, JSC::JSValue jsFunction, JSC::JSValue thisValue, const JSC::ArgList& arguments) |
commit-queue@webkit.org | 9a040ee | 2017-09-06 21:25:19 +0000 | [diff] [blame] | 66 | { |
ysuzuki@apple.com | 52e98bb | 2019-10-22 09:24:48 +0000 | [diff] [blame] | 67 | VM& vm = lexicalGlobalObject.vm(); |
utatane.tea@gmail.com | b860d69 | 2018-05-31 06:19:33 +0000 | [diff] [blame] | 68 | auto scope = DECLARE_CATCH_SCOPE(vm); |
ross.kirsling@sony.com | 924e750 | 2020-04-27 09:09:32 +0000 | [diff] [blame] | 69 | auto callData = JSC::getCallData(vm, jsFunction); |
| 70 | ASSERT(callData.type != JSC::CallData::Type::None); |
| 71 | auto result = call(&lexicalGlobalObject, jsFunction, callData, thisValue, arguments); |
commit-queue@webkit.org | 9a040ee | 2017-09-06 21:25:19 +0000 | [diff] [blame] | 72 | scope.assertNoException(); |
| 73 | return result; |
| 74 | } |
keith_miller@apple.com | ce64b73 | 2017-10-17 07:10:58 +0000 | [diff] [blame] | 75 | } |
commit-queue@webkit.org | 9a040ee | 2017-09-06 21:25:19 +0000 | [diff] [blame] | 76 | |
commit-queue@webkit.org | 48672fa | 2017-09-01 22:53:23 +0000 | [diff] [blame] | 77 | void ReadableStream::pipeTo(ReadableStreamSink& sink) |
| 78 | { |
ysuzuki@apple.com | 52e98bb | 2019-10-22 09:24:48 +0000 | [diff] [blame] | 79 | auto& lexicalGlobalObject = *m_globalObject; |
| 80 | JSVMClientData* clientData = static_cast<JSVMClientData*>(lexicalGlobalObject.vm().clientData); |
commit-queue@webkit.org | 48672fa | 2017-09-01 22:53:23 +0000 | [diff] [blame] | 81 | const Identifier& privateName = clientData->builtinFunctions().readableStreamInternalsBuiltins().readableStreamPipeToPrivateName(); |
| 82 | |
ysuzuki@apple.com | 52e98bb | 2019-10-22 09:24:48 +0000 | [diff] [blame] | 83 | auto readableStreamPipeTo = m_globalObject->get(&lexicalGlobalObject, privateName); |
ross.kirsling@sony.com | 5e63a21 | 2020-04-28 21:51:37 +0000 | [diff] [blame] | 84 | ASSERT(readableStreamPipeTo.isCallable(lexicalGlobalObject.vm())); |
commit-queue@webkit.org | 48672fa | 2017-09-01 22:53:23 +0000 | [diff] [blame] | 85 | |
commit-queue@webkit.org | 48672fa | 2017-09-01 22:53:23 +0000 | [diff] [blame] | 86 | MarkedArgumentBuffer arguments; |
| 87 | arguments.append(readableStream()); |
ysuzuki@apple.com | 52e98bb | 2019-10-22 09:24:48 +0000 | [diff] [blame] | 88 | arguments.append(toJS(&lexicalGlobalObject, m_globalObject.get(), sink)); |
mark.lam@apple.com | aad2231 | 2017-11-02 01:54:43 +0000 | [diff] [blame] | 89 | ASSERT(!arguments.hasOverflowed()); |
ysuzuki@apple.com | 52e98bb | 2019-10-22 09:24:48 +0000 | [diff] [blame] | 90 | ReadableStreamInternal::callFunction(lexicalGlobalObject, readableStreamPipeTo, JSC::jsUndefined(), arguments); |
commit-queue@webkit.org | 48672fa | 2017-09-01 22:53:23 +0000 | [diff] [blame] | 91 | } |
| 92 | |
commit-queue@webkit.org | a57234a | 2017-08-31 20:03:42 +0000 | [diff] [blame] | 93 | std::pair<Ref<ReadableStream>, Ref<ReadableStream>> ReadableStream::tee() |
| 94 | { |
ysuzuki@apple.com | 52e98bb | 2019-10-22 09:24:48 +0000 | [diff] [blame] | 95 | auto& lexicalGlobalObject = *m_globalObject; |
| 96 | JSVMClientData* clientData = static_cast<JSVMClientData*>(lexicalGlobalObject.vm().clientData); |
commit-queue@webkit.org | a57234a | 2017-08-31 20:03:42 +0000 | [diff] [blame] | 97 | const Identifier& privateName = clientData->builtinFunctions().readableStreamInternalsBuiltins().readableStreamTeePrivateName(); |
| 98 | |
ysuzuki@apple.com | 52e98bb | 2019-10-22 09:24:48 +0000 | [diff] [blame] | 99 | auto readableStreamTee = m_globalObject->get(&lexicalGlobalObject, privateName); |
ross.kirsling@sony.com | 5e63a21 | 2020-04-28 21:51:37 +0000 | [diff] [blame] | 100 | ASSERT(readableStreamTee.isCallable(lexicalGlobalObject.vm())); |
commit-queue@webkit.org | a57234a | 2017-08-31 20:03:42 +0000 | [diff] [blame] | 101 | |
commit-queue@webkit.org | a57234a | 2017-08-31 20:03:42 +0000 | [diff] [blame] | 102 | MarkedArgumentBuffer arguments; |
| 103 | arguments.append(readableStream()); |
| 104 | arguments.append(JSC::jsBoolean(true)); |
mark.lam@apple.com | aad2231 | 2017-11-02 01:54:43 +0000 | [diff] [blame] | 105 | ASSERT(!arguments.hasOverflowed()); |
ysuzuki@apple.com | 52e98bb | 2019-10-22 09:24:48 +0000 | [diff] [blame] | 106 | auto returnedValue = ReadableStreamInternal::callFunction(lexicalGlobalObject, readableStreamTee, JSC::jsUndefined(), arguments); |
commit-queue@webkit.org | a57234a | 2017-08-31 20:03:42 +0000 | [diff] [blame] | 107 | |
ysuzuki@apple.com | 52e98bb | 2019-10-22 09:24:48 +0000 | [diff] [blame] | 108 | auto results = Detail::SequenceConverter<IDLInterface<ReadableStream>>::convert(lexicalGlobalObject, returnedValue); |
commit-queue@webkit.org | a57234a | 2017-08-31 20:03:42 +0000 | [diff] [blame] | 109 | |
| 110 | ASSERT(results.size() == 2); |
| 111 | return std::make_pair(results[0].releaseNonNull(), results[1].releaseNonNull()); |
| 112 | } |
| 113 | |
commit-queue@webkit.org | 47214d9 | 2017-09-07 23:23:57 +0000 | [diff] [blame] | 114 | void ReadableStream::lock() |
| 115 | { |
ysuzuki@apple.com | 52e98bb | 2019-10-22 09:24:48 +0000 | [diff] [blame] | 116 | auto& lexicalGlobalObject = *m_globalObject; |
| 117 | VM& vm = lexicalGlobalObject.vm(); |
commit-queue@webkit.org | 47214d9 | 2017-09-07 23:23:57 +0000 | [diff] [blame] | 118 | auto scope = DECLARE_CATCH_SCOPE(vm); |
| 119 | |
| 120 | auto& clientData = *static_cast<JSVMClientData*>(vm.clientData); |
| 121 | |
ysuzuki@apple.com | 52e98bb | 2019-10-22 09:24:48 +0000 | [diff] [blame] | 122 | auto* constructor = JSC::asObject(m_globalObject->get(&lexicalGlobalObject, clientData.builtinNames().ReadableStreamDefaultReaderPrivateName())); |
commit-queue@webkit.org | 47214d9 | 2017-09-07 23:23:57 +0000 | [diff] [blame] | 123 | |
ross.kirsling@sony.com | 924e750 | 2020-04-27 09:09:32 +0000 | [diff] [blame] | 124 | auto constructData = getConstructData(vm, constructor); |
| 125 | ASSERT(constructData.type != CallData::Type::None); |
commit-queue@webkit.org | 47214d9 | 2017-09-07 23:23:57 +0000 | [diff] [blame] | 126 | |
| 127 | MarkedArgumentBuffer args; |
| 128 | args.append(readableStream()); |
mark.lam@apple.com | aad2231 | 2017-11-02 01:54:43 +0000 | [diff] [blame] | 129 | ASSERT(!args.hasOverflowed()); |
commit-queue@webkit.org | 47214d9 | 2017-09-07 23:23:57 +0000 | [diff] [blame] | 130 | |
ross.kirsling@sony.com | 924e750 | 2020-04-27 09:09:32 +0000 | [diff] [blame] | 131 | JSC::construct(&lexicalGlobalObject, constructor, constructData, args); |
commit-queue@webkit.org | 47214d9 | 2017-09-07 23:23:57 +0000 | [diff] [blame] | 132 | scope.assertNoException(); |
| 133 | } |
| 134 | |
commit-queue@webkit.org | 9a040ee | 2017-09-06 21:25:19 +0000 | [diff] [blame] | 135 | static inline bool checkReadableStream(JSDOMGlobalObject& globalObject, JSReadableStream* readableStream, JSC::JSValue function) |
| 136 | { |
ysuzuki@apple.com | 52e98bb | 2019-10-22 09:24:48 +0000 | [diff] [blame] | 137 | auto& lexicalGlobalObject = globalObject; |
commit-queue@webkit.org | 9a040ee | 2017-09-06 21:25:19 +0000 | [diff] [blame] | 138 | |
| 139 | ASSERT(function); |
| 140 | JSC::MarkedArgumentBuffer arguments; |
| 141 | arguments.append(readableStream); |
mark.lam@apple.com | aad2231 | 2017-11-02 01:54:43 +0000 | [diff] [blame] | 142 | ASSERT(!arguments.hasOverflowed()); |
ysuzuki@apple.com | 52e98bb | 2019-10-22 09:24:48 +0000 | [diff] [blame] | 143 | return ReadableStreamInternal::callFunction(lexicalGlobalObject, function, JSC::jsUndefined(), arguments).isTrue(); |
commit-queue@webkit.org | 9a040ee | 2017-09-06 21:25:19 +0000 | [diff] [blame] | 144 | } |
| 145 | |
| 146 | bool ReadableStream::isLocked() const |
| 147 | { |
| 148 | return checkReadableStream(*globalObject(), readableStream(), globalObject()->builtinInternalFunctions().readableStreamInternals().m_isReadableStreamLockedFunction.get()); |
| 149 | } |
| 150 | |
| 151 | bool ReadableStream::isDisturbed() const |
| 152 | { |
| 153 | return checkReadableStream(*globalObject(), readableStream(), globalObject()->builtinInternalFunctions().readableStreamInternals().m_isReadableStreamDisturbedFunction.get()); |
| 154 | } |
| 155 | |
ysuzuki@apple.com | 52e98bb | 2019-10-22 09:24:48 +0000 | [diff] [blame] | 156 | bool ReadableStream::isDisturbed(JSGlobalObject& lexicalGlobalObject, JSValue value) |
commit-queue@webkit.org | 9a040ee | 2017-09-06 21:25:19 +0000 | [diff] [blame] | 157 | { |
ysuzuki@apple.com | 52e98bb | 2019-10-22 09:24:48 +0000 | [diff] [blame] | 158 | auto& vm = lexicalGlobalObject.vm(); |
| 159 | auto& globalObject = *jsDynamicCast<JSDOMGlobalObject*>(vm, &lexicalGlobalObject); |
utatane.tea@gmail.com | 5ec91b7 | 2018-03-08 18:38:09 +0000 | [diff] [blame] | 160 | auto* readableStream = jsDynamicCast<JSReadableStream*>(vm, value); |
commit-queue@webkit.org | 9a040ee | 2017-09-06 21:25:19 +0000 | [diff] [blame] | 161 | |
| 162 | return checkReadableStream(globalObject, readableStream, globalObject.builtinInternalFunctions().readableStreamInternals().m_isReadableStreamDisturbedFunction.get()); |
| 163 | } |
| 164 | |
commit-queue@webkit.org | 2620909 | 2017-08-30 00:39:26 +0000 | [diff] [blame] | 165 | } |