Merge inbound to m-c. a=merge

This commit is contained in:
Ryan VanderMeulen 2014-12-19 15:03:54 -05:00
commit 2b44f330ba
353 changed files with 8214 additions and 2010 deletions

View File

@ -52,4 +52,8 @@ if CONFIG['MOZ_ENABLE_DBUS']:
include('/ipc/chromium/chromium-config.mozbuild')
if CONFIG['CLANG_CXX']:
# Suppress clang warning about unused function from gobject's RTTI macros.
CXXFLAGS += ['-Wno-unused-function']
FAIL_ON_WARNINGS = True

View File

@ -1849,3 +1849,6 @@ pref("extensions.interposition.enabled", true);
#endif
pref("browser.defaultbrowser.notificationbar", false);
// How many milliseconds to wait for a CPOW response from the child process.
pref("dom.ipc.cpow.timeout", 0);

View File

@ -6746,7 +6746,7 @@ function isTabEmpty(aTab) {
if (!gMultiProcessBrowser && browser.contentWindow.opener)
return false;
if (browser.sessionHistory && browser.sessionHistory.count >= 2)
if (browser.canGoForward || browser.canGoBack)
return false;
return true;

View File

@ -29,7 +29,7 @@ Cell.prototype = {
/**
* The cell's DOM node.
*/
get node() this._node,
get node() { return this._node; },
/**
* The cell's offset in the grid.

View File

@ -18,15 +18,15 @@ let gDrag = {
* The site that is dragged.
*/
_draggedSite: null,
get draggedSite() this._draggedSite,
get draggedSite() { return this._draggedSite; },
/**
* The cell width/height at the point the drag started.
*/
_cellWidth: null,
_cellHeight: null,
get cellWidth() this._cellWidth,
get cellHeight() this._cellHeight,
get cellWidth() { return this._cellWidth; },
get cellHeight() { return this._cellHeight; },
/**
* Start a new drag operation.
@ -146,6 +146,6 @@ let gDrag = {
// After the 'dragstart' event has been processed we can remove the
// temporary drag element from the DOM.
setTimeout(function () scrollbox.removeChild(dragElement), 0);
setTimeout(() => scrollbox.removeChild(dragElement), 0);
}
};

View File

@ -73,7 +73,7 @@ let gDrop = {
});
// Re-pin all shifted pinned cells.
pinnedSites.forEach(function (aSite) aSite.pin(sites.indexOf(aSite)), this);
pinnedSites.forEach(aSite => aSite.pin(sites.indexOf(aSite)));
},
/**

View File

@ -18,7 +18,7 @@ let gGrid = {
* The DOM node of the grid.
*/
_node: null,
get node() this._node,
get node() { return this._node; },
/**
* The cached DOM fragment for sites.
@ -29,18 +29,18 @@ let gGrid = {
* All cells contained in the grid.
*/
_cells: [],
get cells() this._cells,
get cells() { return this._cells; },
/**
* All sites contained in the grid's cells. Sites may be empty.
*/
get sites() [for (cell of this.cells) cell.site],
get sites() { return [for (cell of this.cells) cell.site]; },
// Tells whether the grid has already been initialized.
get ready() !!this._ready,
get ready() { return !!this._ready; },
// Returns whether the page has finished loading yet.
get isDocumentLoaded() document.readyState == "complete",
get isDocumentLoaded() { return document.readyState == "complete"; },
/**
* Initializes the grid.

View File

@ -22,22 +22,22 @@ Site.prototype = {
/**
* The site's DOM node.
*/
get node() this._node,
get node() { return this._node; },
/**
* The site's link.
*/
get link() this._link,
get link() { return this._link; },
/**
* The url of the site's link.
*/
get url() this.link.url,
get url() { return this.link.url; },
/**
* The title of the site's link.
*/
get title() this.link.title,
get title() { return this.link.title; },
/**
* The site's parent cell.

View File

@ -1067,7 +1067,7 @@ nsContextMenu.prototype = {
mm.removeMessageListener("ContextMenu:SaveVideoFrameAsImage:Result", onMessage);
let dataURL = message.data.dataURL;
saveImageURL(dataURL, name, "SaveImageTitle", true, false,
document.documentURIObject, this.target.ownerDocument);
document.documentURIObject, document);
};
mm.addMessageListener("ContextMenu:SaveVideoFrameAsImage:Result", onMessage);
},

View File

@ -124,7 +124,7 @@ function restoreSession() {
if (gTreeData[t].checked === 0)
// this window will be restored partially
gStateObject.windows[ix].tabs =
gStateObject.windows[ix].tabs.filter(function(aTabData, aIx)
gStateObject.windows[ix].tabs.filter((aTabData, aIx) =>
gTreeData[t].tabs[aIx].checked);
else if (!gTreeData[t].checked)
// this window won't be restored at all
@ -218,12 +218,14 @@ function getBrowserWindow() {
}
function toggleRowChecked(aIx) {
function isChecked(aItem) {
return aItem.checked;
}
var item = gTreeData[aIx];
item.checked = !item.checked;
treeView.treeBox.invalidateRow(aIx);
function isChecked(aItem) aItem.checked;
if (treeView.isContainer(aIx)) {
// (un)check all tabs of this window as well
for (let tab of item.tabs) {

View File

@ -42,9 +42,9 @@ function checkState(tab) {
// deserialized in the content scope. And in this case, since RegExps are
// not currently Xrayable (see bug 1014991), trying to pull |obj3| (a RegExp)
// off of an Xrayed Object won't work. So we need to waive.
runInContent(tab.linkedBrowser, function(win, event) {
return Cu.waiveXrays(event.state).obj3.toString();
}, aEvent).then(function(stateStr) {
runInContent(tab.linkedBrowser, function(win, state) {
return Cu.waiveXrays(state).obj3.toString();
}, aEvent.state).then(function(stateStr) {
is(stateStr, '/^a$/', "second popstate object.");
// Make sure that the new-elem node is present in the document. If it's

View File

@ -154,12 +154,11 @@ def GeckoFramework(name, **kwargs):
@template
def XPCOMBinaryComponent(name):
def XPCOMBinaryComponent(name, **kwargs):
'''Template defining an XPCOM binary component for Gecko.
`name` is the name of the component.
'''
GeckoSharedLibrary(name)
GeckoSharedLibrary(name, **kwargs)
IS_COMPONENT = True

View File

@ -1200,6 +1200,9 @@ Navigator::SendBeacon(const nsAString& aUrl,
principal,
true);
rv = cors->Init(channel, true);
NS_ENSURE_SUCCESS(rv, false);
// Start a preflight if cross-origin and content type is not whitelisted
rv = secMan->CheckSameOriginURI(documentURI, uri, false);
bool crossOrigin = NS_FAILED(rv);

View File

@ -197,6 +197,24 @@
let savedElement = null;
function recvDomTest(message) {
savedElement = message.objects.element;
// Test to ensure that we don't pass CPOWs to C++-implemented interfaces.
// See bug 1072980.
if (test_state == "remote") {
let walker = Components.classes["@mozilla.org/inspector/deep-tree-walker;1"]
.createInstance(Components.interfaces.inIDeepTreeWalker);
const SHOW_ELEMENT = Components.interfaces.nsIDOMNodeFilter.SHOW_ELEMENT;
walker.showAnonymousContent = true;
walker.showSubDocuments = false;
try {
walker.init(savedElement, SHOW_ELEMENT);
ok(false, "expected exception passing CPOW to C++");
} catch (e) {
is(e.result, Components.results.NS_ERROR_XPC_CANT_PASS_CPOW_TO_NATIVE,
"got exception when passing CPOW to C++");
}
}
}
function recvDomTestAfterGC(message) {

View File

@ -53,7 +53,7 @@ skip-if = buildapp == 'mulet'
skip-if = buildapp == 'mulet'
[test_bug456273.html]
[test_bug457672.html]
skip-if = buildapp == 'mulet' || buildapp == 'b2g' || toolkit == 'android' #CRASH_DUMP, RANDOM
skip-if = buildapp == 'mulet' || buildapp == 'b2g' || toolkit == 'android' || e10s #CRASH_DUMP, RANDOM
[test_bug489671.html]
[test_bug493251.html]
skip-if = buildapp == 'mulet' || (buildapp == 'b2g' && toolkit != 'gonk') #Bug 931116, b2g desktop specific, initial triage

View File

@ -17,7 +17,7 @@ interface nsIServiceWorkerUnregisterCallback : nsISupports
[noscript] void UnregisterFailed();
};
[builtinclass, uuid(79ad5b57-d65d-46d3-b5e9-32d27e16052d)]
[builtinclass, uuid(78fdfe7c-0e2c-4157-ac6e-3952b61df36a)]
interface nsIServiceWorkerManager : nsISupports
{
/**
@ -83,6 +83,11 @@ interface nsIServiceWorkerManager : nsISupports
*/
[noscript] nsISupports GetDocumentController(in nsIDOMWindow aWindow);
/*
* This implements the update algorithm.
*/
void update(in DOMString aScope);
// Testing
DOMString getScopeForUrl(in DOMString path);
};

View File

@ -2458,7 +2458,7 @@ ContentChild::RecvStopProfiler()
}
bool
ContentChild::AnswerGetProfile(nsCString* aProfile)
ContentChild::RecvGetProfile(nsCString* aProfile)
{
char* profile = profiler_get_profile();
if (profile) {

View File

@ -365,7 +365,7 @@ public:
const nsTArray<nsCString>& aFeatures,
const nsTArray<nsCString>& aThreadNameFilters) MOZ_OVERRIDE;
virtual bool RecvStopProfiler() MOZ_OVERRIDE;
virtual bool AnswerGetProfile(nsCString* aProfile) MOZ_OVERRIDE;
virtual bool RecvGetProfile(nsCString* aProfile) MOZ_OVERRIDE;
#ifdef ANDROID
gfxIntSize GetScreenSize() { return mScreenSize; }

View File

@ -927,7 +927,7 @@ ContentParent::RecvCreateChildProcess(const IPCTabContext& aContext,
}
bool
ContentParent::AnswerBridgeToChildProcess(const ContentParentId& aCpId)
ContentParent::RecvBridgeToChildProcess(const ContentParentId& aCpId)
{
ContentProcessManager *cpm = ContentProcessManager::GetSingleton();
ContentParent* cp = cpm->GetContentProcessById(aCpId);
@ -966,7 +966,7 @@ static nsIDocShell* GetOpenerDocShellHelper(Element* aFrameElement)
}
bool
ContentParent::AnswerLoadPlugin(const uint32_t& aPluginId)
ContentParent::RecvLoadPlugin(const uint32_t& aPluginId)
{
return mozilla::plugins::SetupBridge(aPluginId, this);
}
@ -1219,7 +1219,7 @@ ContentParent::CreateContentBridgeParent(const TabContext& aContext,
if (cpId == 0) {
return nullptr;
}
if (!child->CallBridgeToChildProcess(cpId)) {
if (!child->SendBridgeToChildProcess(cpId)) {
return nullptr;
}
ContentBridgeParent* parent = child->GetLastBridge();
@ -2011,6 +2011,9 @@ ContentParent::ContentParent(mozIApplication* aApp,
true /* Send registered chrome */);
ContentProcessManager::GetSingleton()->AddContentProcess(this);
// Set a reply timeout for CPOWs.
SetReplyTimeoutMs(Preferences::GetInt("dom.ipc.cpow.timeout", 0));
}
#ifdef MOZ_NUWA_PROCESS
@ -2866,7 +2869,7 @@ ContentParent::Observe(nsISupports* aSubject,
nsCOMPtr<nsIProfileSaveEvent> pse = do_QueryInterface(aSubject);
if (pse) {
nsCString result;
unused << CallGetProfile(&result);
unused << SendGetProfile(&result);
if (!result.IsEmpty()) {
pse->AddSubProfile(result.get());
}
@ -4263,11 +4266,11 @@ ContentParent::RecvOpenAnonymousTemporaryFile(FileDescriptor *aFD)
static NS_DEFINE_CID(kFormProcessorCID, NS_FORMPROCESSOR_CID);
bool
ContentParent::RecvFormProcessValue(const nsString& oldValue,
const nsString& challenge,
const nsString& keytype,
const nsString& keyparams,
nsString* newValue)
ContentParent::RecvKeygenProcessValue(const nsString& oldValue,
const nsString& challenge,
const nsString& keytype,
const nsString& keyparams,
nsString* newValue)
{
nsCOMPtr<nsIFormProcessor> formProcessor =
do_GetService(kFormProcessorCID);
@ -4282,8 +4285,8 @@ ContentParent::RecvFormProcessValue(const nsString& oldValue,
}
bool
ContentParent::RecvFormProvideContent(nsString* aAttribute,
nsTArray<nsString>* aContent)
ContentParent::RecvKeygenProvideContent(nsString* aAttribute,
nsTArray<nsString>* aContent)
{
nsCOMPtr<nsIFormProcessor> formProcessor =
do_GetService(kFormProcessorCID);

View File

@ -150,9 +150,9 @@ public:
bool* aIsForApp,
bool* aIsForBrowser,
TabId* aTabId) MOZ_OVERRIDE;
virtual bool AnswerBridgeToChildProcess(const ContentParentId& aCpId) MOZ_OVERRIDE;
virtual bool RecvBridgeToChildProcess(const ContentParentId& aCpId) MOZ_OVERRIDE;
virtual bool AnswerLoadPlugin(const uint32_t& aPluginId) MOZ_OVERRIDE;
virtual bool RecvLoadPlugin(const uint32_t& aPluginId) MOZ_OVERRIDE;
virtual bool RecvFindPlugins(const uint32_t& aPluginEpoch,
nsTArray<PluginTag>* aPlugins,
uint32_t* aNewPluginEpoch) MOZ_OVERRIDE;
@ -722,13 +722,13 @@ private:
RecvOpenAnonymousTemporaryFile(FileDescriptor* aFD) MOZ_OVERRIDE;
virtual bool
RecvFormProcessValue(const nsString& oldValue, const nsString& challenge,
const nsString& keytype, const nsString& keyparams,
nsString* newValue) MOZ_OVERRIDE;
RecvKeygenProcessValue(const nsString& oldValue, const nsString& challenge,
const nsString& keytype, const nsString& keyparams,
nsString* newValue) MOZ_OVERRIDE;
virtual bool
RecvFormProvideContent(nsString* aAttribute,
nsTArray<nsString>* aContent) MOZ_OVERRIDE;
RecvKeygenProvideContent(nsString* aAttribute,
nsTArray<nsString>* aContent) MOZ_OVERRIDE;
virtual PFileDescriptorSetParent*
AllocPFileDescriptorSetParent(const mozilla::ipc::FileDescriptor&) MOZ_OVERRIDE;

View File

@ -521,7 +521,7 @@ child:
async StartProfiler(uint32_t aEntries, double aInterval, nsCString[] aFeatures,
nsCString[] aThreadNameFilters);
async StopProfiler();
intr GetProfile()
prio(high) sync GetProfile()
returns (nsCString aProfile);
NuwaFreeze();
@ -557,7 +557,7 @@ parent:
ProcessPriority priority,
TabId openerTabId)
returns (ContentParentId cpId, bool isForApp, bool isForBrowser, TabId tabId);
intr BridgeToChildProcess(ContentParentId cpId);
sync BridgeToChildProcess(ContentParentId cpId);
/**
* This call connects the content process to a plugin process. While this
@ -566,7 +566,7 @@ parent:
* process. We use intr semantics here to ensure that the PluginModuleParent
* allocation message is dispatched before LoadPlugin returns.
*/
intr LoadPlugin(uint32_t pluginId);
sync LoadPlugin(uint32_t pluginId);
/**
* This call returns the set of plugins loaded in the chrome
@ -798,16 +798,17 @@ parent:
* before one is submitted. This is urgent because an extension might use
* a CPOW to synchronously submit a keygen element.
*/
prio(urgent) sync FormProcessValue(nsString oldValue,
nsString challenge,
nsString keytype,
nsString keyparams)
prio(urgent) sync KeygenProcessValue(nsString oldValue,
nsString challenge,
nsString keytype,
nsString keyparams)
returns (nsString newValue);
/**
* Called to provide the options for <keygen> elements.
*/
sync FormProvideContent() returns (nsString aAttribute, nsString[] aContent);
sync KeygenProvideContent()
returns (nsString aAttribute, nsString[] aContent);
// Use only for testing!
sync GetFileReferences(PersistenceType persistenceType,

View File

@ -1,4 +1,4 @@
/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 4 -*- */
/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
/* vim: set sw=4 ts=8 et tw=80 : */
/* This Source Code Form is subject to the terms of the Mozilla Public
* License, v. 2.0. If a copy of the MPL was not distributed with this
@ -131,14 +131,18 @@ ScreenManagerParent::RecvScreenForBrowser(PBrowserParent* aBrowser,
// the nsIScreen it's on.
TabParent* tabParent = static_cast<TabParent*>(aBrowser);
nsCOMPtr<nsIWidget> widget = tabParent->GetWidget();
if (!widget) {
return true;
}
nsCOMPtr<nsIScreen> screen;
if (widget->GetNativeData(NS_NATIVE_WINDOW)) {
mScreenMgr->ScreenForNativeWidget(widget->GetNativeData(NS_NATIVE_WINDOW),
getter_AddRefs(screen));
if (widget) {
if (widget->GetNativeData(NS_NATIVE_WINDOW)) {
mScreenMgr->ScreenForNativeWidget(widget->GetNativeData(NS_NATIVE_WINDOW),
getter_AddRefs(screen));
}
} else {
nsresult rv = mScreenMgr->GetPrimaryScreen(getter_AddRefs(screen));
if (NS_WARN_IF(NS_FAILED(rv))) {
return true;
}
}
NS_ENSURE_TRUE(screen, true);

View File

@ -248,11 +248,10 @@ TabChildBase::InitializeRootMetrics()
mLastRootMetrics.SetDevPixelsPerCSSPixel(WebWidget()->GetDefaultScale());
// We use ParentLayerToLayerScale(1) below in order to turn the
// async zoom amount into the gecko zoom amount.
mLastRootMetrics.mCumulativeResolution =
mLastRootMetrics.GetZoom() / mLastRootMetrics.GetDevPixelsPerCSSPixel() * ParentLayerToLayerScale(1);
mLastRootMetrics.SetCumulativeResolution(mLastRootMetrics.GetZoom() / mLastRootMetrics.GetDevPixelsPerCSSPixel() * ParentLayerToLayerScale(1));
// This is the root layer, so the cumulative resolution is the same
// as the resolution.
mLastRootMetrics.mPresShellResolution = mLastRootMetrics.mCumulativeResolution.scale;
mLastRootMetrics.mPresShellResolution = mLastRootMetrics.GetCumulativeResolution().scale;
mLastRootMetrics.SetScrollOffset(CSSPoint(0, 0));
TABC_LOG("After InitializeRootMetrics, mLastRootMetrics is %s\n",
@ -430,12 +429,12 @@ TabChildBase::HandlePossibleViewportChange(const ScreenIntSize& aOldScreenSize)
}
}
metrics.mCumulativeResolution = metrics.GetZoom()
metrics.SetCumulativeResolution(metrics.GetZoom()
/ metrics.GetDevPixelsPerCSSPixel()
* ParentLayerToLayerScale(1);
* ParentLayerToLayerScale(1));
// This is the root layer, so the cumulative resolution is the same
// as the resolution.
metrics.mPresShellResolution = metrics.mCumulativeResolution.scale;
metrics.mPresShellResolution = metrics.GetCumulativeResolution().scale;
utils->SetResolution(metrics.mPresShellResolution, metrics.mPresShellResolution);
CSSSize scrollPort = metrics.CalculateCompositedSizeInCssPixels();

View File

@ -216,6 +216,7 @@ namespace dom {
TabParent* sEventCapturer;
TabParent *TabParent::mIMETabParent = nullptr;
TabParent::LayerToTabParentTable* TabParent::sLayerToTabParentTable = nullptr;
NS_IMPL_ISUPPORTS(TabParent,
nsITabParent,
@ -261,6 +262,37 @@ TabParent::~TabParent()
{
}
TabParent*
TabParent::GetTabParentFromLayersId(uint64_t aLayersId)
{
if (!sLayerToTabParentTable) {
return nullptr;
}
return sLayerToTabParentTable->Get(aLayersId);
}
void
TabParent::AddTabParentToTable(uint64_t aLayersId, TabParent* aTabParent)
{
if (!sLayerToTabParentTable) {
sLayerToTabParentTable = new LayerToTabParentTable();
}
sLayerToTabParentTable->Put(aLayersId, aTabParent);
}
void
TabParent::RemoveTabParentFromTable(uint64_t aLayersId)
{
if (!sLayerToTabParentTable) {
return;
}
sLayerToTabParentTable->Remove(aLayersId);
if (sLayerToTabParentTable->Count() == 0) {
delete sLayerToTabParentTable;
sLayerToTabParentTable = nullptr;
}
}
void
TabParent::SetOwnerElement(Element* aElement)
{
@ -306,6 +338,7 @@ TabParent::Destroy()
unused << SendDestroy();
if (RenderFrameParent* frame = GetRenderFrame()) {
RemoveTabParentFromTable(frame->GetLayersId());
frame->Destroy();
}
mIsDestroyed = true;
@ -600,6 +633,7 @@ TabParent::Show(const nsIntSize& size)
&layersId,
&success);
MOZ_ASSERT(success);
AddTabParentToTable(layersId, this);
unused << SendPRenderFrameConstructor(renderFrame);
}
}
@ -2009,6 +2043,7 @@ TabParent::AllocPRenderFrameParent()
&layersId,
&success);
MOZ_ASSERT(success);
AddTabParentToTable(layersId, this);
return renderFrame;
} else {
return nullptr;
@ -2115,6 +2150,11 @@ TabParent::MaybeForwardEventToRenderFrame(WidgetInputEvent& aEvent,
if (aOutInputBlockId) {
*aOutInputBlockId = InputAPZContext::GetInputBlockId();
}
// Let the widget know that the event will be sent to the child process,
// which will (hopefully) send a confirmation notice back to APZ.
InputAPZContext::SetRoutedToChildProcess();
return nsEventStatus_eIgnore;
}

View File

@ -461,6 +461,18 @@ private:
nsCOMPtr<nsILoadContext> mLoadContext;
TabId mTabId;
private:
// This is used when APZ needs to find the TabParent associated with a layer
// to dispatch events.
typedef nsDataHashtable<nsUint64HashKey, TabParent*> LayerToTabParentTable;
static LayerToTabParentTable* sLayerToTabParentTable;
static void AddTabParentToTable(uint64_t aLayersId, TabParent* aTabParent);
static void RemoveTabParentFromTable(uint64_t aLayersId);
public:
static TabParent* GetTabParentFromLayersId(uint64_t aLayersId);
};
} // namespace dom

View File

@ -194,6 +194,10 @@ public:
// This queues a call to Update() on the main thread.
void QueueUpdate();
// Notify all streams for the resource ID that the suspended status changed
// at the end of MediaCache::Update.
void QueueSuspendedStatusUpdate(int64_t aResourceID);
// Updates the cache state asynchronously on the main thread:
// -- try to trim the cache back to its desired size, if necessary
// -- suspend channels that are going to read data that's lower priority
@ -347,6 +351,8 @@ protected:
#ifdef DEBUG
bool mInUpdate;
#endif
// A list of resource IDs to notify about the change in suspended status.
nsTArray<int64_t> mSuspendedStatusToNotify;
};
NS_IMETHODIMP
@ -1351,10 +1357,12 @@ MediaCache::Update()
case RESUME:
CACHE_LOG(PR_LOG_DEBUG, ("Stream %p Resumed", stream));
rv = stream->mClient->CacheClientResume();
QueueSuspendedStatusUpdate(stream->mResourceID);
break;
case SUSPEND:
CACHE_LOG(PR_LOG_DEBUG, ("Stream %p Suspended", stream));
rv = stream->mClient->CacheClientSuspend();
QueueSuspendedStatusUpdate(stream->mResourceID);
break;
default:
rv = NS_OK;
@ -1369,6 +1377,15 @@ MediaCache::Update()
stream->CloseInternal(mon);
}
}
// Notify streams about the suspended status changes.
for (uint32_t i = 0; i < mSuspendedStatusToNotify.Length(); ++i) {
MediaCache::ResourceStreamIterator iter(mSuspendedStatusToNotify[i]);
while (MediaCacheStream* stream = iter.Next()) {
stream->mClient->CacheClientNotifySuspendedStatusChanged();
}
}
mSuspendedStatusToNotify.Clear();
}
class UpdateEvent : public nsRunnable
@ -1399,6 +1416,15 @@ MediaCache::QueueUpdate()
NS_DispatchToMainThread(event);
}
void
MediaCache::QueueSuspendedStatusUpdate(int64_t aResourceID)
{
NS_ASSERTION(NS_IsMainThread(), "Only call on main thread");
if (!mSuspendedStatusToNotify.Contains(aResourceID)) {
mSuspendedStatusToNotify.AppendElement(aResourceID);
}
}
#ifdef DEBUG_VERIFY_CACHE
void
MediaCache::Verify()
@ -1980,6 +2006,10 @@ MediaCacheStream::CloseInternal(ReentrantMonitorAutoEnter& aReentrantMonitor)
if (mClosed)
return;
mClosed = true;
// Closing a stream will change the return value of
// MediaCacheStream::AreAllStreamsForResourceSuspended as well as
// ChannelMediaResource::IsSuspendedByCache. Let's notify it.
gMediaCache->QueueSuspendedStatusUpdate(mResourceID);
gMediaCache->ReleaseStreamBlocks(this);
// Wake up any blocked readers
aReentrantMonitor.NotifyAll();

View File

@ -1009,6 +1009,13 @@ ChannelMediaResource::CacheClientNotifyPrincipalChanged()
mDecoder->NotifyPrincipalChanged();
}
void
ChannelMediaResource::CacheClientNotifySuspendedStatusChanged()
{
NS_ASSERTION(NS_IsMainThread(), "Don't call on non-main thread");
mDecoder->NotifySuspendedStatusChanged();
}
nsresult
ChannelMediaResource::CacheClientSeek(int64_t aOffset, bool aResume)
{
@ -1067,8 +1074,6 @@ nsresult
ChannelMediaResource::CacheClientSuspend()
{
Suspend(false);
mDecoder->NotifySuspendedStatusChanged();
return NS_OK;
}
@ -1076,8 +1081,6 @@ nsresult
ChannelMediaResource::CacheClientResume()
{
Resume();
mDecoder->NotifySuspendedStatusChanged();
return NS_OK;
}

View File

@ -538,6 +538,8 @@ public:
void CacheClientNotifyDataEnded(nsresult aStatus);
// Notify that the principal for the cached resource changed.
void CacheClientNotifyPrincipalChanged();
// Notify the decoder that the cache suspended status changed.
void CacheClientNotifySuspendedStatusChanged();
// These are called on the main thread by MediaCache. These shouldn't block,
// but they may grab locks --- the media cache is not holding its lock

View File

@ -118,6 +118,7 @@ class GMPRecordClient {
class GMPRecordIterator {
public:
// Retrieve the name for the current record.
// aOutName is null terminated at character at index (*aOutNameLength).
// Returns GMPNoErr if successful, or GMPEndOfEnumeration if iteration has
// reached the end.
virtual GMPErr GetName(const char ** aOutName, uint32_t * aOutNameLength) = 0;

View File

@ -327,6 +327,7 @@ MediaSourceReader::Shutdown()
void
MediaSourceReader::ContinueShutdown()
{
ReentrantMonitorAutoEnter mon(mDecoder->GetReentrantMonitor());
if (mTrackBuffers.Length()) {
mTrackBuffers[0]->Shutdown()->Then(GetTaskQueue(), __func__, this,
&MediaSourceReader::ContinueShutdown,

View File

@ -39,12 +39,14 @@ TrackBuffer::TrackBuffer(MediaSourceDecoder* aParentDecoder, const nsACString& a
: mParentDecoder(aParentDecoder)
, mType(aType)
, mLastStartTimestamp(0)
, mShutdown(false)
{
MOZ_COUNT_CTOR(TrackBuffer);
mParser = ContainerParser::CreateForMIMEType(aType);
mTaskQueue = new MediaTaskQueue(GetMediaDecodeThreadPool());
aParentDecoder->AddTrackBuffer(this);
mDecoderPerSegment = Preferences::GetBool("media.mediasource.decoder-per-segment", false);
MSE_DEBUG("TrackBuffer(%p) created for parent decoder %p", this, aParentDecoder);
}
TrackBuffer::~TrackBuffer()
@ -101,6 +103,9 @@ private:
nsRefPtr<ShutdownPromise>
TrackBuffer::Shutdown()
{
mParentDecoder->GetReentrantMonitor().AssertCurrentThreadIn();
mShutdown = true;
MOZ_ASSERT(mShutdownPromise.IsEmpty());
nsRefPtr<ShutdownPromise> p = mShutdownPromise.Ensure(__func__);
@ -370,23 +375,42 @@ TrackBuffer::QueueInitializeDecoder(SourceBufferDecoder* aDecoder)
void
TrackBuffer::InitializeDecoder(SourceBufferDecoder* aDecoder)
{
MOZ_ASSERT(mTaskQueue->IsCurrentThreadIn());
// ReadMetadata may block the thread waiting on data, so it must not be
// called with the monitor held.
// ReadMetadata may block the thread waiting on data, so we must be able
// to leave the monitor while we call it. For the rest of this function
// we want to hold the monitor though, since we run on a different task queue
// from the reader and interact heavily with it.
mParentDecoder->GetReentrantMonitor().AssertNotCurrentThreadIn();
ReentrantMonitorAutoEnter mon(mParentDecoder->GetReentrantMonitor());
// We may be shut down at any time by the reader on another thread. So we need
// to check for this each time we acquire the monitor. If that happens, we
// need to abort immediately, because the reader has forgotten about us, and
// important pieces of our state (like mTaskQueue) have also been torn down.
if (mShutdown) {
MSE_DEBUG("TrackBuffer(%p) was shut down. Aborting initialization.", this);
return;
}
MOZ_ASSERT(mTaskQueue->IsCurrentThreadIn());
MediaDecoderReader* reader = aDecoder->GetReader();
MSE_DEBUG("TrackBuffer(%p): Initializing subdecoder %p reader %p",
this, aDecoder, reader);
MediaInfo mi;
nsAutoPtr<MetadataTags> tags; // TODO: Handle metadata.
nsresult rv = reader->ReadMetadata(&mi, getter_Transfers(tags));
nsresult rv;
{
ReentrantMonitorAutoExit mon(mParentDecoder->GetReentrantMonitor());
rv = reader->ReadMetadata(&mi, getter_Transfers(tags));
}
reader->SetIdle();
if (mShutdown) {
MSE_DEBUG("TrackBuffer(%p) was shut down while reading metadata. Aborting initialization.", this);
return;
}
if (NS_SUCCEEDED(rv) && reader->IsWaitingOnCDMResource()) {
ReentrantMonitorAutoEnter mon(mParentDecoder->GetReentrantMonitor());
mWaitingDecoders.AppendElement(aDecoder);
return;
}
@ -442,7 +466,7 @@ TrackBuffer::ValidateTrackFormats(const MediaInfo& aInfo)
bool
TrackBuffer::RegisterDecoder(SourceBufferDecoder* aDecoder)
{
ReentrantMonitorAutoEnter mon(mParentDecoder->GetReentrantMonitor());
mParentDecoder->GetReentrantMonitor().AssertCurrentThreadIn();
const MediaInfo& info = aDecoder->GetReader()->GetMediaInfo();
// Initialize the track info since this is the first decoder.
if (mInitializedDecoders.IsEmpty()) {

View File

@ -163,6 +163,7 @@ private:
void ContinueShutdown();
MediaPromiseHolder<ShutdownPromise> mShutdownPromise;
bool mDecoderPerSegment;
bool mShutdown;
};
} // namespace mozilla

View File

@ -3,9 +3,12 @@ const KEYSYSTEM_TYPE = "org.w3.clearkey";
function bail(message)
{
return function(err) {
if (err) {
message += "; " + String(err)
}
ok(false, message);
if (err) {
info(err);
info(String(err));
}
SimpleTest.finish();
}
@ -70,13 +73,13 @@ function Log(token, msg) {
info(TimeStamp(token) + " " + msg);
}
function UpdateSessionFunc(test, token) {
function UpdateSessionFunc(test, token, sessionType) {
return function(ev) {
var msgStr = ArrayBufferToString(ev.message);
var msg = JSON.parse(msgStr);
Log(token, "got message from CDM: " + msgStr);
is(msg.type, test.sessionType, TimeStamp(token) + " key session type should match");
is(msg.type, sessionType, TimeStamp(token) + " key session type should match");
ok(msg.kids, TimeStamp(token) + " message event should contain key ID array");
var outKeys = [];
@ -211,24 +214,24 @@ function SetupEME(test, token, params)
.then(function(keySystemAccess) {
return keySystemAccess.createMediaKeys();
}, bail(token + " Failed to request key system access."))
.then(function(mediaKeys) {
Log(token, "created MediaKeys object ok");
mediaKeys.sessions = [];
return v.setMediaKeys(mediaKeys);
}, bail("failed to create MediaKeys object"))
.then(function() {
Log(token, "set MediaKeys on <video> element ok");
var session = v.mediaKeys.createSession(test.sessionType);
var sessionType = (params && params.sessionType) ? params.sessionType : "temporary";
var session = v.mediaKeys.createSession(sessionType);
if (params && params.onsessioncreated) {
params.onsessioncreated(session);
}
session.addEventListener("message", UpdateSessionFunc(test, token));
session.addEventListener("message", UpdateSessionFunc(test, token, sessionType));
return session.generateRequest(ev.initDataType, ev.initData);
}, onSetKeysFail)
.then(function() {
Log(token, "generated request");
}, bail(token + " Failed to request key system access2."));

View File

@ -364,6 +364,8 @@ skip-if = (toolkit == 'android' && processor == 'x86') #x86 only bug 914439
skip-if = buildapp == 'b2g' && toolkit != 'gonk' # bug 1082984
[test_eme_canvas_blocked.html]
skip-if = buildapp == 'b2g' || toolkit == 'android' || e10s # bug 1043403, bug 1057908
[test_eme_persistent_sessions.html]
skip-if = buildapp == 'b2g' || toolkit == 'android' || e10s # bug 1043403, bug 1057908
[test_eme_playback.html]
skip-if = buildapp == 'b2g' || toolkit == 'android' || e10s # bug 1043403, bug 1057908
[test_eme_requestKeySystemAccess.html]

View File

@ -0,0 +1,156 @@
<!DOCTYPE HTML>
<html>
<head>
<title>Test Encrypted Media Extensions</title>
<script type="text/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
<link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css" />
<script type="text/javascript" src="manifest.js"></script>
<script type="text/javascript" src="eme.js"></script>
</head>
<body>
<pre id="test">
<script class="testbody" type="text/javascript">
var manager = new MediaTestManager;
function UsableKeyIdsMatch(usableKeyIds, expectedKeyIds) {
var hexKeyIds = usableKeyIds.map(function(keyId) {
return Base64ToHex(window.btoa(ArrayBufferToString(keyId)));
}).sort();
var expected = Object.keys(expectedKeyIds).sort();
if (expected.length != hexKeyIds.length) {
return false;
}
for (var i = 0; i < hexKeyIds.length; i++) {
if (hexKeyIds[i] != expected[i]){
return false;
}
}
return true;
}
function AwaitAllKeysUsable(session, keys, token) {
return new Promise(function(resolve, reject) {
function listener(event) {
session.getUsableKeyIds().then(function(usableKeyIds) {
var u = UsableKeyIdsMatch(usableKeyIds, keys);
if (UsableKeyIdsMatch(usableKeyIds, keys)) {
Log(token, "resolving AwaitAllKeysUsable promise");
session.removeEventListener("keyschange", listener);
resolve();
}
}, bail(token + " failed to get usableKeyIds"));
}
session.addEventListener("keyschange", listener);
});
}
function AwaitAllKeysNotUsable(session, token) {
return new Promise(function(resolve, reject) {
function listener(event) {
session.getUsableKeyIds().then(function(usableKeyIds) {
if (usableKeyIds.length == 0) {
session.removeEventListener("keyschange", listener);
resolve();
}
}, bail(token + " failed to get usableKeyIds"));
}
session.addEventListener("keyschange", listener);
});
}
function startTest(test, token)
{
manager.started(token);
var recreatedSession; // will have remove() called on it.
var keySystemAccess;
var v = SetupEME(test, token,
{
onsessioncreated: function(session) {
Log(token, "Session created");
var sessionId;
initialSession = session;
// Once the session has loaded and has all its keys usable, close
// all sessions without calling remove() on them.
AwaitAllKeysUsable(session, test.keys, token).then(
function() {
sessionId = session.sessionId;
Log(token, "Closing session with id=" + sessionId);
session.close();
}
);
// Once the session is closed, reload the MediaKeys and reload the session
session.closed.then(function() {
return navigator.requestMediaKeySystemAccess(KEYSYSTEM_TYPE)
}, bail("close promise rejected"))
.then(function(requestedKeySystemAccess) {
keySystemAccess = requestedKeySystemAccess;
return keySystemAccess.createMediaKeys();
}, bail(token + " Failed to request key system access."))
.then(function(mediaKeys) {
Log(token, "re-created MediaKeys object ok");
recreatedSession = mediaKeys.createSession("persistent");
Log(token, "Created recreatedSession, loading sessionId=" + sessionId);
return Promise.all([AwaitAllKeysUsable(recreatedSession, test.keys, token), recreatedSession.load(sessionId)]);
}, bail(token + " failed to create mediaKeys"))
.then(function() {
Log(token, "re-loaded persistent session, all keys still usable");
return Promise.all([AwaitAllKeysNotUsable(recreatedSession, token), recreatedSession.remove()]);
}, bail(token + " failed to get reload session or keys"))
.then(function() {
Log(token, "removed session, all keys unusable.");
// Attempt to recreate the session, the attempt should fail.
return keySystemAccess.createMediaKeys();
}, bail(token + " failed to remove session"))
.then(function(mediaKeys) {
Log(token, "re-re-created MediaKeys object ok");
// Trying to load the removed persistent session should fail.
return mediaKeys.createSession("persistent").load(sessionId);
}, bail(token + " failed to create mediaKeys"))
.then(function(suceeded) {
is(suceeded, false, token + " we expect the third session creation to fail, as the session should have been removed.");
manager.finished(token);
}, bail(token + " failure to load session."));
},
sessionType: "persistent",
}
);
v.addEventListener("error", bail(token + " got error event"));
LoadTest(test, v, token);
}
function beginTest() {
manager.runTests(gEMETests, startTest);
}
var prefs = [
[ "media.mediasource.enabled", true ],
[ "media.mediasource.mp4.enabled", true ],
];
if (/Linux/.test(navigator.userAgent) ||
!document.createElement('video').canPlayType("video/mp4")) {
// XXX remove once we have mp4 PlatformDecoderModules on all platforms.
prefs.push([ "media.fragmented-mp4.exposed", true ]);
prefs.push([ "media.fragmented-mp4.use-blank-decoder", true ]);
}
SimpleTest.waitForExplicitFinish();
SpecialPowers.pushPrefEnv({ "set" : prefs }, beginTest);
</script>
</pre>
</body>
</html>

View File

@ -22,6 +22,7 @@ function startTest() {
mStream = stream;
element.mozSrcObject = mStream;
element.play();
})
.catch(function(reason) {
ok(false, "unexpected error = " + reason.message);

View File

@ -128,6 +128,7 @@ function runTest(aCallback) {
if (window.SimpleTest) {
// Running as a Mochitest.
SimpleTest.waitForExplicitFinish();
SimpleTest.requestFlakyTimeout("WebRTC inherently depends on timeouts");
SpecialPowers.pushPrefEnv({'set': [
['dom.messageChannel.enabled', true],
['media.peerconnection.enabled', true],

View File

@ -10,9 +10,6 @@
<body>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
createHTML({
title: "getIdentityAssertion Tests"
});

View File

@ -14,9 +14,6 @@
<div id="display"></div>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
createHTML({
title: "setIdentityProvider leads to peerIdentity and assertions in SDP"
});

View File

@ -12,9 +12,6 @@
<body>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
createHTML({
title: "setIdentityProvider leads to peerIdentity and assertions in SDP"
});

View File

@ -11,9 +11,6 @@
<body>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
createHTML({
title: "Identity Provider returning errors is handled correctly"
});

View File

@ -11,7 +11,6 @@
"use strict";
SimpleTest.waitForExplicitFinish();
SimpleTest.requestFlakyTimeout("untriaged");
// This isn't a single test. It runs the entirety of the PeerConnection
// tests. Each of those has a normal timeout handler, so there's no point in

View File

@ -11,8 +11,6 @@
<body>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
createHTML({
bug: "796895",
title: "Basic data channel audio connection"

View File

@ -11,8 +11,6 @@
<body>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
createHTML({
bug: "796891",
title: "Basic data channel audio/video connection"

View File

@ -11,8 +11,6 @@
<body>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
createHTML({
bug: "796891",
title: "Basic data channel audio/video connection"

View File

@ -11,8 +11,6 @@
<body>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
createHTML({
bug: "796894",
title: "Basic datachannel only connection"

View File

@ -11,8 +11,6 @@
<body>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
createHTML({
bug: "796889",
title: "Basic data channel video connection"

View File

@ -11,8 +11,6 @@
<body>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
createHTML({
bug: "796895",
title: "Basic data channel audio connection"

View File

@ -19,8 +19,6 @@ https://bugzilla.mozilla.org/show_bug.cgi?id=781534
</div>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
/**
* Run a test to verify that we can complete a start and stop media playback
* cycle for an audio LocalMediaStream on an audio HTMLMediaElement.

View File

@ -19,8 +19,6 @@ https://bugzilla.mozilla.org/show_bug.cgi?id=983504
</div>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
/**
* Run a test to verify that we can complete a start and stop media playback
* cycle for an screenshare LocalMediaStream on a video HTMLMediaElement.

View File

@ -19,8 +19,6 @@ https://bugzilla.mozilla.org/show_bug.cgi?id=781534
</div>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
/**
* Run a test to verify that we can complete a start and stop media playback
* cycle for an video LocalMediaStream on a video HTMLMediaElement.

View File

@ -19,8 +19,6 @@ https://bugzilla.mozilla.org/show_bug.cgi?id=781534
</div>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
/**
* Run a test to verify that we can complete a start and stop media playback
* cycle for a video and audio LocalMediaStream on a video HTMLMediaElement.

View File

@ -19,8 +19,6 @@ https://bugzilla.mozilla.org/show_bug.cgi?id=983504
</div>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
/**
* Run a test to verify that we can complete a start and stop media playback
* cycle for an screenshare LocalMediaStream on a video HTMLMediaElement.

View File

@ -20,8 +20,6 @@ https://bugzilla.mozilla.org/show_bug.cgi?id=822109
</div>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
/**
* Run a test that we can complete a playback cycle for a video,
* then upon completion, do a playback cycle with audio, such that

View File

@ -19,8 +19,6 @@ https://bugzilla.mozilla.org/show_bug.cgi?id=942367
</div>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
function theTest() {
function testPeerIdentityConstraint(withConstraint, done) {
var config = { audio: true, video: true, fake: true };

View File

@ -19,8 +19,6 @@ https://bugzilla.mozilla.org/show_bug.cgi?id=822109
</div>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
/**
* Run a test that we can complete an audio playback cycle twice in a row.
*/

View File

@ -19,8 +19,6 @@ https://bugzilla.mozilla.org/show_bug.cgi?id=822109
</div>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
/**
* Run a test that we can complete a video playback cycle twice in a row.
*/

View File

@ -19,8 +19,6 @@ https://bugzilla.mozilla.org/show_bug.cgi?id=822109
</div>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
/**
* Run a test that we can complete a video playback cycle twice in a row.
*/

View File

@ -19,8 +19,6 @@ https://bugzilla.mozilla.org/show_bug.cgi?id=822109
</div>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
/**
* Run a test to verify that we can start an audio stream in a media element,
* call stop() on the stream, and successfully get an ended event fired.

View File

@ -19,8 +19,6 @@ https://bugzilla.mozilla.org/show_bug.cgi?id=822109
</div>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
/**
* Run a test to verify that I can complete an audio gum playback in a media
* element, stop the stream, and then complete another audio gum playback

View File

@ -19,8 +19,6 @@ https://bugzilla.mozilla.org/show_bug.cgi?id=822109
</div>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
/**
* Run a test to verify that we can start a video+audio stream in a
* media element, call stop() on the stream, and successfully get an

View File

@ -19,8 +19,6 @@ https://bugzilla.mozilla.org/show_bug.cgi?id=822109
</div>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
/**
* Run a test to verify that I can complete an video+audio gum playback in a
* media element, stop the stream, and then complete another video+audio gum

View File

@ -19,8 +19,6 @@ https://bugzilla.mozilla.org/show_bug.cgi?id=822109
</div>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
/**
* Run a test to verify that we can start a video stream in a media element,
* call stop() on the stream, and successfully get an ended event fired.

View File

@ -19,8 +19,6 @@ https://bugzilla.mozilla.org/show_bug.cgi?id=822109
</div>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
/**
* Run a test to verify that I can complete an audio gum playback in a media
* element, stop the stream, and then complete another audio gum playback

View File

@ -12,8 +12,6 @@
<body>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
createHTML({
bug: "784519",
title: "addCandidate (answer) in 'have-local-offer'"

View File

@ -12,8 +12,6 @@
<body>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
createHTML({
bug: "796892",
title: "Basic audio-only peer connection"

View File

@ -12,8 +12,6 @@
<body>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
createHTML({
bug: "796890",
title: "Basic audio/video (separate) peer connection"

View File

@ -12,8 +12,6 @@
<body>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
createHTML({
bug: "796890",
title: "Basic audio/video (combined) peer connection"

View File

@ -12,8 +12,6 @@
<body>
<pre id="test">
<script type="application/javascript;version=1.8">
SimpleTest.requestFlakyTimeout("untriaged");
createHTML({
bug: "1040346",
title: "Basic H.264 GMP video-only peer connection"

View File

@ -12,8 +12,6 @@
<body>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
createHTML({
bug: "1039666",
title: "Basic screenshare-only peer connection"

View File

@ -12,8 +12,6 @@
<body>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
createHTML({
bug: "796888",
title: "Basic video-only peer connection"

View File

@ -12,8 +12,6 @@
<body>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
createHTML({
bug: "1038926",
title: "Basic windowshare-only peer connection"

View File

@ -11,8 +11,6 @@
<body>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
createHTML({
bug: "1013809",
title: "Audio-only peer connection with swapped setLocal and setRemote steps"

View File

@ -12,8 +12,6 @@
<body>
<pre id="test">
<script type="application/javascript;version=1.8">
SimpleTest.requestFlakyTimeout("untriaged");
createHTML({
bug: "1040346",
title: "Basic H.264 GMP video-only peer connection"

View File

@ -11,8 +11,6 @@
<body>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
createHTML({
bug: "827843",
title: "Ensure that localDescription and remoteDescription are null after close"

View File

@ -13,8 +13,6 @@
<video id="v1" src="../../test/vp9cake.webm" height="120" width="160" autoplay muted></video>
<pre id="test">
<script type="application/javascript;version=1.8">
SimpleTest.requestFlakyTimeout("untriaged");
createHTML({
bug: "1081409",
title: "Captured video-only over peer connection",

View File

@ -9,8 +9,6 @@
<body>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
createHTML({
bug: "991877",
title: "Basic RTCPeerConnection.close() tests"

View File

@ -13,8 +13,6 @@
<body>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
createHTML({
bug: "1060102",
title: "Basic audio only SDP answer without trickle ICE"

View File

@ -13,8 +13,6 @@
<body>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
createHTML({
bug: "1060102",
title: "Basic audio only SDP offer without trickle ICE"

View File

@ -13,8 +13,6 @@
<body>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
createHTML({
bug: "1060102",
title: "Basic audio only SDP offer and answer without trickle ICE"

View File

@ -11,8 +11,6 @@
<body>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
createHTML({
bug: "850275",
title: "Simple offer media constraint test with audio"

View File

@ -11,8 +11,6 @@
<body>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
createHTML({
bug: "850275",
title: "Simple offer media constraint test with video"

View File

@ -11,8 +11,6 @@
<body>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
createHTML({
bug: "850275",
title: "Simple offer media constraint test with video/audio"

View File

@ -12,8 +12,6 @@
<body>
<pre id="test">
<script type="application/javascript;version=1.8">
SimpleTest.requestFlakyTimeout("untriaged");
createHTML({
bug: "1032839",
title: "Replace video track",

View File

@ -12,8 +12,6 @@
<body>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
createHTML({
bug: "784519",
title: "setLocalDescription (answer) in 'have-local-offer'"

View File

@ -12,8 +12,6 @@
<body>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
createHTML({
bug: "784519",
title: "setLocalDescription (answer) in 'stable'"

View File

@ -12,8 +12,6 @@
<body>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
createHTML({
bug: "784519",
title: "setLocalDescription (offer) in 'have-remote-offer'"

View File

@ -12,8 +12,6 @@
<body>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
createHTML({
bug: "784519",
title: "setRemoteDescription (answer) in 'have-remote-offer'"

View File

@ -12,8 +12,6 @@
<body>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
createHTML({
bug: "784519",
title: "setRemoteDescription (answer) in 'stable'"

View File

@ -12,8 +12,6 @@
<body>
<pre id="test">
<script type="application/javascript">
SimpleTest.requestFlakyTimeout("untriaged");
createHTML({
bug: "784519",
title: "setRemoteDescription (offer) in 'have-local-offer'"

View File

@ -12,8 +12,6 @@
<body>
<pre id="test">
<script type="application/javascript;version=1.8">
SimpleTest.requestFlakyTimeout("untriaged");
createHTML({
bug: "1063971",
title: "Legacy sync setDescription calls",

View File

@ -115,7 +115,7 @@ PluginModuleContentParent::LoadModule(uint32_t aPluginId)
* sSavedModuleParent. We fetch it from there after LoadPlugin finishes.
*/
dom::ContentChild* cp = dom::ContentChild::GetSingleton();
if (!cp->CallLoadPlugin(aPluginId)) {
if (!cp->SendLoadPlugin(aPluginId)) {
return nullptr;
}
@ -571,6 +571,7 @@ PluginModuleChromeParent::ShouldContinueFromReplyTimeout()
FinishHangUI();
#endif // XP_WIN
TerminateChildProcess(MessageLoop::current());
GetIPCChannel()->CloseWithTimeout();
return false;
}

View File

@ -41,6 +41,7 @@
#include "nsIMobileConnectionInfo.h"
#include "nsIMobileConnectionService.h"
#include "nsIMobileCellInfo.h"
#include "nsIMobileNetworkInfo.h"
#include "nsIRadioInterfaceLayer.h"
#endif
@ -502,23 +503,35 @@ GonkGPSGeolocationProvider::SetReferenceLocation()
return;
}
nsCOMPtr<nsIRilContext> rilCtx;
mRadioInterface->GetRilContext(getter_AddRefs(rilCtx));
AGpsRefLocation location;
// TODO: Bug 772750 - get mobile connection technology from rilcontext
location.type = AGPS_REF_LOCATION_TYPE_UMTS_CELLID;
if (rilCtx) {
nsCOMPtr<nsIIccInfo> iccInfo;
rilCtx->GetIccInfo(getter_AddRefs(iccInfo));
if (iccInfo) {
nsCOMPtr<nsIMobileConnectionService> service =
do_GetService(NS_MOBILE_CONNECTION_SERVICE_CONTRACTID);
if (!service) {
NS_WARNING("Cannot get MobileConnectionService");
return;
}
nsCOMPtr<nsIMobileConnection> connection;
// TODO: Bug 878748 - B2G GPS: acquire correct RadioInterface instance in
// MultiSIM configuration
service->GetItemByServiceId(0 /* Client Id */, getter_AddRefs(connection));
NS_ENSURE_TRUE_VOID(connection);
nsCOMPtr<nsIMobileConnectionInfo> voice;
connection->GetVoice(getter_AddRefs(voice));
if (voice) {
nsCOMPtr<nsIMobileNetworkInfo> networkInfo;
voice->GetNetwork(getter_AddRefs(networkInfo));
if (networkInfo) {
nsresult result;
nsAutoString mcc, mnc;
iccInfo->GetMcc(mcc);
iccInfo->GetMnc(mnc);
networkInfo->GetMcc(mcc);
networkInfo->GetMnc(mnc);
location.u.cellID.mcc = mcc.ToInteger(&result);
if (result != NS_OK) {
@ -531,47 +544,41 @@ GonkGPSGeolocationProvider::SetReferenceLocation()
NS_WARNING("Cannot parse mnc to integer");
location.u.cellID.mnc = 0;
}
} else {
NS_WARNING("Cannot get mobile network info.");
location.u.cellID.mcc = 0;
location.u.cellID.mnc = 0;
}
nsCOMPtr<nsIMobileConnectionService> service =
do_GetService(NS_MOBILE_CONNECTION_SERVICE_CONTRACTID);
if (!service) {
NS_WARNING("Cannot get MobileConnectionService");
return;
}
nsCOMPtr<nsIMobileCellInfo> cell;
voice->GetCell(getter_AddRefs(cell));
if (cell) {
int32_t lac;
int64_t cid;
nsCOMPtr<nsIMobileConnection> connection;
// TODO: Bug 878748 - B2G GPS: acquire correct RadioInterface instance in
// MultiSIM configuration
service->GetItemByServiceId(0 /* Client Id */, getter_AddRefs(connection));
NS_ENSURE_TRUE_VOID(connection);
nsCOMPtr<nsIMobileConnectionInfo> voice;
connection->GetVoice(getter_AddRefs(voice));
if (voice) {
nsCOMPtr<nsIMobileCellInfo> cell;
voice->GetCell(getter_AddRefs(cell));
if (cell) {
int32_t lac;
int64_t cid;
cell->GetGsmLocationAreaCode(&lac);
// The valid range of LAC is 0x0 to 0xffff which is defined in
// hardware/ril/include/telephony/ril.h
if (lac >= 0x0 && lac <= 0xffff) {
location.u.cellID.lac = lac;
}
cell->GetGsmCellId(&cid);
// The valid range of cell id is 0x0 to 0xffffffff which is defined in
// hardware/ril/include/telephony/ril.h
if (cid >= 0x0 && cid <= 0xffffffff) {
location.u.cellID.cid = cid;
}
cell->GetGsmLocationAreaCode(&lac);
// The valid range of LAC is 0x0 to 0xffff which is defined in
// hardware/ril/include/telephony/ril.h
if (lac >= 0x0 && lac <= 0xffff) {
location.u.cellID.lac = lac;
}
cell->GetGsmCellId(&cid);
// The valid range of cell id is 0x0 to 0xffffffff which is defined in
// hardware/ril/include/telephony/ril.h
if (cid >= 0x0 && cid <= 0xffffffff) {
location.u.cellID.cid = cid;
}
} else {
NS_WARNING("Cannot get mobile gell info.");
location.u.cellID.lac = -1;
location.u.cellID.cid = -1;
}
mAGpsRilInterface->set_ref_location(&location, sizeof(location));
} else {
NS_WARNING("Cannot get mobile connection info.");
return;
}
mAGpsRilInterface->set_ref_location(&location, sizeof(location));
}
#endif // MOZ_B2G_RIL

View File

@ -0,0 +1,41 @@
/*
* TestSever customized specifically for the needs of:
* Bug 1080987 - navigator.sendBeacon() needs to sent origin header
*/
function handleRequest(request, response)
{
response.setHeader("Cache-Control", "no-cache", false);
response.setHeader("Content-Type", "text/plain", false);
// case XHR-REQUEST: the xhr-request tries to query the
// stored header from the beacon request.
if (request.queryString == "queryheader") {
var header = getState("originHeader");
// if the beacon already stored the header - return.
if (header) {
response.write(header);
setState("originHeader", "");
return;
}
// otherwise wait for the beacon request
response.processAsync();
setObjectState("xhr-response", response);
return;
}
// case BEACON-REQUEST: get the beacon header and
// store the header on the server.
var header = request.getHeader("origin");
setState("originHeader", header);
// if there is an xhr-request waiting, return the header now.
getObjectState("xhr-response", function(xhrResponse) {
if (!xhrResponse) {
return;
}
setState("originHeader", "");
xhrResponse.write(header);
xhrResponse.finish();
});
}

View File

@ -2,8 +2,10 @@
skip-if = buildapp == 'b2g' || e10s
support-files = beacon-frame.html
beacon-handler.sjs
beacon-originheader-handler.sjs
[test_beacon.html]
[test_beaconFrame.html]
[test_beaconPreflight.html]
[test_beaconContentPolicy.html]
[test_beaconOriginHeader.html]

View File

@ -0,0 +1,64 @@
<!DOCTYPE HTML>
<html>
<head>
<title>Bug 1080987 - navigator.sendBeacon() needs to sent origin header</title>
<!-- Including SimpleTest.js so we can use waitForExplicitFinish !-->
<script type="text/javascript" src="/tests/SimpleTest/SimpleTest.js"></script>
<link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css" />
</head>
<body>
<p id="display"></p>
<div id="content" style="visibility: hidden">
<iframe style="width:100%;" id="testframe"></iframe>
</div>
<script class="testbody" type="text/javascript">
SimpleTest.waitForExplicitFinish();
const BEACON_URL = "http://example.com/tests/dom/tests/mochitest/beacon/beacon-originheader-handler.sjs";
const ORIGIN_HEADER = "http://mochi.test:8888";
/* Description of the test:
* We call sendBeacon() cross origin and make sure that the
* origin header is actually set in the request.
*
* Since sendBeacon() does not expect any response, we are storing the
* header on the server (*.sjs) and use an XMLHttpRequest to actually
* retrieve the header back from the server. We assert that the header
* is indeed correct. Since sendBeacon() and also the XMLHttpRequest()
* are performed in an asynchronous fashion, there is no guarantee that
* the sendBeacon() is actually executed before the XMLHttpRequest().
* Hence the xhr-response might be processed asynchronously.
*/
SpecialPowers.pushPrefEnv({'set': [["beacon.enabled", true]]}, runTest);
function queryHeaderFromServer() {
var xhr = new XMLHttpRequest();
xhr.open("GET", "beacon-originheader-handler.sjs?queryheader", true);
xhr.onload = function() {
is(xhr.responseText, ORIGIN_HEADER, "SendBeacon sends right origin header");
SimpleTest.finish();
};
xhr.onerror = function() {
ok(false, "xhr request returned error");
SimpleTest.finish();
};
xhr.send();
}
function runTest() {
// generate data and send beacon
var formData = new FormData();
formData.append('name', 'value');
navigator.sendBeacon(BEACON_URL, formData);
// start quering the result from the server
queryHeaderFromServer();
}
</script>
</pre>
</body>
</html>

View File

@ -259,7 +259,6 @@ class ServiceWorkerUpdateInstance MOZ_FINAL : public nsISupports
{
nsRefPtr<ServiceWorkerRegistrationInfo> mRegistration;
nsCString mScriptSpec;
nsCOMPtr<nsPIDOMWindow> mWindow;
bool mAborted;
@ -268,12 +267,10 @@ class ServiceWorkerUpdateInstance MOZ_FINAL : public nsISupports
public:
NS_DECL_ISUPPORTS
ServiceWorkerUpdateInstance(ServiceWorkerRegistrationInfo *aRegistration,
nsPIDOMWindow* aWindow)
explicit ServiceWorkerUpdateInstance(ServiceWorkerRegistrationInfo *aRegistration)
: mRegistration(aRegistration),
// Capture the current script spec in case register() gets called.
mScriptSpec(aRegistration->mScriptSpec),
mWindow(aWindow),
mAborted(false)
{
AssertIsOnMainThread();
@ -300,10 +297,8 @@ public:
MOZ_ASSERT(swm);
nsRefPtr<ServiceWorker> serviceWorker;
nsresult rv = swm->CreateServiceWorkerForWindow(mWindow,
mScriptSpec,
mRegistration->mScope,
getter_AddRefs(serviceWorker));
nsresult rv = swm->CreateServiceWorker(mScriptSpec, mRegistration->mScope,
getter_AddRefs(serviceWorker));
if (NS_WARN_IF(NS_FAILED(rv))) {
swm->RejectUpdatePromiseObservers(mRegistration, rv);
return;
@ -332,7 +327,7 @@ public:
nsRefPtr<ServiceWorkerManager> swm = ServiceWorkerManager::GetInstance();
MOZ_ASSERT(swm);
swm->FinishFetch(mRegistration, mWindow);
swm->FinishFetch(mRegistration);
}
};
@ -477,7 +472,7 @@ public:
registration->mScriptSpec = spec;
rv = swm->Update(registration, mWindow);
rv = swm->Update(registration);
MOZ_ASSERT(registration->HasUpdatePromise());
// We append this register() call's promise after calling Update() because
@ -950,9 +945,8 @@ ServiceWorkerManager::RejectUpdatePromiseObservers(ServiceWorkerRegistrationInfo
* Update() does not return the Promise that the spec says it should. Callers
* may access the registration's (new) Promise after calling this method.
*/
NS_IMETHODIMP
ServiceWorkerManager::Update(ServiceWorkerRegistrationInfo* aRegistration,
nsPIDOMWindow* aWindow)
nsresult
ServiceWorkerManager::Update(ServiceWorkerRegistrationInfo* aRegistration)
{
if (aRegistration->HasUpdatePromise()) {
NS_WARNING("Already had a UpdatePromise. Aborting that one!");
@ -977,7 +971,7 @@ ServiceWorkerManager::Update(ServiceWorkerRegistrationInfo* aRegistration,
// FIXME(nsm): Bug 931249. Force cache update if > 1 day.
aRegistration->mUpdateInstance =
new ServiceWorkerUpdateInstance(aRegistration, aWindow);
new ServiceWorkerUpdateInstance(aRegistration);
aRegistration->mUpdateInstance->Update();
return NS_OK;
@ -1101,8 +1095,7 @@ ServiceWorkerManager::ResolveRegisterPromises(ServiceWorkerRegistrationInfo* aRe
// Must NS_Free() aString
void
ServiceWorkerManager::FinishFetch(ServiceWorkerRegistrationInfo* aRegistration,
nsPIDOMWindow* aWindow)
ServiceWorkerManager::FinishFetch(ServiceWorkerRegistrationInfo* aRegistration)
{
AssertIsOnMainThread();
@ -1117,10 +1110,9 @@ ServiceWorkerManager::FinishFetch(ServiceWorkerRegistrationInfo* aRegistration,
// We have skipped Steps 3-8.3 of the Update algorithm here!
nsRefPtr<ServiceWorker> worker;
nsresult rv = CreateServiceWorkerForWindow(aWindow,
aRegistration->mScriptSpec,
aRegistration->mScope,
getter_AddRefs(worker));
nsresult rv = CreateServiceWorker(aRegistration->mScriptSpec,
aRegistration->mScope,
getter_AddRefs(worker));
if (NS_WARN_IF(NS_FAILED(rv))) {
RejectUpdatePromiseObservers(aRegistration, rv);
@ -2164,6 +2156,36 @@ ServiceWorkerManager::InvalidateServiceWorkerRegistrationWorker(ServiceWorkerReg
}
}
NS_IMETHODIMP
ServiceWorkerManager::Update(const nsAString& aScope)
{
NS_ConvertUTF16toUTF8 scope(aScope);
nsRefPtr<ServiceWorkerManager::ServiceWorkerDomainInfo> domainInfo =
GetDomainInfo(scope);
if (NS_WARN_IF(!domainInfo)) {
return NS_OK;
}
nsRefPtr<ServiceWorkerRegistrationInfo> registration;
domainInfo->mServiceWorkerRegistrationInfos.Get(scope,
getter_AddRefs(registration));
if (NS_WARN_IF(!registration)) {
return NS_OK;
}
if (registration->mPendingUninstall) {
return NS_OK;
}
if (registration->mInstallingWorker) {
return NS_OK;
}
Update(registration);
return NS_OK;
}
namespace {
class MOZ_STACK_CLASS FilterRegistrationData

View File

@ -297,8 +297,7 @@ public:
const ErrorEventInit& aErrorDesc);
void
FinishFetch(ServiceWorkerRegistrationInfo* aRegistration,
nsPIDOMWindow* aWindow);
FinishFetch(ServiceWorkerRegistrationInfo* aRegistration);
void
FinishInstall(ServiceWorkerRegistrationInfo* aRegistration);
@ -331,8 +330,8 @@ private:
void
AbortCurrentUpdate(ServiceWorkerRegistrationInfo* aRegistration);
NS_IMETHOD
Update(ServiceWorkerRegistrationInfo* aRegistration, nsPIDOMWindow* aWindow);
nsresult
Update(ServiceWorkerRegistrationInfo* aRegistration);
void
Install(ServiceWorkerRegistrationInfo* aRegistration,

View File

@ -73,7 +73,6 @@
#include "nsProxyRelease.h"
#include "nsSandboxFlags.h"
#include "prthread.h"
#include "nsThread.h"
#include "xpcpublic.h"
#ifdef ANDROID
@ -4333,17 +4332,6 @@ WorkerPrivate::DoRunLoop(JSContext* aCx)
{
MutexAutoLock lock(mMutex);
#ifdef MOZ_NUWA_PROCESS
{
nsThread *thr = static_cast<nsThread*>(NS_GetCurrentThread());
ReentrantMonitorAutoEnter mon(thr->ThreadStatusMonitor());
if (mControlQueue.IsEmpty() &&
!(normalRunnablesPending = NS_HasPendingEvents(mThread))) {
thr->SetIdle();
}
}
#endif // MOZ_NUWA_PROCESS
while (mControlQueue.IsEmpty() &&
!(normalRunnablesPending = NS_HasPendingEvents(mThread))) {
WaitForWorkerEvents();
@ -4853,6 +4841,15 @@ WorkerPrivate::WaitForWorkerEvents(PRIntervalTime aInterval)
// The main thread may be waiting so we must notify.
mMemoryReportCondVar.Notify();
#ifdef MOZ_NUWA_PROCESS
{
MOZ_ASSERT(mThread);
ReentrantMonitorAutoEnter mon(mThread->ThreadStatusMonitor());
mThread->SetIdle();
}
#endif // MOZ_NUWA_PROCESS
// Now wait for an actual worker event.
mCondVar.Wait(aInterval);

View File

@ -639,4 +639,45 @@ ServiceWorkerGlobalScope::Unregister(ErrorResult& aRv)
return promise.forget();
}
namespace {
class UpdateRunnable MOZ_FINAL : public nsRunnable
{
nsString mScope;
public:
explicit UpdateRunnable(const nsAString& aScope)
: mScope(aScope)
{ }
NS_IMETHODIMP
Run()
{
AssertIsOnMainThread();
nsresult rv;
nsCOMPtr<nsIServiceWorkerManager> swm =
do_GetService(SERVICEWORKERMANAGER_CONTRACTID, &rv);
if (NS_WARN_IF(NS_FAILED(rv))) {
return NS_OK;
}
swm->Update(mScope);
return NS_OK;
}
};
} //anonymous namespace
void
ServiceWorkerGlobalScope::Update()
{
mWorkerPrivate->AssertIsOnWorkerThread();
MOZ_ASSERT(mWorkerPrivate->IsServiceWorker());
nsRefPtr<UpdateRunnable> runnable =
new UpdateRunnable(mScope);
NS_DispatchToMainThread(runnable);
}
END_WORKERS_NAMESPACE

Some files were not shown because too many files have changed in this diff Show More