Index: webkit/media/buffered_data_source.cc |
diff --git a/webkit/media/buffered_data_source.cc b/webkit/media/buffered_data_source.cc |
index a766b30ab5e3230a5af72aa54b0ea4400fc175e7..0fdba21609c205a053fa36d5d161692f6e479630 100644 |
--- a/webkit/media/buffered_data_source.cc |
+++ b/webkit/media/buffered_data_source.cc |
@@ -26,6 +26,13 @@ const int kNumCacheMissRetries = 3; |
namespace webkit_media { |
+// Non-HTTP resources are assumed to be fully loaded so we ignore any |
+// loading/progress related callbacks. |
+static void NonHttpLoadingStateChangedCallback( |
+ BufferedResourceLoader::LoadingState) { |
+} |
+static void NonHttpProgressCallback(int64) {} |
+ |
BufferedDataSource::BufferedDataSource( |
MessageLoop* render_loop, |
WebFrame* frame, |
@@ -36,7 +43,6 @@ BufferedDataSource::BufferedDataSource( |
buffered_bytes_(0), |
streaming_(false), |
frame_(frame), |
- is_downloading_data_(false), |
read_size_(0), |
read_buffer_(NULL), |
last_read_start_(0), |
@@ -105,7 +111,8 @@ void BufferedDataSource::Initialize( |
loader_.reset(CreateResourceLoader(0, kPositionNotSpecified)); |
loader_->Start( |
base::Bind(&BufferedDataSource::HttpInitialStartCallback, this), |
- base::Bind(&BufferedDataSource::NetworkEventCallback, this), |
+ base::Bind(&BufferedDataSource::HttpLoadingStateChangedCallback, this), |
+ base::Bind(&BufferedDataSource::HttpProgressCallback, this), |
frame_); |
return; |
} |
@@ -117,7 +124,8 @@ void BufferedDataSource::Initialize( |
kPositionNotSpecified)); |
loader_->Start( |
base::Bind(&BufferedDataSource::NonHttpInitialStartCallback, this), |
- base::Bind(&BufferedDataSource::NetworkEventCallback, this), |
+ base::Bind(&NonHttpLoadingStateChangedCallback), |
+ base::Bind(&NonHttpProgressCallback), |
frame_); |
} |
@@ -269,12 +277,22 @@ void BufferedDataSource::RestartLoadingTask() { |
return; |
} |
+ // Start reading from where we last left off until the end of the resource. |
loader_.reset( |
CreateResourceLoader(last_read_start_, kPositionNotSpecified)); |
- loader_->Start( |
- base::Bind(&BufferedDataSource::PartialReadStartCallback, this), |
- base::Bind(&BufferedDataSource::NetworkEventCallback, this), |
- frame_); |
+ if (url_.SchemeIs(kHttpScheme) || url_.SchemeIs(kHttpsScheme)) { |
+ loader_->Start( |
+ base::Bind(&BufferedDataSource::PartialReadStartCallback, this), |
+ base::Bind(&BufferedDataSource::HttpLoadingStateChangedCallback, this), |
+ base::Bind(&BufferedDataSource::HttpProgressCallback, this), |
+ frame_); |
+ } else { |
+ loader_->Start( |
+ base::Bind(&BufferedDataSource::NonHttpInitialStartCallback, this), |
+ base::Bind(&NonHttpLoadingStateChangedCallback), |
+ base::Bind(&NonHttpProgressCallback), |
+ frame_); |
+ } |
} |
void BufferedDataSource::SetPlaybackRateTask(float playback_rate) { |
@@ -518,14 +536,8 @@ void BufferedDataSource::ReadCallback( |
bytes_read = kReadError; |
} |
- // We need to prevent calling to filter host and running the callback if |
- // we have received the stop signal. We need to lock down the whole callback |
- // method to prevent bad things from happening. The reason behind this is |
- // that we cannot guarantee tasks on render thread have completely stopped |
- // when we receive the Stop() method call. So only way to solve this is to |
- // let tasks on render thread to run but make sure they don't call outside |
- // this object when Stop() method is ever called. Locking this method is safe |
- // because |lock_| is only acquired in tasks on render thread. |
+ // TODO(scherkus): we shouldn't have to lock to signal host(), see |
+ // http://crbug.com/113712 for details. |
base::AutoLock auto_lock(lock_); |
if (stop_signal_received_) |
return; |
@@ -547,42 +559,55 @@ void BufferedDataSource::ReadCallback( |
DoneRead_Locked(bytes_read); |
} |
-void BufferedDataSource::NetworkEventCallback() { |
+void BufferedDataSource::HttpLoadingStateChangedCallback( |
+ BufferedResourceLoader::LoadingState state) { |
DCHECK(MessageLoop::current() == render_loop_); |
- DCHECK(loader_.get()); |
+ DCHECK(url_.SchemeIs(kHttpScheme) || url_.SchemeIs(kHttpsScheme)); |
- // In case of non-HTTP request we don't need to report network events, |
- // so return immediately. |
- if (!url_.SchemeIs(kHttpScheme) && !url_.SchemeIs(kHttpsScheme)) |
+ // TODO(scherkus): we shouldn't have to lock to signal host(), see |
+ // http://crbug.com/113712 for details. |
+ base::AutoLock auto_lock(lock_); |
+ if (stop_signal_received_) |
return; |
- downloading_cb_.Run(loader_->is_downloading_data()); |
+ bool is_downloading_data; |
+ switch (state) { |
+ case BufferedResourceLoader::kLoading: |
+ is_downloading_data = true; |
+ break; |
+ case BufferedResourceLoader::kLoadingDeferred: |
+ is_downloading_data = false; |
+ break; |
+ |
+ // TODO(scherkus): we don't signal network activity changes when loads |
+ // complete or fail to preserve existing behaviour when deferring is |
+ // toggled, however we considering changing DownloadingCB to also |
+ // propagate loading state. For example there isn't any signal today |
+ // to notify the client that loading has failed/finished (we only get |
+ // errors on subsequent reads). |
+ case BufferedResourceLoader::kLoadingFailed: |
+ case BufferedResourceLoader::kLoadingFinished: |
+ return; |
+ } |
- int64 current_buffered_position = loader_->GetBufferedPosition(); |
+ downloading_cb_.Run(is_downloading_data); |
Ami GONE FROM CHROMIUM
2012/07/10 02:43:53
This is now run under lock, where it didn't use to
scherkus (not reviewing)
2012/07/10 04:10:53
I don't *think* it should be an issue, but now tha
|
+} |
- // If we get an unspecified value, return immediately. |
- if (current_buffered_position == kPositionNotSpecified) |
- return; |
+void BufferedDataSource::HttpProgressCallback(int64 position) { |
+ DCHECK(MessageLoop::current() == render_loop_); |
+ DCHECK(url_.SchemeIs(kHttpScheme) || url_.SchemeIs(kHttpsScheme)); |
- // We need to prevent calling to filter host and running the callback if |
- // we have received the stop signal. We need to lock down the whole callback |
- // method to prevent bad things from happening. The reason behind this is |
- // that we cannot guarantee tasks on render thread have completely stopped |
- // when we receive the Stop() method call. So only way to solve this is to |
- // let tasks on render thread to run but make sure they don't call outside |
- // this object when Stop() method is ever called. Locking this method is safe |
- // because |lock_| is only acquired in tasks on render thread. |
+ // TODO(scherkus): we shouldn't have to lock to signal host(), see |
+ // http://crbug.com/113712 for details. |
base::AutoLock auto_lock(lock_); |
if (stop_signal_received_) |
return; |
- int64 start = loader_->first_byte_position(); |
- if (host() && current_buffered_position > start) |
- host()->AddBufferedByteRange(start, current_buffered_position); |
+ if (host() && position > last_read_start_) |
+ host()->AddBufferedByteRange(last_read_start_, position); |
} |
void BufferedDataSource::UpdateHostState_Locked() { |
- // Called from various threads, under lock. |
lock_.AssertAcquired(); |
if (!host()) |