Bug 1395017. P1 - dispatch a task to the main thread to update the principal when necessary. r=cpearce

MozReview-Commit-ID: BWyDmKglWsl

--HG--
extra : rebase_source : 5931a534ac880828a03a39afda87402c2b81dbbc
extra : intermediate-source : fc38148a0fb851d714da7ed477c8232a327daac0
extra : source : 4150f78ba66d820509b0bae87cc47e39c2f4ade1
This commit is contained in:
JW Wang 2017-08-29 17:57:00 +08:00
Родитель c4131f69bd
Коммит eef07d01d2
4 изменённых файлов: 45 добавлений и 40 удалений

Просмотреть файл

@ -1876,8 +1876,7 @@ MediaCacheStream::UpdatePrincipal(nsIPrincipal* aPrincipal)
}
void
MediaCacheStream::NotifyDataReceived(int64_t aSize, const char* aData,
nsIPrincipal* aPrincipal)
MediaCacheStream::NotifyDataReceived(int64_t aSize, const char* aData)
{
// This might happen off the main thread.
MOZ_DIAGNOSTIC_ASSERT(!mClosed);
@ -1890,9 +1889,7 @@ MediaCacheStream::NotifyDataReceived(int64_t aSize, const char* aData,
{
MediaCache::ResourceStreamIterator iter(mMediaCache, mResourceID);
while (MediaCacheStream* stream = iter.Next()) {
if (stream->UpdatePrincipal(aPrincipal)) {
stream->mClient->CacheClientNotifyPrincipalChanged();
}
stream->mClient->CacheClientUpdatePrincipal();
}
}

Просмотреть файл

@ -261,8 +261,7 @@ public:
// the cache requested the offset in
// ChannelMediaResource::CacheClientSeek, or because it defaulted to 0.
// We pass in the principal that was used to load this data.
void NotifyDataReceived(int64_t aSize, const char* aData,
nsIPrincipal* aPrincipal);
void NotifyDataReceived(int64_t aSize, const char* aData);
// Notifies the cache that the current bytes should be written to disk.
// Called on the main thread.
void FlushPartialBlock();
@ -348,6 +347,9 @@ public:
size_t SizeOfExcludingThis(MallocSizeOf aMallocSizeOf) const;
// Update mPrincipal given that data has been received from aPrincipal
bool UpdatePrincipal(nsIPrincipal* aPrincipal);
private:
friend class MediaCache;
@ -425,8 +427,6 @@ private:
// If |aNotifyAll| is true, this function will wake up readers who may be
// waiting on the media cache monitor. Called on the main thread only.
void FlushPartialBlockInternal(bool aNotify, ReentrantMonitorAutoEnter& aReentrantMonitor);
// Update mPrincipal given that data has been received from aPrincipal
bool UpdatePrincipal(nsIPrincipal* aPrincipal);
// Instance of MediaCache to use with this MediaCacheStream.
RefPtr<MediaCache> mMediaCache;

Просмотреть файл

@ -456,8 +456,7 @@ ChannelMediaResource::OnChannelRedirect(nsIChannel* aOld, nsIChannel* aNew,
}
nsresult
ChannelMediaResource::CopySegmentToCache(nsIPrincipal* aPrincipal,
const char* aFromSegment,
ChannelMediaResource::CopySegmentToCache(const char* aFromSegment,
uint32_t aCount,
uint32_t* aWriteCount)
{
@ -466,28 +465,21 @@ ChannelMediaResource::CopySegmentToCache(nsIPrincipal* aPrincipal,
"[%d] bytes for decoder[%p]",
mOffset, aCount, mCallback.get());
mOffset += aCount;
mCacheStream.NotifyDataReceived(aCount, aFromSegment, aPrincipal);
mCacheStream.NotifyDataReceived(aCount, aFromSegment);
*aWriteCount = aCount;
return NS_OK;
}
struct CopySegmentClosure {
nsCOMPtr<nsIPrincipal> mPrincipal;
ChannelMediaResource* mResource;
};
nsresult
ChannelMediaResource::CopySegmentToCache(nsIInputStream* aInStream,
void* aClosure,
void* aResource,
const char* aFromSegment,
uint32_t aToOffset,
uint32_t aCount,
uint32_t* aWriteCount)
{
CopySegmentClosure* closure = static_cast<CopySegmentClosure*>(aClosure);
return closure->mResource->CopySegmentToCache(
closure->mPrincipal, aFromSegment, aCount, aWriteCount);
ChannelMediaResource* res = static_cast<ChannelMediaResource*>(aResource);
return res->CopySegmentToCache(aFromSegment, aCount, aWriteCount);
}
nsresult
@ -502,18 +494,10 @@ ChannelMediaResource::OnDataAvailable(nsIRequest* aRequest,
mChannelStatistics.AddBytes(aCount);
}
CopySegmentClosure closure;
nsIScriptSecurityManager* secMan = nsContentUtils::GetSecurityManager();
if (secMan && mChannel) {
secMan->GetChannelResultPrincipal(mChannel, getter_AddRefs(closure.mPrincipal));
}
closure.mResource = this;
uint32_t count = aCount;
while (count > 0) {
uint32_t read;
nsresult rv = aStream->ReadSegments(CopySegmentToCache, &closure, count,
&read);
nsresult rv = aStream->ReadSegments(CopySegmentToCache, this, count, &read);
if (NS_FAILED(rv))
return rv;
NS_ASSERTION(read > 0, "Read 0 bytes while data was available?");
@ -637,7 +621,8 @@ nsresult ChannelMediaResource::Close()
return NS_OK;
}
already_AddRefed<nsIPrincipal> ChannelMediaResource::GetCurrentPrincipal()
already_AddRefed<nsIPrincipal>
ChannelMediaResource::GetCurrentPrincipal()
{
NS_ASSERTION(NS_IsMainThread(), "Only call on main thread");
@ -888,11 +873,33 @@ ChannelMediaResource::CacheClientNotifyDataEnded(nsresult aStatus)
}
void
ChannelMediaResource::CacheClientNotifyPrincipalChanged()
ChannelMediaResource::UpdatePrincipal()
{
NS_ASSERTION(NS_IsMainThread(), "Don't call on non-main thread");
MOZ_ASSERT(NS_IsMainThread());
nsCOMPtr<nsIPrincipal> principal;
nsIScriptSecurityManager* secMan = nsContentUtils::GetSecurityManager();
if (secMan && mChannel) {
secMan->GetChannelResultPrincipal(mChannel, getter_AddRefs(principal));
}
if (mCacheStream.UpdatePrincipal(principal)) {
mCallback->NotifyPrincipalChanged();
}
}
mCallback->NotifyPrincipalChanged();
void
ChannelMediaResource::CacheClientUpdatePrincipal()
{
// This might happen off the main thread.
if (NS_IsMainThread()) {
UpdatePrincipal();
return;
}
SystemGroup::Dispatch(
TaskCategory::Other,
NewRunnableMethod("ChannelMediaResource::UpdatePrincipal",
this,
&ChannelMediaResource::UpdatePrincipal));
}
void

Просмотреть файл

@ -435,8 +435,8 @@ public:
// if this stream didn't read any data, since another stream might have
// received data for the same resource.
void CacheClientNotifyDataEnded(nsresult aStatus);
// Notify that the principal for the cached resource changed.
void CacheClientNotifyPrincipalChanged();
// Notified by the cache to update the principal of the resource.
void CacheClientUpdatePrincipal();
// Notify the decoder that the cache suspended status changed.
void CacheClientNotifySuspendedStatusChanged();
@ -547,6 +547,8 @@ protected:
nsresult SetupChannelHeaders();
// Closes the channel. Main thread only.
void CloseChannel();
// Update the principal for the resource. Main thread only.
void UpdatePrincipal();
// Parses 'Content-Range' header and returns results via parameters.
// Returns error if header is not available, values are not parse-able or
@ -557,14 +559,13 @@ protected:
int64_t& aRangeTotal);
static nsresult CopySegmentToCache(nsIInputStream* aInStream,
void* aClosure,
void* aResource,
const char* aFromSegment,
uint32_t aToOffset,
uint32_t aCount,
uint32_t* aWriteCount);
nsresult CopySegmentToCache(nsIPrincipal* aPrincipal,
const char* aFromSegment,
nsresult CopySegmentToCache(const char* aFromSegment,
uint32_t aCount,
uint32_t* aWriteCount);