mirror of
https://gitlab.winehq.org/wine/wine-gecko.git
synced 2024-09-13 09:24:08 -07:00
Merge m-c to fx-team.
This commit is contained in:
commit
b85bb04b05
@ -176,9 +176,10 @@ static nsRoleMapEntry sWAIRoleMaps[] =
|
||||
eNoAction,
|
||||
eNoLiveAttr,
|
||||
eSelect | eTable,
|
||||
states::FOCUSABLE,
|
||||
kNoReqStates,
|
||||
eARIAMultiSelectable,
|
||||
eARIAReadonlyOrEditable
|
||||
eARIAReadonlyOrEditable,
|
||||
eFocusableUntilDisabled
|
||||
},
|
||||
{ // gridcell
|
||||
&nsGkAtoms::gridcell,
|
||||
@ -263,7 +264,8 @@ static nsRoleMapEntry sWAIRoleMaps[] =
|
||||
eListControl | eSelect,
|
||||
kNoReqStates,
|
||||
eARIAMultiSelectable,
|
||||
eARIAReadonly
|
||||
eARIAReadonly,
|
||||
eFocusableUntilDisabled
|
||||
},
|
||||
{ // listitem
|
||||
&nsGkAtoms::listitem,
|
||||
@ -605,7 +607,8 @@ static nsRoleMapEntry sWAIRoleMaps[] =
|
||||
eSelect,
|
||||
kNoReqStates,
|
||||
eARIAReadonly,
|
||||
eARIAMultiSelectable
|
||||
eARIAMultiSelectable,
|
||||
eFocusableUntilDisabled
|
||||
},
|
||||
{ // treegrid
|
||||
&nsGkAtoms::treegrid,
|
||||
@ -617,7 +620,8 @@ static nsRoleMapEntry sWAIRoleMaps[] =
|
||||
eSelect | eTable,
|
||||
kNoReqStates,
|
||||
eARIAReadonly,
|
||||
eARIAMultiSelectable
|
||||
eARIAMultiSelectable,
|
||||
eFocusableUntilDisabled
|
||||
},
|
||||
{ // treeitem
|
||||
&nsGkAtoms::treeitem,
|
||||
|
@ -5,6 +5,7 @@
|
||||
* You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
#include "ARIAMap.h"
|
||||
#include "nsAccUtils.h"
|
||||
#include "States.h"
|
||||
|
||||
#include "mozilla/dom/Element.h"
|
||||
@ -327,6 +328,16 @@ aria::MapToState(EStateRule aRule, dom::Element* aElement, uint64_t* aState)
|
||||
return true;
|
||||
}
|
||||
|
||||
case eFocusableUntilDisabled:
|
||||
{
|
||||
if (!nsAccUtils::HasDefinedARIAToken(aElement, nsGkAtoms::aria_disabled) ||
|
||||
aElement->AttrValueIs(kNameSpaceID_None, nsGkAtoms::aria_disabled,
|
||||
nsGkAtoms::_false, eCaseMatters))
|
||||
*aState |= states::FOCUSABLE;
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
default:
|
||||
return false;
|
||||
}
|
||||
|
@ -44,7 +44,8 @@ enum EStateRule
|
||||
eARIASelectable,
|
||||
eARIASelectableIfDefined,
|
||||
eReadonlyUntilEditable,
|
||||
eIndeterminateIfNoValue
|
||||
eIndeterminateIfNoValue,
|
||||
eFocusableUntilDisabled
|
||||
};
|
||||
|
||||
/**
|
||||
|
@ -718,33 +718,19 @@ HyperTextAccessible::GetRelativeOffset(nsIPresShell* aPresShell,
|
||||
0, kIsJumpLinesOk, kIsScrollViewAStop, kIsKeyboardSelect, kIsVisualBidi,
|
||||
aWordMovementType);
|
||||
rv = aFromFrame->PeekOffset(&pos);
|
||||
if (NS_FAILED(rv)) {
|
||||
pos.mResultContent = aFromFrame->GetContent();
|
||||
if (aDirection == eDirPrevious) {
|
||||
// Use passed-in frame as starting point in failure case for now,
|
||||
// this is a hack to deal with starting on a list bullet frame,
|
||||
// which fails in PeekOffset() because the line iterator doesn't see it.
|
||||
// XXX Need to look at our overall handling of list bullets, which are an odd case
|
||||
int32_t endOffsetUnused;
|
||||
aFromFrame->GetOffsets(pos.mContentOffset, endOffsetUnused);
|
||||
}
|
||||
else {
|
||||
// XXX: PeekOffset fails on a last frame in the document for
|
||||
// eSelectLine/eDirNext. DOM selection (up/down arrowing processing) has
|
||||
// similar code to handle this case. One day it should be incorporated
|
||||
// into PeekOffset.
|
||||
int32_t startOffsetUnused;
|
||||
aFromFrame->GetOffsets(startOffsetUnused, pos.mContentOffset);
|
||||
}
|
||||
}
|
||||
|
||||
// Turn the resulting node and offset into a hyperTextOffset
|
||||
int32_t hyperTextOffset;
|
||||
// PeekOffset fails on last/first lines of the text in certain cases.
|
||||
if (NS_FAILED(rv) && aAmount == eSelectLine) {
|
||||
pos.mAmount = (aDirection == eDirNext) ? eSelectEndLine : eSelectBeginLine;
|
||||
aFromFrame->PeekOffset(&pos);
|
||||
}
|
||||
if (!pos.mResultContent)
|
||||
return -1;
|
||||
|
||||
// Turn the resulting node and offset into a hyperTextOffset
|
||||
// If finalAccessible is nullptr, then DOMPointToHypertextOffset() searched
|
||||
// through the hypertext children without finding the node/offset position.
|
||||
int32_t hyperTextOffset;
|
||||
Accessible* finalAccessible =
|
||||
DOMPointToHypertextOffset(pos.mResultContent, pos.mContentOffset,
|
||||
&hyperTextOffset, aDirection == eDirNext);
|
||||
|
@ -201,6 +201,9 @@ this.AccessFu = {
|
||||
case 'AccessFu:ActivateContextMenu':
|
||||
this.Input.activateContextMenu(aMessage.json);
|
||||
break;
|
||||
case 'AccessFu:DoScroll':
|
||||
this.Input.doScroll(aMessage.json);
|
||||
break;
|
||||
}
|
||||
},
|
||||
|
||||
@ -240,6 +243,7 @@ this.AccessFu = {
|
||||
aMessageManager.addMessageListener('AccessFu:Input', this);
|
||||
aMessageManager.addMessageListener('AccessFu:Ready', this);
|
||||
aMessageManager.addMessageListener('AccessFu:ActivateContextMenu', this);
|
||||
aMessageManager.addMessageListener('AccessFu:DoScroll', this);
|
||||
},
|
||||
|
||||
_removeMessageListeners: function _removeMessageListeners(aMessageManager) {
|
||||
@ -247,6 +251,7 @@ this.AccessFu = {
|
||||
aMessageManager.removeMessageListener('AccessFu:Input', this);
|
||||
aMessageManager.removeMessageListener('AccessFu:Ready', this);
|
||||
aMessageManager.removeMessageListener('AccessFu:ActivateContextMenu', this);
|
||||
aMessageManager.removeMessageListener('AccessFu:DoScroll', this);
|
||||
},
|
||||
|
||||
_handleMessageManager: function _handleMessageManager(aMessageManager) {
|
||||
@ -668,16 +673,16 @@ var Input = {
|
||||
this.moveCursor('movePrevious', 'Simple', 'gesture');
|
||||
break;
|
||||
case 'swiperight2':
|
||||
this.scroll(-1, true);
|
||||
this.sendScrollMessage(-1, true);
|
||||
break;
|
||||
case 'swipedown2':
|
||||
this.scroll(-1);
|
||||
this.sendScrollMessage(-1);
|
||||
break;
|
||||
case 'swipeleft2':
|
||||
this.scroll(1, true);
|
||||
this.sendScrollMessage(1, true);
|
||||
break;
|
||||
case 'swipeup2':
|
||||
this.scroll(1);
|
||||
this.sendScrollMessage(1);
|
||||
break;
|
||||
case 'explore2':
|
||||
Utils.CurrentBrowser.contentWindow.scrollBy(
|
||||
@ -820,9 +825,9 @@ var Input = {
|
||||
mm.sendAsyncMessage('AccessFu:ContextMenu', {});
|
||||
},
|
||||
|
||||
activateContextMenu: function activateContextMenu(aMessage) {
|
||||
activateContextMenu: function activateContextMenu(aDetails) {
|
||||
if (Utils.MozBuildApp === 'mobile/android') {
|
||||
let p = AccessFu.adjustContentBounds(aMessage.bounds, Utils.CurrentBrowser,
|
||||
let p = AccessFu.adjustContentBounds(aDetails.bounds, Utils.CurrentBrowser,
|
||||
true, true).center();
|
||||
Services.obs.notifyObservers(null, 'Gesture:LongPress',
|
||||
JSON.stringify({x: p.x, y: p.y}));
|
||||
@ -833,11 +838,29 @@ var Input = {
|
||||
this.editState = aEditState;
|
||||
},
|
||||
|
||||
// XXX: This is here for backwards compatability with screen reader simulator
|
||||
// it should be removed when the extension is updated on amo.
|
||||
scroll: function scroll(aPage, aHorizontal) {
|
||||
this.sendScrollMessage(aPage, aHorizontal);
|
||||
},
|
||||
|
||||
sendScrollMessage: function sendScrollMessage(aPage, aHorizontal) {
|
||||
let mm = Utils.getMessageManager(Utils.CurrentBrowser);
|
||||
mm.sendAsyncMessage('AccessFu:Scroll', {page: aPage, horizontal: aHorizontal, origin: 'top'});
|
||||
},
|
||||
|
||||
doScroll: function doScroll(aDetails) {
|
||||
let horizontal = aDetails.horizontal;
|
||||
let page = aDetails.page;
|
||||
let p = AccessFu.adjustContentBounds(aDetails.bounds, Utils.CurrentBrowser,
|
||||
true, true).center();
|
||||
let wu = Utils.win.QueryInterface(Ci.nsIInterfaceRequestor).
|
||||
getInterface(Ci.nsIDOMWindowUtils);
|
||||
wu.sendWheelEvent(p.x, p.y,
|
||||
horizontal ? page : 0, horizontal ? 0 : page, 0,
|
||||
Utils.win.WheelEvent.DOM_DELTA_PAGE, 0, 0, 0, 0);
|
||||
},
|
||||
|
||||
get keyMap() {
|
||||
delete this.keyMap;
|
||||
this.keyMap = {
|
||||
|
@ -306,80 +306,17 @@ function presentCaretChange(aText, aOldOffset, aNewOffset) {
|
||||
}
|
||||
|
||||
function scroll(aMessage) {
|
||||
let vc = Utils.getVirtualCursor(content.document);
|
||||
|
||||
function tryToScroll() {
|
||||
let horiz = aMessage.json.horizontal;
|
||||
let page = aMessage.json.page;
|
||||
|
||||
// Search up heirarchy for scrollable element.
|
||||
let acc = vc.position;
|
||||
while (acc) {
|
||||
let elem = acc.DOMNode;
|
||||
|
||||
// This is inspired by IndieUI events. Once they are
|
||||
// implemented, it should be easy to transition to them.
|
||||
// https://dvcs.w3.org/hg/IndieUI/raw-file/tip/src/indie-ui-events.html#scrollrequest
|
||||
let uiactions = elem.getAttribute ? elem.getAttribute('uiactions') : '';
|
||||
if (uiactions && uiactions.split(' ').indexOf('scroll') >= 0) {
|
||||
let evt = elem.ownerDocument.createEvent('CustomEvent');
|
||||
let details = horiz ? { deltaX: page * elem.clientWidth } :
|
||||
{ deltaY: page * elem.clientHeight };
|
||||
evt.initCustomEvent(
|
||||
'scrollrequest', true, true,
|
||||
ObjectWrapper.wrap(details, elem.ownerDocument.defaultView));
|
||||
if (!elem.dispatchEvent(evt))
|
||||
return;
|
||||
}
|
||||
|
||||
// We will do window scrolling next.
|
||||
if (elem == content.document)
|
||||
break;
|
||||
|
||||
if (!horiz && elem.clientHeight < elem.scrollHeight) {
|
||||
let s = content.getComputedStyle(elem);
|
||||
if (s.overflowY == 'scroll' || s.overflowY == 'auto') {
|
||||
elem.scrollTop += page * elem.clientHeight;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
|
||||
if (horiz) {
|
||||
if (elem.clientWidth < elem.scrollWidth) {
|
||||
let s = content.getComputedStyle(elem);
|
||||
if (s.overflowX == 'scroll' || s.overflowX == 'auto') {
|
||||
elem.scrollLeft += page * elem.clientWidth;
|
||||
return true;
|
||||
}
|
||||
}
|
||||
}
|
||||
acc = acc.parent;
|
||||
}
|
||||
|
||||
// Scroll window.
|
||||
if (!horiz && content.scrollMaxY &&
|
||||
((page > 0 && content.scrollY < content.scrollMaxY) ||
|
||||
(page < 0 && content.scrollY > 0))) {
|
||||
content.scroll(0, content.innerHeight * page + content.scrollY);
|
||||
return true;
|
||||
} else if (horiz && content.scrollMaxX &&
|
||||
((page > 0 && content.scrollX < content.scrollMaxX) ||
|
||||
(page < 0 && content.scrollX > 0))) {
|
||||
content.scroll(content.innerWidth * page + content.scrollX);
|
||||
return true;
|
||||
}
|
||||
|
||||
return false;
|
||||
function sendScrollCoordinates(aAccessible) {
|
||||
let bounds = Utils.getBounds(aAccessible);
|
||||
sendAsyncMessage('AccessFu:DoScroll',
|
||||
{ bounds: bounds,
|
||||
page: aMessage.json.page,
|
||||
horizontal: aMessage.json.horizontal });
|
||||
}
|
||||
|
||||
if (aMessage.json.origin != 'child' &&
|
||||
forwardToChild(aMessage, scroll, vc.position)) {
|
||||
return;
|
||||
}
|
||||
|
||||
if (!tryToScroll()) {
|
||||
// Failed to scroll anything in this document. Try in parent document.
|
||||
forwardToParent(aMessage);
|
||||
let position = Utils.getVirtualCursor(content.document).position;
|
||||
if (!forwardToChild(aMessage, scroll, position)) {
|
||||
sendScrollCoordinates(position);
|
||||
}
|
||||
}
|
||||
|
||||
|
@ -158,7 +158,7 @@ function isObject(aObj, aExpectedObj, aMsg)
|
||||
/**
|
||||
* Return the DOM node by identifier (may be accessible, DOM node or ID).
|
||||
*/
|
||||
function getNode(aAccOrNodeOrID)
|
||||
function getNode(aAccOrNodeOrID, aDocument)
|
||||
{
|
||||
if (!aAccOrNodeOrID)
|
||||
return null;
|
||||
@ -169,7 +169,7 @@ function getNode(aAccOrNodeOrID)
|
||||
if (aAccOrNodeOrID instanceof nsIAccessible)
|
||||
return aAccOrNodeOrID.DOMNode;
|
||||
|
||||
node = document.getElementById(aAccOrNodeOrID);
|
||||
node = (aDocument || document).getElementById(aAccOrNodeOrID);
|
||||
if (!node) {
|
||||
ok(false, "Can't get DOM element for " + aAccOrNodeOrID);
|
||||
return null;
|
||||
|
@ -198,6 +198,14 @@
|
||||
testStates("aria_progressbar_valuenow", 0, 0, STATE_MIXED);
|
||||
testStates("aria_progressbar_valuetext", 0, 0, STATE_MIXED);
|
||||
|
||||
testStates("aria_listbox", STATE_FOCUSABLE);
|
||||
testStates("aria_grid", STATE_FOCUSABLE);
|
||||
testStates("aria_tree", STATE_FOCUSABLE);
|
||||
testStates("aria_treegrid", STATE_FOCUSABLE);
|
||||
testStates("aria_listbox_disabled", 0, 0, STATE_FOCUSABLE);
|
||||
testStates("aria_grid_disabled", 0, 0, STATE_FOCUSABLE);
|
||||
testStates("aria_tree_disabled", 0, 0, STATE_FOCUSABLE);
|
||||
testStates("aria_treegrid_disabled", 0, 0, STATE_FOCUSABLE);
|
||||
SimpleTest.finish();
|
||||
}
|
||||
|
||||
@ -219,6 +227,11 @@
|
||||
title="Propagate aria-disabled to descendants">
|
||||
Mozilla Bug 429285
|
||||
</a>
|
||||
<a target="_blank"
|
||||
href="https://bugzilla.mozilla.org/show_bug.cgi?id=457226"
|
||||
title="Mochitests for ARIA states">
|
||||
Mozilla Bug 457226
|
||||
</a>
|
||||
<a target="_blank"
|
||||
href="https://bugzilla.mozilla.org/show_bug.cgi?id=499653"
|
||||
title="Unify ARIA state attributes mapping rules">
|
||||
@ -234,20 +247,20 @@
|
||||
title="aria-orientation should be applied to separator and slider roles">
|
||||
Mozilla Bug 681674
|
||||
</a>
|
||||
<a target="_blank"
|
||||
href="https://bugzilla.mozilla.org/show_bug.cgi?id=699017"
|
||||
title="File input control should be propogate states to descendants">
|
||||
Mozilla Bug 699017
|
||||
</a>
|
||||
<a target="_blank"
|
||||
href="https://bugzilla.mozilla.org/show_bug.cgi?id=689847"
|
||||
title="Expose active state on current item of selectable widgets">
|
||||
Mozilla Bug 689847
|
||||
</a>
|
||||
<a target="_blank"
|
||||
href="https://bugzilla.mozilla.org/show_bug.cgi?id=457226"
|
||||
title="Mochitests for ARIA states">
|
||||
Mozilla Bug 457226
|
||||
href="https://bugzilla.mozilla.org/show_bug.cgi?id=699017"
|
||||
title="File input control should be propogate states to descendants">
|
||||
Mozilla Bug 699017
|
||||
</a>
|
||||
<a target="_blank"
|
||||
href="https://bugzilla.mozilla.org/show_bug.cgi?id=690199"
|
||||
title="ARIA select widget should expose focusable state regardless the way they manage its children">
|
||||
Mozilla Bug 690199
|
||||
</a>
|
||||
<a target="_blank"
|
||||
href="https://bugzilla.mozilla.org/show_bug.cgi?id=740851"
|
||||
@ -255,15 +268,16 @@
|
||||
Mozilla Bug 740851
|
||||
</a>
|
||||
<a target="_blank"
|
||||
href="https://bugzilla.mozilla.org/show_bug.cgi?id=762876
|
||||
href="https://bugzilla.mozilla.org/show_bug.cgi?id=762876"
|
||||
title="fix default horizontal / vertical state of role=scrollbar and ensure only one of horizontal / vertical states is exposed">
|
||||
Mozilla Bug 762876
|
||||
</a>
|
||||
<a target="_blank"
|
||||
href="https://bugzilla.mozilla.org/show_bug.cgi?id=835121
|
||||
href="https://bugzilla.mozilla.org/show_bug.cgi?id=835121"
|
||||
title="ARIA grid should be editable by default">
|
||||
Mozilla Bug 835121
|
||||
</a>
|
||||
|
||||
<p id="display"></p>
|
||||
<div id="content" style="display: none"></div>
|
||||
<pre id="test">
|
||||
@ -413,5 +427,39 @@
|
||||
<div id="aria_progressbar" role="progressbar"></div>
|
||||
<div id="aria_progressbar_valuenow" role="progressbar" aria-valuenow="1"></div>
|
||||
<div id="aria_progressbar_valuetext" role="progressbar" aria-valuetext="value"></div>
|
||||
|
||||
<!-- ARIA select widget should expose focusable state regardless the way they manage its children -->
|
||||
<div id="aria_listbox" role="listbox">
|
||||
<div role="option" tabindex="0">A</div>
|
||||
<div role="option" tabindex="0">a</div>
|
||||
</div>
|
||||
<div id="aria_grid" role="grid">
|
||||
<div role="row"><div role="gridcell" tabindex="0">B</div></div></div>
|
||||
<div role="row"><div role="gridcell" tabindex="0">b</div></div></div>
|
||||
<div id="aria_tree" role="tree">
|
||||
<div role="treeitem" tabindex="0">C</div>
|
||||
<div role="treeitem" tabindex="0">c</div>
|
||||
</div>
|
||||
<div id="aria_treegrid" role="treegrid">
|
||||
<div role="row"><div role="gridcell" tabindex="0">D</div></div>
|
||||
<div role="row"><div role="gridcell" tabindex="0">d</div></div>
|
||||
</div>
|
||||
<div id="aria_listbox_disabled" role="listbox" aria-disabled="true">
|
||||
<div role="option">E</div>
|
||||
<div role="option">e</div>
|
||||
</div>
|
||||
<div id="aria_grid_disabled" role="grid" aria-disabled="true">
|
||||
<div role="row"><div role="gridcell">F</div></div>
|
||||
<div role="row"><div role="gridcell">f</div></div>
|
||||
</div>
|
||||
<div id="aria_tree_disabled" role="tree" aria-disabled="true">
|
||||
<div role="treeitem">G</div>
|
||||
<div role="treeitem">g</div>
|
||||
</div>
|
||||
<div id="aria_treegrid_disabled" role="treegrid" aria-disabled="true">
|
||||
<div role="row"><div role="gridcell">H</div></div>
|
||||
<div role="row"><div role="gridcell">h</div></div>
|
||||
</div>
|
||||
|
||||
</body>
|
||||
</html>
|
||||
|
@ -115,7 +115,7 @@
|
||||
// __w__o__r__d__s
|
||||
// 10 11 12 13 14 15
|
||||
|
||||
traverseTextByLines(gQueue, "textarea",
|
||||
traverseTextByLines(gQueue, "textarea",
|
||||
[ [ "aword", "\n", 0, 5 ],
|
||||
[ "two ", "", 6, 10 ],
|
||||
[ "words", "", 10, 15 ]] );
|
||||
|
@ -17,7 +17,8 @@
|
||||
// __h__e__l__l__o__ __m__y__ __f__r__i__e__n__d__
|
||||
// 0 1 2 3 4 5 6 7 8 9 10 11 12 13 14 15
|
||||
|
||||
var IDs = [ "input", "div", "editable", "textarea" ];
|
||||
var IDs = [ "input", "div", "editable", "textarea",
|
||||
getNode("ta", getNode("ta_cntr").contentDocument) ];
|
||||
|
||||
testTextBeforeOffset(IDs, BOUNDARY_LINE_START,
|
||||
[ [ 0, 15, "", 0, 0 ] ]);
|
||||
@ -76,6 +77,26 @@
|
||||
[ 9, 18, "\n", 18, 19 ],
|
||||
[ 19, 19, "", 19, 19 ]]);
|
||||
|
||||
//////////////////////////////////////////////////////////////////////////
|
||||
// a * b (* is embedded char for link)
|
||||
testTextBeforeOffset([ getAccessible("ht_1").firstChild ], BOUNDARY_LINE_START,
|
||||
[ [ 0, 5, "", 0, 0 ] ]);
|
||||
|
||||
testTextBeforeOffset([ getAccessible("ht_1").firstChild ], BOUNDARY_LINE_END,
|
||||
[ [ 0, 5, "", 0, 0 ] ]);
|
||||
|
||||
testTextAtOffset([ getAccessible("ht_1").firstChild ], BOUNDARY_LINE_START,
|
||||
[ [ 0, 5, "a " + kEmbedChar + " c", 0, 5 ] ]);
|
||||
|
||||
testTextAtOffset([ getAccessible("ht_1").firstChild ], BOUNDARY_LINE_END,
|
||||
[ [ 0, 5, "a " + kEmbedChar + " c", 0, 5 ] ]);
|
||||
|
||||
testTextAfterOffset([ getAccessible("ht_1").firstChild ], BOUNDARY_LINE_START,
|
||||
[ [ 0, 5, "", 5, 5 ] ]);
|
||||
|
||||
testTextAfterOffset([ getAccessible("ht_1").firstChild ], BOUNDARY_LINE_END,
|
||||
[ [ 0, 5, "", 5, 5 ] ]);
|
||||
|
||||
SimpleTest.finish();
|
||||
}
|
||||
|
||||
@ -110,6 +131,8 @@
|
||||
<div id="div">hello my friend</div>
|
||||
<div id="editable" contenteditable="true">hello my friend</div>
|
||||
<textarea id="textarea">hello my friend</textarea>
|
||||
<iframe id="ta_cntr"
|
||||
src="data:text/html,<html><body><textarea id='ta'>hello my friend</textarea></body></html>"></iframe>
|
||||
|
||||
<pre>
|
||||
<div id="ml_div">oneword
|
||||
@ -127,5 +150,7 @@ two words
|
||||
two words
|
||||
</textarea>
|
||||
</pre>
|
||||
|
||||
<iframe id="ht_1" src="data:text/html,<html><body>a <a href=''>b</a> c</body></html>"></iframe>
|
||||
</body>
|
||||
</html>
|
||||
|
@ -12,7 +12,7 @@ this.EXPORTED_SYMBOLS = ["TelURIParser"];
|
||||
this.TelURIParser = {
|
||||
parseURI: function(scheme, uri) {
|
||||
// https://www.ietf.org/rfc/rfc2806.txt
|
||||
let subscriber = uri.slice((scheme + ':').length);
|
||||
let subscriber = decodeURIComponent(uri.slice((scheme + ':').length));
|
||||
|
||||
if (!subscriber.length) {
|
||||
return null;
|
||||
@ -23,7 +23,7 @@ this.TelURIParser = {
|
||||
let len = subscriber.length;
|
||||
|
||||
// visual-separator
|
||||
let visualSeparator = [ '-', '.', '(', ')' ];
|
||||
let visualSeparator = [ ' ', '-', '.', '(', ')' ];
|
||||
let digits = [ '0', '1', '2', '3', '4', '5', '6', '7', '8', '9' ];
|
||||
let dtmfDigits = [ '*', '#', 'A', 'B', 'C', 'D' ];
|
||||
let pauseCharacter = [ 'p', 'w' ];
|
||||
|
@ -5,7 +5,10 @@ function run_test() {
|
||||
Components.utils.import("resource:///modules/TelURIParser.jsm")
|
||||
|
||||
// global-phone-number
|
||||
do_check_eq(TelURIParser.parseURI('tel', 'tel:+1234'), '+1234');
|
||||
do_check_eq(TelURIParser.parseURI('tel', 'tel:+1234'), '+1234');
|
||||
|
||||
// global-phone-number => white space separator
|
||||
do_check_eq(TelURIParser.parseURI('tel', 'tel:+123 456 789'), '+123 456 789');
|
||||
|
||||
// global-phone-number => ignored chars
|
||||
do_check_eq(TelURIParser.parseURI('tel', 'tel:+1234_123'), '+1234');
|
||||
|
@ -1,4 +1,4 @@
|
||||
{
|
||||
"revision": "72f1b7c657c65389c843dcd032e5bb787f4afafc",
|
||||
"revision": "f2454e95b24f028b6ebc1b1edb880c12f80454de",
|
||||
"repo_path": "/integration/gaia-central"
|
||||
}
|
||||
|
@ -241,6 +241,9 @@ static int do_main(int argc, char* argv[], nsIFile *xreDirectory)
|
||||
for (int idx = 1; idx < argc; idx++) {
|
||||
if (IsArg(argv[idx], "metrodesktop")) {
|
||||
metroOnDesktop = true;
|
||||
// Disable crash reporting when running in metrodesktop mode.
|
||||
char crashSwitch[] = "MOZ_CRASHREPORTER_DISABLE=1";
|
||||
putenv(crashSwitch);
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
@ -763,6 +763,12 @@ pref("browser.safebrowsing.reportMalwareErrorURL", "http://%LOCALE%.malware-erro
|
||||
|
||||
pref("browser.safebrowsing.warning.infoURL", "https://www.mozilla.org/%LOCALE%/firefox/phishing-protection/");
|
||||
pref("browser.safebrowsing.malware.reportURL", "http://safebrowsing.clients.google.com/safebrowsing/diagnostic?client=%NAME%&hl=%LOCALE%&site=");
|
||||
// Since the application reputation query isn't hooked in anywhere yet, this
|
||||
// preference does not matter. To be extra safe, don't turn this preference on
|
||||
// for official builds without whitelisting (bug 842828).
|
||||
#ifndef MOZILLA_OFFICIAL
|
||||
pref("browser.safebrowsing.appRepURL", "https://sb-ssl.google.com/safebrowsing/clientreport/download");
|
||||
#endif
|
||||
|
||||
#ifdef MOZILLA_OFFICIAL
|
||||
// Normally the "client ID" sent in updates is appinfo.name, but for
|
||||
|
@ -269,7 +269,7 @@ var gPluginHandler = {
|
||||
let iconStatus = doc.getAnonymousElementByAttribute(plugin, "class", "icon");
|
||||
iconStatus.setAttribute("installable", "true");
|
||||
|
||||
let installLink = doc.getAnonymousElementByAttribute(plugin, "class", "installPluginLink");
|
||||
let installLink = doc.getAnonymousElementByAttribute(plugin, "anonid", "installPluginLink");
|
||||
this.addLinkClickCallback(installLink, "installSinglePlugin", plugin);
|
||||
}
|
||||
break;
|
||||
@ -280,7 +280,7 @@ var gPluginHandler = {
|
||||
break;
|
||||
|
||||
case "PluginVulnerableUpdatable":
|
||||
let updateLink = doc.getAnonymousElementByAttribute(plugin, "class", "checkForUpdatesLink");
|
||||
let updateLink = doc.getAnonymousElementByAttribute(plugin, "anonid", "checkForUpdatesLink");
|
||||
this.addLinkClickCallback(updateLink, "openPluginUpdatePage");
|
||||
/* FALLTHRU */
|
||||
|
||||
@ -306,7 +306,7 @@ var gPluginHandler = {
|
||||
break;
|
||||
|
||||
case "PluginDisabled":
|
||||
let manageLink = doc.getAnonymousElementByAttribute(plugin, "class", "managePluginsLink");
|
||||
let manageLink = doc.getAnonymousElementByAttribute(plugin, "anonid", "managePluginsLink");
|
||||
this.addLinkClickCallback(manageLink, "managePlugins");
|
||||
shouldShowNotification = true;
|
||||
break;
|
||||
|
@ -134,7 +134,7 @@ function test3() {
|
||||
ok(pluginNode, "Test 3, Found plugin in page");
|
||||
var objLoadingContent = pluginNode.QueryInterface(Ci.nsIObjectLoadingContent);
|
||||
is(objLoadingContent.pluginFallbackType, Ci.nsIObjectLoadingContent.PLUGIN_DISABLED, "Test 3, plugin fallback type should be PLUGIN_DISABLED");
|
||||
var manageLink = gTestBrowser.contentDocument.getAnonymousElementByAttribute(pluginNode, "class", "managePluginsLink");
|
||||
var manageLink = gTestBrowser.contentDocument.getAnonymousElementByAttribute(pluginNode, "anonid", "managePluginsLink");
|
||||
ok(manageLink, "Test 3, found 'manage' link in plugin-problem binding");
|
||||
|
||||
EventUtils.synthesizeMouseAtCenter(manageLink, {}, gTestBrowser.contentWindow);
|
||||
@ -344,7 +344,7 @@ function test18a() {
|
||||
ok(!objLoadingContent.activated, "Test 18a, Plugin should not be activated");
|
||||
var overlay = doc.getAnonymousElementByAttribute(plugin, "class", "mainBox");
|
||||
ok(overlay.style.visibility != "hidden", "Test 18a, Plugin overlay should exist, not be hidden");
|
||||
var updateLink = doc.getAnonymousElementByAttribute(plugin, "class", "checkForUpdatesLink");
|
||||
var updateLink = doc.getAnonymousElementByAttribute(plugin, "anonid", "checkForUpdatesLink");
|
||||
ok(updateLink.style.visibility != "hidden", "Test 18a, Plugin should have an update link");
|
||||
|
||||
var tabOpenListener = new TabOpenListener(Services.urlFormatter.formatURLPref("plugins.update.url"), false, false);
|
||||
@ -387,7 +387,7 @@ function test18c() {
|
||||
ok(!objLoadingContent.activated, "Test 18c, Plugin should not be activated");
|
||||
var overlay = doc.getAnonymousElementByAttribute(plugin, "class", "mainBox");
|
||||
ok(overlay.style.visibility != "hidden", "Test 18c, Plugin overlay should exist, not be hidden");
|
||||
var updateLink = doc.getAnonymousElementByAttribute(plugin, "class", "checkForUpdatesLink");
|
||||
var updateLink = doc.getAnonymousElementByAttribute(plugin, "anonid", "checkForUpdatesLink");
|
||||
ok(updateLink.style.display != "block", "Test 18c, Plugin should not have an update link");
|
||||
|
||||
// check that click "Always allow" works with blocklisted plugins
|
||||
|
@ -117,6 +117,7 @@ MOCHITEST_BROWSER_FILES = \
|
||||
browser_netpanel_longstring_expand.js \
|
||||
browser_repeated_messages_accuracy.js \
|
||||
browser_webconsole_bug_821877_csp_errors.js \
|
||||
browser_webconsole_bug_846918_hsts_invalid-headers.js \
|
||||
browser_eval_in_debugger_stackframe.js \
|
||||
browser_console_variables_view.js \
|
||||
browser_console_variables_view_while_debugging.js \
|
||||
@ -185,8 +186,6 @@ MOCHITEST_BROWSER_FILES += \
|
||||
test-bug-595934-svg.xhtml \
|
||||
test-bug-595934-workers.html \
|
||||
test-bug-595934-workers.js \
|
||||
test-bug-595934-canvas.html \
|
||||
test-bug-595934-canvas.js \
|
||||
test-bug-595934-css-parser.html \
|
||||
test-bug-595934-css-parser.css \
|
||||
test-bug-595934-canvas-css.html \
|
||||
@ -236,6 +235,8 @@ MOCHITEST_BROWSER_FILES += \
|
||||
test-bug-766001-js-errors.js \
|
||||
test-bug-821877-csperrors.html \
|
||||
test-bug-821877-csperrors.html^headers^ \
|
||||
test-bug-846918-hsts-invalid-headers.html \
|
||||
test-bug-846918-hsts-invalid-headers.html^headers^ \
|
||||
test-eval-in-stackframe.html \
|
||||
test-bug-859170-longstring-hang.html \
|
||||
test-bug-837351-security-errors.html \
|
||||
|
@ -46,31 +46,26 @@ const TESTS = [
|
||||
matchString: "fooBarSVG",
|
||||
},
|
||||
{ // #6
|
||||
file: "test-bug-595934-canvas.html",
|
||||
category: "Canvas",
|
||||
matchString: "strokeStyle",
|
||||
},
|
||||
{ // #7
|
||||
file: "test-bug-595934-css-parser.html",
|
||||
category: "CSS Parser",
|
||||
matchString: "foobarCssParser",
|
||||
},
|
||||
{ // #8
|
||||
{ // #7
|
||||
file: "test-bug-595934-malformedxml-external.html",
|
||||
category: "malformed-xml",
|
||||
matchString: "</html>",
|
||||
},
|
||||
{ // #9
|
||||
{ // #8
|
||||
file: "test-bug-595934-empty-getelementbyid.html",
|
||||
category: "DOM",
|
||||
matchString: "getElementById",
|
||||
},
|
||||
{ // #10
|
||||
{ // #9
|
||||
file: "test-bug-595934-canvas-css.html",
|
||||
category: "CSS Parser",
|
||||
matchString: "foobarCanvasCssParser",
|
||||
},
|
||||
{ // #11
|
||||
{ // #10
|
||||
file: "test-bug-595934-image.html",
|
||||
category: "Image",
|
||||
matchString: "corrupt",
|
||||
|
@ -0,0 +1,27 @@
|
||||
/* Any copyright is dedicated to the Public Domain.
|
||||
* http://creativecommons.org/publicdomain/zero/1.0/ */
|
||||
/* Tests that errors about invalid HSTS security headers are logged
|
||||
* to the web console */
|
||||
const TEST_URI = "https://example.com/browser/browser/devtools/webconsole/test/test-bug-846918-hsts-invalid-headers.html";
|
||||
const HSTS_INVALID_HEADER_MSG = "The site specified an invalid Strict-Transport-Security header.";
|
||||
|
||||
function test()
|
||||
{
|
||||
addTab(TEST_URI);
|
||||
browser.addEventListener("load", function onLoad(aEvent) {
|
||||
browser.removeEventListener(aEvent.type, onLoad, true);
|
||||
openConsole(null, function testHSTSErrorLogged (hud) {
|
||||
waitForMessages({
|
||||
webconsole: hud,
|
||||
messages: [
|
||||
{
|
||||
name: "Invalid HSTS header error displayed successfully",
|
||||
text: HSTS_INVALID_HEADER_MSG,
|
||||
category: CATEGORY_SECURITY,
|
||||
severity: SEVERITY_WARNING
|
||||
},
|
||||
],
|
||||
}).then(finishTest);
|
||||
});
|
||||
}, true);
|
||||
}
|
@ -1,15 +0,0 @@
|
||||
<!DOCTYPE html>
|
||||
<html lang="en">
|
||||
<head>
|
||||
<meta charset="utf-8">
|
||||
<title>Web Console test for bug 595934 - category: Canvas</title>
|
||||
<!-- Any copyright is dedicated to the Public Domain.
|
||||
http://creativecommons.org/publicdomain/zero/1.0/ -->
|
||||
<script type="text/javascript"
|
||||
src="test-bug-595934-canvas.js"></script>
|
||||
</head>
|
||||
<body>
|
||||
<p>Web Console test for bug 595934 - category "Canvas".</p>
|
||||
<p><canvas width="200" height="200">Canvas support is required!</canvas></p>
|
||||
</body>
|
||||
</html>
|
@ -1,11 +0,0 @@
|
||||
/*
|
||||
* Any copyright is dedicated to the Public Domain.
|
||||
* http://creativecommons.org/publicdomain/zero/1.0/
|
||||
*/
|
||||
|
||||
window.addEventListener("DOMContentLoaded", function() {
|
||||
var canvas = document.querySelector("canvas");
|
||||
var context = canvas.getContext("2d");
|
||||
context.strokeStyle = document;
|
||||
}, false);
|
||||
|
@ -0,0 +1,13 @@
|
||||
<!doctype html>
|
||||
<html>
|
||||
<head>
|
||||
<meta charset="utf8">
|
||||
<title>Bug 846918 - Report invalid strict-transport-security
|
||||
headers to the web console</title>
|
||||
<!-- Any copyright is dedicated to the Public Domain.
|
||||
http://creativecommons.org/publicdomain/zero/1.0/ -->
|
||||
</head>
|
||||
<body>
|
||||
<p>This page is served with an invalid STS header.</p>
|
||||
</body>
|
||||
</html>
|
@ -0,0 +1 @@
|
||||
Strict-Transport-Security: max-age444
|
@ -4421,6 +4421,7 @@ var Utils = {
|
||||
|
||||
case "Mixed Content Blocker":
|
||||
case "CSP":
|
||||
case "Invalid HSTS Headers":
|
||||
return CATEGORY_SECURITY;
|
||||
|
||||
default:
|
||||
|
@ -21,6 +21,9 @@ window.sizeToContent = function() {
|
||||
Cu.reportError("window.sizeToContent is not allowed in this window");
|
||||
}
|
||||
|
||||
/*
|
||||
* Returns the browser for the currently displayed tab.
|
||||
*/
|
||||
function getBrowser() {
|
||||
return Browser.selectedBrowser;
|
||||
}
|
||||
@ -127,11 +130,20 @@ var Browser = {
|
||||
Util.forceOnline();
|
||||
|
||||
// If this is an intial window launch the commandline handler passes us the default
|
||||
// page as an argument. commandURL _should_ never be empty, but we protect against it
|
||||
// below. However, we delay trying to get the fallback homepage until we really need it.
|
||||
// page as an argument.
|
||||
let commandURL = null;
|
||||
if (window.arguments && window.arguments[0])
|
||||
commandURL = window.arguments[0];
|
||||
try {
|
||||
let argsObj = window.arguments[0].wrappedJSObject;
|
||||
if (argsObj && argsObj.pageloadURL) {
|
||||
// Talos tp-cmdline parameter
|
||||
commandURL = argsObj.pageloadURL;
|
||||
} else if (window.arguments && window.arguments[0]) {
|
||||
// BrowserCLH paramerter
|
||||
commandURL = window.arguments[0];
|
||||
}
|
||||
} catch (ex) {
|
||||
Util.dumpLn(ex);
|
||||
}
|
||||
|
||||
messageManager.addMessageListener("DOMLinkAdded", this);
|
||||
messageManager.addMessageListener("MozScrolledAreaChanged", this);
|
||||
|
@ -268,17 +268,18 @@ documenttab[selected] .documenttab-selection {
|
||||
transition-duration: .3s;
|
||||
transition-timing-function: ease-in-out;
|
||||
}
|
||||
|
||||
#browsers browser {
|
||||
transition: padding-bottom @metro_animation_duration@ @metro_animation_easing@;
|
||||
/* unset padding-bottom immediately */
|
||||
transition-duration: 0s;
|
||||
transition-delay: 0s;
|
||||
transition-property: padding-bottom;
|
||||
}
|
||||
|
||||
#browsers[findbar] browser {
|
||||
/* delay setting padding-bottom until the findbar has transitioned in */
|
||||
transition-delay: @metro_animation_duration@;
|
||||
padding-bottom: @findbar_height@;
|
||||
}
|
||||
|
||||
/* Selection overlay and monocles */
|
||||
|
||||
#page,
|
||||
.selection-overlay {
|
||||
-moz-stack-sizing: ignore;
|
||||
|
@ -65,6 +65,7 @@ MACH_MODULES = [
|
||||
'testing/marionette/mach_commands.py',
|
||||
'testing/mochitest/mach_commands.py',
|
||||
'testing/xpcshell/mach_commands.py',
|
||||
'testing/talos/mach_commands.py',
|
||||
'tools/mach_commands.py',
|
||||
]
|
||||
|
||||
|
@ -20,3 +20,6 @@ ac_add_options --disable-install-strip
|
||||
ac_add_options --disable-jemalloc
|
||||
ac_add_options --disable-crashreporter
|
||||
ac_add_options --disable-elf-hack
|
||||
|
||||
# Avoid dependency on libstdc++ 4.7
|
||||
ac_add_options --enable-stdcxx-compat
|
||||
|
@ -208,6 +208,8 @@
|
||||
#include "nsIEditor.h"
|
||||
#include "nsIDOMCSSStyleRule.h"
|
||||
#include "mozilla/css/Rule.h"
|
||||
#include "nsIHttpChannelInternal.h"
|
||||
#include "nsISecurityConsoleMessage.h"
|
||||
|
||||
using namespace mozilla;
|
||||
using namespace mozilla::dom;
|
||||
@ -2468,6 +2470,23 @@ CSPErrorQueue::Flush(nsIDocument* aDocument)
|
||||
mErrors.Clear();
|
||||
}
|
||||
|
||||
void
|
||||
nsDocument::SendToConsole(nsCOMArray<nsISecurityConsoleMessage>& aMessages)
|
||||
{
|
||||
for (uint32_t i = 0; i < aMessages.Length(); ++i) {
|
||||
nsAutoString messageTag;
|
||||
aMessages[i]->GetTag(messageTag);
|
||||
|
||||
nsAutoString category;
|
||||
aMessages[i]->GetCategory(category);
|
||||
|
||||
nsContentUtils::ReportToConsole(nsIScriptError::warningFlag,
|
||||
NS_ConvertUTF16toUTF8(category).get(),
|
||||
this, nsContentUtils::eSECURITY_PROPERTIES,
|
||||
NS_ConvertUTF16toUTF8(messageTag).get());
|
||||
}
|
||||
}
|
||||
|
||||
nsresult
|
||||
nsDocument::InitCSP(nsIChannel* aChannel)
|
||||
{
|
||||
@ -4286,8 +4305,16 @@ nsDocument::SetScriptGlobalObject(nsIScriptGlobalObject *aScriptGlobalObject)
|
||||
mWindow = window;
|
||||
|
||||
// Now that we know what our window is, we can flush the CSP errors to the
|
||||
// Web Console.
|
||||
// Web Console. We are flushing all messages that occured and were stored
|
||||
// in the queue prior to this point.
|
||||
FlushCSPWebConsoleErrorQueue();
|
||||
nsCOMPtr<nsIHttpChannelInternal> internalChannel =
|
||||
do_QueryInterface(GetChannel());
|
||||
if (internalChannel) {
|
||||
nsCOMArray<nsISecurityConsoleMessage> messages;
|
||||
internalChannel->TakeAllSecurityMessages(messages);
|
||||
SendToConsole(messages);
|
||||
}
|
||||
|
||||
// Set our visibility state, but do not fire the event. This is correct
|
||||
// because either we're coming out of bfcache (in which case IsVisible() will
|
||||
|
@ -94,6 +94,7 @@ class nsWindowSizes;
|
||||
class nsHtml5TreeOpExecutor;
|
||||
class nsDocumentOnStack;
|
||||
class nsPointerLockPermissionRequest;
|
||||
class nsISecurityConsoleMessage;
|
||||
|
||||
namespace mozilla {
|
||||
namespace dom {
|
||||
@ -754,6 +755,7 @@ public:
|
||||
|
||||
private:
|
||||
nsRadioGroupStruct* GetRadioGroupInternal(const nsAString& aName) const;
|
||||
void SendToConsole(nsCOMArray<nsISecurityConsoleMessage>& aMessages);
|
||||
|
||||
public:
|
||||
// nsIDOMNode
|
||||
|
@ -13,19 +13,14 @@
|
||||
#include "mozilla/gfx/2D.h"
|
||||
#include "nsWrapperCache.h"
|
||||
|
||||
#define NS_CANVASGRADIENTAZURE_PRIVATE_IID \
|
||||
{0x28425a6a, 0x90e0, 0x4d42, {0x9c, 0x75, 0xff, 0x60, 0x09, 0xb3, 0x10, 0xa8}}
|
||||
|
||||
namespace mozilla {
|
||||
namespace dom {
|
||||
|
||||
class CanvasGradient : public nsISupports,
|
||||
public nsWrapperCache
|
||||
class CanvasGradient : public nsWrapperCache
|
||||
{
|
||||
public:
|
||||
NS_DECLARE_STATIC_IID_ACCESSOR(NS_CANVASGRADIENTAZURE_PRIVATE_IID)
|
||||
NS_DECL_CYCLE_COLLECTING_ISUPPORTS
|
||||
NS_DECL_CYCLE_COLLECTION_SCRIPT_HOLDER_CLASS(CanvasGradient)
|
||||
NS_INLINE_DECL_CYCLE_COLLECTING_NATIVE_REFCOUNTING(CanvasGradient)
|
||||
NS_DECL_CYCLE_COLLECTION_SCRIPT_HOLDER_NATIVE_CLASS(CanvasGradient)
|
||||
|
||||
enum Type
|
||||
{
|
||||
|
@ -12,8 +12,6 @@
|
||||
#include "nsISupports.h"
|
||||
#include "nsWrapperCache.h"
|
||||
|
||||
#define NS_CANVASPATTERNAZURE_PRIVATE_IID \
|
||||
{0xc9bacc25, 0x28da, 0x421e, {0x9a, 0x4b, 0xbb, 0xd6, 0x93, 0x05, 0x12, 0xbc}}
|
||||
class nsIPrincipal;
|
||||
|
||||
namespace mozilla {
|
||||
@ -23,13 +21,11 @@ class SourceSurface;
|
||||
|
||||
namespace dom {
|
||||
|
||||
class CanvasPattern MOZ_FINAL : public nsISupports,
|
||||
public nsWrapperCache
|
||||
class CanvasPattern MOZ_FINAL : public nsWrapperCache
|
||||
{
|
||||
public:
|
||||
NS_DECLARE_STATIC_IID_ACCESSOR(NS_CANVASPATTERNAZURE_PRIVATE_IID)
|
||||
NS_DECL_CYCLE_COLLECTING_ISUPPORTS
|
||||
NS_DECL_CYCLE_COLLECTION_SCRIPT_HOLDER_CLASS(CanvasPattern)
|
||||
NS_INLINE_DECL_CYCLE_COLLECTING_NATIVE_REFCOUNTING(CanvasPattern)
|
||||
NS_DECL_CYCLE_COLLECTION_SCRIPT_HOLDER_NATIVE_CLASS(CanvasPattern)
|
||||
|
||||
enum RepeatMode
|
||||
{
|
||||
|
@ -92,10 +92,11 @@
|
||||
#include "nsJSUtils.h"
|
||||
#include "XPCQuickStubs.h"
|
||||
#include "mozilla/dom/BindingUtils.h"
|
||||
#include "mozilla/dom/CanvasRenderingContext2DBinding.h"
|
||||
#include "mozilla/dom/HTMLImageElement.h"
|
||||
#include "mozilla/dom/HTMLVideoElement.h"
|
||||
#include "mozilla/dom/CanvasRenderingContext2DBinding.h"
|
||||
#include "mozilla/dom/TextMetrics.h"
|
||||
#include "mozilla/dom/UnionTypes.h"
|
||||
|
||||
#ifdef USE_SKIA_GPU
|
||||
#undef free // apparently defined by some windows header, clashing with a free()
|
||||
@ -400,32 +401,16 @@ CanvasGradient::AddColorStop(float offset, const nsAString& colorstr, ErrorResul
|
||||
mRawStops.AppendElement(newStop);
|
||||
}
|
||||
|
||||
NS_DEFINE_STATIC_IID_ACCESSOR(CanvasGradient, NS_CANVASGRADIENTAZURE_PRIVATE_IID)
|
||||
|
||||
NS_IMPL_CYCLE_COLLECTING_ADDREF(CanvasGradient)
|
||||
NS_IMPL_CYCLE_COLLECTING_RELEASE(CanvasGradient)
|
||||
NS_IMPL_CYCLE_COLLECTION_ROOT_NATIVE(CanvasGradient, AddRef)
|
||||
NS_IMPL_CYCLE_COLLECTION_UNROOT_NATIVE(CanvasGradient, Release)
|
||||
|
||||
NS_IMPL_CYCLE_COLLECTION_WRAPPERCACHE_1(CanvasGradient, mContext)
|
||||
|
||||
NS_INTERFACE_MAP_BEGIN_CYCLE_COLLECTION(CanvasGradient)
|
||||
NS_WRAPPERCACHE_INTERFACE_MAP_ENTRY
|
||||
NS_INTERFACE_MAP_ENTRY(mozilla::dom::CanvasGradient)
|
||||
NS_INTERFACE_MAP_ENTRY(nsISupports)
|
||||
NS_INTERFACE_MAP_END
|
||||
|
||||
NS_DEFINE_STATIC_IID_ACCESSOR(CanvasPattern, NS_CANVASPATTERNAZURE_PRIVATE_IID)
|
||||
|
||||
NS_IMPL_CYCLE_COLLECTING_ADDREF(CanvasPattern)
|
||||
NS_IMPL_CYCLE_COLLECTING_RELEASE(CanvasPattern)
|
||||
NS_IMPL_CYCLE_COLLECTION_ROOT_NATIVE(CanvasPattern, AddRef)
|
||||
NS_IMPL_CYCLE_COLLECTION_UNROOT_NATIVE(CanvasPattern, Release)
|
||||
|
||||
NS_IMPL_CYCLE_COLLECTION_WRAPPERCACHE_1(CanvasPattern, mContext)
|
||||
|
||||
NS_INTERFACE_MAP_BEGIN_CYCLE_COLLECTION(CanvasPattern)
|
||||
NS_WRAPPERCACHE_INTERFACE_MAP_ENTRY
|
||||
NS_INTERFACE_MAP_ENTRY(mozilla::dom::CanvasPattern)
|
||||
NS_INTERFACE_MAP_ENTRY(nsISupports)
|
||||
NS_INTERFACE_MAP_END
|
||||
|
||||
class CanvasRenderingContext2DUserData : public LayerUserData {
|
||||
public:
|
||||
CanvasRenderingContext2DUserData(CanvasRenderingContext2D *aContext)
|
||||
@ -648,17 +633,6 @@ CanvasRenderingContext2D::Reset()
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
static void
|
||||
WarnAboutUnexpectedStyle(HTMLCanvasElement* canvasElement)
|
||||
{
|
||||
nsContentUtils::ReportToConsole(
|
||||
nsIScriptError::warningFlag,
|
||||
"Canvas",
|
||||
canvasElement ? canvasElement->OwnerDoc() : nullptr,
|
||||
nsContentUtils::eDOM_PROPERTIES,
|
||||
"UnexpectedCanvasVariantStyle");
|
||||
}
|
||||
|
||||
void
|
||||
CanvasRenderingContext2D::SetStyleFromString(const nsAString& str,
|
||||
Style whichStyle)
|
||||
@ -673,27 +647,18 @@ CanvasRenderingContext2D::SetStyleFromString(const nsAString& str,
|
||||
CurrentState().SetColorStyle(whichStyle, color);
|
||||
}
|
||||
|
||||
nsISupports*
|
||||
CanvasRenderingContext2D::GetStyleAsStringOrInterface(nsAString& aStr,
|
||||
CanvasMultiGetterType& aType,
|
||||
Style aWhichStyle)
|
||||
void
|
||||
CanvasRenderingContext2D::GetStyleAsUnion(StringOrCanvasGradientOrCanvasPatternReturnValue& aValue,
|
||||
Style aWhichStyle)
|
||||
{
|
||||
const ContextState &state = CurrentState();
|
||||
nsISupports* supports;
|
||||
if (state.patternStyles[aWhichStyle]) {
|
||||
aStr.SetIsVoid(true);
|
||||
supports = state.patternStyles[aWhichStyle];
|
||||
aType = CMG_STYLE_PATTERN;
|
||||
aValue.SetAsCanvasPattern() = state.patternStyles[aWhichStyle];
|
||||
} else if (state.gradientStyles[aWhichStyle]) {
|
||||
aStr.SetIsVoid(true);
|
||||
supports = state.gradientStyles[aWhichStyle];
|
||||
aType = CMG_STYLE_GRADIENT;
|
||||
aValue.SetAsCanvasGradient() = state.gradientStyles[aWhichStyle];
|
||||
} else {
|
||||
StyleColorToString(state.colorStyles[aWhichStyle], aStr);
|
||||
supports = nullptr;
|
||||
aType = CMG_STYLE_STRING;
|
||||
StyleColorToString(state.colorStyles[aWhichStyle], aValue.SetAsString());
|
||||
}
|
||||
return supports;
|
||||
}
|
||||
|
||||
// static
|
||||
@ -1349,92 +1314,25 @@ CanvasRenderingContext2D::GetMozCurrentTransformInverse(JSContext* cx,
|
||||
//
|
||||
|
||||
void
|
||||
CanvasRenderingContext2D::SetStyleFromJSValue(JSContext* cx,
|
||||
JS::Handle<JS::Value> value,
|
||||
Style whichStyle)
|
||||
CanvasRenderingContext2D::SetStyleFromUnion(const StringOrCanvasGradientOrCanvasPattern& value,
|
||||
Style whichStyle)
|
||||
{
|
||||
if (value.isString()) {
|
||||
nsDependentJSString strokeStyle;
|
||||
if (strokeStyle.init(cx, value.toString())) {
|
||||
SetStyleFromString(strokeStyle, whichStyle);
|
||||
}
|
||||
if (value.IsString()) {
|
||||
SetStyleFromString(value.GetAsString(), whichStyle);
|
||||
return;
|
||||
}
|
||||
|
||||
if (value.isObject()) {
|
||||
nsCOMPtr<nsISupports> holder;
|
||||
|
||||
CanvasGradient* gradient;
|
||||
JS::Rooted<JS::Value> rootedVal(cx, value);
|
||||
nsresult rv = xpc_qsUnwrapArg<CanvasGradient>(cx, value, &gradient,
|
||||
static_cast<nsISupports**>(getter_AddRefs(holder)),
|
||||
rootedVal.address());
|
||||
if (NS_SUCCEEDED(rv)) {
|
||||
SetStyleFromGradient(gradient, whichStyle);
|
||||
return;
|
||||
}
|
||||
|
||||
CanvasPattern* pattern;
|
||||
rv = xpc_qsUnwrapArg<CanvasPattern>(cx, value, &pattern,
|
||||
static_cast<nsISupports**>(getter_AddRefs(holder)),
|
||||
rootedVal.address());
|
||||
if (NS_SUCCEEDED(rv)) {
|
||||
SetStyleFromPattern(pattern, whichStyle);
|
||||
return;
|
||||
}
|
||||
if (value.IsCanvasGradient()) {
|
||||
SetStyleFromGradient(value.GetAsCanvasGradient(), whichStyle);
|
||||
return;
|
||||
}
|
||||
|
||||
WarnAboutUnexpectedStyle(mCanvasElement);
|
||||
}
|
||||
|
||||
static JS::Value
|
||||
WrapStyle(JSContext* cx, JSObject* objArg,
|
||||
CanvasRenderingContext2D::CanvasMultiGetterType type,
|
||||
nsAString& str, nsISupports* supports, ErrorResult& error)
|
||||
{
|
||||
JS::Rooted<JS::Value> v(cx);
|
||||
bool ok;
|
||||
switch (type) {
|
||||
case CanvasRenderingContext2D::CMG_STYLE_STRING:
|
||||
{
|
||||
ok = xpc::StringToJsval(cx, str, v.address());
|
||||
break;
|
||||
}
|
||||
case CanvasRenderingContext2D::CMG_STYLE_PATTERN:
|
||||
case CanvasRenderingContext2D::CMG_STYLE_GRADIENT:
|
||||
{
|
||||
JS::Rooted<JSObject*> obj(cx, objArg);
|
||||
ok = dom::WrapObject(cx, obj, supports, &v);
|
||||
break;
|
||||
}
|
||||
default:
|
||||
MOZ_CRASH("unexpected CanvasMultiGetterType");
|
||||
if (value.IsCanvasPattern()) {
|
||||
SetStyleFromPattern(value.GetAsCanvasPattern(), whichStyle);
|
||||
return;
|
||||
}
|
||||
if (!ok) {
|
||||
error.Throw(NS_ERROR_FAILURE);
|
||||
}
|
||||
return v;
|
||||
}
|
||||
|
||||
|
||||
JS::Value
|
||||
CanvasRenderingContext2D::GetStrokeStyle(JSContext* cx,
|
||||
ErrorResult& error)
|
||||
{
|
||||
nsString str;
|
||||
CanvasMultiGetterType t;
|
||||
nsISupports* supports = GetStyleAsStringOrInterface(str, t, STYLE_STROKE);
|
||||
return WrapStyle(cx, GetWrapper(), t, str, supports, error);
|
||||
}
|
||||
|
||||
JS::Value
|
||||
CanvasRenderingContext2D::GetFillStyle(JSContext* cx,
|
||||
ErrorResult& error)
|
||||
{
|
||||
nsString str;
|
||||
CanvasMultiGetterType t;
|
||||
nsISupports* supports = GetStyleAsStringOrInterface(str, t, STYLE_FILL);
|
||||
return WrapStyle(cx, GetWrapper(), t, str, supports, error);
|
||||
MOZ_ASSUME_UNREACHABLE("Invalid union value");
|
||||
}
|
||||
|
||||
void
|
||||
|
@ -17,7 +17,6 @@
|
||||
#include "gfxFont.h"
|
||||
#include "mozilla/ErrorResult.h"
|
||||
#include "mozilla/dom/ImageData.h"
|
||||
#include "mozilla/dom/UnionTypes.h"
|
||||
#include "mozilla/dom/CanvasGradient.h"
|
||||
#include "mozilla/dom/CanvasRenderingContext2DBinding.h"
|
||||
#include "mozilla/dom/CanvasPattern.h"
|
||||
@ -31,6 +30,9 @@ class SourceSurface;
|
||||
}
|
||||
|
||||
namespace dom {
|
||||
class HTMLImageElementOrHTMLCanvasElementOrHTMLVideoElement;
|
||||
class StringOrCanvasGradientOrCanvasPattern;
|
||||
class StringOrCanvasGradientOrCanvasPatternReturnValue;
|
||||
class TextMetrics;
|
||||
|
||||
extern const mozilla::gfx::Float SIGMA_MAX;
|
||||
@ -47,7 +49,7 @@ class CanvasRenderingContext2D :
|
||||
public nsICanvasRenderingContextInternal,
|
||||
public nsWrapperCache
|
||||
{
|
||||
typedef mozilla::dom::HTMLImageElementOrHTMLCanvasElementOrHTMLVideoElement
|
||||
typedef HTMLImageElementOrHTMLCanvasElementOrHTMLVideoElement
|
||||
HTMLImageOrCanvasOrVideoElement;
|
||||
|
||||
public:
|
||||
@ -91,18 +93,25 @@ public:
|
||||
void GetGlobalCompositeOperation(nsAString& op, mozilla::ErrorResult& error);
|
||||
void SetGlobalCompositeOperation(const nsAString& op,
|
||||
mozilla::ErrorResult& error);
|
||||
JS::Value GetStrokeStyle(JSContext* cx, mozilla::ErrorResult& error);
|
||||
|
||||
void SetStrokeStyle(JSContext* cx, JS::Handle<JS::Value> value)
|
||||
void GetStrokeStyle(StringOrCanvasGradientOrCanvasPatternReturnValue& value)
|
||||
{
|
||||
SetStyleFromJSValue(cx, value, STYLE_STROKE);
|
||||
GetStyleAsUnion(value, STYLE_STROKE);
|
||||
}
|
||||
|
||||
JS::Value GetFillStyle(JSContext* cx, mozilla::ErrorResult& error);
|
||||
|
||||
void SetFillStyle(JSContext* cx, JS::Handle<JS::Value> value)
|
||||
void SetStrokeStyle(const StringOrCanvasGradientOrCanvasPattern& value)
|
||||
{
|
||||
SetStyleFromJSValue(cx, value, STYLE_FILL);
|
||||
SetStyleFromUnion(value, STYLE_STROKE);
|
||||
}
|
||||
|
||||
void GetFillStyle(StringOrCanvasGradientOrCanvasPatternReturnValue& value)
|
||||
{
|
||||
GetStyleAsUnion(value, STYLE_FILL);
|
||||
}
|
||||
|
||||
void SetFillStyle(const StringOrCanvasGradientOrCanvasPattern& value)
|
||||
{
|
||||
SetStyleFromUnion(value, STYLE_FILL);
|
||||
}
|
||||
|
||||
already_AddRefed<CanvasGradient>
|
||||
@ -162,10 +171,10 @@ public:
|
||||
bool IsPointInPath(double x, double y, const CanvasWindingRule& winding);
|
||||
bool IsPointInStroke(double x, double y);
|
||||
void FillText(const nsAString& text, double x, double y,
|
||||
const mozilla::dom::Optional<double>& maxWidth,
|
||||
const Optional<double>& maxWidth,
|
||||
mozilla::ErrorResult& error);
|
||||
void StrokeText(const nsAString& text, double x, double y,
|
||||
const mozilla::dom::Optional<double>& maxWidth,
|
||||
const Optional<double>& maxWidth,
|
||||
mozilla::ErrorResult& error);
|
||||
TextMetrics*
|
||||
MeasureText(const nsAString& rawText, mozilla::ErrorResult& error);
|
||||
@ -190,18 +199,18 @@ public:
|
||||
DrawImage(image, sx, sy, sw, sh, dx, dy, dw, dh, 6, error);
|
||||
}
|
||||
|
||||
already_AddRefed<mozilla::dom::ImageData>
|
||||
already_AddRefed<ImageData>
|
||||
CreateImageData(JSContext* cx, double sw, double sh,
|
||||
mozilla::ErrorResult& error);
|
||||
already_AddRefed<mozilla::dom::ImageData>
|
||||
CreateImageData(JSContext* cx, mozilla::dom::ImageData& imagedata,
|
||||
already_AddRefed<ImageData>
|
||||
CreateImageData(JSContext* cx, ImageData& imagedata,
|
||||
mozilla::ErrorResult& error);
|
||||
already_AddRefed<mozilla::dom::ImageData>
|
||||
already_AddRefed<ImageData>
|
||||
GetImageData(JSContext* cx, double sx, double sy, double sw, double sh,
|
||||
mozilla::ErrorResult& error);
|
||||
void PutImageData(mozilla::dom::ImageData& imageData,
|
||||
void PutImageData(ImageData& imageData,
|
||||
double dx, double dy, mozilla::ErrorResult& error);
|
||||
void PutImageData(mozilla::dom::ImageData& imageData,
|
||||
void PutImageData(ImageData& imageData,
|
||||
double dx, double dy, double dirtyX, double dirtyY,
|
||||
double dirtyWidth, double dirtyHeight,
|
||||
mozilla::ErrorResult& error);
|
||||
@ -271,7 +280,7 @@ public:
|
||||
void LineTo(double x, double y)
|
||||
{
|
||||
EnsureWritablePath();
|
||||
|
||||
|
||||
LineTo(mozilla::gfx::Point(ToFloat(x), ToFloat(y)));
|
||||
}
|
||||
|
||||
@ -474,21 +483,22 @@ protected:
|
||||
static mozilla::gfx::DrawTarget* sErrorTarget;
|
||||
|
||||
// Some helpers. Doesn't modify a color on failure.
|
||||
void SetStyleFromJSValue(JSContext* cx, JS::Handle<JS::Value> value,
|
||||
Style whichStyle);
|
||||
void SetStyleFromUnion(const StringOrCanvasGradientOrCanvasPattern& value,
|
||||
Style whichStyle);
|
||||
void SetStyleFromString(const nsAString& str, Style whichStyle);
|
||||
|
||||
void SetStyleFromGradient(CanvasGradient *gradient, Style whichStyle)
|
||||
void SetStyleFromGradient(CanvasGradient& gradient, Style whichStyle)
|
||||
{
|
||||
CurrentState().SetGradientStyle(whichStyle, gradient);
|
||||
CurrentState().SetGradientStyle(whichStyle, &gradient);
|
||||
}
|
||||
|
||||
void SetStyleFromPattern(CanvasPattern *pattern, Style whichStyle)
|
||||
void SetStyleFromPattern(CanvasPattern& pattern, Style whichStyle)
|
||||
{
|
||||
CurrentState().SetPatternStyle(whichStyle, pattern);
|
||||
CurrentState().SetPatternStyle(whichStyle, &pattern);
|
||||
}
|
||||
|
||||
nsISupports* GetStyleAsStringOrInterface(nsAString& aStr, CanvasMultiGetterType& aType, Style aWhichStyle);
|
||||
void GetStyleAsUnion(StringOrCanvasGradientOrCanvasPatternReturnValue& aValue,
|
||||
Style aWhichStyle);
|
||||
|
||||
// Returns whether a color was successfully parsed.
|
||||
bool ParseColor(const nsAString& aString, nscolor* aColor);
|
||||
@ -716,7 +726,7 @@ protected:
|
||||
nsresult DrawOrMeasureText(const nsAString& text,
|
||||
float x,
|
||||
float y,
|
||||
const mozilla::dom::Optional<double>& maxWidth,
|
||||
const Optional<double>& maxWidth,
|
||||
TextDrawOperation op,
|
||||
float* aWidth);
|
||||
|
||||
|
@ -13,6 +13,7 @@
|
||||
#include "mozilla/CheckedInt.h"
|
||||
#include "mozilla/dom/CanvasRenderingContext2D.h"
|
||||
#include "mozilla/dom/HTMLCanvasElementBinding.h"
|
||||
#include "mozilla/dom/UnionTypes.h"
|
||||
#include "mozilla/gfx/Rect.h"
|
||||
#include "mozilla/Preferences.h"
|
||||
#include "mozilla/Telemetry.h"
|
||||
|
@ -5,19 +5,13 @@
|
||||
<title>Test for Bug 341604</title>
|
||||
<link rel="stylesheet" type="text/css" href="/tests/SimpleTest/test.css"/>
|
||||
</head>
|
||||
|
||||
<script type="application/javascript">
|
||||
function doTest() {
|
||||
if (location.search == "?onreload") {
|
||||
try {
|
||||
window.parent.modify_if_8();
|
||||
} catch (error) {
|
||||
window.parent.postMessage({ok: true, desc: "allow-same-origin is no longer in effect after reload - parent access blocked."}, "*");
|
||||
}
|
||||
} else {
|
||||
function doTest() {
|
||||
window.parent.modify_if_8();
|
||||
}
|
||||
}
|
||||
</script>
|
||||
|
||||
<body onload="doTest()">
|
||||
I am sandboxed with 'allow-scripts' and 'allow-same-origin' the first time I am loaded, and with 'allow-scripts' the second time
|
||||
</body>
|
||||
|
@ -15,6 +15,9 @@ https://bugzilla.mozilla.org/show_bug.cgi?id=893537
|
||||
|
||||
<pre id="test">
|
||||
<script>
|
||||
<!-- Bug 895303 -->
|
||||
SimpleTest.expectAssertions(0, 1);
|
||||
|
||||
SimpleTest.waitForExplicitFinish();
|
||||
var pframe = $("pframe");
|
||||
|
||||
|
@ -43,7 +43,7 @@ windowsToClose.push(window.open("about:blank", "window_to_navigate2"));
|
||||
|
||||
var attemptedTests = 0;
|
||||
var passedTests = 0;
|
||||
var totalTestsToPass = 8;
|
||||
var totalTestsToPass = 7;
|
||||
var totalTestsToAttempt = 13;
|
||||
|
||||
function ok_wrapper(result, desc, addToAttempted = true) {
|
||||
@ -120,7 +120,7 @@ function doTest() {
|
||||
// (done by file_iframe_sandbox_d_if6.html which simulates a link click and navigates
|
||||
// to file_iframe_sandbox_d_if7.html which attempts to call back into its parent).
|
||||
|
||||
// passes if good, fails if bad
|
||||
// fails if bad
|
||||
// 6) An iframe (if_8) has sandbox="allow-same-origin allow-scripts", the sandboxed document
|
||||
// (file_iframe_sandbox_d_if_8.html) that it contains accesses its parent (this file) and removes
|
||||
// 'allow-same-origin' and then triggers a reload.
|
||||
@ -180,7 +180,7 @@ window.modified_if_8 = false;
|
||||
|
||||
function reload_if_8() {
|
||||
var if_8 = document.getElementById('if_8');
|
||||
if_8.src = 'file_iframe_sandbox_d_if8.html?onreload';
|
||||
if_8.src = 'file_iframe_sandbox_d_if8.html';
|
||||
}
|
||||
|
||||
function modify_if_8() {
|
||||
@ -188,7 +188,7 @@ function modify_if_8() {
|
||||
// that's a failed test (allow-same-origin was removed
|
||||
// the first time).
|
||||
if (window.modified_if_8) {
|
||||
ok_wrapper(false, "an sandboxed iframe from which 'allow-same-origin' was removed should not be able to access its parent");
|
||||
ok_wrapper(false, "a sandboxed iframe from which 'allow-same-origin' was removed should not be able to access its parent");
|
||||
|
||||
// need to return here since we end up in an infinite loop otherwise
|
||||
return;
|
||||
@ -199,6 +199,7 @@ function modify_if_8() {
|
||||
|
||||
if_8.sandbox = 'allow-scripts';
|
||||
sendMouseEvent({type:'click'}, 'a_button');
|
||||
testAttempted();
|
||||
}
|
||||
|
||||
window.modified_if_9 = false;
|
||||
|
@ -39,6 +39,20 @@ WriteZeroesToAudioBlock(AudioChunk* aChunk, uint32_t aStart, uint32_t aLength)
|
||||
}
|
||||
}
|
||||
|
||||
void AudioBufferCopyWithScale(const float* aInput,
|
||||
float aScale,
|
||||
float* aOutput,
|
||||
uint32_t aSize)
|
||||
{
|
||||
if (aScale == 1.0f) {
|
||||
PodCopy(aOutput, aInput, aSize);
|
||||
} else {
|
||||
for (uint32_t i = 0; i < aSize; ++i) {
|
||||
aOutput[i] = aInput[i]*aScale;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
void AudioBufferAddWithScale(const float* aInput,
|
||||
float aScale,
|
||||
float* aOutput,
|
||||
|
@ -87,6 +87,14 @@ void AllocateAudioBlock(uint32_t aChannelCount, AudioChunk* aChunk);
|
||||
*/
|
||||
void WriteZeroesToAudioBlock(AudioChunk* aChunk, uint32_t aStart, uint32_t aLength);
|
||||
|
||||
/**
|
||||
* Copy with scale. aScale == 1.0f should be optimized.
|
||||
*/
|
||||
void AudioBufferCopyWithScale(const float* aInput,
|
||||
float aScale,
|
||||
float* aOutput,
|
||||
uint32_t aSize);
|
||||
|
||||
/**
|
||||
* Pointwise multiply-add operation. aScale == 1.0f should be optimized.
|
||||
*/
|
||||
|
@ -4,6 +4,7 @@
|
||||
* You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
#include "MediaStreamGraphImpl.h"
|
||||
#include "mozilla/LinkedList.h"
|
||||
|
||||
#include "AudioSegment.h"
|
||||
#include "VideoSegment.h"
|
||||
@ -23,6 +24,7 @@
|
||||
#include "AudioNodeStream.h"
|
||||
#include <algorithm>
|
||||
#include "DOMMediaStream.h"
|
||||
#include "GeckoProfiler.h"
|
||||
|
||||
using namespace mozilla::layers;
|
||||
using namespace mozilla::dom;
|
||||
@ -313,20 +315,30 @@ MediaStreamGraphImpl::GetAudioPosition(MediaStream* aStream)
|
||||
void
|
||||
MediaStreamGraphImpl::UpdateCurrentTime()
|
||||
{
|
||||
GraphTime prevCurrentTime = mCurrentTime;
|
||||
TimeStamp now = TimeStamp::Now();
|
||||
GraphTime nextCurrentTime =
|
||||
SecondsToMediaTime((now - mCurrentTimeStamp).ToSeconds()) + mCurrentTime;
|
||||
GraphTime prevCurrentTime, nextCurrentTime;
|
||||
if (mRealtime) {
|
||||
TimeStamp now = TimeStamp::Now();
|
||||
prevCurrentTime = mCurrentTime;
|
||||
nextCurrentTime =
|
||||
SecondsToMediaTime((now - mCurrentTimeStamp).ToSeconds()) + mCurrentTime;
|
||||
|
||||
mCurrentTimeStamp = now;
|
||||
LOG(PR_LOG_DEBUG+1, ("Updating current time to %f (real %f, mStateComputedTime %f)",
|
||||
MediaTimeToSeconds(nextCurrentTime),
|
||||
(now - mInitialTimeStamp).ToSeconds(),
|
||||
MediaTimeToSeconds(mStateComputedTime)));
|
||||
} else {
|
||||
prevCurrentTime = mCurrentTime;
|
||||
nextCurrentTime = mCurrentTime + MEDIA_GRAPH_TARGET_PERIOD_MS;
|
||||
LOG(PR_LOG_DEBUG+1, ("Updating offline current time to %f (mStateComputedTime %f)",
|
||||
MediaTimeToSeconds(nextCurrentTime),
|
||||
MediaTimeToSeconds(mStateComputedTime)));
|
||||
}
|
||||
|
||||
if (mStateComputedTime < nextCurrentTime) {
|
||||
LOG(PR_LOG_WARNING, ("Media graph global underrun detected"));
|
||||
nextCurrentTime = mStateComputedTime;
|
||||
}
|
||||
mCurrentTimeStamp = now;
|
||||
|
||||
LOG(PR_LOG_DEBUG+1, ("Updating current time to %f (real %f, mStateComputedTime %f)",
|
||||
MediaTimeToSeconds(nextCurrentTime),
|
||||
(now - mInitialTimeStamp).ToSeconds(),
|
||||
MediaTimeToSeconds(mStateComputedTime)));
|
||||
|
||||
if (prevCurrentTime >= nextCurrentTime) {
|
||||
NS_ASSERTION(prevCurrentTime == nextCurrentTime, "Time can't go backwards!");
|
||||
@ -454,22 +466,24 @@ MediaStreamGraphImpl::MarkConsumed(MediaStream* aStream)
|
||||
}
|
||||
|
||||
void
|
||||
MediaStreamGraphImpl::UpdateStreamOrderForStream(nsTArray<MediaStream*>* aStack,
|
||||
MediaStreamGraphImpl::UpdateStreamOrderForStream(mozilla::LinkedList<MediaStream>* aStack,
|
||||
already_AddRefed<MediaStream> aStream)
|
||||
{
|
||||
nsRefPtr<MediaStream> stream = aStream;
|
||||
NS_ASSERTION(!stream->mHasBeenOrdered, "stream should not have already been ordered");
|
||||
if (stream->mIsOnOrderingStack) {
|
||||
for (int32_t i = aStack->Length() - 1; ; --i) {
|
||||
aStack->ElementAt(i)->AsProcessedStream()->mInCycle = true;
|
||||
if (aStack->ElementAt(i) == stream)
|
||||
break;
|
||||
MediaStream* iter = aStack->getLast();
|
||||
if (iter) {
|
||||
do {
|
||||
iter->AsProcessedStream()->mInCycle = true;
|
||||
iter = iter->getPrevious();
|
||||
} while (iter && iter != stream);
|
||||
}
|
||||
return;
|
||||
}
|
||||
ProcessedMediaStream* ps = stream->AsProcessedStream();
|
||||
if (ps) {
|
||||
aStack->AppendElement(stream);
|
||||
aStack->insertBack(stream);
|
||||
stream->mIsOnOrderingStack = true;
|
||||
for (uint32_t i = 0; i < ps->mInputs.Length(); ++i) {
|
||||
MediaStream* source = ps->mInputs[i]->mSource;
|
||||
@ -478,7 +492,7 @@ MediaStreamGraphImpl::UpdateStreamOrderForStream(nsTArray<MediaStream*>* aStack,
|
||||
UpdateStreamOrderForStream(aStack, s.forget());
|
||||
}
|
||||
}
|
||||
aStack->RemoveElementAt(aStack->Length() - 1);
|
||||
aStack->popLast();
|
||||
stream->mIsOnOrderingStack = false;
|
||||
}
|
||||
|
||||
@ -489,10 +503,10 @@ MediaStreamGraphImpl::UpdateStreamOrderForStream(nsTArray<MediaStream*>* aStack,
|
||||
void
|
||||
MediaStreamGraphImpl::UpdateStreamOrder()
|
||||
{
|
||||
nsTArray<nsRefPtr<MediaStream> > oldStreams;
|
||||
oldStreams.SwapElements(mStreams);
|
||||
for (uint32_t i = 0; i < oldStreams.Length(); ++i) {
|
||||
MediaStream* stream = oldStreams[i];
|
||||
mOldStreams.SwapElements(mStreams);
|
||||
mStreams.ClearAndRetainStorage();
|
||||
for (uint32_t i = 0; i < mOldStreams.Length(); ++i) {
|
||||
MediaStream* stream = mOldStreams[i];
|
||||
stream->mHasBeenOrdered = false;
|
||||
stream->mIsConsumed = false;
|
||||
stream->mIsOnOrderingStack = false;
|
||||
@ -503,9 +517,9 @@ MediaStreamGraphImpl::UpdateStreamOrder()
|
||||
}
|
||||
}
|
||||
|
||||
nsAutoTArray<MediaStream*,10> stack;
|
||||
for (uint32_t i = 0; i < oldStreams.Length(); ++i) {
|
||||
nsRefPtr<MediaStream>& s = oldStreams[i];
|
||||
mozilla::LinkedList<MediaStream> stack;
|
||||
for (uint32_t i = 0; i < mOldStreams.Length(); ++i) {
|
||||
nsRefPtr<MediaStream>& s = mOldStreams[i];
|
||||
if (!s->mAudioOutputs.IsEmpty() || !s->mVideoOutputs.IsEmpty()) {
|
||||
MarkConsumed(s);
|
||||
}
|
||||
@ -888,28 +902,47 @@ MediaStreamGraphImpl::PlayVideo(MediaStream* aStream)
|
||||
}
|
||||
}
|
||||
|
||||
bool
|
||||
MediaStreamGraphImpl::ShouldUpdateMainThread()
|
||||
{
|
||||
if (mRealtime) {
|
||||
return true;
|
||||
}
|
||||
|
||||
TimeStamp now = TimeStamp::Now();
|
||||
if ((now - mLastMainThreadUpdate).ToMilliseconds() > MEDIA_GRAPH_TARGET_PERIOD_MS) {
|
||||
mLastMainThreadUpdate = now;
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
void
|
||||
MediaStreamGraphImpl::PrepareUpdatesToMainThreadState(bool aFinalUpdate)
|
||||
{
|
||||
mMonitor.AssertCurrentThreadOwns();
|
||||
|
||||
mStreamUpdates.SetCapacity(mStreamUpdates.Length() + mStreams.Length());
|
||||
for (uint32_t i = 0; i < mStreams.Length(); ++i) {
|
||||
MediaStream* stream = mStreams[i];
|
||||
if (!stream->MainThreadNeedsUpdates()) {
|
||||
continue;
|
||||
// We don't want to update the main thread about timing update when we are not
|
||||
// running in realtime.
|
||||
if (ShouldUpdateMainThread()) {
|
||||
mStreamUpdates.SetCapacity(mStreamUpdates.Length() + mStreams.Length());
|
||||
for (uint32_t i = 0; i < mStreams.Length(); ++i) {
|
||||
MediaStream* stream = mStreams[i];
|
||||
if (!stream->MainThreadNeedsUpdates()) {
|
||||
continue;
|
||||
}
|
||||
StreamUpdate* update = mStreamUpdates.AppendElement();
|
||||
update->mGraphUpdateIndex = stream->mGraphUpdateIndices.GetAt(mCurrentTime);
|
||||
update->mStream = stream;
|
||||
update->mNextMainThreadCurrentTime =
|
||||
GraphTimeToStreamTime(stream, mCurrentTime);
|
||||
update->mNextMainThreadFinished =
|
||||
stream->mFinished &&
|
||||
StreamTimeToGraphTime(stream, stream->GetBufferEnd()) <= mCurrentTime;
|
||||
}
|
||||
if (!mPendingUpdateRunnables.IsEmpty()) {
|
||||
mUpdateRunnables.MoveElementsFrom(mPendingUpdateRunnables);
|
||||
}
|
||||
StreamUpdate* update = mStreamUpdates.AppendElement();
|
||||
update->mGraphUpdateIndex = stream->mGraphUpdateIndices.GetAt(mCurrentTime);
|
||||
update->mStream = stream;
|
||||
update->mNextMainThreadCurrentTime =
|
||||
GraphTimeToStreamTime(stream, mCurrentTime);
|
||||
update->mNextMainThreadFinished =
|
||||
stream->mFinished &&
|
||||
StreamTimeToGraphTime(stream, stream->GetBufferEnd()) <= mCurrentTime;
|
||||
}
|
||||
if (!mPendingUpdateRunnables.IsEmpty()) {
|
||||
mUpdateRunnables.MoveElementsFrom(mPendingUpdateRunnables);
|
||||
}
|
||||
|
||||
// Don't send the message to the main thread if it's not going to have
|
||||
@ -1172,6 +1205,7 @@ MediaStreamGraphImpl::RunThread()
|
||||
if (!mRealtime) {
|
||||
mNonRealtimeIsRunning = false;
|
||||
}
|
||||
profiler_unregister_thread();
|
||||
}
|
||||
|
||||
void
|
||||
@ -1217,6 +1251,23 @@ MediaStreamGraphImpl::ForceShutDown()
|
||||
|
||||
namespace {
|
||||
|
||||
class MediaStreamGraphInitThreadRunnable : public nsRunnable {
|
||||
public:
|
||||
explicit MediaStreamGraphInitThreadRunnable(MediaStreamGraphImpl* aGraph)
|
||||
: mGraph(aGraph)
|
||||
{
|
||||
}
|
||||
NS_IMETHOD Run()
|
||||
{
|
||||
char aLocal;
|
||||
profiler_register_thread("MediaStreamGraph", &aLocal);
|
||||
mGraph->RunThread();
|
||||
return NS_OK;
|
||||
}
|
||||
private:
|
||||
MediaStreamGraphImpl* mGraph;
|
||||
};
|
||||
|
||||
class MediaStreamGraphThreadRunnable : public nsRunnable {
|
||||
public:
|
||||
explicit MediaStreamGraphThreadRunnable(MediaStreamGraphImpl* aGraph)
|
||||
@ -1356,7 +1407,7 @@ MediaStreamGraphImpl::RunInStableState()
|
||||
// Start the thread now. We couldn't start it earlier because
|
||||
// the graph might exit immediately on finding it has no streams. The
|
||||
// first message for a new graph must create a stream.
|
||||
nsCOMPtr<nsIRunnable> event = new MediaStreamGraphThreadRunnable(this);
|
||||
nsCOMPtr<nsIRunnable> event = new MediaStreamGraphInitThreadRunnable(this);
|
||||
NS_NewNamedThread("MediaStreamGrph", getter_AddRefs(mThread), event);
|
||||
}
|
||||
|
||||
@ -2168,7 +2219,7 @@ MediaStreamGraphImpl::MediaStreamGraphImpl(bool aRealtime)
|
||||
}
|
||||
#endif
|
||||
|
||||
mCurrentTimeStamp = mInitialTimeStamp = TimeStamp::Now();
|
||||
mCurrentTimeStamp = mInitialTimeStamp = mLastMainThreadUpdate = TimeStamp::Now();
|
||||
}
|
||||
|
||||
NS_IMPL_ISUPPORTS1(MediaStreamGraphShutdownObserver, nsIObserver)
|
||||
|
@ -7,6 +7,7 @@
|
||||
#define MOZILLA_MEDIASTREAMGRAPH_H_
|
||||
|
||||
#include "mozilla/Mutex.h"
|
||||
#include "mozilla/LinkedList.h"
|
||||
#include "AudioStream.h"
|
||||
#include "nsTArray.h"
|
||||
#include "nsIRunnable.h"
|
||||
@ -257,7 +258,7 @@ struct AudioChunk;
|
||||
* for those objects in arbitrary order and the MediaStreamGraph has to be able
|
||||
* to handle this.
|
||||
*/
|
||||
class MediaStream {
|
||||
class MediaStream : public mozilla::LinkedListElement<MediaStream> {
|
||||
public:
|
||||
NS_INLINE_DECL_THREADSAFE_REFCOUNTING(MediaStream)
|
||||
|
||||
|
@ -15,6 +15,9 @@
|
||||
|
||||
namespace mozilla {
|
||||
|
||||
template <typename T>
|
||||
class LinkedList;
|
||||
|
||||
#ifdef PR_LOGGING
|
||||
extern PRLogModuleInfo* gMediaStreamGraphLog;
|
||||
#define LOG(type, msg) PR_LOG(gMediaStreamGraphLog, type, msg)
|
||||
@ -190,6 +193,12 @@ public:
|
||||
* mMonitor must be held.
|
||||
*/
|
||||
void PrepareUpdatesToMainThreadState(bool aFinalUpdate);
|
||||
/**
|
||||
* If we are rendering in non-realtime mode, we don't want to send messages to
|
||||
* the main thread at each iteration for performance reasons. We instead
|
||||
* notify the main thread at the same rate
|
||||
*/
|
||||
bool ShouldUpdateMainThread();
|
||||
// The following methods are the various stages of RunThread processing.
|
||||
/**
|
||||
* Compute a new current time for the graph and advance all on-graph-thread
|
||||
@ -215,7 +224,7 @@ public:
|
||||
* If aStream hasn't already been ordered, push it onto aStack and order
|
||||
* its children.
|
||||
*/
|
||||
void UpdateStreamOrderForStream(nsTArray<MediaStream*>* aStack,
|
||||
void UpdateStreamOrderForStream(mozilla::LinkedList<MediaStream>* aStack,
|
||||
already_AddRefed<MediaStream> aStream);
|
||||
/**
|
||||
* Mark aStream and all its inputs (recursively) as consumed.
|
||||
@ -370,6 +379,11 @@ public:
|
||||
// is not running and this state can be used from the main thread.
|
||||
|
||||
nsTArray<nsRefPtr<MediaStream> > mStreams;
|
||||
/**
|
||||
* mOldStreams is used as temporary storage for streams when computing the
|
||||
* order in which we compute them.
|
||||
*/
|
||||
nsTArray<nsRefPtr<MediaStream> > mOldStreams;
|
||||
/**
|
||||
* The current graph time for the current iteration of the RunThread control
|
||||
* loop.
|
||||
@ -389,6 +403,10 @@ public:
|
||||
* The real timestamp of the latest run of UpdateCurrentTime.
|
||||
*/
|
||||
TimeStamp mCurrentTimeStamp;
|
||||
/**
|
||||
* Date of the last time we updated the main thread with the graph state.
|
||||
*/
|
||||
TimeStamp mLastMainThreadUpdate;
|
||||
/**
|
||||
* Which update batch we are currently processing.
|
||||
*/
|
||||
|
@ -149,8 +149,6 @@ function nextTest() {
|
||||
}
|
||||
|
||||
function done() {
|
||||
netscape.security.PrivilegeManager.enablePrivilege("UniversalXPConnect");
|
||||
mediaTestCleanup();
|
||||
opener.done();
|
||||
}
|
||||
|
||||
|
@ -216,7 +216,7 @@ var gInvalidTests = [
|
||||
// we've specified.
|
||||
function fileUriToSrc(path, mustExist) {
|
||||
// android mochitest doesn't support file://
|
||||
if (navigator.appVersion.indexOf("Android") != -1)
|
||||
if (navigator.appVersion.indexOf("Android") != -1 || SpecialPowers.Services.appinfo.name == "B2G")
|
||||
return path;
|
||||
|
||||
const Ci = SpecialPowers.Ci;
|
||||
@ -691,25 +691,25 @@ function mediaTestCleanup() {
|
||||
var oldGStreamer = undefined;
|
||||
var oldOpus = undefined;
|
||||
|
||||
try { oldGStreamer = branch.getBoolPref("gstreamer.enabled"); } catch(ex) { }
|
||||
try { oldDefault = branch.getIntPref("preload.default"); } catch(ex) { }
|
||||
try { oldAuto = branch.getIntPref("preload.auto"); } catch(ex) { }
|
||||
try { oldOpus = branch.getBoolPref("opus.enabled"); } catch(ex) { }
|
||||
try { oldGStreamer = SpecialPowers.getBoolPref("media.gstreamer.enabled"); } catch(ex) { }
|
||||
try { oldDefault = SpecialPowers.getIntPref("media.preload.default"); } catch(ex) { }
|
||||
try { oldAuto = SpecialPowers.getIntPref("media.preload.auto"); } catch(ex) { }
|
||||
try { oldOpus = SpecialPowers.getBoolPref("media.opus.enabled"); } catch(ex) { }
|
||||
|
||||
branch.setIntPref("preload.default", 2); // preload_metadata
|
||||
branch.setIntPref("preload.auto", 3); // preload_enough
|
||||
SpecialPowers.setIntPref("media.preload.default", 2); // preload_metadata
|
||||
SpecialPowers.setIntPref("media.preload.auto", 3); // preload_enough
|
||||
// test opus playback iff the pref exists
|
||||
if (oldOpus !== undefined)
|
||||
branch.setBoolPref("opus.enabled", true);
|
||||
SpecialPowers.setBoolPref("media.opus.enabled", true);
|
||||
if (oldGStreamer !== undefined)
|
||||
branch.setBoolPref("gstreamer.enabled", true);
|
||||
SpecialPowers.setBoolPref("media.gstreamer.enabled", true);
|
||||
|
||||
window.addEventListener("unload", function() {
|
||||
if (oldGStreamer !== undefined)
|
||||
branch.setBoolPref("gstreamer.enabled", oldGStreamer);
|
||||
branch.setIntPref("preload.default", oldDefault);
|
||||
branch.setIntPref("preload.auto", oldAuto);
|
||||
SpecialPowers.setBoolPref("media.gstreamer.enabled", oldGStreamer);
|
||||
SpecialPowers.setIntPref("media.preload.default", oldDefault);
|
||||
SpecialPowers.setIntPref("media.preload.auto", oldAuto);
|
||||
if (oldOpus !== undefined)
|
||||
branch.setBoolPref("opus.enabled", oldOpus);
|
||||
SpecialPowers.setBoolPref("media.opus.enabled", oldOpus);
|
||||
}, false);
|
||||
})();
|
||||
|
@ -80,41 +80,43 @@ Reverb::Reverb(ThreadSharedFloatArrayBufferList* impulseResponse, size_t impulse
|
||||
{
|
||||
float scale = 1;
|
||||
|
||||
nsAutoTArray<const float*,4> irChannels;
|
||||
for (size_t i = 0; i < impulseResponse->GetChannels(); ++i) {
|
||||
irChannels.AppendElement(impulseResponse->GetData(i));
|
||||
}
|
||||
nsAutoTArray<float,1024> tempBuf;
|
||||
|
||||
if (normalize) {
|
||||
scale = calculateNormalizationScale(impulseResponse, impulseResponseBufferLength, sampleRate);
|
||||
|
||||
if (scale) {
|
||||
for (uint32_t i = 0; i < impulseResponse->GetChannels(); ++i) {
|
||||
AudioBufferInPlaceScale(const_cast<float*>(impulseResponse->GetData(i)),
|
||||
1, scale, impulseResponseBufferLength);
|
||||
tempBuf.SetLength(irChannels.Length()*impulseResponseBufferLength);
|
||||
for (uint32_t i = 0; i < irChannels.Length(); ++i) {
|
||||
float* buf = &tempBuf[i*impulseResponseBufferLength];
|
||||
AudioBufferCopyWithScale(irChannels[i], scale, buf,
|
||||
impulseResponseBufferLength);
|
||||
irChannels[i] = buf;
|
||||
}
|
||||
}
|
||||
}
|
||||
|
||||
initialize(impulseResponse, impulseResponseBufferLength, renderSliceSize, maxFFTSize, numberOfChannels, useBackgroundThreads);
|
||||
|
||||
// Undo scaling since this shouldn't be a destructive operation on impulseResponse.
|
||||
// FIXME: What about roundoff? Perhaps consider making a temporary scaled copy
|
||||
// instead of scaling and unscaling in place.
|
||||
if (normalize && scale) {
|
||||
for (uint32_t i = 0; i < impulseResponse->GetChannels(); ++i) {
|
||||
AudioBufferInPlaceScale(const_cast<float*>(impulseResponse->GetData(i)),
|
||||
1, 1 / scale, impulseResponseBufferLength);
|
||||
}
|
||||
}
|
||||
initialize(irChannels, impulseResponseBufferLength, renderSliceSize,
|
||||
maxFFTSize, numberOfChannels, useBackgroundThreads);
|
||||
}
|
||||
|
||||
void Reverb::initialize(ThreadSharedFloatArrayBufferList* impulseResponseBuffer, size_t impulseResponseBufferLength, size_t renderSliceSize, size_t maxFFTSize, size_t numberOfChannels, bool useBackgroundThreads)
|
||||
void Reverb::initialize(const nsTArray<const float*>& impulseResponseBuffer,
|
||||
size_t impulseResponseBufferLength, size_t renderSliceSize,
|
||||
size_t maxFFTSize, size_t numberOfChannels, bool useBackgroundThreads)
|
||||
{
|
||||
m_impulseResponseLength = impulseResponseBufferLength;
|
||||
|
||||
// The reverb can handle a mono impulse response and still do stereo processing
|
||||
size_t numResponseChannels = impulseResponseBuffer->GetChannels();
|
||||
size_t numResponseChannels = impulseResponseBuffer.Length();
|
||||
m_convolvers.SetCapacity(numberOfChannels);
|
||||
|
||||
int convolverRenderPhase = 0;
|
||||
for (size_t i = 0; i < numResponseChannels; ++i) {
|
||||
const float* channel = impulseResponseBuffer->GetData(i);
|
||||
const float* channel = impulseResponseBuffer[i];
|
||||
size_t length = impulseResponseBufferLength;
|
||||
|
||||
nsAutoPtr<ReverbConvolver> convolver(new ReverbConvolver(channel, length, renderSliceSize, maxFFTSize, convolverRenderPhase, useBackgroundThreads));
|
||||
|
@ -55,7 +55,7 @@ public:
|
||||
size_t latencyFrames() const;
|
||||
|
||||
private:
|
||||
void initialize(mozilla::ThreadSharedFloatArrayBufferList* impulseResponseBuffer, size_t impulseResponseBufferLength, size_t renderSliceSize, size_t maxFFTSize, size_t numberOfChannels, bool useBackgroundThreads);
|
||||
void initialize(const nsTArray<const float*>& impulseResponseBuffer, size_t impulseResponseBufferLength, size_t renderSliceSize, size_t maxFFTSize, size_t numberOfChannels, bool useBackgroundThreads);
|
||||
|
||||
size_t m_impulseResponseLength;
|
||||
|
||||
|
@ -157,7 +157,7 @@ var tests = [
|
||||
numberOfChannels: 2,
|
||||
duration: 0.2760,
|
||||
length: 13248,
|
||||
fuzzTolerance: 72,
|
||||
fuzzTolerance: 76,
|
||||
fuzzToleranceMobile: 14844
|
||||
},
|
||||
// A wave file
|
||||
|
30
content/xbl/crashtests/895805-1.xhtml
Normal file
30
content/xbl/crashtests/895805-1.xhtml
Normal file
@ -0,0 +1,30 @@
|
||||
<?xml version="1.0" encoding="utf-8"?>
|
||||
<html xmlns="http://www.w3.org/1999/xhtml"
|
||||
xmlns:xbl="http://www.mozilla.org/xbl">
|
||||
<head>
|
||||
<title>Bug 895805 - Adopting bound element to another document.</title>
|
||||
<xbl:bindings>
|
||||
<xbl:binding id="crash">
|
||||
<xbl:content>
|
||||
<xbl:children />
|
||||
Bug 895805 dummy binding
|
||||
</xbl:content>
|
||||
</xbl:binding>
|
||||
</xbl:bindings>
|
||||
<style type="text/css">
|
||||
#test {
|
||||
-moz-binding:url(#crash);
|
||||
}
|
||||
</style>
|
||||
</head>
|
||||
<body onload="init()">
|
||||
<span id="test">Test</span>
|
||||
<script>
|
||||
function init() {
|
||||
var boundElement = document.getElementById('test');
|
||||
var otherDoc = document.implementation.createDocument('', '', null);
|
||||
otherDoc.adoptNode(boundElement);
|
||||
}
|
||||
</script>
|
||||
</body>
|
||||
</html>
|
@ -37,3 +37,4 @@ load 507628-1.xhtml
|
||||
load 507991-1.xhtml
|
||||
load set-field-bad-this.xhtml
|
||||
load 830614-1.xul
|
||||
load 895805-1.xhtml
|
||||
|
@ -1114,7 +1114,7 @@ nsBindingManager::Traverse(nsIContent *aContent,
|
||||
return;
|
||||
}
|
||||
|
||||
if (mBoundContentSet.Contains(aContent)) {
|
||||
if (mBoundContentSet.IsInitialized() && mBoundContentSet.Contains(aContent)) {
|
||||
NS_CYCLE_COLLECTION_NOTE_EDGE_NAME(cb, "[via binding manager] mBoundContentSet entry");
|
||||
cb.NoteXPCOMChild(aContent);
|
||||
}
|
||||
|
@ -280,9 +280,7 @@ FieldSetterImpl(JSContext *cx, JS::CallArgs args)
|
||||
}
|
||||
|
||||
if (installed) {
|
||||
JS::Rooted<JS::Value> v(cx,
|
||||
args.length() > 0 ? args[0] : JS::UndefinedValue());
|
||||
if (!::JS_SetPropertyById(cx, thisObj, id, &v)) {
|
||||
if (!::JS_SetPropertyById(cx, thisObj, id, args.get(0))) {
|
||||
return false;
|
||||
}
|
||||
}
|
||||
|
@ -1404,7 +1404,7 @@ nsXULTemplateBuilder::InitHTMLTemplateRoot()
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
|
||||
bool ok;
|
||||
ok = JS_SetProperty(jscontext, jselement, "database", &jsdatabase);
|
||||
ok = JS_SetProperty(jscontext, jselement, "database", jsdatabase);
|
||||
NS_ASSERTION(ok, "unable to set database property");
|
||||
if (! ok)
|
||||
return NS_ERROR_FAILURE;
|
||||
@ -1421,7 +1421,7 @@ nsXULTemplateBuilder::InitHTMLTemplateRoot()
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
|
||||
bool ok;
|
||||
ok = JS_SetProperty(jscontext, jselement, "builder", &jsbuilder);
|
||||
ok = JS_SetProperty(jscontext, jselement, "builder", jsbuilder);
|
||||
if (! ok)
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
@ -1,8 +1,9 @@
|
||||
function handleRequest(request, response)
|
||||
{
|
||||
var count = parseInt(getState('count'));
|
||||
if (!count)
|
||||
if (!count || request.queryString == 'countreset')
|
||||
count = 0;
|
||||
|
||||
setState('count', count + 1 + '');
|
||||
|
||||
response.setHeader('Content-Type', 'text/html', false);
|
||||
|
@ -66,6 +66,12 @@ function checkPopupLoadCount()
|
||||
|
||||
function test()
|
||||
{
|
||||
// Step 0 - Make sure the count is reset to 0 in case of reload
|
||||
popup.location = 'file_bug669671.sjs?countreset';
|
||||
yield;
|
||||
is(popup.document.body.innerHTML, '0',
|
||||
'Load count should be reset to 0');
|
||||
|
||||
// Step 1 - The popup's body counts how many times we've requested the
|
||||
// resource. This is the first time we've requested it, so it should be '0'.
|
||||
checkPopupLoadCount();
|
||||
|
@ -30,7 +30,6 @@
|
||||
#include "PowerManager.h"
|
||||
#include "nsIDOMWakeLock.h"
|
||||
#include "nsIPowerManagerService.h"
|
||||
#include "mozilla/dom/SmsManager.h"
|
||||
#include "mozilla/dom/MobileMessageManager.h"
|
||||
#include "nsISmsService.h"
|
||||
#include "mozilla/Hal.h"
|
||||
@ -141,7 +140,6 @@ NS_IMPL_CYCLE_COLLECTION_TRAVERSE_BEGIN(Navigator)
|
||||
NS_IMPL_CYCLE_COLLECTION_TRAVERSE(mNotification)
|
||||
NS_IMPL_CYCLE_COLLECTION_TRAVERSE(mBatteryManager)
|
||||
NS_IMPL_CYCLE_COLLECTION_TRAVERSE(mPowerManager)
|
||||
NS_IMPL_CYCLE_COLLECTION_TRAVERSE(mSmsManager)
|
||||
NS_IMPL_CYCLE_COLLECTION_TRAVERSE(mMobileMessageManager)
|
||||
#ifdef MOZ_B2G_RIL
|
||||
NS_IMPL_CYCLE_COLLECTION_TRAVERSE(mTelephony)
|
||||
@ -204,11 +202,6 @@ Navigator::Invalidate()
|
||||
mPowerManager = nullptr;
|
||||
}
|
||||
|
||||
if (mSmsManager) {
|
||||
mSmsManager->Shutdown();
|
||||
mSmsManager = nullptr;
|
||||
}
|
||||
|
||||
if (mMobileMessageManager) {
|
||||
mMobileMessageManager->Shutdown();
|
||||
mMobileMessageManager = nullptr;
|
||||
@ -968,10 +961,6 @@ Navigator::GetDeviceStorages(const nsAString& aType,
|
||||
Geolocation*
|
||||
Navigator::GetGeolocation(ErrorResult& aRv)
|
||||
{
|
||||
if (!Preferences::GetBool("geo.enabled", true)) {
|
||||
return nullptr;
|
||||
}
|
||||
|
||||
if (mGeolocation) {
|
||||
return mGeolocation;
|
||||
}
|
||||
@ -1114,19 +1103,6 @@ Navigator::RequestWakeLock(const nsAString &aTopic, ErrorResult& aRv)
|
||||
return wakelock.forget();
|
||||
}
|
||||
|
||||
nsIDOMMozSmsManager*
|
||||
Navigator::GetMozSms()
|
||||
{
|
||||
if (!mSmsManager) {
|
||||
NS_ENSURE_TRUE(mWindow, nullptr);
|
||||
NS_ENSURE_TRUE(mWindow->GetDocShell(), nullptr);
|
||||
|
||||
mSmsManager = SmsManager::CreateInstance(mWindow);
|
||||
}
|
||||
|
||||
return mSmsManager;
|
||||
}
|
||||
|
||||
nsIDOMMozMobileMessageManager*
|
||||
Navigator::GetMozMobileMessage()
|
||||
{
|
||||
@ -1615,14 +1591,6 @@ Navigator::HasWakeLockSupport(JSContext* /* unused*/, JSObject* /*unused */)
|
||||
return !!pmService;
|
||||
}
|
||||
|
||||
/* static */
|
||||
bool
|
||||
Navigator::HasSmsSupport(JSContext* /* unused */, JSObject* aGlobal)
|
||||
{
|
||||
nsCOMPtr<nsPIDOMWindow> win = GetWindowFromGlobal(aGlobal);
|
||||
return win && SmsManager::CreationIsAllowed(win);
|
||||
}
|
||||
|
||||
/* static */
|
||||
bool
|
||||
Navigator::HasMobileMessageSupport(JSContext* /* unused */, JSObject* aGlobal)
|
||||
|
@ -9,7 +9,6 @@
|
||||
|
||||
#include "mozilla/MemoryReporting.h"
|
||||
#include "nsIDOMNavigator.h"
|
||||
#include "nsIDOMSmsManager.h"
|
||||
#include "nsIDOMMobileMessageManager.h"
|
||||
#include "nsIMozNavigatorNetwork.h"
|
||||
#include "nsAutoPtr.h"
|
||||
@ -63,7 +62,6 @@ class BatteryManager;
|
||||
} // namespace battery
|
||||
|
||||
class DesktopNotificationCenter;
|
||||
class SmsManager;
|
||||
class MobileMessageManager;
|
||||
class MozIdleObserver;
|
||||
#ifdef MOZ_GAMEPAD
|
||||
@ -208,7 +206,6 @@ public:
|
||||
DesktopNotificationCenter* GetMozNotification(ErrorResult& aRv);
|
||||
bool MozIsLocallyAvailable(const nsAString& aURI, bool aWhenOffline,
|
||||
ErrorResult& aRv);
|
||||
nsIDOMMozSmsManager* GetMozSms();
|
||||
nsIDOMMozMobileMessageManager* GetMozMobileMessage();
|
||||
nsIDOMMozConnection* GetMozConnection();
|
||||
nsDOMCameraManager* GetMozCameras(ErrorResult& aRv);
|
||||
@ -257,7 +254,6 @@ public:
|
||||
{
|
||||
return HasDesktopNotificationSupport();
|
||||
}
|
||||
static bool HasSmsSupport(JSContext* /* unused */, JSObject* aGlobal);
|
||||
static bool HasMobileMessageSupport(JSContext* /* unused */,
|
||||
JSObject* aGlobal);
|
||||
static bool HasCameraSupport(JSContext* /* unused */,
|
||||
@ -306,7 +302,6 @@ private:
|
||||
nsRefPtr<DesktopNotificationCenter> mNotification;
|
||||
nsRefPtr<battery::BatteryManager> mBatteryManager;
|
||||
nsRefPtr<power::PowerManager> mPowerManager;
|
||||
nsRefPtr<SmsManager> mSmsManager;
|
||||
nsRefPtr<MobileMessageManager> mMobileMessageManager;
|
||||
#ifdef MOZ_B2G_RIL
|
||||
nsCOMPtr<nsIDOMTelephony> mTelephony;
|
||||
|
@ -218,7 +218,6 @@ using mozilla::dom::workers::ResolveWorkerClasses;
|
||||
#include "BatteryManager.h"
|
||||
#include "nsIDOMPowerManager.h"
|
||||
#include "nsIDOMWakeLock.h"
|
||||
#include "nsIDOMSmsManager.h"
|
||||
#include "nsIDOMMobileMessageManager.h"
|
||||
#include "nsIDOMMozSmsMessage.h"
|
||||
#include "nsIDOMMozMmsMessage.h"
|
||||
@ -577,9 +576,6 @@ static nsDOMClassInfoData sClassInfoData[] = {
|
||||
NS_DEFINE_CLASSINFO_DATA(MozWakeLock, nsDOMGenericSH,
|
||||
DOM_DEFAULT_SCRIPTABLE_FLAGS)
|
||||
|
||||
NS_DEFINE_CLASSINFO_DATA(MozSmsManager, nsDOMGenericSH,
|
||||
DOM_DEFAULT_SCRIPTABLE_FLAGS)
|
||||
|
||||
NS_DEFINE_CLASSINFO_DATA(MozMobileMessageManager, nsDOMGenericSH,
|
||||
DOM_DEFAULT_SCRIPTABLE_FLAGS)
|
||||
|
||||
@ -1441,10 +1437,6 @@ nsDOMClassInfo::Init()
|
||||
DOM_CLASSINFO_MAP_ENTRY(nsIDOMMozWakeLock)
|
||||
DOM_CLASSINFO_MAP_END
|
||||
|
||||
DOM_CLASSINFO_MAP_BEGIN(MozSmsManager, nsIDOMMozSmsManager)
|
||||
DOM_CLASSINFO_MAP_ENTRY(nsIDOMMozSmsManager)
|
||||
DOM_CLASSINFO_MAP_END
|
||||
|
||||
DOM_CLASSINFO_MAP_BEGIN(MozMobileMessageManager, nsIDOMMozMobileMessageManager)
|
||||
DOM_CLASSINFO_MAP_ENTRY(nsIDOMMozMobileMessageManager)
|
||||
DOM_CLASSINFO_MAP_END
|
||||
|
@ -95,7 +95,6 @@ DOMCI_CLASS(ModalContentWindow)
|
||||
DOMCI_CLASS(MozPowerManager)
|
||||
DOMCI_CLASS(MozWakeLock)
|
||||
|
||||
DOMCI_CLASS(MozSmsManager)
|
||||
DOMCI_CLASS(MozMobileMessageManager)
|
||||
DOMCI_CLASS(MozSmsMessage)
|
||||
DOMCI_CLASS(MozMmsMessage)
|
||||
|
@ -157,10 +157,17 @@ DOMInterfaces = {
|
||||
'headerFile': 'DOMCameraManager.h'
|
||||
},
|
||||
|
||||
'CanvasGradient' : {
|
||||
'nativeOwnership': 'refcounted'
|
||||
},
|
||||
|
||||
'CanvasPattern' : {
|
||||
'nativeOwnership': 'refcounted'
|
||||
},
|
||||
|
||||
'CanvasRenderingContext2D': {
|
||||
'implicitJSContext': [
|
||||
'createImageData', 'getImageData', 'strokeStyle',
|
||||
'fillStyle', 'mozDash'
|
||||
'createImageData', 'getImageData', 'mozDash'
|
||||
],
|
||||
'resultNotAddRefed': [ 'canvas', 'measureText' ],
|
||||
'binaryNames': {
|
||||
@ -1705,7 +1712,6 @@ addExternalIface('MozPowerManager', headerFile='nsIDOMPowerManager.h')
|
||||
addExternalIface('MozRDFCompositeDataSource', nativeType='nsIRDFCompositeDataSource',
|
||||
notflattened=True)
|
||||
addExternalIface('MozRDFResource', nativeType='nsIRDFResource', notflattened=True)
|
||||
addExternalIface('MozSmsManager', headerFile='nsIDOMSmsManager.h')
|
||||
addExternalIface('MozTelephony', nativeType='nsIDOMTelephony')
|
||||
addExternalIface('MozTreeBoxObject', nativeType='nsITreeBoxObject',
|
||||
notflattened=True)
|
||||
|
@ -9,6 +9,7 @@ import os
|
||||
import re
|
||||
import string
|
||||
import math
|
||||
import itertools
|
||||
|
||||
from WebIDL import BuiltinTypes, IDLBuiltinType, IDLNullValue, IDLSequenceType, IDLType
|
||||
from Configuration import NoSuchDescriptorError, getTypesFromDescriptor, getTypesFromDictionary, getTypesFromCallback, Descriptor
|
||||
@ -735,6 +736,7 @@ def UnionTypes(descriptors, dictionaries, callbacks, config):
|
||||
implheaders = set(["UnionTypes.h"])
|
||||
declarations = set()
|
||||
unionStructs = dict()
|
||||
unionReturnValues = dict()
|
||||
|
||||
def addInfoForType(t, descriptor=None, dictionary=None):
|
||||
"""
|
||||
@ -751,6 +753,10 @@ def UnionTypes(descriptors, dictionaries, callbacks, config):
|
||||
config)
|
||||
# FIXME: Unions are broken in workers. See bug 809899.
|
||||
unionStructs[name] = CGUnionStruct(t, providers[0])
|
||||
# Unions cannot contain JSObject*.
|
||||
if not any(member.isObject() or member.isSpiderMonkeyInterface() for member in t.flatMemberTypes):
|
||||
unionReturnValues[name] = CGUnionReturnValueStruct(t, providers[0])
|
||||
|
||||
for f in t.flatMemberTypes:
|
||||
f = f.unroll()
|
||||
if f.isInterface():
|
||||
@ -772,7 +778,8 @@ def UnionTypes(descriptors, dictionaries, callbacks, config):
|
||||
callForEachType(descriptors, dictionaries, callbacks, addInfoForType)
|
||||
|
||||
return (headers, implheaders, declarations,
|
||||
CGList(SortedDictValues(unionStructs), "\n"))
|
||||
CGList(itertools.chain(SortedDictValues(unionStructs),
|
||||
SortedDictValues(unionReturnValues)), "\n"))
|
||||
|
||||
def UnionConversions(descriptors, dictionaries, callbacks, config):
|
||||
"""
|
||||
@ -1438,6 +1445,17 @@ class MethodDefiner(PropertyDefiner):
|
||||
self.chrome.append(toStringDesc)
|
||||
else:
|
||||
self.regular.append(toStringDesc)
|
||||
jsonifier = descriptor.operations['Jsonifier']
|
||||
if jsonifier:
|
||||
toJSONDesc = { "name": "toJSON",
|
||||
"nativeName": jsonifier.identifier.name,
|
||||
"length": 0,
|
||||
"flags": "JSPROP_ENUMERATE",
|
||||
"condition": PropertyDefiner.getControllingCondition(jsonifier) }
|
||||
if isChromeOnly(jsonifier):
|
||||
self.chrome.append(toJSONDesc)
|
||||
else:
|
||||
self.regular.append(toJSONDesc)
|
||||
elif (descriptor.interface.isJSImplemented() and
|
||||
descriptor.interface.hasInterfaceObject()):
|
||||
self.chrome.append({"name": '_create',
|
||||
@ -2058,7 +2076,7 @@ def InitUnforgeablePropertiesOnObject(descriptor, obj, properties, failureReturn
|
||||
if len(failureReturnValue) > 0:
|
||||
failureReturn += " " + failureReturnValue
|
||||
failureReturn += ";"
|
||||
|
||||
|
||||
defineUnforgeables = ("if (!DefineUnforgeableAttributes(aCx, " + obj + ", %s)) {\n"
|
||||
" " + failureReturn + "\n"
|
||||
"}")
|
||||
@ -2477,6 +2495,7 @@ def getJSToNativeConversionInfo(type, descriptorProvider, failureCode=None,
|
||||
lenientFloatCode=None,
|
||||
allowTreatNonCallableAsNull=False,
|
||||
isCallbackReturnValue=False,
|
||||
isInUnionReturnValue=False,
|
||||
sourceDescription="value"):
|
||||
"""
|
||||
Get a template for converting a JS value to a native object based on the
|
||||
@ -3025,13 +3044,16 @@ for (uint32_t i = 0; i < length; ++i) {
|
||||
isCallbackReturnValue)
|
||||
|
||||
# Sequences and non-worker callbacks have to hold a strong ref to the
|
||||
# thing being passed down. Also, callback return values always end up
|
||||
# thing being passed down. Union return values must hold a strong ref
|
||||
# because they may be returning an addrefed pointer.
|
||||
# Also, callback return values always end up
|
||||
# addrefing anyway, so there is no point trying to avoid it here and it
|
||||
# makes other things simpler since we can assume the return value is a
|
||||
# strong ref.
|
||||
forceOwningType = ((descriptor.interface.isCallback() and
|
||||
not descriptor.workers) or
|
||||
isMember or
|
||||
isInUnionReturnValue or
|
||||
isCallbackReturnValue)
|
||||
|
||||
typeName = descriptor.nativeType
|
||||
@ -3248,6 +3270,8 @@ for (uint32_t i = 0; i < length; ++i) {
|
||||
|
||||
if isOptional:
|
||||
declType = "Optional<nsAString>"
|
||||
elif isInUnionReturnValue:
|
||||
declType = "nsString"
|
||||
else:
|
||||
declType = "NonNull<nsAString>"
|
||||
|
||||
@ -4089,15 +4113,7 @@ if (!returnArray) {
|
||||
# NB: setValue(..., True) calls JS_WrapValue(), so is fallible
|
||||
return (setValue(toValue % result, wrapType), False)
|
||||
|
||||
if type.isUnion():
|
||||
if type.nullable():
|
||||
prefix = "%s->"
|
||||
else:
|
||||
prefix = "%s."
|
||||
return (wrapAndSetPtr((prefix % result) +
|
||||
"ToJSVal(cx, ${obj}, ${jsvalHandle})"), False)
|
||||
|
||||
if not (type.isPrimitive() or type.isDictionary() or type.isDate()):
|
||||
if not (type.isUnion() or type.isPrimitive() or type.isDictionary() or type.isDate()):
|
||||
raise TypeError("Need to learn to wrap %s" % type)
|
||||
|
||||
if type.nullable():
|
||||
@ -4108,6 +4124,10 @@ if (!returnArray) {
|
||||
CGIndenter(CGGeneric(setValue("JSVAL_NULL"))).define() + "\n" +
|
||||
"}\n" + recTemplate, recInfal)
|
||||
|
||||
if type.isUnion():
|
||||
return (wrapAndSetPtr("%s.ToJSVal(cx, ${obj}, ${jsvalHandle})" % result),
|
||||
False)
|
||||
|
||||
if type.isDictionary():
|
||||
return (wrapAndSetPtr("%s.ToObject(cx, ${obj}, ${jsvalHandle})" % result),
|
||||
False)
|
||||
@ -4311,7 +4331,10 @@ def getRetvalDeclarationForType(returnType, descriptorProvider,
|
||||
resultArgs = None
|
||||
return result, True, None, resultArgs
|
||||
if returnType.isUnion():
|
||||
raise TypeError("Need to sort out ownership model for union retvals");
|
||||
result = CGGeneric(returnType.unroll().name + "ReturnValue")
|
||||
if returnType.nullable():
|
||||
result = CGTemplatedType("Nullable", result)
|
||||
return result, True, None, None
|
||||
if returnType.isDate():
|
||||
result = CGGeneric("Date")
|
||||
if returnType.nullable():
|
||||
@ -4419,7 +4442,7 @@ class CGCallGenerator(CGThing):
|
||||
|
||||
if isFallible:
|
||||
self.cgRoot.prepend(CGGeneric("ErrorResult rv;"))
|
||||
self.cgRoot.append(CGGeneric("rv.WouldReportJSException();"));
|
||||
self.cgRoot.append(CGGeneric("rv.WouldReportJSException();"))
|
||||
self.cgRoot.append(CGGeneric("if (rv.Failed()) {"))
|
||||
self.cgRoot.append(CGIndenter(errorReport))
|
||||
self.cgRoot.append(CGGeneric("}"))
|
||||
@ -5207,6 +5230,32 @@ class CGSpecializedMethod(CGAbstractStaticMethod):
|
||||
name = method.identifier.name
|
||||
return MakeNativeName(descriptor.binaryNames.get(name, name))
|
||||
|
||||
class CGJsonifierMethod(CGSpecializedMethod):
|
||||
def __init__(self, descriptor, method):
|
||||
assert method.isJsonifier()
|
||||
CGSpecializedMethod.__init__(self, descriptor, method)
|
||||
|
||||
def definition_body(self):
|
||||
ret = ('JS::Rooted<JSObject*> result(cx, JS_NewObject(cx, nullptr, nullptr, nullptr));\n'
|
||||
'if (!result) {\n'
|
||||
' return false;\n'
|
||||
'}\n')
|
||||
for m in self.descriptor.interface.members:
|
||||
if m.isAttr() and not m.isStatic():
|
||||
ret += ('{ // scope for "temp"\n'
|
||||
' JS::Rooted<JS::Value> temp(cx);\n'
|
||||
' if (!get_%s(cx, obj, self, JSJitGetterCallArgs(&temp))) {\n'
|
||||
' return false;\n'
|
||||
' }\n'
|
||||
' if (!JS_DefineProperty(cx, result, "%s", temp, nullptr, nullptr, JSPROP_ENUMERATE)) {\n'
|
||||
' return false;\n'
|
||||
' }\n'
|
||||
'}\n' % (m.identifier.name, m.identifier.name))
|
||||
|
||||
ret += ('args.rval().setObject(*result);\n'
|
||||
'return true;')
|
||||
return CGIndenter(CGGeneric(ret)).define()
|
||||
|
||||
class CGLegacyCallHook(CGAbstractBindingMethod):
|
||||
"""
|
||||
Call hook for our object
|
||||
@ -5802,7 +5851,7 @@ def getUnionAccessorSignatureType(type, descriptorProvider):
|
||||
typeName = CGTemplatedType("Nullable", typeName, isReference=True)
|
||||
return typeName
|
||||
|
||||
def getUnionTypeTemplateVars(unionType, type, descriptorProvider):
|
||||
def getUnionTypeTemplateVars(unionType, type, descriptorProvider, isReturnValue=False):
|
||||
# For dictionaries and sequences we need to pass None as the failureCode
|
||||
# for getJSToNativeConversionInfo.
|
||||
# Also, for dictionaries we would need to handle conversion of
|
||||
@ -5827,7 +5876,7 @@ return true;"""
|
||||
}""" % name) + tryNextCode
|
||||
conversionInfo = getJSToNativeConversionInfo(
|
||||
type, descriptorProvider, failureCode=tryNextCode,
|
||||
isDefinitelyObject=True,
|
||||
isDefinitelyObject=True, isInUnionReturnValue=isReturnValue,
|
||||
sourceDescription="member of %s" % unionType)
|
||||
|
||||
# This is ugly, but UnionMember needs to call a constructor with no
|
||||
@ -5921,7 +5970,7 @@ class CGUnionStruct(CGThing):
|
||||
}"""
|
||||
methods.extend(mapTemplate(methodTemplate, templateVars))
|
||||
# Now have to be careful: we do not want the SetAsObject() method!
|
||||
setterTemplate = """ ${structType}& SetAs${name}()
|
||||
setterTemplate = """ ${structType}& SetAs${name}()
|
||||
{
|
||||
mType = e${name};
|
||||
return mValue.m${name}.SetValue();
|
||||
@ -5983,7 +6032,7 @@ ${destructors}
|
||||
if self.type.hasNullableType:
|
||||
conversionsToJS.append(" case eNull:\n"
|
||||
" {\n"
|
||||
" rval.set(JS::NullValue());\n"
|
||||
" rval.setNull();\n"
|
||||
" return true;\n"
|
||||
" }")
|
||||
conversionsToJS.extend(
|
||||
@ -6025,7 +6074,161 @@ ${doConversionsToJS}
|
||||
"jsvalHandle": "rval",
|
||||
"obj": "scopeObj",
|
||||
"result": val,
|
||||
"objectCanBeNonNull": True
|
||||
})
|
||||
return CGIndenter(CGList([CGGeneric("case e%(name)s:" % templateVars),
|
||||
CGWrapper(CGIndenter(CGGeneric(wrapCode)),
|
||||
pre="{\n",
|
||||
post="\n}")],
|
||||
"\n"),
|
||||
4).define()
|
||||
|
||||
class CGUnionReturnValueStruct(CGThing):
|
||||
def __init__(self, type, descriptorProvider):
|
||||
CGThing.__init__(self)
|
||||
self.type = type.unroll()
|
||||
self.descriptorProvider = descriptorProvider
|
||||
self.templateVars = map(
|
||||
lambda t: getUnionTypeTemplateVars(self.type, t,
|
||||
self.descriptorProvider,
|
||||
isReturnValue=True),
|
||||
self.type.flatMemberTypes)
|
||||
|
||||
def declare(self):
|
||||
templateVars = self.templateVars
|
||||
|
||||
enumValues = []
|
||||
methods = []
|
||||
if self.type.hasNullableType:
|
||||
enumValues.append("eNull")
|
||||
methods.append(""" bool IsNull() const
|
||||
{
|
||||
return mType == eNull;
|
||||
}
|
||||
|
||||
bool SetNull()
|
||||
{
|
||||
mType = eNull;
|
||||
return true;
|
||||
}""")
|
||||
|
||||
enumValues.extend(mapTemplate("e${name}", templateVars))
|
||||
methodTemplate = " ${structType}& SetAs${name}();"
|
||||
methods.extend(mapTemplate(methodTemplate, templateVars))
|
||||
values = mapTemplate("UnionMember<${structType} > m${name};", templateVars)
|
||||
return string.Template("""
|
||||
class ${structName}ReturnValue {
|
||||
public:
|
||||
${structName}ReturnValue() : mType(eUninitialized)
|
||||
{
|
||||
}
|
||||
~${structName}ReturnValue();
|
||||
|
||||
${methods}
|
||||
|
||||
bool ToJSVal(JSContext* cx, JS::Handle<JSObject*> scopeObj,
|
||||
JS::MutableHandle<JS::Value> rval) const;
|
||||
|
||||
private:
|
||||
enum Type {
|
||||
eUninitialized,
|
||||
${enumValues}
|
||||
};
|
||||
union Value {
|
||||
${values}
|
||||
};
|
||||
|
||||
Type mType;
|
||||
Value mValue;
|
||||
};
|
||||
|
||||
""").substitute(
|
||||
{
|
||||
"structName": self.type.__str__(),
|
||||
"methods": "\n\n".join(methods),
|
||||
"enumValues": ",\n ".join(enumValues),
|
||||
"values": "\n ".join(values)
|
||||
})
|
||||
|
||||
def define(self):
|
||||
templateVars = self.templateVars
|
||||
conversionsToJS = []
|
||||
if self.type.hasNullableType:
|
||||
conversionsToJS.append(" case eNull:\n"
|
||||
" {\n"
|
||||
" rval.setNull();\n"
|
||||
" return true;\n"
|
||||
" }")
|
||||
conversionsToJS.extend(
|
||||
map(self.getConversionToJS,
|
||||
zip(templateVars, self.type.flatMemberTypes)))
|
||||
|
||||
toJSVal = string.Template("""
|
||||
|
||||
bool
|
||||
${structName}ReturnValue::ToJSVal(JSContext* cx, JS::Handle<JSObject*> scopeObj, JS::MutableHandle<JS::Value> rval) const
|
||||
{
|
||||
switch (mType) {
|
||||
${doConversionsToJS}
|
||||
|
||||
case eUninitialized:
|
||||
{
|
||||
break;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
""").substitute({
|
||||
"structName": str(self.type),
|
||||
"doConversionsToJS": "\n\n".join(conversionsToJS)
|
||||
})
|
||||
templateVars = self.templateVars
|
||||
|
||||
methods = []
|
||||
methodTemplate = """${structType}&
|
||||
%sReturnValue::SetAs${name}()
|
||||
{
|
||||
mType = e${name};
|
||||
return mValue.m${name}.SetValue();
|
||||
}""" % str(self.type)
|
||||
methods.extend(mapTemplate(methodTemplate, templateVars))
|
||||
|
||||
callDestructors = []
|
||||
if self.type.hasNullableType:
|
||||
callDestructors.append(" case eNull:\n"
|
||||
" break;")
|
||||
callDestructors.extend(mapTemplate(" case e${name}:\n"
|
||||
" mValue.m${name}.Destroy();\n"
|
||||
" mType = eUninitialized;\n"
|
||||
" break;", templateVars))
|
||||
destructor = string.Template("""
|
||||
${structName}ReturnValue::~${structName}ReturnValue()
|
||||
{
|
||||
switch (mType) {
|
||||
${callDestructors}
|
||||
case eUninitialized:
|
||||
break;
|
||||
}
|
||||
}
|
||||
|
||||
""").substitute(
|
||||
{
|
||||
"structName": self.type.__str__(),
|
||||
"callDestructors": "\n".join(callDestructors),
|
||||
})
|
||||
|
||||
return destructor + "\n\n".join(methods) + toJSVal
|
||||
|
||||
def getConversionToJS(self, arg):
|
||||
(templateVars, type) = arg
|
||||
assert not type.nullable() # flatMemberTypes never has nullable types
|
||||
val = "mValue.m%(name)s.Value()" % templateVars
|
||||
wrapCode = wrapForType(
|
||||
type, self.descriptorProvider,
|
||||
{
|
||||
"jsvalRef": "rval",
|
||||
"jsvalHandle": "rval",
|
||||
"obj": "scopeObj",
|
||||
"result": val,
|
||||
})
|
||||
return CGIndenter(CGList([CGGeneric("case e%(name)s:" % templateVars),
|
||||
CGWrapper(CGIndenter(CGGeneric(wrapCode)),
|
||||
@ -7544,15 +7747,19 @@ class CGDescriptor(CGThing):
|
||||
|
||||
cgThings = []
|
||||
# These are set to true if at least one non-static
|
||||
# method/getter/setter exist on the interface.
|
||||
(hasMethod, hasGetter, hasLenientGetter,
|
||||
hasSetter, hasLenientSetter) = False, False, False, False, False
|
||||
# method/getter/setter or jsonifier exist on the interface.
|
||||
(hasMethod, hasGetter, hasLenientGetter, hasSetter, hasJsonifier,
|
||||
hasLenientSetter) = False, False, False, False, False, False
|
||||
for n in descriptor.interface.namedConstructors:
|
||||
cgThings.append(CGClassConstructor(descriptor, n,
|
||||
NamedConstructorName(n)))
|
||||
for m in descriptor.interface.members:
|
||||
if (m.isMethod() and
|
||||
(not m.isIdentifierLess() or m == descriptor.operations['Stringifier'])):
|
||||
if (m.isMethod() and m == descriptor.operations['Jsonifier']):
|
||||
hasJsonifier = True
|
||||
hasMethod = True
|
||||
jsonifierMethod = m
|
||||
elif (m.isMethod() and
|
||||
(not m.isIdentifierLess() or m == descriptor.operations['Stringifier'])):
|
||||
if m.isStatic():
|
||||
assert descriptor.interface.hasInterfaceObject
|
||||
cgThings.append(CGStaticMethod(descriptor, m))
|
||||
@ -7586,6 +7793,9 @@ class CGDescriptor(CGThing):
|
||||
if (not m.isStatic() and
|
||||
descriptor.interface.hasInterfacePrototypeObject()):
|
||||
cgThings.append(CGMemberJITInfo(descriptor, m))
|
||||
if hasJsonifier:
|
||||
cgThings.append(CGJsonifierMethod(descriptor, jsonifierMethod))
|
||||
cgThings.append(CGMemberJITInfo(descriptor, jsonifierMethod))
|
||||
if hasMethod: cgThings.append(CGGenericMethod(descriptor))
|
||||
if hasGetter: cgThings.append(CGGenericGetter(descriptor))
|
||||
if hasLenientGetter: cgThings.append(CGGenericGetter(descriptor,
|
||||
@ -8989,6 +9199,9 @@ class CGBindingImplClass(CGClass):
|
||||
else:
|
||||
# We already added this method
|
||||
return
|
||||
if name == "Jsonifier":
|
||||
# We already added this method
|
||||
return
|
||||
self.methodDecls.append(
|
||||
CGNativeMember(descriptor, op,
|
||||
name,
|
||||
@ -9554,7 +9767,7 @@ class CGCallbackInterface(CGCallback):
|
||||
setters = [CallbackSetter(a, descriptor) for a in attrs
|
||||
if not a.readonly]
|
||||
methods = [m for m in iface.members
|
||||
if m.isMethod() and not m.isStatic()]
|
||||
if m.isMethod() and not m.isStatic() and not m.isIdentifierLess()]
|
||||
methods = [CallbackOperation(m, sig, descriptor) for m in methods
|
||||
for sig in m.signatures()]
|
||||
if iface.isJSImplemented() and iface.ctor():
|
||||
|
@ -277,7 +277,8 @@ class Descriptor(DescriptorProvider):
|
||||
'NamedCreator': None,
|
||||
'NamedDeleter': None,
|
||||
'Stringifier': None,
|
||||
'LegacyCaller': None
|
||||
'LegacyCaller': None,
|
||||
'Jsonifier': None
|
||||
}
|
||||
if self.concrete:
|
||||
self.proxy = False
|
||||
@ -290,6 +291,8 @@ class Descriptor(DescriptorProvider):
|
||||
for m in iface.members:
|
||||
if m.isMethod() and m.isStringifier():
|
||||
addOperation('Stringifier', m)
|
||||
if m.isMethod() and m.isJsonifier():
|
||||
addOperation('Jsonifier', m)
|
||||
# Don't worry about inheriting legacycallers either: in
|
||||
# practice these are on most-derived prototypes.
|
||||
if m.isMethod() and m.isLegacycaller():
|
||||
|
@ -718,12 +718,15 @@ class IDLInterface(IDLObjectWithScope):
|
||||
memberType = "deleters"
|
||||
elif member.isStringifier():
|
||||
memberType = "stringifiers"
|
||||
elif member.isJsonifier():
|
||||
memberType = "jsonifiers"
|
||||
elif member.isLegacycaller():
|
||||
memberType = "legacycallers"
|
||||
else:
|
||||
continue
|
||||
|
||||
if memberType != "stringifiers" and memberType != "legacycallers":
|
||||
if (memberType != "stringifiers" and memberType != "legacycallers" and
|
||||
memberType != "jsonifiers"):
|
||||
if member.isNamed():
|
||||
memberType = "named " + memberType
|
||||
else:
|
||||
@ -2501,7 +2504,7 @@ class IDLAttribute(IDLInterfaceMember):
|
||||
raise WebIDLError("An attribute cannot be of a sequence type",
|
||||
[self.location])
|
||||
if self.type.isUnion():
|
||||
for f in self.type.flatMemberTypes:
|
||||
for f in self.type.unroll().flatMemberTypes:
|
||||
if f.isDictionary():
|
||||
raise WebIDLError("An attribute cannot be of a union "
|
||||
"type if one of its member types (or "
|
||||
@ -2812,7 +2815,7 @@ class IDLMethod(IDLInterfaceMember, IDLScope):
|
||||
def __init__(self, location, identifier, returnType, arguments,
|
||||
static=False, getter=False, setter=False, creator=False,
|
||||
deleter=False, specialType=NamedOrIndexed.Neither,
|
||||
legacycaller=False, stringifier=False):
|
||||
legacycaller=False, stringifier=False, jsonifier=False):
|
||||
# REVIEW: specialType is NamedOrIndexed -- wow, this is messed up.
|
||||
IDLInterfaceMember.__init__(self, location, identifier,
|
||||
IDLInterfaceMember.Tags.Method)
|
||||
@ -2838,6 +2841,8 @@ class IDLMethod(IDLInterfaceMember, IDLScope):
|
||||
self._legacycaller = legacycaller
|
||||
assert isinstance(stringifier, bool)
|
||||
self._stringifier = stringifier
|
||||
assert isinstance(jsonifier, bool)
|
||||
self._jsonifier = jsonifier
|
||||
self._specialType = specialType
|
||||
|
||||
if static and identifier.name == "prototype":
|
||||
@ -2875,6 +2880,12 @@ class IDLMethod(IDLInterfaceMember, IDLScope):
|
||||
assert len(overload.arguments) == 0
|
||||
assert overload.returnType == BuiltinTypes[IDLBuiltinType.Types.domstring]
|
||||
|
||||
if self._jsonifier:
|
||||
assert len(self._overloads) == 1
|
||||
overload = self._overloads[0]
|
||||
assert len(overload.arguments) == 0
|
||||
assert overload.returnType == BuiltinTypes[IDLBuiltinType.Types.object]
|
||||
|
||||
def isStatic(self):
|
||||
return self._static
|
||||
|
||||
@ -2906,6 +2917,9 @@ class IDLMethod(IDLInterfaceMember, IDLScope):
|
||||
def isStringifier(self):
|
||||
return self._stringifier
|
||||
|
||||
def isJsonifier(self):
|
||||
return self._jsonifier
|
||||
|
||||
def hasOverloads(self):
|
||||
return self._hasOverloads
|
||||
|
||||
@ -2951,6 +2965,8 @@ class IDLMethod(IDLInterfaceMember, IDLScope):
|
||||
assert not method.isDeleter()
|
||||
assert not self.isStringifier()
|
||||
assert not method.isStringifier()
|
||||
assert not self.isJsonifier()
|
||||
assert not method.isJsonifier()
|
||||
|
||||
return self
|
||||
|
||||
@ -3284,6 +3300,7 @@ class Tokenizer(object):
|
||||
"false": "FALSE",
|
||||
"serializer": "SERIALIZER",
|
||||
"stringifier": "STRINGIFIER",
|
||||
"jsonifier": "JSONIFIER",
|
||||
"unrestricted": "UNRESTRICTED",
|
||||
"attribute": "ATTRIBUTE",
|
||||
"readonly": "READONLY",
|
||||
@ -3914,6 +3931,19 @@ class Parser(Tokenizer):
|
||||
stringifier=True)
|
||||
p[0] = method
|
||||
|
||||
def p_Jsonifier(self, p):
|
||||
"""
|
||||
Operation : JSONIFIER SEMICOLON
|
||||
"""
|
||||
identifier = IDLUnresolvedIdentifier(BuiltinLocation("<auto-generated-identifier>"),
|
||||
"__jsonifier", allowDoubleUnderscore=True)
|
||||
method = IDLMethod(self.getLocation(p, 1),
|
||||
identifier,
|
||||
returnType=BuiltinTypes[IDLBuiltinType.Types.object],
|
||||
arguments=[],
|
||||
jsonifier=True)
|
||||
p[0] = method
|
||||
|
||||
def p_QualifierStatic(self, p):
|
||||
"""
|
||||
Qualifier : STATIC
|
||||
@ -4066,6 +4096,7 @@ class Parser(Tokenizer):
|
||||
| SETTER
|
||||
| STATIC
|
||||
| STRINGIFIER
|
||||
| JSONIFIER
|
||||
| TYPEDEF
|
||||
| UNRESTRICTED
|
||||
"""
|
||||
@ -4195,6 +4226,7 @@ class Parser(Tokenizer):
|
||||
| SHORT
|
||||
| STATIC
|
||||
| STRINGIFIER
|
||||
| JSONIFIER
|
||||
| TRUE
|
||||
| TYPEDEF
|
||||
| UNSIGNED
|
||||
|
@ -507,6 +507,16 @@ public:
|
||||
//void PassUnionWithCallback(JSContext*, const TestCallbackOrLong&);
|
||||
void PassUnionWithObject(JSContext*, const ObjectOrLong&);
|
||||
|
||||
void ReceiveUnion(const CanvasPatternOrCanvasGradientReturnValue&);
|
||||
void ReceiveUnionContainingNull(const CanvasPatternOrNullOrCanvasGradientReturnValue&);
|
||||
void ReceiveNullableUnion(const Nullable<CanvasPatternOrCanvasGradientReturnValue>&);
|
||||
void GetWritableUnion(const CanvasPatternOrCanvasGradientReturnValue&);
|
||||
void SetWritableUnion(const CanvasPatternOrCanvasGradient&);
|
||||
void GetWritableUnionContainingNull(const CanvasPatternOrNullOrCanvasGradientReturnValue&);
|
||||
void SetWritableUnionContainingNull(const CanvasPatternOrNullOrCanvasGradient&);
|
||||
void GetWritableNullableUnion(const Nullable<CanvasPatternOrCanvasGradientReturnValue>&);
|
||||
void SetWritableNullableUnion(const Nullable<CanvasPatternOrCanvasGradient>&);
|
||||
|
||||
// Date types
|
||||
void PassDate(Date);
|
||||
void PassNullableDate(const Nullable<Date>&);
|
||||
|
@ -452,6 +452,14 @@ interface TestInterface {
|
||||
void passUnionWithObject((object or long) arg);
|
||||
//void passUnionWithDict((Dict or long) arg);
|
||||
|
||||
(CanvasPattern or CanvasGradient) receiveUnion();
|
||||
(CanvasPattern? or CanvasGradient) receiveUnionContainingNull();
|
||||
(CanvasPattern or CanvasGradient)? receiveNullableUnion();
|
||||
|
||||
attribute (CanvasPattern or CanvasGradient) writableUnion;
|
||||
attribute (CanvasPattern? or CanvasGradient) writableUnionContainingNull;
|
||||
attribute (CanvasPattern or CanvasGradient)? writableNullableUnion;
|
||||
|
||||
// Date types
|
||||
void passDate(Date arg);
|
||||
void passNullableDate(Date? arg);
|
||||
@ -575,6 +583,7 @@ interface TestInterface {
|
||||
optional TestInterface? arg2 = null,
|
||||
optional Dict arg3, optional double arg4 = 5.0,
|
||||
optional float arg5);
|
||||
jsonifier;
|
||||
|
||||
// If you add things here, add them to TestExampleGen and TestJSImplGen as well
|
||||
};
|
||||
|
@ -348,6 +348,14 @@ interface TestExampleInterface {
|
||||
void passUnionWithObject((object or long) arg);
|
||||
//void passUnionWithDict((Dict or long) arg);
|
||||
|
||||
//(CanvasPattern or CanvasGradient) receiveUnion();
|
||||
//(CanvasPattern? or CanvasGradient) receiveUnionContainingNull();
|
||||
//(CanvasPattern or CanvasGradient)? receiveNullableUnion();
|
||||
|
||||
//attribute (CanvasPattern or CanvasGradient) writableUnion;
|
||||
//attribute (CanvasPattern? or CanvasGradient) writableUnionContainingNull;
|
||||
//attribute (CanvasPattern or CanvasGradient)? writableNullableUnion;
|
||||
|
||||
// Date types
|
||||
void passDate(Date arg);
|
||||
void passNullableDate(Date? arg);
|
||||
@ -472,6 +480,7 @@ interface TestExampleInterface {
|
||||
optional TestInterface? arg2 = null,
|
||||
optional Dict arg3, optional double arg4 = 5.0,
|
||||
optional float arg5);
|
||||
jsonifier;
|
||||
|
||||
// If you add things here, add them to TestCodeGen and TestJSImplGen as well
|
||||
};
|
||||
|
@ -372,6 +372,14 @@ interface TestJSImplInterface {
|
||||
void passUnionWithObject((object or long) arg);
|
||||
//void passUnionWithDict((Dict or long) arg);
|
||||
|
||||
//(CanvasPattern or CanvasGradient) receiveUnion();
|
||||
//(CanvasPattern? or CanvasGradient) receiveUnionContainingNull();
|
||||
//(CanvasPattern or CanvasGradient)? receiveNullableUnion();
|
||||
|
||||
//attribute (CanvasPattern or CanvasGradient) writableUnion;
|
||||
//attribute (CanvasPattern? or CanvasGradient) writableUnionContainingNull;
|
||||
//attribute (CanvasPattern or CanvasGradient)? writableNullableUnion;
|
||||
|
||||
// Date types
|
||||
void passDate(Date arg);
|
||||
void passNullableDate(Date? arg);
|
||||
@ -464,6 +472,7 @@ interface TestJSImplInterface {
|
||||
optional TestInterface? arg2 = null,
|
||||
optional Dict arg3, optional double arg4 = 5.0,
|
||||
optional float arg5);
|
||||
jsonifier;
|
||||
|
||||
// If you add things here, add them to TestCodeGen as well
|
||||
};
|
||||
|
@ -61,7 +61,7 @@ SetJsObject(JSContext* aContext,
|
||||
|
||||
if (!JS_SetProperty(aContext, aObj,
|
||||
NS_ConvertUTF16toUTF8(arr[i].name()).get(),
|
||||
&val)) {
|
||||
val)) {
|
||||
NS_WARNING("Failed to set property");
|
||||
return false;
|
||||
}
|
||||
|
@ -161,27 +161,27 @@ CameraControlImpl::Get(JSContext* aCx, uint32_t aKey, JS::Value* aValue)
|
||||
|
||||
DOM_CAMERA_LOGI("top=%d\n", r->top);
|
||||
v = INT_TO_JSVAL(r->top);
|
||||
if (!JS_SetProperty(aCx, o, "top", &v)) {
|
||||
if (!JS_SetProperty(aCx, o, "top", v)) {
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
DOM_CAMERA_LOGI("left=%d\n", r->left);
|
||||
v = INT_TO_JSVAL(r->left);
|
||||
if (!JS_SetProperty(aCx, o, "left", &v)) {
|
||||
if (!JS_SetProperty(aCx, o, "left", v)) {
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
DOM_CAMERA_LOGI("bottom=%d\n", r->bottom);
|
||||
v = INT_TO_JSVAL(r->bottom);
|
||||
if (!JS_SetProperty(aCx, o, "bottom", &v)) {
|
||||
if (!JS_SetProperty(aCx, o, "bottom", v)) {
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
DOM_CAMERA_LOGI("right=%d\n", r->right);
|
||||
v = INT_TO_JSVAL(r->right);
|
||||
if (!JS_SetProperty(aCx, o, "right", &v)) {
|
||||
if (!JS_SetProperty(aCx, o, "right", v)) {
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
DOM_CAMERA_LOGI("weight=%d\n", r->weight);
|
||||
v = INT_TO_JSVAL(r->weight);
|
||||
if (!JS_SetProperty(aCx, o, "weight", &v)) {
|
||||
if (!JS_SetProperty(aCx, o, "weight", v)) {
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
|
@ -36,31 +36,31 @@ RecorderVideoProfile::GetJsObject(JSContext* aCx, JSObject** aObject)
|
||||
|
||||
JS::Rooted<JSString*> s(aCx, JS_NewStringCopyZ(aCx, codec));
|
||||
JS::Rooted<JS::Value> v(aCx, STRING_TO_JSVAL(s));
|
||||
if (!JS_SetProperty(aCx, o, "codec", &v)) {
|
||||
if (!JS_SetProperty(aCx, o, "codec", v)) {
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
if (mBitrate != -1) {
|
||||
v = INT_TO_JSVAL(mBitrate);
|
||||
if (!JS_SetProperty(aCx, o, "bitrate", &v)) {
|
||||
if (!JS_SetProperty(aCx, o, "bitrate", v)) {
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
}
|
||||
if (mFramerate != -1) {
|
||||
v = INT_TO_JSVAL(mFramerate);
|
||||
if (!JS_SetProperty(aCx, o, "framerate", &v)) {
|
||||
if (!JS_SetProperty(aCx, o, "framerate", v)) {
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
}
|
||||
if (mWidth != -1) {
|
||||
v = INT_TO_JSVAL(mWidth);
|
||||
if (!JS_SetProperty(aCx, o, "width", &v)) {
|
||||
if (!JS_SetProperty(aCx, o, "width", v)) {
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
}
|
||||
if (mHeight != -1) {
|
||||
v = INT_TO_JSVAL(mHeight);
|
||||
if (!JS_SetProperty(aCx, o, "height", &v)) {
|
||||
if (!JS_SetProperty(aCx, o, "height", v)) {
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
}
|
||||
@ -97,25 +97,25 @@ RecorderAudioProfile::GetJsObject(JSContext* aCx, JSObject** aObject)
|
||||
|
||||
JS::Rooted<JSString*> s(aCx, JS_NewStringCopyZ(aCx, codec));
|
||||
JS::Rooted<JS::Value> v(aCx, STRING_TO_JSVAL(s));
|
||||
if (!JS_SetProperty(aCx, o, "codec", &v)) {
|
||||
if (!JS_SetProperty(aCx, o, "codec", v)) {
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
if (mBitrate != -1) {
|
||||
v = INT_TO_JSVAL(mBitrate);
|
||||
if (!JS_SetProperty(aCx, o, "bitrate", &v)) {
|
||||
if (!JS_SetProperty(aCx, o, "bitrate", v)) {
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
}
|
||||
if (mSamplerate != -1) {
|
||||
v = INT_TO_JSVAL(mSamplerate);
|
||||
if (!JS_SetProperty(aCx, o, "samplerate", &v)) {
|
||||
if (!JS_SetProperty(aCx, o, "samplerate", v)) {
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
}
|
||||
if (mChannels != -1) {
|
||||
v = INT_TO_JSVAL(mChannels);
|
||||
if (!JS_SetProperty(aCx, o, "channels", &v)) {
|
||||
if (!JS_SetProperty(aCx, o, "channels", v)) {
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
}
|
||||
@ -185,7 +185,7 @@ RecorderProfileManager::GetJsObject(JSContext* aCx, JSObject** aObject) const
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
JS::Rooted<JS::Value> v(aCx, OBJECT_TO_JSVAL(p));
|
||||
|
||||
if (!JS_SetProperty(aCx, o, profileName, &v)) {
|
||||
if (!JS_SetProperty(aCx, o, profileName, v)) {
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
}
|
||||
|
@ -180,7 +180,7 @@ public:
|
||||
|
||||
JS::Rooted<JSString*> s(aCx, JS_NewStringCopyZ(aCx, format));
|
||||
JS::Rooted<JS::Value> v(aCx, STRING_TO_JSVAL(s));
|
||||
if (!JS_SetProperty(aCx, o, "format", &v)) {
|
||||
if (!JS_SetProperty(aCx, o, "format", v)) {
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
@ -188,7 +188,7 @@ public:
|
||||
nsresult rv = mVideo.GetJsObject(aCx, video.address());
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
v = OBJECT_TO_JSVAL(video);
|
||||
if (!JS_SetProperty(aCx, o, "video", &v)) {
|
||||
if (!JS_SetProperty(aCx, o, "video", v)) {
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
@ -196,7 +196,7 @@ public:
|
||||
rv = mAudio.GetJsObject(aCx, audio.address());
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
v = OBJECT_TO_JSVAL(audio);
|
||||
if (!JS_SetProperty(aCx, o, "audio", &v)) {
|
||||
if (!JS_SetProperty(aCx, o, "audio", v)) {
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
|
@ -95,10 +95,10 @@ ParseDimensionItemAndAdd(JSContext* aCx, JS::Handle<JSObject*> aArray,
|
||||
return NS_ERROR_OUT_OF_MEMORY;
|
||||
}
|
||||
|
||||
if (!JS_SetProperty(aCx, o, "width", &w)) {
|
||||
if (!JS_SetProperty(aCx, o, "width", w)) {
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
if (!JS_SetProperty(aCx, o, "height", &h)) {
|
||||
if (!JS_SetProperty(aCx, o, "height", h)) {
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
@ -371,11 +371,11 @@ DOMCameraCapabilities::GetVideoSizes(JSContext* cx, JS::Value* aVideoSizes)
|
||||
for (uint32_t i = 0; i < sizes.Length(); ++i) {
|
||||
JS::Rooted<JSObject*> o(cx, JS_NewObject(cx, nullptr, nullptr, nullptr));
|
||||
JS::Rooted<JS::Value> v(cx, INT_TO_JSVAL(sizes[i].width));
|
||||
if (!JS_SetProperty(cx, o, "width", &v)) {
|
||||
if (!JS_SetProperty(cx, o, "width", v)) {
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
v = INT_TO_JSVAL(sizes[i].height);
|
||||
if (!JS_SetProperty(cx, o, "height", &v)) {
|
||||
if (!JS_SetProperty(cx, o, "height", v)) {
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
|
@ -106,7 +106,7 @@ ContactDB.prototype = {
|
||||
_dispatcher: {},
|
||||
|
||||
upgradeSchema: function upgradeSchema(aTransaction, aDb, aOldVersion, aNewVersion) {
|
||||
function loadInitialContacts() {
|
||||
let loadInitialContacts = function() {
|
||||
// Add default contacts
|
||||
let jsm = {};
|
||||
Cu.import("resource://gre/modules/FileUtils.jsm", jsm);
|
||||
@ -155,7 +155,7 @@ ContactDB.prototype = {
|
||||
if (DEBUG) debug("import: " + JSON.stringify(contact));
|
||||
objectStore.put(contact);
|
||||
}
|
||||
}
|
||||
}.bind(this);
|
||||
|
||||
if (DEBUG) debug("upgrade schema from: " + aOldVersion + " to " + aNewVersion + " called!");
|
||||
let db = aDb;
|
||||
|
@ -9,3 +9,5 @@ ReportOnlyCSPIgnored=Report-only CSP policy will be ignored because there are ot
|
||||
OldCSPHeaderDeprecated=The X-Content-Security-Policy and X-Content-Security-Report-Only headers will be deprecated in the future. Please use the Content-Security-Policy and Content-Security-Report-Only headers with CSP spec compliant syntax instead.
|
||||
# LOCALIZATION NOTE: Do not translate "X-Content-Security-Policy/Report-Only" or "Content-Security-Policy/Report-Only"
|
||||
BothCSPHeadersPresent=This site specified both an X-Content-Security-Policy/Report-Only header and a Content-Security-Policy/Report-Only header. The X-Content-Security-Policy/Report-Only header(s) will be ignored.
|
||||
# LOCALIZATION NOTE: Do not translate "Strict-Transport-Security" or "HSTS"
|
||||
InvalidSTSHeaders=The site specified an invalid Strict-Transport-Security header.
|
||||
|
@ -12,7 +12,6 @@ XPIDL_SOURCES += [
|
||||
'nsIDOMMozSmsEvent.idl',
|
||||
'nsIDOMMozSmsMessage.idl',
|
||||
'nsIDOMSmsFilter.idl',
|
||||
'nsIDOMSmsManager.idl',
|
||||
'nsIDOMSmsSegmentInfo.idl',
|
||||
'nsIMmsService.idl',
|
||||
'nsIMobileMessageCallback.idl',
|
||||
|
@ -1,44 +0,0 @@
|
||||
/* 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 file,
|
||||
* You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
#include "nsIDOMEventTarget.idl"
|
||||
|
||||
interface nsIDOMDOMCursor;
|
||||
interface nsIDOMDOMRequest;
|
||||
interface nsIDOMEventListener;
|
||||
interface nsIDOMMozSmsFilter;
|
||||
interface nsIDOMMozSmsSegmentInfo;
|
||||
|
||||
[scriptable, builtinclass, uuid(8ce00d77-71b4-43f6-92a1-2eae7c9581b9)]
|
||||
interface nsIDOMMozSmsManager : nsIDOMEventTarget
|
||||
{
|
||||
nsIDOMMozSmsSegmentInfo getSegmentInfoForText(in DOMString text);
|
||||
|
||||
// The first parameter can be either a DOMString (only one number) or an array
|
||||
// of DOMStrings.
|
||||
// The method returns a DOMRequest object if one number has been passed.
|
||||
// An array of DOMRequest objects otherwise.
|
||||
jsval send(in jsval number, in DOMString message);
|
||||
|
||||
[binaryname(GetMessageMoz)]
|
||||
nsIDOMDOMRequest getMessage(in long id);
|
||||
|
||||
// The parameter can be either a message id or a SmsMessage.
|
||||
nsIDOMDOMRequest delete(in jsval param);
|
||||
|
||||
// Iterates through nsIDOMMozSmsMessage.
|
||||
nsIDOMDOMCursor getMessages(in nsIDOMMozSmsFilter filter, in boolean reverse);
|
||||
|
||||
nsIDOMDOMRequest markMessageRead(in long id, in boolean aValue);
|
||||
|
||||
// Iterates through nsIDOMMozMobileMessageThread.
|
||||
nsIDOMDOMCursor getThreads();
|
||||
|
||||
[implicit_jscontext] attribute jsval onreceived;
|
||||
[implicit_jscontext] attribute jsval onsending;
|
||||
[implicit_jscontext] attribute jsval onsent;
|
||||
[implicit_jscontext] attribute jsval onfailed;
|
||||
[implicit_jscontext] attribute jsval ondeliverysuccess;
|
||||
[implicit_jscontext] attribute jsval ondeliveryerror;
|
||||
};
|
@ -18,14 +18,12 @@ namespace dom {
|
||||
|
||||
class DOMCursor;
|
||||
class MobileMessageManager;
|
||||
class SmsManager;
|
||||
|
||||
namespace mobilemessage {
|
||||
|
||||
class MobileMessageCursorCallback : public nsIMobileMessageCursorCallback
|
||||
{
|
||||
friend class mozilla::dom::MobileMessageManager;
|
||||
friend class mozilla::dom::SmsManager;
|
||||
|
||||
public:
|
||||
NS_DECL_CYCLE_COLLECTING_ISUPPORTS
|
||||
|
@ -1,502 +0,0 @@
|
||||
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||
/* 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 file,
|
||||
* You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
#include "SmsFilter.h"
|
||||
#include "SmsManager.h"
|
||||
#include "nsIDOMClassInfo.h"
|
||||
#include "nsISmsService.h"
|
||||
#include "nsIObserverService.h"
|
||||
#include "mozilla/Preferences.h"
|
||||
#include "mozilla/Services.h"
|
||||
#include "Constants.h"
|
||||
#include "nsIDOMMozSmsEvent.h"
|
||||
#include "nsIDOMMozSmsMessage.h"
|
||||
#include "nsJSUtils.h"
|
||||
#include "nsContentUtils.h"
|
||||
#include "nsCxPusher.h"
|
||||
#include "nsIMobileMessageDatabaseService.h"
|
||||
#include "nsIXPConnect.h"
|
||||
#include "nsIPermissionManager.h"
|
||||
#include "GeneratedEvents.h"
|
||||
#include "MobileMessageCallback.h"
|
||||
#include "MobileMessageCursorCallback.h"
|
||||
#include "DOMCursor.h"
|
||||
|
||||
#define RECEIVED_EVENT_NAME NS_LITERAL_STRING("received")
|
||||
#define SENDING_EVENT_NAME NS_LITERAL_STRING("sending")
|
||||
#define SENT_EVENT_NAME NS_LITERAL_STRING("sent")
|
||||
#define FAILED_EVENT_NAME NS_LITERAL_STRING("failed")
|
||||
#define DELIVERY_SUCCESS_EVENT_NAME NS_LITERAL_STRING("deliverysuccess")
|
||||
#define DELIVERY_ERROR_EVENT_NAME NS_LITERAL_STRING("deliveryerror")
|
||||
|
||||
using namespace mozilla::dom::mobilemessage;
|
||||
|
||||
DOMCI_DATA(MozSmsManager, mozilla::dom::SmsManager)
|
||||
|
||||
namespace mozilla {
|
||||
namespace dom {
|
||||
|
||||
NS_INTERFACE_MAP_BEGIN(SmsManager)
|
||||
NS_INTERFACE_MAP_ENTRY(nsIDOMMozSmsManager)
|
||||
NS_INTERFACE_MAP_ENTRY(nsIObserver)
|
||||
NS_DOM_INTERFACE_MAP_ENTRY_CLASSINFO(MozSmsManager)
|
||||
NS_INTERFACE_MAP_END_INHERITING(nsDOMEventTargetHelper)
|
||||
|
||||
NS_IMPL_ADDREF_INHERITED(SmsManager, nsDOMEventTargetHelper)
|
||||
NS_IMPL_RELEASE_INHERITED(SmsManager, nsDOMEventTargetHelper)
|
||||
|
||||
NS_IMPL_EVENT_HANDLER(SmsManager, received)
|
||||
NS_IMPL_EVENT_HANDLER(SmsManager, sending)
|
||||
NS_IMPL_EVENT_HANDLER(SmsManager, sent)
|
||||
NS_IMPL_EVENT_HANDLER(SmsManager, failed)
|
||||
NS_IMPL_EVENT_HANDLER(SmsManager, deliverysuccess)
|
||||
NS_IMPL_EVENT_HANDLER(SmsManager, deliveryerror)
|
||||
|
||||
/* static */
|
||||
bool
|
||||
SmsManager::CreationIsAllowed(nsPIDOMWindow* aWindow)
|
||||
{
|
||||
NS_ASSERTION(aWindow, "Null pointer!");
|
||||
|
||||
#ifndef MOZ_WEBSMS_BACKEND
|
||||
return false;
|
||||
#endif
|
||||
|
||||
// First of all, the general pref has to be turned on.
|
||||
bool enabled = false;
|
||||
Preferences::GetBool("dom.sms.enabled", &enabled);
|
||||
NS_ENSURE_TRUE(enabled, false);
|
||||
|
||||
nsCOMPtr<nsIPermissionManager> permMgr =
|
||||
do_GetService(NS_PERMISSIONMANAGER_CONTRACTID);
|
||||
NS_ENSURE_TRUE(permMgr, false);
|
||||
|
||||
uint32_t permission = nsIPermissionManager::DENY_ACTION;
|
||||
permMgr->TestPermissionFromWindow(aWindow, "sms", &permission);
|
||||
|
||||
if (permission != nsIPermissionManager::ALLOW_ACTION) {
|
||||
return false;
|
||||
}
|
||||
|
||||
// Check the Sms Service:
|
||||
nsCOMPtr<nsISmsService> smsService = do_GetService(SMS_SERVICE_CONTRACTID);
|
||||
NS_ENSURE_TRUE(smsService, false);
|
||||
|
||||
bool result = false;
|
||||
smsService->HasSupport(&result);
|
||||
if (!result) {
|
||||
return false;
|
||||
}
|
||||
|
||||
return true;
|
||||
}
|
||||
|
||||
// static
|
||||
already_AddRefed<SmsManager>
|
||||
SmsManager::CreateInstance(nsPIDOMWindow* aWindow)
|
||||
{
|
||||
nsRefPtr<SmsManager> smsMgr = new SmsManager();
|
||||
smsMgr->Init(aWindow);
|
||||
|
||||
return smsMgr.forget();
|
||||
}
|
||||
|
||||
void
|
||||
SmsManager::Init(nsPIDOMWindow *aWindow)
|
||||
{
|
||||
BindToOwner(aWindow);
|
||||
|
||||
nsCOMPtr<nsIObserverService> obs = services::GetObserverService();
|
||||
// GetObserverService() can return null is some situations like shutdown.
|
||||
if (!obs) {
|
||||
return;
|
||||
}
|
||||
|
||||
obs->AddObserver(this, kSmsReceivedObserverTopic, false);
|
||||
obs->AddObserver(this, kSmsSendingObserverTopic, false);
|
||||
obs->AddObserver(this, kSmsSentObserverTopic, false);
|
||||
obs->AddObserver(this, kSmsFailedObserverTopic, false);
|
||||
obs->AddObserver(this, kSmsDeliverySuccessObserverTopic, false);
|
||||
obs->AddObserver(this, kSmsDeliveryErrorObserverTopic, false);
|
||||
}
|
||||
|
||||
void
|
||||
SmsManager::Shutdown()
|
||||
{
|
||||
nsCOMPtr<nsIObserverService> obs = services::GetObserverService();
|
||||
// GetObserverService() can return null is some situations like shutdown.
|
||||
if (!obs) {
|
||||
return;
|
||||
}
|
||||
|
||||
obs->RemoveObserver(this, kSmsReceivedObserverTopic);
|
||||
obs->RemoveObserver(this, kSmsSendingObserverTopic);
|
||||
obs->RemoveObserver(this, kSmsSentObserverTopic);
|
||||
obs->RemoveObserver(this, kSmsFailedObserverTopic);
|
||||
obs->RemoveObserver(this, kSmsDeliverySuccessObserverTopic);
|
||||
obs->RemoveObserver(this, kSmsDeliveryErrorObserverTopic);
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
SmsManager::GetSegmentInfoForText(const nsAString& aText,
|
||||
nsIDOMMozSmsSegmentInfo** aResult)
|
||||
{
|
||||
nsCOMPtr<nsISmsService> smsService = do_GetService(SMS_SERVICE_CONTRACTID);
|
||||
NS_ENSURE_TRUE(smsService, NS_ERROR_FAILURE);
|
||||
|
||||
return smsService->GetSegmentInfoForText(aText, aResult);
|
||||
}
|
||||
|
||||
nsresult
|
||||
SmsManager::Send(JSContext* aCx, JS::Handle<JSObject*> aGlobal, JS::Handle<JSString*> aNumber,
|
||||
const nsAString& aMessage, JS::Value* aRequest)
|
||||
{
|
||||
nsCOMPtr<nsISmsService> smsService = do_GetService(SMS_SERVICE_CONTRACTID);
|
||||
NS_ENSURE_TRUE(smsService, NS_ERROR_FAILURE);
|
||||
|
||||
nsDependentJSString number;
|
||||
number.init(aCx, aNumber);
|
||||
|
||||
nsRefPtr<DOMRequest> request = new DOMRequest(GetOwner());
|
||||
nsCOMPtr<nsIMobileMessageCallback> msgCallback =
|
||||
new MobileMessageCallback(request);
|
||||
|
||||
nsresult rv = smsService->Send(number, aMessage, msgCallback);
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
|
||||
JS::Rooted<JSObject*> global(aCx, aGlobal);
|
||||
rv = nsContentUtils::WrapNative(aCx, global,
|
||||
static_cast<nsIDOMDOMRequest*>(request.get()),
|
||||
aRequest);
|
||||
if (NS_FAILED(rv)) {
|
||||
NS_ERROR("Failed to create the js value!");
|
||||
return rv;
|
||||
}
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
SmsManager::Send(const JS::Value& aNumber, const nsAString& aMessage, JS::Value* aReturn)
|
||||
{
|
||||
nsresult rv;
|
||||
nsIScriptContext* sc = GetContextForEventHandlers(&rv);
|
||||
NS_ENSURE_STATE(sc);
|
||||
AutoPushJSContext cx(sc->GetNativeContext());
|
||||
NS_ASSERTION(cx, "Failed to get a context!");
|
||||
|
||||
if (!aNumber.isString() &&
|
||||
!(aNumber.isObject() && JS_IsArrayObject(cx, &aNumber.toObject()))) {
|
||||
return NS_ERROR_INVALID_ARG;
|
||||
}
|
||||
|
||||
JS::Rooted<JSObject*> global(cx, sc->GetNativeGlobal());
|
||||
NS_ASSERTION(global, "Failed to get global object!");
|
||||
|
||||
JSAutoCompartment ac(cx, global);
|
||||
|
||||
if (aNumber.isString()) {
|
||||
JS::Rooted<JSString*> number(cx, aNumber.toString());
|
||||
return Send(cx, global, number, aMessage, aReturn);
|
||||
}
|
||||
|
||||
// Must be an object then.
|
||||
if (!aNumber.isObject()) {
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
JS::Rooted<JSObject*> numbers(cx, &aNumber.toObject());
|
||||
uint32_t size;
|
||||
if (!JS_GetArrayLength(cx, numbers, &size)) {
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
JS::AutoValueVector requests(cx);
|
||||
if (!requests.resize(size)) {
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
JS::RootedString str(cx);
|
||||
for (uint32_t i = 0; i < size; ++i) {
|
||||
JS::Rooted<JS::Value> number(cx);
|
||||
if (!JS_GetElement(cx, numbers, i, number.address())) {
|
||||
return NS_ERROR_INVALID_ARG;
|
||||
}
|
||||
|
||||
str = JS_ValueToString(cx, number);
|
||||
if (!str) {
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
nsresult rv = Send(cx, global, str, aMessage, &requests[i]);
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
}
|
||||
|
||||
JSObject* obj = JS_NewArrayObject(cx, requests.length(), requests.begin());
|
||||
if (!obj) {
|
||||
return NS_ERROR_FAILURE;
|
||||
}
|
||||
|
||||
aReturn->setObject(*obj);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
SmsManager::GetMessageMoz(int32_t aId, nsIDOMDOMRequest** aRequest)
|
||||
{
|
||||
nsCOMPtr<nsIMobileMessageDatabaseService> dbService =
|
||||
do_GetService(MOBILE_MESSAGE_DATABASE_SERVICE_CONTRACTID);
|
||||
NS_ENSURE_TRUE(dbService, NS_ERROR_FAILURE);
|
||||
|
||||
nsRefPtr<DOMRequest> request = new DOMRequest(GetOwner());
|
||||
nsCOMPtr<nsIMobileMessageCallback> msgCallback =
|
||||
new MobileMessageCallback(request);
|
||||
|
||||
nsresult rv = dbService->GetMessageMoz(aId, msgCallback);
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
|
||||
request.forget(aRequest);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
nsresult
|
||||
SmsManager::GetSmsMessageId(AutoPushJSContext &aCx,
|
||||
const JS::Value &aSmsMessage, int32_t &aId)
|
||||
{
|
||||
nsCOMPtr<nsIDOMMozSmsMessage> message =
|
||||
do_QueryInterface(nsContentUtils::XPConnect()->GetNativeOfWrapper(aCx, &aSmsMessage.toObject()));
|
||||
NS_ENSURE_TRUE(message, NS_ERROR_INVALID_ARG);
|
||||
|
||||
return message->GetId(&aId);
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
SmsManager::Delete(const JS::Value& aParam, nsIDOMDOMRequest** aRequest)
|
||||
{
|
||||
// We expect Int32, SmsMessage, Int32[], SmsMessage[]
|
||||
if (!aParam.isObject() && !aParam.isInt32()) {
|
||||
return NS_ERROR_INVALID_ARG;
|
||||
}
|
||||
|
||||
nsresult rv;
|
||||
nsIScriptContext* sc = GetContextForEventHandlers(&rv);
|
||||
AutoPushJSContext cx(sc->GetNativeContext());
|
||||
NS_ENSURE_STATE(sc);
|
||||
|
||||
int32_t id, *idArray;
|
||||
uint32_t size;
|
||||
|
||||
if (aParam.isInt32()) {
|
||||
// Single Integer Message ID
|
||||
id = aParam.toInt32();
|
||||
|
||||
size = 1;
|
||||
idArray = &id;
|
||||
} else if (!JS_IsArrayObject(cx, &aParam.toObject())) {
|
||||
// Single SmsMessage object
|
||||
rv = GetSmsMessageId(cx, aParam, id);
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
|
||||
size = 1;
|
||||
idArray = &id;
|
||||
} else {
|
||||
// Int32[] or SmsMessage[]
|
||||
JS::Rooted<JSObject*> ids(cx, &aParam.toObject());
|
||||
|
||||
JS_ALWAYS_TRUE(JS_GetArrayLength(cx, ids, &size));
|
||||
nsAutoArrayPtr<int32_t> idAutoArray(new int32_t[size]);
|
||||
|
||||
JS::Rooted<JS::Value> idJsValue(cx);
|
||||
for (uint32_t i = 0; i < size; i++) {
|
||||
if (!JS_GetElement(cx, ids, i, idJsValue.address())) {
|
||||
return NS_ERROR_INVALID_ARG;
|
||||
}
|
||||
|
||||
if (idJsValue.get().isInt32()) {
|
||||
idAutoArray[i] = idJsValue.get().toInt32();
|
||||
} else if (idJsValue.get().isObject()) {
|
||||
rv = GetSmsMessageId(cx, idJsValue, id);
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
|
||||
idAutoArray[i] = id;
|
||||
}
|
||||
}
|
||||
|
||||
idArray = idAutoArray.forget();
|
||||
}
|
||||
|
||||
nsCOMPtr<nsIMobileMessageDatabaseService> dbService =
|
||||
do_GetService(MOBILE_MESSAGE_DATABASE_SERVICE_CONTRACTID);
|
||||
NS_ENSURE_TRUE(dbService, NS_ERROR_FAILURE);
|
||||
|
||||
nsRefPtr<DOMRequest> request = new DOMRequest(GetOwner());
|
||||
nsCOMPtr<nsIMobileMessageCallback> msgCallback =
|
||||
new MobileMessageCallback(request);
|
||||
|
||||
rv = dbService->DeleteMessage(idArray, size, msgCallback);
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
|
||||
request.forget(aRequest);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
SmsManager::GetMessages(nsIDOMMozSmsFilter* aFilter,
|
||||
bool aReverse,
|
||||
nsIDOMDOMCursor** aCursor)
|
||||
{
|
||||
nsCOMPtr<nsIMobileMessageDatabaseService> dbService =
|
||||
do_GetService(MOBILE_MESSAGE_DATABASE_SERVICE_CONTRACTID);
|
||||
NS_ENSURE_TRUE(dbService, NS_ERROR_FAILURE);
|
||||
|
||||
nsCOMPtr<nsIDOMMozSmsFilter> filter = aFilter;
|
||||
if (!filter) {
|
||||
filter = new SmsFilter();
|
||||
}
|
||||
|
||||
nsRefPtr<MobileMessageCursorCallback> cursorCallback =
|
||||
new MobileMessageCursorCallback();
|
||||
|
||||
nsCOMPtr<nsICursorContinueCallback> continueCallback;
|
||||
nsresult rv = dbService->CreateMessageCursor(filter, aReverse, cursorCallback,
|
||||
getter_AddRefs(continueCallback));
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
|
||||
cursorCallback->mDOMCursor = new DOMCursor(GetOwner(), continueCallback);
|
||||
NS_ADDREF(*aCursor = cursorCallback->mDOMCursor);
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
SmsManager::MarkMessageRead(int32_t aId, bool aValue,
|
||||
nsIDOMDOMRequest** aRequest)
|
||||
{
|
||||
nsCOMPtr<nsIMobileMessageDatabaseService> dbService =
|
||||
do_GetService(MOBILE_MESSAGE_DATABASE_SERVICE_CONTRACTID);
|
||||
NS_ENSURE_TRUE(dbService, NS_ERROR_FAILURE);
|
||||
|
||||
nsRefPtr<DOMRequest> request = new DOMRequest(GetOwner());
|
||||
nsCOMPtr<nsIMobileMessageCallback> msgCallback =
|
||||
new MobileMessageCallback(request);
|
||||
|
||||
nsresult rv = dbService->MarkMessageRead(aId, aValue, msgCallback);
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
|
||||
request.forget(aRequest);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
SmsManager::GetThreads(nsIDOMDOMCursor** aCursor)
|
||||
{
|
||||
nsCOMPtr<nsIMobileMessageDatabaseService> dbService =
|
||||
do_GetService(MOBILE_MESSAGE_DATABASE_SERVICE_CONTRACTID);
|
||||
NS_ENSURE_TRUE(dbService, NS_ERROR_FAILURE);
|
||||
|
||||
nsRefPtr<MobileMessageCursorCallback> cursorCallback =
|
||||
new MobileMessageCursorCallback();
|
||||
|
||||
nsCOMPtr<nsICursorContinueCallback> continueCallback;
|
||||
nsresult rv = dbService->CreateThreadCursor(cursorCallback,
|
||||
getter_AddRefs(continueCallback));
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
|
||||
cursorCallback->mDOMCursor = new DOMCursor(GetOwner(), continueCallback);
|
||||
NS_ADDREF(*aCursor = cursorCallback->mDOMCursor);
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
nsresult
|
||||
SmsManager::DispatchTrustedSmsEventToSelf(const nsAString& aEventName, nsIDOMMozSmsMessage* aMessage)
|
||||
{
|
||||
nsCOMPtr<nsIDOMEvent> event;
|
||||
NS_NewDOMMozSmsEvent(getter_AddRefs(event), this, nullptr, nullptr);
|
||||
NS_ASSERTION(event, "This should never fail!");
|
||||
|
||||
nsCOMPtr<nsIDOMMozSmsEvent> se = do_QueryInterface(event);
|
||||
MOZ_ASSERT(se);
|
||||
nsresult rv = se->InitMozSmsEvent(aEventName, false, false, aMessage);
|
||||
NS_ENSURE_SUCCESS(rv, rv);
|
||||
|
||||
return DispatchTrustedEvent(event);
|
||||
}
|
||||
|
||||
NS_IMETHODIMP
|
||||
SmsManager::Observe(nsISupports* aSubject, const char* aTopic,
|
||||
const PRUnichar* aData)
|
||||
{
|
||||
if (!strcmp(aTopic, kSmsReceivedObserverTopic)) {
|
||||
nsCOMPtr<nsIDOMMozSmsMessage> message = do_QueryInterface(aSubject);
|
||||
if (!message) {
|
||||
NS_ERROR("Got a 'sms-received' topic without a valid message!");
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
DispatchTrustedSmsEventToSelf(RECEIVED_EVENT_NAME, message);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
if (!strcmp(aTopic, kSmsSendingObserverTopic)) {
|
||||
nsCOMPtr<nsIDOMMozSmsMessage> message = do_QueryInterface(aSubject);
|
||||
if (!message) {
|
||||
NS_ERROR("Got a 'sms-sending' topic without a valid message!");
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
DispatchTrustedSmsEventToSelf(SENDING_EVENT_NAME, message);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
if (!strcmp(aTopic, kSmsSentObserverTopic)) {
|
||||
nsCOMPtr<nsIDOMMozSmsMessage> message = do_QueryInterface(aSubject);
|
||||
if (!message) {
|
||||
NS_ERROR("Got a 'sms-sent' topic without a valid message!");
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
DispatchTrustedSmsEventToSelf(SENT_EVENT_NAME, message);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
if (!strcmp(aTopic, kSmsFailedObserverTopic)) {
|
||||
nsCOMPtr<nsIDOMMozSmsMessage> message = do_QueryInterface(aSubject);
|
||||
if (!message) {
|
||||
NS_ERROR("Got a 'sms-failed' topic without a valid message!");
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
DispatchTrustedSmsEventToSelf(FAILED_EVENT_NAME, message);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
if (!strcmp(aTopic, kSmsDeliverySuccessObserverTopic)) {
|
||||
nsCOMPtr<nsIDOMMozSmsMessage> message = do_QueryInterface(aSubject);
|
||||
if (!message) {
|
||||
NS_ERROR("Got a 'sms-delivery-success' topic without a valid message!");
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
DispatchTrustedSmsEventToSelf(DELIVERY_SUCCESS_EVENT_NAME, message);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
if (!strcmp(aTopic, kSmsDeliveryErrorObserverTopic)) {
|
||||
nsCOMPtr<nsIDOMMozSmsMessage> message = do_QueryInterface(aSubject);
|
||||
if (!message) {
|
||||
NS_ERROR("Got a 'sms-delivery-error' topic without a valid message!");
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
DispatchTrustedSmsEventToSelf(DELIVERY_ERROR_EVENT_NAME, message);
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
return NS_OK;
|
||||
}
|
||||
|
||||
} // namespace dom
|
||||
} // namespace mozilla
|
@ -1,58 +0,0 @@
|
||||
/* -*- Mode: C++; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
|
||||
/* 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
|
||||
* file, You can obtain one at http://mozilla.org/MPL/2.0/. */
|
||||
|
||||
#ifndef mozilla_dom_mobilemessage_SmsManager_h
|
||||
#define mozilla_dom_mobilemessage_SmsManager_h
|
||||
|
||||
#include "nsIDOMSmsManager.h"
|
||||
#include "nsIObserver.h"
|
||||
#include "nsDOMEventTargetHelper.h"
|
||||
|
||||
class nsIDOMMozSmsMessage;
|
||||
|
||||
namespace mozilla {
|
||||
namespace dom {
|
||||
|
||||
class SmsManager : public nsDOMEventTargetHelper
|
||||
, public nsIDOMMozSmsManager
|
||||
, public nsIObserver
|
||||
{
|
||||
public:
|
||||
NS_DECL_ISUPPORTS_INHERITED
|
||||
NS_DECL_NSIOBSERVER
|
||||
NS_DECL_NSIDOMMOZSMSMANAGER
|
||||
|
||||
NS_REALLY_FORWARD_NSIDOMEVENTTARGET(nsDOMEventTargetHelper)
|
||||
|
||||
static already_AddRefed<SmsManager>
|
||||
CreateInstance(nsPIDOMWindow *aWindow);
|
||||
|
||||
static bool
|
||||
CreationIsAllowed(nsPIDOMWindow *aWindow);
|
||||
|
||||
void Init(nsPIDOMWindow *aWindow);
|
||||
void Shutdown();
|
||||
|
||||
private:
|
||||
/**
|
||||
* Internal Send() method used to send one message.
|
||||
*/
|
||||
nsresult Send(JSContext* aCx, JS::Handle<JSObject*> aGlobal, JS::Handle<JSString*> aNumber,
|
||||
const nsAString& aMessage, JS::Value* aRequest);
|
||||
|
||||
nsresult DispatchTrustedSmsEventToSelf(const nsAString& aEventName,
|
||||
nsIDOMMozSmsMessage* aMessage);
|
||||
|
||||
/**
|
||||
* Helper to get message ID from SMS Message object
|
||||
*/
|
||||
nsresult GetSmsMessageId(AutoPushJSContext &aCx, const JS::Value &aSmsMessage,
|
||||
int32_t &aId);
|
||||
};
|
||||
|
||||
} // namespace dom
|
||||
} // namespace mozilla
|
||||
|
||||
#endif // mozilla_dom_mobilemessage_SmsManager_h
|
@ -42,7 +42,6 @@ EXPORTS.mozilla.dom += [
|
||||
'MmsMessage.h',
|
||||
'MobileMessageManager.h',
|
||||
'SmsFilter.h',
|
||||
'SmsManager.h',
|
||||
'SmsMessage.h',
|
||||
'SmsSegmentInfo.h',
|
||||
]
|
||||
@ -58,7 +57,6 @@ CPP_SOURCES += [
|
||||
'SmsChild.cpp',
|
||||
'SmsFilter.cpp',
|
||||
'SmsIPCService.cpp',
|
||||
'SmsManager.cpp',
|
||||
'SmsMessage.cpp',
|
||||
'SmsParent.cpp',
|
||||
'SmsSegmentInfo.cpp',
|
||||
|
@ -17,17 +17,17 @@ class SMSTest(MarionetteTestCase):
|
||||
# Setup the event listsener on the receiver, which should store
|
||||
# a global variable when an SMS is received.
|
||||
message = 'hello world!'
|
||||
self.assertTrue(receiver.execute_script("return window.navigator.mozSms != null;"))
|
||||
self.assertTrue(receiver.execute_script("return window.navigator.mozMobileMessage != null;"))
|
||||
receiver.execute_script("""
|
||||
global.smsreceived = null;
|
||||
window.navigator.mozSms.addEventListener("received", function(e) {
|
||||
window.navigator.mozMobileMessage.addEventListener("received", function(e) {
|
||||
global.smsreceived = e.message.body;
|
||||
});
|
||||
""", new_sandbox=False)
|
||||
|
||||
# Send the SMS from the sender.
|
||||
sender.execute_script("""
|
||||
window.navigator.mozSms.send("%d", "%s");
|
||||
window.navigator.mozMobileMessage.send("%d", "%s");
|
||||
""" % (receiver.emulator.port, message))
|
||||
|
||||
# On the receiver, wait up to 10s for an SMS to be received, by
|
||||
|
@ -6,12 +6,14 @@ MARIONETTE_TIMEOUT = 60000;
|
||||
SpecialPowers.setBoolPref("dom.sms.enabled", true);
|
||||
SpecialPowers.addPermission("sms", true, document);
|
||||
|
||||
let sms = window.navigator.mozSms;
|
||||
let manager = window.navigator.mozMobileMessage;
|
||||
ok(manager instanceof MozMobileMessageManager,
|
||||
"manager is instance of " + manager.constructor);
|
||||
|
||||
// Note: 378 chars and below is fine, but 379 and above will cause the issue.
|
||||
// Sending first message works, but second one we get emulator callback but
|
||||
// the actual SMS is never received, so script will timeout waiting for the
|
||||
// sms.onreceived event. Also note that a single larger message (i.e. 1600
|
||||
// onreceived event. Also note that a single larger message (i.e. 1600
|
||||
// characters) works; so it is not a compounded send limit.
|
||||
let fromNumber = "5551110000";
|
||||
let msgLength = 379;
|
||||
@ -41,9 +43,9 @@ function simulateIncomingSms(nextFunction) {
|
||||
log("Simulating incoming multipart SMS (" + msgText.length
|
||||
+ " chars total).");
|
||||
|
||||
sms.onreceived = function onreceived(event) {
|
||||
log("Received 'onreceived' smsmanager event.");
|
||||
sms.onreceived = null;
|
||||
manager.onreceived = function onreceived(event) {
|
||||
log("Received 'onreceived' event.");
|
||||
manager.onreceived = null;
|
||||
|
||||
let incomingSms = event.message;
|
||||
ok(incomingSms, "incoming sms");
|
||||
|
@ -14,8 +14,9 @@ function cleanUp() {
|
||||
finish();
|
||||
}
|
||||
|
||||
let sms = window.navigator.mozSms;
|
||||
ok(sms instanceof MozSmsManager);
|
||||
let manager = window.navigator.mozMobileMessage;
|
||||
ok(manager instanceof MozMobileMessageManager,
|
||||
"manager is instance of " + manager.constructor);
|
||||
|
||||
function randomString16() {
|
||||
return Math.random().toString(36).substr(2, 16);
|
||||
@ -33,7 +34,7 @@ function repeat(func, array, oncomplete) {
|
||||
}
|
||||
|
||||
function doTest(body, callback) {
|
||||
sms.addEventListener("received", function onReceived(event) {
|
||||
manager.addEventListener("received", function onReceived(event) {
|
||||
event.target.removeEventListener(event.type, arguments.callee);
|
||||
|
||||
let message = event.message;
|
||||
@ -42,7 +43,7 @@ function doTest(body, callback) {
|
||||
window.setTimeout(callback, 0);
|
||||
});
|
||||
|
||||
let request = sms.send(SELF, body);
|
||||
let request = manager.send(SELF, body);
|
||||
request.onerror = function onerror() {
|
||||
ok(false, "failed to send message '" + body + "' to '" + SELF + "'");
|
||||
};
|
||||
|
@ -6,13 +6,14 @@ MARIONETTE_TIMEOUT = 60000;
|
||||
SpecialPowers.addPermission("sms", true, document);
|
||||
SpecialPowers.setBoolPref("dom.sms.enabled", true);
|
||||
|
||||
let sms = window.navigator.mozSms;
|
||||
let manager = window.navigator.mozMobileMessage;
|
||||
let numberMsgs = 10;
|
||||
let smsList = new Array();
|
||||
|
||||
function verifyInitialState() {
|
||||
log("Verifying initial state.");
|
||||
ok(sms, "mozSms");
|
||||
ok(manager instanceof MozMobileMessageManager,
|
||||
"manager is instance of " + manager.constructor);
|
||||
// Ensure test is starting clean with no existing sms messages
|
||||
deleteAllMsgs(simulateIncomingSms);
|
||||
}
|
||||
@ -21,7 +22,7 @@ function deleteAllMsgs(nextFunction) {
|
||||
let msgList = new Array();
|
||||
let filter = new MozSmsFilter;
|
||||
|
||||
let cursor = sms.getMessages(filter, false);
|
||||
let cursor = manager.getMessages(filter, false);
|
||||
ok(cursor instanceof DOMCursor,
|
||||
"cursor is instanceof " + cursor.constructor);
|
||||
|
||||
@ -46,7 +47,7 @@ function deleteAllMsgs(nextFunction) {
|
||||
cursor.onerror = function(event) {
|
||||
log("Received 'onerror' event.");
|
||||
ok(event.target.error, "domerror obj");
|
||||
log("sms.getMessages error: " + event.target.error.name);
|
||||
log("manager.getMessages error: " + event.target.error.name);
|
||||
ok(false,"Could not get SMS messages");
|
||||
cleanUp();
|
||||
};
|
||||
@ -56,7 +57,7 @@ function deleteMsgs(msgList, nextFunction) {
|
||||
let smsId = msgList.shift();
|
||||
|
||||
log("Deleting SMS (id: " + smsId + ").");
|
||||
let request = sms.delete(smsId);
|
||||
let request = manager.delete(smsId);
|
||||
ok(request instanceof DOMRequest,
|
||||
"request is instanceof " + request.constructor);
|
||||
|
||||
@ -72,7 +73,7 @@ function deleteMsgs(msgList, nextFunction) {
|
||||
}
|
||||
} else {
|
||||
log("SMS delete failed.");
|
||||
ok(false,"sms.delete request returned false");
|
||||
ok(false,"manager.delete request returned false");
|
||||
cleanUp();
|
||||
}
|
||||
};
|
||||
@ -80,7 +81,7 @@ function deleteMsgs(msgList, nextFunction) {
|
||||
request.onerror = function(event) {
|
||||
log("Received 'onerror' smsrequest event.");
|
||||
ok(event.target.error, "domerror obj");
|
||||
ok(false, "sms.delete request returned unexpected error: "
|
||||
ok(false, "manager.delete request returned unexpected error: "
|
||||
+ event.target.error.name );
|
||||
cleanUp();
|
||||
};
|
||||
@ -102,7 +103,7 @@ function simulateIncomingSms() {
|
||||
}
|
||||
|
||||
// Callback for incoming sms
|
||||
sms.onreceived = function onreceived(event) {
|
||||
manager.onreceived = function onreceived(event) {
|
||||
log("Received 'onreceived' sms event.");
|
||||
let incomingSms = event.message;
|
||||
log("Received SMS (id: " + incomingSms.id + ").");
|
||||
@ -136,7 +137,7 @@ function getMsgs() {
|
||||
|
||||
log("Getting SMS messages with dates between " + yesterday + " and "
|
||||
+ tomorrow +".");
|
||||
let cursor = sms.getMessages(filter, false);
|
||||
let cursor = manager.getMessages(filter, false);
|
||||
ok(cursor instanceof DOMCursor,
|
||||
"cursor is instanceof " + cursor.constructor);
|
||||
|
||||
@ -159,7 +160,7 @@ function getMsgs() {
|
||||
} else {
|
||||
log("SMS getMessages returned " + foundSmsList.length +
|
||||
" messages, but expected " + smsList.length + ".");
|
||||
ok(false, "Incorrect number of messages returned by sms.getMessages");
|
||||
ok(false, "Incorrect number of messages returned by manager.getMessages");
|
||||
deleteAllMsgs(cleanUp);
|
||||
}
|
||||
}
|
||||
@ -168,7 +169,7 @@ function getMsgs() {
|
||||
cursor.onerror = function(event) {
|
||||
log("Received 'onerror' event.");
|
||||
ok(event.target.error, "domerror obj");
|
||||
log("sms.getMessages error: " + event.target.error.name);
|
||||
log("manager.getMessages error: " + event.target.error.name);
|
||||
ok(false,"Could not get SMS messages");
|
||||
cleanUp();
|
||||
};
|
||||
@ -184,7 +185,7 @@ function verifyFoundMsgs(foundSmsList) {
|
||||
}
|
||||
|
||||
function cleanUp() {
|
||||
sms.onreceived = null;
|
||||
manager.onreceived = null;
|
||||
SpecialPowers.removePermission("sms", document);
|
||||
SpecialPowers.clearUserPref("dom.sms.enabled");
|
||||
finish();
|
||||
|
@ -6,13 +6,14 @@ MARIONETTE_TIMEOUT = 60000;
|
||||
SpecialPowers.addPermission("sms", true, document);
|
||||
SpecialPowers.setBoolPref("dom.sms.enabled", true);
|
||||
|
||||
let sms = window.navigator.mozSms;
|
||||
let manager = window.navigator.mozMobileMessage;
|
||||
let numberMsgs = 10;
|
||||
let smsList = new Array();
|
||||
|
||||
function verifyInitialState() {
|
||||
log("Verifying initial state.");
|
||||
ok(sms, "mozSms");
|
||||
ok(manager instanceof MozMobileMessageManager,
|
||||
"manager is instance of " + manager.constructor);
|
||||
// Ensure test is starting clean with no existing sms messages
|
||||
deleteAllMsgs(simulateIncomingSms);
|
||||
}
|
||||
@ -21,7 +22,7 @@ function deleteAllMsgs(nextFunction) {
|
||||
let msgList = new Array();
|
||||
let filter = new MozSmsFilter;
|
||||
|
||||
let cursor = sms.getMessages(filter, false);
|
||||
let cursor = manager.getMessages(filter, false);
|
||||
ok(cursor instanceof DOMCursor,
|
||||
"cursor is instanceof " + cursor.constructor);
|
||||
|
||||
@ -46,7 +47,7 @@ function deleteAllMsgs(nextFunction) {
|
||||
cursor.onerror = function(event) {
|
||||
log("Received 'onerror' event.");
|
||||
ok(event.target.error, "domerror obj");
|
||||
log("sms.getMessages error: " + event.target.error.name);
|
||||
log("manager.getMessages error: " + event.target.error.name);
|
||||
ok(false,"Could not get SMS messages");
|
||||
cleanUp();
|
||||
};
|
||||
@ -56,7 +57,7 @@ function deleteMsgs(msgList, nextFunction) {
|
||||
let smsId = msgList.shift();
|
||||
|
||||
log("Deleting SMS (id: " + smsId + ").");
|
||||
let request = sms.delete(smsId);
|
||||
let request = manager.delete(smsId);
|
||||
ok(request instanceof DOMRequest,
|
||||
"request is instanceof " + request.constructor);
|
||||
|
||||
@ -72,7 +73,7 @@ function deleteMsgs(msgList, nextFunction) {
|
||||
}
|
||||
} else {
|
||||
log("SMS delete failed.");
|
||||
ok(false,"sms.delete request returned false");
|
||||
ok(false,"manager.delete request returned false");
|
||||
cleanUp();
|
||||
}
|
||||
};
|
||||
@ -80,7 +81,7 @@ function deleteMsgs(msgList, nextFunction) {
|
||||
request.onerror = function(event) {
|
||||
log("Received 'onerror' smsrequest event.");
|
||||
ok(event.target.error, "domerror obj");
|
||||
ok(false, "sms.delete request returned unexpected error: "
|
||||
ok(false, "manager.delete request returned unexpected error: "
|
||||
+ event.target.error.name );
|
||||
cleanUp();
|
||||
};
|
||||
@ -102,7 +103,7 @@ function simulateIncomingSms() {
|
||||
}
|
||||
|
||||
// Callback for incoming sms
|
||||
sms.onreceived = function onreceived(event) {
|
||||
manager.onreceived = function onreceived(event) {
|
||||
log("Received 'onreceived' sms event.");
|
||||
let incomingSms = event.message;
|
||||
log("Received SMS (id: " + incomingSms.id + ").");
|
||||
@ -136,7 +137,7 @@ function getMsgs() {
|
||||
|
||||
log("Getting SMS messages with dates between " + twoDaysAgo + " and "
|
||||
+ yesterday +".");
|
||||
let cursor = sms.getMessages(filter, false);
|
||||
let cursor = manager.getMessages(filter, false);
|
||||
ok(cursor instanceof DOMCursor,
|
||||
"cursor is instanceof " + cursor.constructor);
|
||||
|
||||
@ -158,14 +159,14 @@ function getMsgs() {
|
||||
cursor.onerror = function(event) {
|
||||
log("Received 'onerror' event.");
|
||||
ok(event.target.error, "domerror obj");
|
||||
log("sms.getMessages error: " + event.target.error.name);
|
||||
log("manager.getMessages error: " + event.target.error.name);
|
||||
ok(false,"Could not get SMS messages");
|
||||
cleanUp();
|
||||
};
|
||||
}
|
||||
|
||||
function cleanUp() {
|
||||
sms.onreceived = null;
|
||||
manager.onreceived = null;
|
||||
SpecialPowers.removePermission("sms", document);
|
||||
SpecialPowers.clearUserPref("dom.sms.enabled");
|
||||
finish();
|
||||
|
@ -9,8 +9,9 @@ const NUM_THREADS = 10;
|
||||
SpecialPowers.addPermission("sms", true, document);
|
||||
SpecialPowers.setBoolPref("dom.sms.enabled", true);
|
||||
|
||||
let sms = window.navigator.mozSms;
|
||||
ok(sms instanceof MozSmsManager);
|
||||
let manager = window.navigator.mozMobileMessage;
|
||||
ok(manager instanceof MozMobileMessageManager,
|
||||
"manager is instance of " + manager.constructor);
|
||||
|
||||
let pendingEmulatorCmdCount = 0;
|
||||
function sendSmsToEmulator(from, text) {
|
||||
@ -62,7 +63,7 @@ function getAllMessages(callback, filter, reverse) {
|
||||
filter = new MozSmsFilter;
|
||||
}
|
||||
let messages = [];
|
||||
let request = sms.getMessages(filter, reverse || false);
|
||||
let request = manager.getMessages(filter, reverse || false);
|
||||
request.onsuccess = function(event) {
|
||||
if (request.result) {
|
||||
messages.push(request.result);
|
||||
@ -83,7 +84,7 @@ function deleteAllMessages(next) {
|
||||
return;
|
||||
}
|
||||
|
||||
let request = sms.delete(message.id);
|
||||
let request = manager.delete(message.id);
|
||||
request.onsuccess = deleteAll.bind(null, messages);
|
||||
request.onerror = function (event) {
|
||||
ok(false, "failed to delete all messages");
|
||||
@ -124,9 +125,9 @@ tasks.push(function populateMessages() {
|
||||
let count = 0;
|
||||
|
||||
function sendMessage(iter) {
|
||||
let request = sms.send("+1555531555" + iter, "Nice to meet you");
|
||||
let request = manager.send("+1555531555" + iter, "Nice to meet you");
|
||||
request.onsuccess = function onRequestSuccess(event) {
|
||||
sms.addEventListener("received", onReceived);
|
||||
manager.addEventListener("received", onReceived);
|
||||
|
||||
threadIds.push(request.result.threadId);
|
||||
|
||||
@ -138,7 +139,7 @@ tasks.push(function populateMessages() {
|
||||
}
|
||||
|
||||
function onReceived(event) {
|
||||
sms.removeEventListener("received", onReceived);
|
||||
manager.removeEventListener("received", onReceived);
|
||||
|
||||
if (event.message.threadId != threadIds[threadIds.length - 1]) {
|
||||
ok(false, "Thread IDs of sent and received message mismatch.");
|
||||
@ -148,7 +149,7 @@ tasks.push(function populateMessages() {
|
||||
|
||||
++count;
|
||||
if (count % 2) {
|
||||
let request = sms.markMessageRead(event.message.id, true);
|
||||
let request = manager.markMessageRead(event.message.id, true);
|
||||
request.onsuccess = function onRequestSuccess(event) {
|
||||
if (count < NUM_THREADS) {
|
||||
sendMessage(count);
|
||||
|
@ -6,14 +6,15 @@ MARIONETTE_TIMEOUT = 60000;
|
||||
SpecialPowers.addPermission("sms", true, document);
|
||||
SpecialPowers.setBoolPref("dom.sms.enabled", true);
|
||||
|
||||
let sms = window.navigator.mozSms;
|
||||
let manager = window.navigator.mozMobileMessage;
|
||||
let numberMsgs = 10;
|
||||
let smsList = new Array();
|
||||
let defaultRemoteNumber = "+15552227777";
|
||||
|
||||
function verifyInitialState() {
|
||||
log("Verifying initial state.");
|
||||
ok(sms, "mozSms");
|
||||
ok(manager instanceof MozMobileMessageManager,
|
||||
"manager is instance of " + manager.constructor);
|
||||
// Ensure test is starting clean with no existing sms messages
|
||||
deleteAllMsgs(sendSms);
|
||||
}
|
||||
@ -23,7 +24,7 @@ function deleteAllMsgs(nextFunction) {
|
||||
let msgList = new Array();
|
||||
let filter = new MozSmsFilter;
|
||||
|
||||
let cursor = sms.getMessages(filter, false);
|
||||
let cursor = manager.getMessages(filter, false);
|
||||
ok(cursor instanceof DOMCursor,
|
||||
"cursor is instanceof " + cursor.constructor);
|
||||
|
||||
@ -48,7 +49,7 @@ function deleteAllMsgs(nextFunction) {
|
||||
cursor.onerror = function(event) {
|
||||
log("Received 'onerror' event.");
|
||||
ok(event.target.error, "domerror obj");
|
||||
log("sms.getMessages error: " + event.target.error.name);
|
||||
log("manager.getMessages error: " + event.target.error.name);
|
||||
ok(false,"Could not get SMS messages");
|
||||
cleanUp();
|
||||
};
|
||||
@ -59,7 +60,7 @@ function deleteMsgs(msgList, nextFunction) {
|
||||
let smsId = msgList.shift();
|
||||
|
||||
log("Deleting SMS (id: " + smsId + ").");
|
||||
let request = sms.delete(smsId);
|
||||
let request = manager.delete(smsId);
|
||||
ok(request instanceof DOMRequest,
|
||||
"request is instanceof " + request.constructor);
|
||||
|
||||
@ -75,7 +76,7 @@ function deleteMsgs(msgList, nextFunction) {
|
||||
}
|
||||
} else {
|
||||
log("SMS delete failed.");
|
||||
ok(false,"sms.delete request returned false");
|
||||
ok(false,"manager.delete request returned false");
|
||||
cleanUp();
|
||||
}
|
||||
};
|
||||
@ -83,7 +84,7 @@ function deleteMsgs(msgList, nextFunction) {
|
||||
request.onerror = function(event) {
|
||||
log("Received 'onerror' smsrequest event.");
|
||||
ok(event.target.error, "domerror obj");
|
||||
ok(false, "sms.delete request returned unexpected error: "
|
||||
ok(false, "manager.delete request returned unexpected error: "
|
||||
+ event.target.error.name );
|
||||
cleanUp();
|
||||
};
|
||||
@ -98,8 +99,8 @@ function sendSms() {
|
||||
|
||||
log("Sending an SMS.");
|
||||
|
||||
sms.onsent = function(event) {
|
||||
log("Received 'onsent' smsmanager event.");
|
||||
manager.onsent = function(event) {
|
||||
log("Received 'onsent' event.");
|
||||
gotSmsSent = true;
|
||||
log("Sent SMS (id: " + event.message.id + ").");
|
||||
if (gotSmsSent && gotRequestSuccess) {
|
||||
@ -107,7 +108,7 @@ function sendSms() {
|
||||
}
|
||||
};
|
||||
|
||||
let request = sms.send(remoteNumber, text);
|
||||
let request = manager.send(remoteNumber, text);
|
||||
ok(request instanceof DOMRequest,
|
||||
"request is instanceof " + request.constructor);
|
||||
|
||||
@ -119,7 +120,7 @@ function sendSms() {
|
||||
simulateIncomingSms();
|
||||
}
|
||||
} else {
|
||||
log("smsrequest returned false for sms.send");
|
||||
log("smsrequest returned false for manager.send");
|
||||
ok(false,"SMS send failed");
|
||||
cleanUp();
|
||||
}
|
||||
@ -128,7 +129,7 @@ function sendSms() {
|
||||
request.onerror = function(event) {
|
||||
log("Received 'onerror' smsrequest event.");
|
||||
ok(event.target.error, "domerror obj");
|
||||
ok(false, "sms.send request returned unexpected error: "
|
||||
ok(false, "manager.send request returned unexpected error: "
|
||||
+ event.target.error.name );
|
||||
cleanUp();
|
||||
};
|
||||
@ -151,7 +152,7 @@ function simulateIncomingSms(remoteNumber) {
|
||||
});
|
||||
}
|
||||
|
||||
sms.onreceived = function onreceived(event) {
|
||||
manager.onreceived = function onreceived(event) {
|
||||
// Callback for incoming SMS
|
||||
log("Received 'onreceived' sms event.");
|
||||
let incomingSms = event.message;
|
||||
@ -190,7 +191,7 @@ function getMsgs(secondNumber) {
|
||||
|
||||
log("Getting the SMS messages with numbers " + defaultRemoteNumber + " and "
|
||||
+ secondNumber + ".");
|
||||
let cursor = sms.getMessages(filter, false);
|
||||
let cursor = manager.getMessages(filter, false);
|
||||
ok(cursor instanceof DOMCursor,
|
||||
"cursor is instanceof " + cursor.constructor);
|
||||
|
||||
@ -213,7 +214,7 @@ function getMsgs(secondNumber) {
|
||||
} else {
|
||||
log("SMS getMessages returned " + foundSmsList.length +
|
||||
" messages, but expected " + smsList.length + ".");
|
||||
ok(false, "Incorrect number of messages returned by sms.getMessages");
|
||||
ok(false, "Incorrect number of messages returned by manager.getMessages");
|
||||
deleteAllMsgs(cleanUp);
|
||||
}
|
||||
}
|
||||
@ -222,7 +223,7 @@ function getMsgs(secondNumber) {
|
||||
cursor.onerror = function(event) {
|
||||
log("Received 'onerror' event.");
|
||||
ok(event.target.error, "domerror obj");
|
||||
log("sms.getMessages error: " + event.target.error.name);
|
||||
log("manager.getMessages error: " + event.target.error.name);
|
||||
ok(false,"Could not get SMS messages");
|
||||
cleanUp();
|
||||
};
|
||||
@ -238,7 +239,7 @@ function verifyFoundMsgs(foundSmsList) {
|
||||
}
|
||||
|
||||
function cleanUp() {
|
||||
sms.onreceived = null;
|
||||
manager.onreceived = null;
|
||||
SpecialPowers.removePermission("sms", document);
|
||||
SpecialPowers.clearUserPref("dom.sms.enabled");
|
||||
finish();
|
||||
|
@ -6,14 +6,15 @@ MARIONETTE_TIMEOUT = 60000;
|
||||
SpecialPowers.addPermission("sms", true, document);
|
||||
SpecialPowers.setBoolPref("dom.sms.enabled", true);
|
||||
|
||||
let sms = window.navigator.mozSms;
|
||||
let manager = window.navigator.mozMobileMessage;
|
||||
let numberMsgs = 10;
|
||||
let smsList = new Array();
|
||||
let defaultRemoteNumber = "+15552227777";
|
||||
|
||||
function verifyInitialState() {
|
||||
log("Verifying initial state.");
|
||||
ok(sms, "mozSms");
|
||||
ok(manager instanceof MozMobileMessageManager,
|
||||
"manager is instance of " + manager.constructor);
|
||||
// Ensure test is starting clean with no existing sms messages
|
||||
deleteAllMsgs(simulateIncomingSms);
|
||||
}
|
||||
@ -23,7 +24,7 @@ function deleteAllMsgs(nextFunction) {
|
||||
let msgList = new Array();
|
||||
let filter = new MozSmsFilter;
|
||||
|
||||
let cursor = sms.getMessages(filter, false);
|
||||
let cursor = manager.getMessages(filter, false);
|
||||
ok(cursor instanceof DOMCursor,
|
||||
"cursor is instanceof " + cursor.constructor);
|
||||
|
||||
@ -48,7 +49,7 @@ function deleteAllMsgs(nextFunction) {
|
||||
cursor.onerror = function(event) {
|
||||
log("Received 'onerror' event.");
|
||||
ok(event.target.error, "domerror obj");
|
||||
log("sms.getMessages error: " + event.target.error.name);
|
||||
log("manager.getMessages error: " + event.target.error.name);
|
||||
ok(false,"Could not get SMS messages");
|
||||
cleanUp();
|
||||
};
|
||||
@ -59,7 +60,7 @@ function deleteMsgs(msgList, nextFunction) {
|
||||
let smsId = msgList.shift();
|
||||
|
||||
log("Deleting SMS (id: " + smsId + ").");
|
||||
let request = sms.delete(smsId);
|
||||
let request = manager.delete(smsId);
|
||||
ok(request instanceof DOMRequest,
|
||||
"request is instanceof " + request.constructor);
|
||||
|
||||
@ -75,7 +76,7 @@ function deleteMsgs(msgList, nextFunction) {
|
||||
}
|
||||
} else {
|
||||
log("SMS delete failed.");
|
||||
ok(false,"sms.delete request returned false");
|
||||
ok(false,"manager.delete request returned false");
|
||||
cleanUp();
|
||||
}
|
||||
};
|
||||
@ -83,7 +84,7 @@ function deleteMsgs(msgList, nextFunction) {
|
||||
request.onerror = function(event) {
|
||||
log("Received 'onerror' smsrequest event.");
|
||||
ok(event.target.error, "domerror obj");
|
||||
ok(false, "sms.delete request returned unexpected error: "
|
||||
ok(false, "manager.delete request returned unexpected error: "
|
||||
+ event.target.error.name );
|
||||
cleanUp();
|
||||
};
|
||||
@ -106,7 +107,7 @@ function simulateIncomingSms(remoteNumber) {
|
||||
});
|
||||
}
|
||||
|
||||
sms.onreceived = function onreceived(event) {
|
||||
manager.onreceived = function onreceived(event) {
|
||||
// Callback for incoming SMS
|
||||
log("Received 'onreceived' sms event.");
|
||||
let incomingSms = event.message;
|
||||
@ -148,7 +149,7 @@ function getMsgs() {
|
||||
filter.numbers = new Array(defaultRemoteNumber);
|
||||
|
||||
log("Getting the SMS messages from sender " + defaultRemoteNumber + ".");
|
||||
let cursor = sms.getMessages(filter, false);
|
||||
let cursor = manager.getMessages(filter, false);
|
||||
ok(cursor instanceof DOMCursor,
|
||||
"cursor is instanceof " + cursor.constructor);
|
||||
|
||||
@ -171,7 +172,7 @@ function getMsgs() {
|
||||
} else {
|
||||
log("SMS getMessages returned " + foundSmsList.length +
|
||||
" messages, but expected " + smsList.length + ".");
|
||||
ok(false, "Incorrect number of messages returned by sms.getMessages");
|
||||
ok(false, "Incorrect number of messages returned by manager.getMessages");
|
||||
deleteAllMsgs(cleanUp);
|
||||
}
|
||||
}
|
||||
@ -180,7 +181,7 @@ function getMsgs() {
|
||||
cursor.onerror = function(event) {
|
||||
log("Received 'onerror' event.");
|
||||
ok(event.target.error, "domerror obj");
|
||||
log("sms.getMessages error: " + event.target.error.name);
|
||||
log("manager.getMessages error: " + event.target.error.name);
|
||||
ok(false,"Could not get SMS messages");
|
||||
cleanUp();
|
||||
};
|
||||
@ -196,7 +197,7 @@ function verifyFoundMsgs(foundSmsList) {
|
||||
}
|
||||
|
||||
function cleanUp() {
|
||||
sms.onreceived = null;
|
||||
manager.onreceived = null;
|
||||
SpecialPowers.removePermission("sms", document);
|
||||
SpecialPowers.clearUserPref("dom.sms.enabled");
|
||||
finish();
|
||||
|
@ -6,13 +6,14 @@ MARIONETTE_TIMEOUT = 60000;
|
||||
SpecialPowers.addPermission("sms", true, document);
|
||||
SpecialPowers.setBoolPref("dom.sms.enabled", true);
|
||||
|
||||
let sms = window.navigator.mozSms;
|
||||
let manager = window.navigator.mozMobileMessage;
|
||||
let numberMsgs = 10;
|
||||
let smsList = new Array();
|
||||
|
||||
function verifyInitialState() {
|
||||
log("Verifying initial state.");
|
||||
ok(sms, "mozSms");
|
||||
ok(manager instanceof MozMobileMessageManager,
|
||||
"manager is instance of " + manager.constructor);
|
||||
// Ensure test is starting clean with no existing sms messages
|
||||
deleteAllMsgs(simulateIncomingSms);
|
||||
}
|
||||
@ -21,7 +22,7 @@ function deleteAllMsgs(nextFunction) {
|
||||
let msgList = new Array();
|
||||
let filter = new MozSmsFilter;
|
||||
|
||||
let cursor = sms.getMessages(filter, false);
|
||||
let cursor = manager.getMessages(filter, false);
|
||||
ok(cursor instanceof DOMCursor,
|
||||
"cursor is instanceof " + cursor.constructor);
|
||||
|
||||
@ -46,7 +47,7 @@ function deleteAllMsgs(nextFunction) {
|
||||
cursor.onerror = function(event) {
|
||||
log("Received 'onerror' event.");
|
||||
ok(event.target.error, "domerror obj");
|
||||
log("sms.getMessages error: " + event.target.error.name);
|
||||
log("manager.getMessages error: " + event.target.error.name);
|
||||
ok(false,"Could not get SMS messages");
|
||||
cleanUp();
|
||||
};
|
||||
@ -56,7 +57,7 @@ function deleteMsgs(msgList, nextFunction) {
|
||||
let smsId = msgList.shift();
|
||||
|
||||
log("Deleting SMS (id: " + smsId + ").");
|
||||
let request = sms.delete(smsId);
|
||||
let request = manager.delete(smsId);
|
||||
ok(request instanceof DOMRequest,
|
||||
"request is instanceof " + request.constructor);
|
||||
|
||||
@ -72,7 +73,7 @@ function deleteMsgs(msgList, nextFunction) {
|
||||
}
|
||||
} else {
|
||||
log("SMS delete failed.");
|
||||
ok(false,"sms.delete request returned false");
|
||||
ok(false,"manager.delete request returned false");
|
||||
cleanUp();
|
||||
}
|
||||
};
|
||||
@ -80,7 +81,7 @@ function deleteMsgs(msgList, nextFunction) {
|
||||
request.onerror = function(event) {
|
||||
log("Received 'onerror' smsrequest event.");
|
||||
ok(event.target.error, "domerror obj");
|
||||
ok(false, "sms.delete request returned unexpected error: "
|
||||
ok(false, "manager.delete request returned unexpected error: "
|
||||
+ event.target.error.name );
|
||||
cleanUp();
|
||||
};
|
||||
@ -102,7 +103,7 @@ function simulateIncomingSms() {
|
||||
}
|
||||
|
||||
// Callback for incoming sms
|
||||
sms.onreceived = function onreceived(event) {
|
||||
manager.onreceived = function onreceived(event) {
|
||||
log("Received 'onreceived' sms event.");
|
||||
let incomingSms = event.message;
|
||||
log("Received SMS (id: " + incomingSms.id + ").");
|
||||
@ -130,7 +131,7 @@ function nextRep() {
|
||||
function markMsgRead(smsMsgs) {
|
||||
nextSms = smsMsgs.shift();
|
||||
log("Marking SMS (id: " + nextSms.id + ") as read.");
|
||||
let request = sms.markMessageRead(nextSms.id, true);
|
||||
let request = manager.markMessageRead(nextSms.id, true);
|
||||
ok(request instanceof DOMRequest,
|
||||
"request is instanceof " + request.constructor);
|
||||
|
||||
@ -146,7 +147,7 @@ function markMsgRead(smsMsgs) {
|
||||
}
|
||||
} else {
|
||||
log("SMS markMessageRead failed.");
|
||||
ok(false,"sms.markMessageRead request returned false");
|
||||
ok(false,"manager.markMessageRead request returned false");
|
||||
cleanUp();
|
||||
}
|
||||
};
|
||||
@ -154,7 +155,7 @@ function markMsgRead(smsMsgs) {
|
||||
request.onerror = function(event) {
|
||||
log("Received 'onerror' smsrequest event.");
|
||||
ok(event.target.error, "domerror obj");
|
||||
ok(false, "sms.markMessageRead request returned unexpected error: "
|
||||
ok(false, "manager.markMessageRead request returned unexpected error: "
|
||||
+ event.target.error.name );
|
||||
cleanUp();
|
||||
};
|
||||
@ -168,7 +169,7 @@ function getMsgs() {
|
||||
filter.read = true;
|
||||
|
||||
log("Getting the read SMS messages.");
|
||||
let cursor = sms.getMessages(filter, false);
|
||||
let cursor = manager.getMessages(filter, false);
|
||||
ok(cursor instanceof DOMCursor,
|
||||
"cursor is instanceof " + cursor.constructor);
|
||||
|
||||
@ -191,7 +192,7 @@ function getMsgs() {
|
||||
} else {
|
||||
log("SMS getMessages returned " + foundSmsList.length +
|
||||
" messages, but expected " + smsList.length + ".");
|
||||
ok(false, "Incorrect number of messages returned by sms.getMessages");
|
||||
ok(false, "Incorrect number of messages returned by manager.getMessages");
|
||||
deleteAllMsgs(cleanUp);
|
||||
}
|
||||
}
|
||||
@ -200,7 +201,7 @@ function getMsgs() {
|
||||
cursor.onerror = function(event) {
|
||||
log("Received 'onerror' event.");
|
||||
ok(event.target.error, "domerror obj");
|
||||
log("sms.getMessages error: " + event.target.error.name);
|
||||
log("manager.getMessages error: " + event.target.error.name);
|
||||
ok(false,"Could not get SMS messages");
|
||||
cleanUp();
|
||||
};
|
||||
@ -215,7 +216,7 @@ function verifyFoundMsgs(foundSmsList) {
|
||||
}
|
||||
|
||||
function cleanUp() {
|
||||
sms.onreceived = null;
|
||||
manager.onreceived = null;
|
||||
SpecialPowers.removePermission("sms", document);
|
||||
SpecialPowers.clearUserPref("dom.sms.enabled");
|
||||
finish();
|
||||
|
@ -6,13 +6,14 @@ MARIONETTE_TIMEOUT = 60000;
|
||||
SpecialPowers.addPermission("sms", true, document);
|
||||
SpecialPowers.setBoolPref("dom.sms.enabled", true);
|
||||
|
||||
let sms = window.navigator.mozSms;
|
||||
let manager = window.navigator.mozMobileMessage;
|
||||
let numberMsgs = 10;
|
||||
let smsList = new Array();
|
||||
|
||||
function verifyInitialState() {
|
||||
log("Verifying initial state.");
|
||||
ok(sms, "mozSms");
|
||||
ok(manager instanceof MozMobileMessageManager,
|
||||
"manager is instance of " + manager.constructor);
|
||||
// Ensure test is starting clean with no existing sms messages
|
||||
deleteAllMsgs(simulateIncomingSms);
|
||||
}
|
||||
@ -21,7 +22,7 @@ function deleteAllMsgs(nextFunction) {
|
||||
let msgList = new Array();
|
||||
let filter = new MozSmsFilter;
|
||||
|
||||
let cursor = sms.getMessages(filter, false);
|
||||
let cursor = manager.getMessages(filter, false);
|
||||
ok(cursor instanceof DOMCursor,
|
||||
"cursor is instanceof " + cursor.constructor);
|
||||
|
||||
@ -46,7 +47,7 @@ function deleteAllMsgs(nextFunction) {
|
||||
cursor.onerror = function(event) {
|
||||
log("Received 'onerror' event.");
|
||||
ok(event.target.error, "domerror obj");
|
||||
log("sms.getMessages error: " + event.target.error.name);
|
||||
log("manager.getMessages error: " + event.target.error.name);
|
||||
ok(false,"Could not get SMS messages");
|
||||
cleanUp();
|
||||
};
|
||||
@ -56,7 +57,7 @@ function deleteMsgs(msgList, nextFunction) {
|
||||
let smsId = msgList.shift();
|
||||
|
||||
log("Deleting SMS (id: " + smsId + ").");
|
||||
let request = sms.delete(smsId);
|
||||
let request = manager.delete(smsId);
|
||||
ok(request instanceof DOMRequest,
|
||||
"request is instanceof " + request.constructor);
|
||||
|
||||
@ -72,7 +73,7 @@ function deleteMsgs(msgList, nextFunction) {
|
||||
}
|
||||
} else {
|
||||
log("SMS delete failed.");
|
||||
ok(false,"sms.delete request returned false");
|
||||
ok(false,"manager.delete request returned false");
|
||||
cleanUp();
|
||||
}
|
||||
};
|
||||
@ -80,7 +81,7 @@ function deleteMsgs(msgList, nextFunction) {
|
||||
request.onerror = function(event) {
|
||||
log("Received 'onerror' smsrequest event.");
|
||||
ok(event.target.error, "domerror obj");
|
||||
ok(false, "sms.delete request returned unexpected error: "
|
||||
ok(false, "manager.delete request returned unexpected error: "
|
||||
+ event.target.error.name );
|
||||
cleanUp();
|
||||
};
|
||||
@ -102,7 +103,7 @@ function simulateIncomingSms() {
|
||||
}
|
||||
|
||||
// Callback for incoming sms
|
||||
sms.onreceived = function onreceived(event) {
|
||||
manager.onreceived = function onreceived(event) {
|
||||
log("Received 'onreceived' sms event.");
|
||||
let incomingSms = event.message;
|
||||
log("Received SMS (id: " + incomingSms.id + ").");
|
||||
@ -132,8 +133,8 @@ function sendSms() {
|
||||
|
||||
log("Sending an SMS.");
|
||||
|
||||
sms.onsent = function(event) {
|
||||
log("Received 'onsent' smsmanager event.");
|
||||
manager.onsent = function(event) {
|
||||
log("Received 'onsent' event.");
|
||||
gotSmsSent = true;
|
||||
let sentSms = event.message;
|
||||
log("Sent SMS (id: " + sentSms.id + ").");
|
||||
@ -144,7 +145,7 @@ function sendSms() {
|
||||
}
|
||||
};
|
||||
|
||||
let request = sms.send(remoteNumber, text);
|
||||
let request = manager.send(remoteNumber, text);
|
||||
ok(request instanceof DOMRequest,
|
||||
"request is instanceof " + request.constructor);
|
||||
|
||||
@ -157,7 +158,7 @@ function sendSms() {
|
||||
getMsgs();
|
||||
}
|
||||
} else {
|
||||
log("smsrequest returned false for sms.send");
|
||||
log("smsrequest returned false for manager.send");
|
||||
ok(false,"SMS send failed");
|
||||
cleanUp();
|
||||
}
|
||||
@ -166,7 +167,7 @@ function sendSms() {
|
||||
request.onerror = function(event) {
|
||||
log("Received 'onerror' smsrequest event.");
|
||||
ok(event.target.error, "domerror obj");
|
||||
ok(false, "sms.send request returned unexpected error: "
|
||||
ok(false, "manager.send request returned unexpected error: "
|
||||
+ event.target.error.name );
|
||||
cleanUp();
|
||||
};
|
||||
@ -180,7 +181,7 @@ function getMsgs() {
|
||||
filter.delivery = "received";
|
||||
|
||||
log("Getting the received SMS messages.");
|
||||
let cursor = sms.getMessages(filter, false);
|
||||
let cursor = manager.getMessages(filter, false);
|
||||
ok(cursor instanceof DOMCursor,
|
||||
"cursor is instanceof " + cursor.constructor);
|
||||
|
||||
@ -203,7 +204,7 @@ function getMsgs() {
|
||||
} else {
|
||||
log("SMS getMessages returned " + foundSmsList.length +
|
||||
" messages, but expected " + smsList.length + ".");
|
||||
ok(false, "Incorrect number of messages returned by sms.getMessages");
|
||||
ok(false, "Incorrect number of messages returned by manager.getMessages");
|
||||
deleteAllMsgs(cleanUp);
|
||||
}
|
||||
}
|
||||
@ -212,7 +213,7 @@ function getMsgs() {
|
||||
cursor.onerror = function(event) {
|
||||
log("Received 'onerror' event.");
|
||||
ok(event.target.error, "domerror obj");
|
||||
log("sms.getMessages error: " + event.target.error.name);
|
||||
log("manager.getMessages error: " + event.target.error.name);
|
||||
ok(false,"Could not get SMS messages");
|
||||
cleanUp();
|
||||
};
|
||||
@ -227,7 +228,7 @@ function verifyFoundMsgs(foundSmsList) {
|
||||
}
|
||||
|
||||
function cleanUp() {
|
||||
sms.onreceived = null;
|
||||
manager.onreceived = null;
|
||||
SpecialPowers.removePermission("sms", document);
|
||||
SpecialPowers.clearUserPref("dom.sms.enabled");
|
||||
finish();
|
||||
|
@ -6,13 +6,14 @@ MARIONETTE_TIMEOUT = 60000;
|
||||
SpecialPowers.addPermission("sms", true, document);
|
||||
SpecialPowers.setBoolPref("dom.sms.enabled", true);
|
||||
|
||||
let sms = window.navigator.mozSms;
|
||||
let manager = window.navigator.mozMobileMessage;
|
||||
let numberMsgs = 10;
|
||||
let smsList = new Array();
|
||||
|
||||
function verifyInitialState() {
|
||||
log("Verifying initial state.");
|
||||
ok(sms, "mozSms");
|
||||
ok(manager instanceof MozMobileMessageManager,
|
||||
"manager is instance of " + manager.constructor);
|
||||
// Ensure test is starting clean with no existing sms messages
|
||||
deleteAllMsgs(sendSms);
|
||||
}
|
||||
@ -21,7 +22,7 @@ function deleteAllMsgs(nextFunction) {
|
||||
let msgList = new Array();
|
||||
let filter = new MozSmsFilter;
|
||||
|
||||
let cursor = sms.getMessages(filter, false);
|
||||
let cursor = manager.getMessages(filter, false);
|
||||
ok(cursor instanceof DOMCursor,
|
||||
"cursor is instanceof " + cursor.constructor);
|
||||
|
||||
@ -46,7 +47,7 @@ function deleteAllMsgs(nextFunction) {
|
||||
cursor.onerror = function(event) {
|
||||
log("Received 'onerror' event.");
|
||||
ok(event.target.error, "domerror obj");
|
||||
log("sms.getMessages error: " + event.target.error.name);
|
||||
log("manager.getMessages error: " + event.target.error.name);
|
||||
ok(false,"Could not get SMS messages");
|
||||
cleanUp();
|
||||
};
|
||||
@ -56,7 +57,7 @@ function deleteMsgs(msgList, nextFunction) {
|
||||
let smsId = msgList.shift();
|
||||
|
||||
log("Deleting SMS (id: " + smsId + ").");
|
||||
let request = sms.delete(smsId);
|
||||
let request = manager.delete(smsId);
|
||||
ok(request instanceof DOMRequest,
|
||||
"request is instanceof " + request.constructor);
|
||||
|
||||
@ -72,7 +73,7 @@ function deleteMsgs(msgList, nextFunction) {
|
||||
}
|
||||
} else {
|
||||
log("SMS delete failed.");
|
||||
ok(false,"sms.delete request returned false");
|
||||
ok(false,"manager.delete request returned false");
|
||||
cleanUp();
|
||||
}
|
||||
};
|
||||
@ -80,7 +81,7 @@ function deleteMsgs(msgList, nextFunction) {
|
||||
request.onerror = function(event) {
|
||||
log("Received 'onerror' smsrequest event.");
|
||||
ok(event.target.error, "domerror obj");
|
||||
ok(false, "sms.delete request returned unexpected error: "
|
||||
ok(false, "manager.delete request returned unexpected error: "
|
||||
+ event.target.error.name );
|
||||
cleanUp();
|
||||
};
|
||||
@ -95,8 +96,8 @@ function sendSms() {
|
||||
log("Sending SMS " + (smsList.length + 1) + " of "
|
||||
+ (numberMsgs - 1) + ".");
|
||||
|
||||
sms.onsent = function(event) {
|
||||
log("Received 'onsent' smsmanager event.");
|
||||
manager.onsent = function(event) {
|
||||
log("Received 'onsent' event.");
|
||||
gotSmsSent = true;
|
||||
let sentSms = event.message;
|
||||
log("Sent SMS (id: " + sentSms.id + ").");
|
||||
@ -107,7 +108,7 @@ function sendSms() {
|
||||
}
|
||||
};
|
||||
|
||||
let request = sms.send(remoteNumber, text);
|
||||
let request = manager.send(remoteNumber, text);
|
||||
ok(request instanceof DOMRequest,
|
||||
"request is instanceof " + request.constructor);
|
||||
|
||||
@ -119,7 +120,7 @@ function sendSms() {
|
||||
nextRep();
|
||||
}
|
||||
} else {
|
||||
log("smsrequest returned false for sms.send");
|
||||
log("smsrequest returned false for manager.send");
|
||||
ok(false,"SMS send failed");
|
||||
cleanUp();
|
||||
}
|
||||
@ -128,7 +129,7 @@ function sendSms() {
|
||||
request.onerror = function(event) {
|
||||
log("Received 'onerror' smsrequest event.");
|
||||
ok(event.target.error, "domerror obj");
|
||||
ok(false, "sms.send request returned unexpected error: "
|
||||
ok(false, "manager.send request returned unexpected error: "
|
||||
+ event.target.error.name );
|
||||
cleanUp();
|
||||
};
|
||||
@ -158,7 +159,7 @@ function simulateIncomingSms() {
|
||||
}
|
||||
|
||||
// Callback for incoming sms
|
||||
sms.onreceived = function onreceived(event) {
|
||||
manager.onreceived = function onreceived(event) {
|
||||
log("Received 'onreceived' sms event.");
|
||||
let incomingSms = event.message;
|
||||
log("Received SMS (id: " + incomingSms.id + ").");
|
||||
@ -177,7 +178,7 @@ function getMsgs() {
|
||||
filter.delivery = "sent";
|
||||
|
||||
log("Getting the sent SMS messages.");
|
||||
let cursor = sms.getMessages(filter, false);
|
||||
let cursor = manager.getMessages(filter, false);
|
||||
ok(cursor instanceof DOMCursor,
|
||||
"cursor is instanceof " + cursor.constructor);
|
||||
|
||||
@ -200,7 +201,7 @@ function getMsgs() {
|
||||
} else {
|
||||
log("SMS getMessages returned " + foundSmsList.length +
|
||||
" messages, but expected " + smsList.length + ".");
|
||||
ok(false, "Incorrect number of messages returned by sms.getMessages");
|
||||
ok(false, "Incorrect number of messages returned by manager.getMessages");
|
||||
deleteAllMsgs(cleanUp);
|
||||
}
|
||||
}
|
||||
@ -209,7 +210,7 @@ function getMsgs() {
|
||||
cursor.onerror = function(event) {
|
||||
log("Received 'onerror' event.");
|
||||
ok(event.target.error, "domerror obj");
|
||||
log("sms.getMessages error: " + event.target.error.name);
|
||||
log("manager.getMessages error: " + event.target.error.name);
|
||||
ok(false,"Could not get SMS messages");
|
||||
cleanUp();
|
||||
};
|
||||
@ -224,7 +225,7 @@ function verifyFoundMsgs(foundSmsList) {
|
||||
}
|
||||
|
||||
function cleanUp() {
|
||||
sms.onreceived = null;
|
||||
manager.onreceived = null;
|
||||
SpecialPowers.removePermission("sms", document);
|
||||
SpecialPowers.clearUserPref("dom.sms.enabled");
|
||||
finish();
|
||||
|
@ -6,13 +6,14 @@ MARIONETTE_TIMEOUT = 60000;
|
||||
SpecialPowers.addPermission("sms", true, document);
|
||||
SpecialPowers.setBoolPref("dom.sms.enabled", true);
|
||||
|
||||
let sms = window.navigator.mozSms;
|
||||
let manager = window.navigator.mozMobileMessage;
|
||||
let numberMsgs = 10;
|
||||
let smsList = new Array();
|
||||
|
||||
function verifyInitialState() {
|
||||
log("Verifying initial state.");
|
||||
ok(sms, "mozSms");
|
||||
ok(manager instanceof MozMobileMessageManager,
|
||||
"manager is instance of " + manager.constructor);
|
||||
// Ensure test is starting clean with no existing sms messages
|
||||
deleteAllMsgs(simulateIncomingSms);
|
||||
}
|
||||
@ -21,7 +22,7 @@ function deleteAllMsgs(nextFunction) {
|
||||
let msgList = new Array();
|
||||
let filter = new MozSmsFilter;
|
||||
|
||||
let cursor = sms.getMessages(filter, false);
|
||||
let cursor = manager.getMessages(filter, false);
|
||||
ok(cursor instanceof DOMCursor,
|
||||
"cursor is instanceof " + cursor.constructor);
|
||||
|
||||
@ -46,7 +47,7 @@ function deleteAllMsgs(nextFunction) {
|
||||
cursor.onerror = function(event) {
|
||||
log("Received 'onerror' event.");
|
||||
ok(event.target.error, "domerror obj");
|
||||
log("sms.getMessages error: " + event.target.error.name);
|
||||
log("manager.getMessages error: " + event.target.error.name);
|
||||
ok(false,"Could not get SMS messages");
|
||||
cleanUp();
|
||||
};
|
||||
@ -56,7 +57,7 @@ function deleteMsgs(msgList, nextFunction) {
|
||||
let smsId = msgList.shift();
|
||||
|
||||
log("Deleting SMS (id: " + smsId + ").");
|
||||
let request = sms.delete(smsId);
|
||||
let request = manager.delete(smsId);
|
||||
ok(request instanceof DOMRequest,
|
||||
"request is instanceof " + request.constructor);
|
||||
|
||||
@ -72,7 +73,7 @@ function deleteMsgs(msgList, nextFunction) {
|
||||
}
|
||||
} else {
|
||||
log("SMS delete failed.");
|
||||
ok(false,"sms.delete request returned false");
|
||||
ok(false,"manager.delete request returned false");
|
||||
cleanUp();
|
||||
}
|
||||
};
|
||||
@ -80,7 +81,7 @@ function deleteMsgs(msgList, nextFunction) {
|
||||
request.onerror = function(event) {
|
||||
log("Received 'onerror' smsrequest event.");
|
||||
ok(event.target.error, "domerror obj");
|
||||
ok(false, "sms.delete request returned unexpected error: "
|
||||
ok(false, "manager.delete request returned unexpected error: "
|
||||
+ event.target.error.name );
|
||||
cleanUp();
|
||||
};
|
||||
@ -102,7 +103,7 @@ function simulateIncomingSms() {
|
||||
}
|
||||
|
||||
// Callback for incoming sms
|
||||
sms.onreceived = function onreceived(event) {
|
||||
manager.onreceived = function onreceived(event) {
|
||||
log("Received 'onreceived' sms event.");
|
||||
let incomingSms = event.message;
|
||||
log("Received SMS (id: " + incomingSms.id + ").");
|
||||
@ -127,7 +128,7 @@ function nextRep() {
|
||||
function markMsgRead() {
|
||||
// Mark first message read so not all will be found by filter
|
||||
log("Marking SMS (id: " + smsList[0].id + ") as read.");
|
||||
let request = sms.markMessageRead(smsList[0].id, true);
|
||||
let request = manager.markMessageRead(smsList[0].id, true);
|
||||
ok(request instanceof DOMRequest,
|
||||
"request is instanceof " + request.constructor);
|
||||
|
||||
@ -140,7 +141,7 @@ function markMsgRead() {
|
||||
getMsgs();
|
||||
} else {
|
||||
log("SMS markMessageRead failed.");
|
||||
ok(false,"sms.markMessageRead request returned false");
|
||||
ok(false,"manager.markMessageRead request returned false");
|
||||
cleanUp();
|
||||
}
|
||||
};
|
||||
@ -148,7 +149,7 @@ function markMsgRead() {
|
||||
request.onerror = function(event) {
|
||||
log("Received 'onerror' smsrequest event.");
|
||||
ok(event.target.error, "domerror obj");
|
||||
ok(false, "sms.markMessageRead request returned unexpected error: "
|
||||
ok(false, "manager.markMessageRead request returned unexpected error: "
|
||||
+ event.target.error.name );
|
||||
cleanUp();
|
||||
};
|
||||
@ -162,7 +163,7 @@ function getMsgs() {
|
||||
filter.read = false;
|
||||
|
||||
log("Getting the unread SMS messages.");
|
||||
let cursor = sms.getMessages(filter, false);
|
||||
let cursor = manager.getMessages(filter, false);
|
||||
ok(cursor instanceof DOMCursor,
|
||||
"cursor is instanceof " + cursor.constructor);
|
||||
|
||||
@ -185,7 +186,7 @@ function getMsgs() {
|
||||
} else {
|
||||
log("SMS getMessages returned " + foundSmsList.length +
|
||||
" messages, but expected " + smsList.length + ".");
|
||||
ok(false, "Incorrect number of messages returned by sms.getMessages");
|
||||
ok(false, "Incorrect number of messages returned by manager.getMessages");
|
||||
deleteAllMsgs(cleanUp);
|
||||
}
|
||||
}
|
||||
@ -194,7 +195,7 @@ function getMsgs() {
|
||||
cursor.onerror = function(event) {
|
||||
log("Received 'onerror' event.");
|
||||
ok(event.target.error, "domerror obj");
|
||||
log("sms.getMessages error: " + event.target.error.name);
|
||||
log("manager.getMessages error: " + event.target.error.name);
|
||||
ok(false,"Could not get SMS messages");
|
||||
cleanUp();
|
||||
};
|
||||
@ -209,7 +210,7 @@ function verifyFoundMsgs(foundSmsList) {
|
||||
}
|
||||
|
||||
function cleanUp() {
|
||||
sms.onreceived = null;
|
||||
manager.onreceived = null;
|
||||
SpecialPowers.removePermission("sms", document);
|
||||
SpecialPowers.clearUserPref("dom.sms.enabled");
|
||||
finish();
|
||||
|
@ -10,7 +10,7 @@ SpecialPowers.addPermission("sms", true, document);
|
||||
const REMOTE = "5559997777"; // the remote number
|
||||
const EMULATOR = "15555215554"; // the emulator's number
|
||||
|
||||
let sms = window.navigator.mozSms;
|
||||
let manager = window.navigator.mozMobileMessage;
|
||||
let inText = "Incoming SMS message. Mozilla Firefox OS!";
|
||||
let outText = "Outgoing SMS message. Mozilla Firefox OS!";
|
||||
let gotSmsOnsent = false;
|
||||
@ -24,15 +24,16 @@ let outSmsTimeStamp;
|
||||
|
||||
function verifyInitialState() {
|
||||
log("Verifying initial state.");
|
||||
ok(sms, "mozSms");
|
||||
ok(manager instanceof MozMobileMessageManager,
|
||||
"manager is instance of " + manager.constructor);
|
||||
simulateIncomingSms();
|
||||
}
|
||||
|
||||
function simulateIncomingSms() {
|
||||
log("Simulating incoming SMS.");
|
||||
|
||||
sms.onreceived = function onreceived(event) {
|
||||
log("Received 'onreceived' smsmanager event.");
|
||||
manager.onreceived = function onreceived(event) {
|
||||
log("Received 'onreceived' event.");
|
||||
let incomingSms = event.message;
|
||||
ok(incomingSms, "incoming sms");
|
||||
ok(incomingSms.id, "sms id");
|
||||
@ -59,8 +60,8 @@ function simulateIncomingSms() {
|
||||
|
||||
function sendSms() {
|
||||
log("Sending an SMS.");
|
||||
sms.onsent = function(event) {
|
||||
log("Received 'onsent' smsmanager event.");
|
||||
manager.onsent = function(event) {
|
||||
log("Received 'onsent' event.");
|
||||
gotSmsOnsent = true;
|
||||
let sentSms = event.message;
|
||||
ok(sentSms, "outgoing sms");
|
||||
@ -82,7 +83,7 @@ function sendSms() {
|
||||
if (gotSmsOnsent && gotReqOnsuccess) { getReceivedSms(); }
|
||||
};
|
||||
|
||||
let requestRet = sms.send(REMOTE, outText);
|
||||
let requestRet = manager.send(REMOTE, outText);
|
||||
ok(requestRet, "smsrequest obj returned");
|
||||
|
||||
requestRet.onsuccess = function(event) {
|
||||
@ -91,7 +92,7 @@ function sendSms() {
|
||||
if(event.target.result){
|
||||
if (gotSmsOnsent && gotReqOnsuccess) { getReceivedSms(); }
|
||||
} else {
|
||||
log("smsrequest returned false for sms.send");
|
||||
log("smsrequest returned false for manager.send");
|
||||
ok(false,"SMS send failed");
|
||||
cleanUp();
|
||||
}
|
||||
@ -100,7 +101,7 @@ function sendSms() {
|
||||
requestRet.onerror = function(event) {
|
||||
log("Received 'onerror' smsrequest event.");
|
||||
ok(event.target.error, "domerror obj");
|
||||
ok(false, "sms.send request returned unexpected error: "
|
||||
ok(false, "manager.send request returned unexpected error: "
|
||||
+ event.target.error.name );
|
||||
cleanUp();
|
||||
};
|
||||
@ -109,7 +110,7 @@ function sendSms() {
|
||||
function getReceivedSms() {
|
||||
log("Getting the received SMS message (id: " + inSmsId + ").");
|
||||
|
||||
let requestRet = sms.getMessage(inSmsId);
|
||||
let requestRet = manager.getMessage(inSmsId);
|
||||
ok(requestRet, "smsrequest obj returned");
|
||||
|
||||
requestRet.onsuccess = function(event) {
|
||||
@ -143,7 +144,7 @@ function getReceivedSms() {
|
||||
|
||||
function getSentSms() {
|
||||
log("Getting the sent SMS message (id: " + outSmsId + ").");
|
||||
let requestRet = sms.getMessage(outSmsId);
|
||||
let requestRet = manager.getMessage(outSmsId);
|
||||
ok(requestRet, "smsrequest obj returned");
|
||||
|
||||
requestRet.onsuccess = function(event) {
|
||||
@ -177,14 +178,14 @@ function getSentSms() {
|
||||
|
||||
function deleteMsgs() {
|
||||
log("Deleting SMS (id: " + inSmsId + ").");
|
||||
let requestRet = sms.delete(inSmsId);
|
||||
let requestRet = manager.delete(inSmsId);
|
||||
ok(requestRet,"smsrequest obj returned");
|
||||
|
||||
requestRet.onsuccess = function(event) {
|
||||
log("Received 'onsuccess' smsrequest event.");
|
||||
if(event.target.result){
|
||||
log("Deleting SMS (id: " + outSmsId + ").");
|
||||
let nextReqRet = sms.delete(outSmsId);
|
||||
let nextReqRet = manager.delete(outSmsId);
|
||||
ok(nextReqRet,"smsrequest obj returned");
|
||||
|
||||
nextReqRet.onsuccess = function(event) {
|
||||
@ -192,12 +193,12 @@ function deleteMsgs() {
|
||||
if(event.target.result) {
|
||||
cleanUp();
|
||||
} else {
|
||||
log("smsrequest returned false for sms.delete");
|
||||
log("smsrequest returned false for manager.delete");
|
||||
ok(false,"SMS delete failed");
|
||||
}
|
||||
};
|
||||
} else {
|
||||
log("smsrequest returned false for sms.delete");
|
||||
log("smsrequest returned false for manager.delete");
|
||||
ok(false,"SMS delete failed");
|
||||
}
|
||||
};
|
||||
@ -205,14 +206,14 @@ function deleteMsgs() {
|
||||
requestRet.onerror = function(event) {
|
||||
log("Received 'onerror' smsrequest event.");
|
||||
ok(event.target.error, "domerror obj");
|
||||
ok(false, "sms.delete request returned unexpected error: "
|
||||
ok(false, "manager.delete request returned unexpected error: "
|
||||
+ event.target.error.name );
|
||||
cleanUp();
|
||||
};
|
||||
}
|
||||
|
||||
function cleanUp() {
|
||||
sms.onreceived = null;
|
||||
manager.onreceived = null;
|
||||
SpecialPowers.removePermission("sms", document);
|
||||
SpecialPowers.clearUserPref("dom.sms.enabled");
|
||||
SpecialPowers.clearUserPref("dom.sms.requestStatusReport");
|
||||
|
@ -6,7 +6,7 @@ MARIONETTE_TIMEOUT = 60000;
|
||||
SpecialPowers.setBoolPref("dom.sms.enabled", true);
|
||||
SpecialPowers.addPermission("sms", true, document);
|
||||
|
||||
let sms = window.navigator.mozSms;
|
||||
let manager = window.navigator.mozMobileMessage;
|
||||
let myNumber = "15555215554";
|
||||
let inText = "Incoming SMS message. Mozilla Firefox OS!";
|
||||
let remoteNumber = "5559997777";
|
||||
@ -14,15 +14,16 @@ let inSmsId = 0;
|
||||
|
||||
function verifyInitialState() {
|
||||
log("Verifying initial state.");
|
||||
ok(sms, "mozSms");
|
||||
ok(manager instanceof MozMobileMessageManager,
|
||||
"manager is instance of " + manager.constructor);
|
||||
simulateIncomingSms();
|
||||
}
|
||||
|
||||
function simulateIncomingSms() {
|
||||
log("Simulating incoming SMS.");
|
||||
|
||||
sms.onreceived = function onreceived(event) {
|
||||
log("Received 'onreceived' smsmanager event.");
|
||||
manager.onreceived = function onreceived(event) {
|
||||
log("Received 'onreceived' event.");
|
||||
let incomingSms = event.message;
|
||||
ok(incomingSms, "incoming sms");
|
||||
ok(incomingSms.id, "sms id");
|
||||
@ -41,7 +42,7 @@ function simulateIncomingSms() {
|
||||
function getNonExistentMsg() {
|
||||
let msgIdNoExist = inSmsId + 1;
|
||||
log("Attempting to get non-existent message (id: " + msgIdNoExist + ").");
|
||||
let requestRet = sms.getMessage(msgIdNoExist);
|
||||
let requestRet = manager.getMessage(msgIdNoExist);
|
||||
ok(requestRet, "smsrequest obj returned");
|
||||
|
||||
requestRet.onsuccess = function(event) {
|
||||
@ -65,7 +66,7 @@ function getNonExistentMsg() {
|
||||
function getMsgInvalidId() {
|
||||
invalidId = -1;
|
||||
log("Attempting to get sms with invalid id (id: " + invalidId + ").");
|
||||
let requestRet = sms.getMessage(invalidId);
|
||||
let requestRet = manager.getMessage(invalidId);
|
||||
ok(requestRet, "smsrequest obj returned");
|
||||
|
||||
requestRet.onsuccess = function(event) {
|
||||
@ -89,7 +90,7 @@ function getMsgInvalidId() {
|
||||
|
||||
function deleteMsg() {
|
||||
log("Deleting SMS (id: " + inSmsId + ").");
|
||||
let requestRet = sms.delete(inSmsId);
|
||||
let requestRet = manager.delete(inSmsId);
|
||||
ok(requestRet,"smsrequest obj returned");
|
||||
|
||||
requestRet.onsuccess = function(event) {
|
||||
@ -102,14 +103,14 @@ function deleteMsg() {
|
||||
requestRet.onerror = function(event) {
|
||||
log("Received 'onerror' smsrequest event.");
|
||||
ok(event.target.error, "domerror obj");
|
||||
ok(false, "sms.delete request returned unexpected error: "
|
||||
ok(false, "manager.delete request returned unexpected error: "
|
||||
+ event.target.error.name );
|
||||
cleanUp();
|
||||
};
|
||||
}
|
||||
|
||||
function cleanUp() {
|
||||
sms.onreceived = null;
|
||||
manager.onreceived = null;
|
||||
SpecialPowers.removePermission("sms", document);
|
||||
SpecialPowers.setBoolPref("dom.sms.enabled", false);
|
||||
finish();
|
||||
|
@ -6,13 +6,14 @@ MARIONETTE_TIMEOUT = 60000;
|
||||
SpecialPowers.addPermission("sms", true, document);
|
||||
SpecialPowers.setBoolPref("dom.sms.enabled", true);
|
||||
|
||||
let sms = window.navigator.mozSms;
|
||||
let manager = window.navigator.mozMobileMessage;
|
||||
let numberMsgs = 10;
|
||||
let smsList = new Array();
|
||||
|
||||
function verifyInitialState() {
|
||||
log("Verifying initial state.");
|
||||
ok(sms, "mozSms");
|
||||
ok(manager instanceof MozMobileMessageManager,
|
||||
"manager is instance of " + manager.constructor);
|
||||
// Ensure test is starting clean with no existing sms messages
|
||||
deleteAllMsgs(simulateIncomingSms);
|
||||
}
|
||||
@ -25,7 +26,7 @@ function deleteAllMsgs(nextFunction) {
|
||||
let msgList = new Array();
|
||||
let smsFilter = new MozSmsFilter;
|
||||
|
||||
let cursor = sms.getMessages(smsFilter, false);
|
||||
let cursor = manager.getMessages(smsFilter, false);
|
||||
ok(cursor instanceof DOMCursor,
|
||||
"cursor is instanceof " + cursor.constructor);
|
||||
|
||||
@ -50,7 +51,7 @@ function deleteAllMsgs(nextFunction) {
|
||||
cursor.onerror = function(event) {
|
||||
log("Received 'onerror' event.");
|
||||
ok(event.target.error, "domerror obj");
|
||||
log("sms.getMessages error: " + event.target.error.name);
|
||||
log("manager.getMessages error: " + event.target.error.name);
|
||||
ok(false,"Could not get SMS messages");
|
||||
cleanUp();
|
||||
};
|
||||
@ -60,7 +61,7 @@ function deleteMsgs(msgList, nextFunction) {
|
||||
let smsId = msgList.shift();
|
||||
|
||||
log("Deleting SMS (id: " + smsId + ").");
|
||||
let request = sms.delete(smsId);
|
||||
let request = manager.delete(smsId);
|
||||
ok(request instanceof DOMRequest,
|
||||
"request is instanceof " + request.constructor);
|
||||
|
||||
@ -76,7 +77,7 @@ function deleteMsgs(msgList, nextFunction) {
|
||||
}
|
||||
} else {
|
||||
log("SMS delete failed.");
|
||||
ok(false,"sms.delete request returned false");
|
||||
ok(false,"manager.delete request returned false");
|
||||
cleanUp();
|
||||
}
|
||||
};
|
||||
@ -84,7 +85,7 @@ function deleteMsgs(msgList, nextFunction) {
|
||||
request.onerror = function(event) {
|
||||
log("Received 'onerror' smsrequest event.");
|
||||
ok(event.target.error, "domerror obj");
|
||||
ok(false, "sms.delete request returned unexpected error: "
|
||||
ok(false, "manager.delete request returned unexpected error: "
|
||||
+ event.target.error.name );
|
||||
cleanUp();
|
||||
};
|
||||
@ -106,7 +107,7 @@ function simulateIncomingSms() {
|
||||
}
|
||||
|
||||
// Callback for incoming sms
|
||||
sms.onreceived = function onreceived(event) {
|
||||
manager.onreceived = function onreceived(event) {
|
||||
log("Received 'onreceived' sms event.");
|
||||
let incomingSms = event.message;
|
||||
log("Received SMS (id: " + incomingSms.id + ").");
|
||||
@ -142,7 +143,7 @@ function getMsgs(reverse) {
|
||||
|
||||
// Note: This test is intended for getMessages, so just a basic test with
|
||||
// no filter (default); separate tests will be written for sms filtering
|
||||
let cursor = sms.getMessages(smsFilter, reverse);
|
||||
let cursor = manager.getMessages(smsFilter, reverse);
|
||||
ok(cursor instanceof DOMCursor,
|
||||
"cursor is instanceof " + cursor.constructor);
|
||||
|
||||
@ -165,7 +166,7 @@ function getMsgs(reverse) {
|
||||
} else {
|
||||
log("SMS getMessages returned " + foundSmsCount +
|
||||
" messages, but expected " + numberMsgs + ".");
|
||||
ok(false, "Incorrect number of messages returned by sms.getMessages");
|
||||
ok(false, "Incorrect number of messages returned by manager.getMessages");
|
||||
}
|
||||
verifyFoundMsgs(foundSmsList, reverse);
|
||||
}
|
||||
@ -174,7 +175,7 @@ function getMsgs(reverse) {
|
||||
cursor.onerror = function(event) {
|
||||
log("Received 'onerror' event.");
|
||||
ok(event.target.error, "domerror obj");
|
||||
log("sms.getMessages error: " + event.target.error.name);
|
||||
log("manager.getMessages error: " + event.target.error.name);
|
||||
ok(false,"Could not get SMS messages");
|
||||
cleanUp();
|
||||
};
|
||||
@ -216,7 +217,7 @@ function verifyFoundMsgs(foundSmsList, reverse) {
|
||||
}
|
||||
|
||||
function cleanUp() {
|
||||
sms.onreceived = null;
|
||||
manager.onreceived = null;
|
||||
SpecialPowers.removePermission("sms", document);
|
||||
SpecialPowers.clearUserPref("dom.sms.enabled");
|
||||
finish();
|
||||
|
@ -9,8 +9,9 @@ const PDU_MAX_USER_DATA_7BIT = 160;
|
||||
SpecialPowers.setBoolPref("dom.sms.enabled", true);
|
||||
SpecialPowers.addPermission("sms", true, document);
|
||||
|
||||
let sms = window.navigator.mozSms;
|
||||
ok(sms instanceof MozSmsManager, "mozSmsManager");
|
||||
let manager = window.navigator.mozMobileMessage;
|
||||
ok(manager instanceof MozMobileMessageManager,
|
||||
"manager is instance of " + manager.constructor);
|
||||
|
||||
let tasks = {
|
||||
// List of test fuctions. Each of them should call |tasks.next()| when
|
||||
@ -48,7 +49,7 @@ let tasks = {
|
||||
function addTest(text, segments, charsPerSegment, charsAvailableInLastSegment) {
|
||||
tasks.push(function () {
|
||||
log("Testing '" + text + "' ...");
|
||||
let info = sms.getSegmentInfoForText(text);
|
||||
let info = manager.getSegmentInfoForText(text);
|
||||
is(info.segments, segments, "info.segments");
|
||||
is(info.charsPerSegment, charsPerSegment, "info.charsPerSegment");
|
||||
is(info.charsAvailableInLastSegment, charsAvailableInLastSegment,
|
||||
@ -62,7 +63,7 @@ function addTestThrows(text) {
|
||||
tasks.push(function () {
|
||||
log("Testing '" + text + "' ...");
|
||||
try {
|
||||
let info = sms.getSegmentInfoForText(text);
|
||||
let info = manager.getSegmentInfoForText(text);
|
||||
|
||||
ok(false, "Not thrown");
|
||||
tasks.finish();
|
||||
|
@ -6,8 +6,9 @@ MARIONETTE_TIMEOUT = 40000;
|
||||
SpecialPowers.addPermission("sms", true, document);
|
||||
SpecialPowers.setBoolPref("dom.sms.enabled", true);
|
||||
|
||||
let sms = window.navigator.mozSms;
|
||||
ok(sms instanceof MozSmsManager);
|
||||
let manager = window.navigator.mozMobileMessage;
|
||||
ok(manager instanceof MozMobileMessageManager,
|
||||
"manager is instance of " + manager.constructor);
|
||||
|
||||
let pendingEmulatorCmdCount = 0;
|
||||
function sendSmsToEmulator(from, text, callback) {
|
||||
@ -59,7 +60,7 @@ function getAllMessages(callback, filter, reverse) {
|
||||
filter = new MozSmsFilter;
|
||||
}
|
||||
let messages = [];
|
||||
let request = sms.getMessages(filter, reverse || false);
|
||||
let request = manager.getMessages(filter, reverse || false);
|
||||
request.onsuccess = function(event) {
|
||||
if (!request.done) {
|
||||
messages.push(request.result);
|
||||
@ -80,7 +81,7 @@ function deleteAllMessages() {
|
||||
return;
|
||||
}
|
||||
|
||||
let request = sms.delete(message.id);
|
||||
let request = manager.delete(message.id);
|
||||
request.onsuccess = deleteAll.bind(null, messages);
|
||||
request.onerror = function (event) {
|
||||
ok(false, "failed to delete all messages");
|
||||
@ -90,17 +91,17 @@ function deleteAllMessages() {
|
||||
}
|
||||
|
||||
function sendMessage(to, body) {
|
||||
sms.onsent = function () {
|
||||
sms.onsent = null;
|
||||
manager.onsent = function () {
|
||||
manager.onsent = null;
|
||||
tasks.next();
|
||||
};
|
||||
let request = sms.send(to, body);
|
||||
let request = manager.send(to, body);
|
||||
request.onerror = tasks.finish.bind(tasks);
|
||||
}
|
||||
|
||||
function receiveMessage(from, body) {
|
||||
sms.onreceived = function () {
|
||||
sms.onreceived = null;
|
||||
manager.onreceived = function () {
|
||||
manager.onreceived = null;
|
||||
tasks.next();
|
||||
};
|
||||
sendSmsToEmulator(from, body, function (success) {
|
||||
@ -113,7 +114,7 @@ function receiveMessage(from, body) {
|
||||
function getAllThreads(callback) {
|
||||
let threads = [];
|
||||
|
||||
let cursor = sms.getThreads();
|
||||
let cursor = manager.getThreads();
|
||||
ok(cursor instanceof DOMCursor,
|
||||
"cursor is instanceof " + cursor.constructor);
|
||||
|
||||
|
@ -9,7 +9,10 @@ SpecialPowers.addPermission("sms", true, document);
|
||||
const SENDER = "5555552368"; // the remote number
|
||||
const RECEIVER = "15555215554"; // the emulator's number
|
||||
|
||||
let sms = window.navigator.mozSms;
|
||||
let manager = window.navigator.mozMobileMessage;
|
||||
ok(manager instanceof MozMobileMessageManager,
|
||||
"manager is instance of " + manager.constructor);
|
||||
|
||||
let body = "Hello SMS world!";
|
||||
|
||||
let completed = false;
|
||||
@ -19,7 +22,7 @@ runEmulatorCmd("sms send " + SENDER + " " + body, function(result) {
|
||||
completed = true;
|
||||
});
|
||||
|
||||
sms.onreceived = function onreceived(event) {
|
||||
manager.onreceived = function onreceived(event) {
|
||||
log("Received an SMS!");
|
||||
|
||||
let message = event.message;
|
||||
|
@ -9,20 +9,21 @@ SpecialPowers.addPermission("sms", true, document);
|
||||
const SENDER = "5555552368"; // the remote number
|
||||
const RECEIVER = "15555215554"; // the emulator's number
|
||||
|
||||
let sms = window.navigator.mozSms;
|
||||
let manager = window.navigator.mozMobileMessage;
|
||||
let msgText = "Mozilla Firefox OS!";
|
||||
|
||||
function verifyInitialState() {
|
||||
log("Verifying initial state.");
|
||||
ok(sms, "mozSms");
|
||||
ok(manager instanceof MozMobileMessageManager,
|
||||
"manager is instance of " + manager.constructor);
|
||||
simulateIncomingSms();
|
||||
}
|
||||
|
||||
function simulateIncomingSms() {
|
||||
log("Simulating incoming SMS.");
|
||||
|
||||
sms.onreceived = function onreceived(event) {
|
||||
log("Received 'onreceived' smsmanager event.");
|
||||
manager.onreceived = function onreceived(event) {
|
||||
log("Received 'onreceived' event.");
|
||||
let incomingSms = event.message;
|
||||
ok(incomingSms, "incoming sms");
|
||||
ok(incomingSms.id, "sms id");
|
||||
@ -46,7 +47,7 @@ function simulateIncomingSms() {
|
||||
|
||||
function verifySmsExists(incomingSms) {
|
||||
log("Getting SMS (id: " + incomingSms.id + ").");
|
||||
let requestRet = sms.getMessage(incomingSms.id);
|
||||
let requestRet = manager.getMessage(incomingSms.id);
|
||||
ok(requestRet, "smsrequest obj returned");
|
||||
|
||||
requestRet.onsuccess = function(event) {
|
||||
@ -78,7 +79,7 @@ function verifySmsExists(incomingSms) {
|
||||
|
||||
function deleteSms(smsMsgObj){
|
||||
log("Deleting SMS (id: " + smsMsgObj.id + ") using smsmsg obj parameter.");
|
||||
let requestRet = sms.delete(smsMsgObj);
|
||||
let requestRet = manager.delete(smsMsgObj);
|
||||
ok(requestRet,"smsrequest obj returned");
|
||||
|
||||
requestRet.onsuccess = function(event) {
|
||||
@ -86,7 +87,7 @@ function deleteSms(smsMsgObj){
|
||||
if(event.target.result){
|
||||
verifySmsDeleted(smsMsgObj.id);
|
||||
} else {
|
||||
log("smsrequest returned false for sms.delete");
|
||||
log("smsrequest returned false for manager.delete");
|
||||
ok(false,"SMS delete failed");
|
||||
cleanUp();
|
||||
}
|
||||
@ -95,7 +96,7 @@ function deleteSms(smsMsgObj){
|
||||
requestRet.onerror = function(event) {
|
||||
log("Received 'onerror' smsrequest event.");
|
||||
ok(event.target.error, "domerror obj");
|
||||
ok(false, "sms.delete request returned unexpected error: "
|
||||
ok(false, "manager.delete request returned unexpected error: "
|
||||
+ event.target.error.name );
|
||||
cleanUp();
|
||||
};
|
||||
@ -103,7 +104,7 @@ function deleteSms(smsMsgObj){
|
||||
|
||||
function verifySmsDeleted(smsId) {
|
||||
log("Getting SMS (id: " + smsId + ").");
|
||||
let requestRet = sms.getMessage(smsId);
|
||||
let requestRet = manager.getMessage(smsId);
|
||||
ok(requestRet, "smsrequest obj returned");
|
||||
|
||||
requestRet.onsuccess = function(event) {
|
||||
@ -127,7 +128,7 @@ function verifySmsDeleted(smsId) {
|
||||
}
|
||||
|
||||
function cleanUp() {
|
||||
sms.onreceived = null;
|
||||
manager.onreceived = null;
|
||||
SpecialPowers.removePermission("sms", document);
|
||||
SpecialPowers.setBoolPref("dom.sms.enabled", false);
|
||||
finish();
|
||||
|
Some files were not shown because too many files have changed in this diff Show More
Loading…
Reference in New Issue
Block a user