| OLD | NEW |
| 1 // Copyright 2015 The Chromium Authors. All rights reserved. | 1 // Copyright 2015 The Chromium Authors. All rights reserved. |
| 2 // Use of this source code is governed by a BSD-style license that can be | 2 // Use of this source code is governed by a BSD-style license that can be |
| 3 // found in the LICENSE file. | 3 // found in the LICENSE file. |
| 4 | 4 |
| 5 #include "modules/fetch/DataConsumerTee.h" | 5 #include "modules/fetch/DataConsumerTee.h" |
| 6 | 6 |
| 7 #include "core/dom/ActiveDOMObject.h" | 7 #include "core/dom/ActiveDOMObject.h" |
| 8 #include "core/dom/ExecutionContext.h" | 8 #include "core/dom/ExecutionContext.h" |
| 9 #include "modules/fetch/DataConsumerHandleUtil.h" | 9 #include "modules/fetch/DataConsumerHandleUtil.h" |
| 10 #include "modules/fetch/FetchBlobDataConsumerHandle.h" | 10 #include "modules/fetch/FetchBlobDataConsumerHandle.h" |
| (...skipping 142 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 153 std::unique_ptr<Vector<char>> data = wrapUnique(new Vector<char>); | 153 std::unique_ptr<Vector<char>> data = wrapUnique(new Vector<char>); |
| 154 data->append(buffer, size); | 154 data->append(buffer, size); |
| 155 m_queue.append(std::move(data)); | 155 m_queue.append(std::move(data)); |
| 156 } | 156 } |
| 157 if (needsNotification) | 157 if (needsNotification) |
| 158 notify(); | 158 notify(); |
| 159 } | 159 } |
| 160 | 160 |
| 161 void setResult(Result r) | 161 void setResult(Result r) |
| 162 { | 162 { |
| 163 ASSERT(r != WebDataConsumerHandle::Ok); | 163 DCHECK(r != WebDataConsumerHandle::Ok); |
| 164 ASSERT(r != WebDataConsumerHandle::ShouldWait); | 164 DCHECK(r != WebDataConsumerHandle::ShouldWait); |
| 165 { | 165 { |
| 166 MutexLocker locker(m_mutex); | 166 MutexLocker locker(m_mutex); |
| 167 if (m_result != WebDataConsumerHandle::ShouldWait) { | 167 if (m_result != WebDataConsumerHandle::ShouldWait) { |
| 168 // The result was already set. | 168 // The result was already set. |
| 169 return; | 169 return; |
| 170 } | 170 } |
| 171 m_result = r; | 171 m_result = r; |
| 172 if (r != WebDataConsumerHandle::Done && !m_isTwoPhaseReadInProgress) | 172 if (r != WebDataConsumerHandle::Done && !m_isTwoPhaseReadInProgress) |
| 173 m_queue.clear(); | 173 m_queue.clear(); |
| 174 } | 174 } |
| 175 notify(); | 175 notify(); |
| 176 } | 176 } |
| 177 | 177 |
| 178 void notify() | 178 void notify() |
| 179 { | 179 { |
| 180 { | 180 { |
| 181 MutexLocker locker(m_mutex); | 181 MutexLocker locker(m_mutex); |
| 182 if (!m_client) { | 182 if (!m_client) { |
| 183 // No client is registered. | 183 // No client is registered. |
| 184 return; | 184 return; |
| 185 } | 185 } |
| 186 ASSERT(m_readerThread); | 186 DCHECK(m_readerThread); |
| 187 if (!m_readerThread->isCurrentThread()) { | 187 if (!m_readerThread->isCurrentThread()) { |
| 188 m_readerThread->getWebTaskRunner()->postTask(BLINK_FROM_HERE, cr
ossThreadBind(&DestinationContext::notify, wrapPassRefPtr(this))); | 188 m_readerThread->getWebTaskRunner()->postTask(BLINK_FROM_HERE, cr
ossThreadBind(&DestinationContext::notify, wrapPassRefPtr(this))); |
| 189 return; | 189 return; |
| 190 } | 190 } |
| 191 } | 191 } |
| 192 // The reading thread is the current thread. | 192 // The reading thread is the current thread. |
| 193 if (m_client) | 193 if (m_client) |
| 194 m_client->didGetReadable(); | 194 m_client->didGetReadable(); |
| 195 } | 195 } |
| 196 | 196 |
| 197 Mutex& mutex() { return m_mutex; } | 197 Mutex& mutex() { return m_mutex; } |
| 198 | 198 |
| 199 // The following functions don't use lock. They should be protected by the | 199 // The following functions don't use lock. They should be protected by the |
| 200 // caller. | 200 // caller. |
| 201 void attachReader(WebDataConsumerHandle::Client* client) | 201 void attachReader(WebDataConsumerHandle::Client* client) |
| 202 { | 202 { |
| 203 ASSERT(!m_readerThread); | 203 DCHECK(!m_readerThread); |
| 204 ASSERT(!m_client); | 204 DCHECK(!m_client); |
| 205 m_readerThread = Platform::current()->currentThread(); | 205 m_readerThread = Platform::current()->currentThread(); |
| 206 m_client = client; | 206 m_client = client; |
| 207 } | 207 } |
| 208 void detachReader() | 208 void detachReader() |
| 209 { | 209 { |
| 210 ASSERT(m_readerThread && m_readerThread->isCurrentThread()); | 210 DCHECK(m_readerThread && m_readerThread->isCurrentThread()); |
| 211 m_readerThread = nullptr; | 211 m_readerThread = nullptr; |
| 212 m_client = nullptr; | 212 m_client = nullptr; |
| 213 } | 213 } |
| 214 const std::unique_ptr<Vector<char>>& top() const { return m_queue.first(); } | 214 const std::unique_ptr<Vector<char>>& top() const { return m_queue.first(); } |
| 215 bool isEmpty() const { return m_queue.isEmpty(); } | 215 bool isEmpty() const { return m_queue.isEmpty(); } |
| 216 size_t offset() const { return m_offset; } | 216 size_t offset() const { return m_offset; } |
| 217 void consume(size_t size) | 217 void consume(size_t size) |
| 218 { | 218 { |
| 219 const auto& top = m_queue.first(); | 219 const auto& top = m_queue.first(); |
| 220 ASSERT(m_offset <= m_offset + size); | 220 DCHECK(m_offset <= m_offset + size); |
| 221 ASSERT(m_offset + size <= top->size()); | 221 DCHECK(m_offset + size <= top->size()); |
| 222 if (top->size() <= m_offset + size) { | 222 if (top->size() <= m_offset + size) { |
| 223 m_offset = 0; | 223 m_offset = 0; |
| 224 m_queue.removeFirst(); | 224 m_queue.removeFirst(); |
| 225 } else { | 225 } else { |
| 226 m_offset += size; | 226 m_offset += size; |
| 227 } | 227 } |
| 228 } | 228 } |
| 229 Result getResult() { return m_result; } | 229 Result getResult() { return m_result; } |
| 230 | 230 |
| 231 private: | 231 private: |
| 232 DestinationContext() | 232 DestinationContext() |
| 233 : m_result(WebDataConsumerHandle::ShouldWait) | 233 : m_result(WebDataConsumerHandle::ShouldWait) |
| 234 , m_readerThread(nullptr) | 234 , m_readerThread(nullptr) |
| 235 , m_client(nullptr) | 235 , m_client(nullptr) |
| 236 , m_offset(0) | 236 , m_offset(0) |
| 237 , m_isTwoPhaseReadInProgress(false) | 237 , m_isTwoPhaseReadInProgress(false) |
| 238 { | 238 { |
| 239 } | 239 } |
| 240 | 240 |
| 241 void detach() | 241 void detach() |
| 242 { | 242 { |
| 243 MutexLocker locker(m_mutex); | 243 MutexLocker locker(m_mutex); |
| 244 ASSERT(!m_client); | 244 DCHECK(!m_client); |
| 245 ASSERT(!m_readerThread); | 245 DCHECK(!m_readerThread); |
| 246 m_queue.clear(); | 246 m_queue.clear(); |
| 247 } | 247 } |
| 248 | 248 |
| 249 Result m_result; | 249 Result m_result; |
| 250 Deque<std::unique_ptr<Vector<char>>> m_queue; | 250 Deque<std::unique_ptr<Vector<char>>> m_queue; |
| 251 // Note: Holding a WebThread raw pointer is not generally safe, but we can | 251 // Note: Holding a WebThread raw pointer is not generally safe, but we can |
| 252 // do that in this case because: | 252 // do that in this case because: |
| 253 // 1. Destructing a ReaderImpl when the bound thread ends is a user's | 253 // 1. Destructing a ReaderImpl when the bound thread ends is a user's |
| 254 // responsibility. | 254 // responsibility. |
| 255 // 2. |m_readerThread| will never be used after the associated reader is | 255 // 2. |m_readerThread| will never be used after the associated reader is |
| (...skipping 87 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 343 { | 343 { |
| 344 suspendIfNeeded(); | 344 suspendIfNeeded(); |
| 345 } | 345 } |
| 346 ~SourceContext() override | 346 ~SourceContext() override |
| 347 { | 347 { |
| 348 stopInternal(); | 348 stopInternal(); |
| 349 } | 349 } |
| 350 | 350 |
| 351 void didGetReadable() override | 351 void didGetReadable() override |
| 352 { | 352 { |
| 353 ASSERT(m_reader); | 353 DCHECK(m_reader); |
| 354 Result r = WebDataConsumerHandle::Ok; | 354 Result r = WebDataConsumerHandle::Ok; |
| 355 while (true) { | 355 while (true) { |
| 356 const void* buffer = nullptr; | 356 const void* buffer = nullptr; |
| 357 size_t available = 0; | 357 size_t available = 0; |
| 358 r = m_reader->beginRead(&buffer, WebDataConsumerHandle::FlagNone, &a
vailable); | 358 r = m_reader->beginRead(&buffer, WebDataConsumerHandle::FlagNone, &a
vailable); |
| 359 if (r == WebDataConsumerHandle::ShouldWait) | 359 if (r == WebDataConsumerHandle::ShouldWait) |
| 360 return; | 360 return; |
| 361 if (r != WebDataConsumerHandle::Ok) | 361 if (r != WebDataConsumerHandle::Ok) |
| 362 break; | 362 break; |
| 363 m_dest1->enqueue(static_cast<const char*>(buffer), available); | 363 m_dest1->enqueue(static_cast<const char*>(buffer), available); |
| (...skipping 62 matching lines...) Expand 10 before | Expand all | Expand 10 after Loading... |
| 426 } | 426 } |
| 427 | 427 |
| 428 std::unique_ptr<WebDataConsumerHandle> webDest1, webDest2; | 428 std::unique_ptr<WebDataConsumerHandle> webDest1, webDest2; |
| 429 DataConsumerTee::create(executionContext, static_cast<std::unique_ptr<WebDat
aConsumerHandle>>(std::move(src)), &webDest1, &webDest2); | 429 DataConsumerTee::create(executionContext, static_cast<std::unique_ptr<WebDat
aConsumerHandle>>(std::move(src)), &webDest1, &webDest2); |
| 430 *dest1 = createFetchDataConsumerHandleFromWebHandle(std::move(webDest1)); | 430 *dest1 = createFetchDataConsumerHandleFromWebHandle(std::move(webDest1)); |
| 431 *dest2 = createFetchDataConsumerHandleFromWebHandle(std::move(webDest2)); | 431 *dest2 = createFetchDataConsumerHandleFromWebHandle(std::move(webDest2)); |
| 432 return; | 432 return; |
| 433 } | 433 } |
| 434 | 434 |
| 435 } // namespace blink | 435 } // namespace blink |
| OLD | NEW |