diff --git a/CLOBBER b/CLOBBER
index 07be57e6865e..537e3880f198 100644
--- a/CLOBBER
+++ b/CLOBBER
@@ -22,4 +22,8 @@
# changes to stick? As of bug 928195, this shouldn't be necessary! Please
# don't change CLOBBER for WebIDL changes any more.
+<<<<<<< local
+Bug 1092813 needs a CLOBBER
+=======
Bug 1056337 - Change the default compiler on B2G ICS to gcc 4.8.
+>>>>>>> other
diff --git a/accessible/atk/moz.build b/accessible/atk/moz.build
index 557ca5d47b23..cfd826711040 100644
--- a/accessible/atk/moz.build
+++ b/accessible/atk/moz.build
@@ -50,4 +50,4 @@ if CONFIG['MOZ_ENABLE_GTK']:
if CONFIG['MOZ_ENABLE_DBUS']:
CXXFLAGS += CONFIG['MOZ_DBUS_CFLAGS']
- include('/ipc/chromium/chromium-config.mozbuild')
+include('/ipc/chromium/chromium-config.mozbuild')
diff --git a/browser/app/macbuild/Contents/MacOS-files.in b/browser/app/macbuild/Contents/MacOS-files.in
index 32ebf105f3ee..849336bc9be6 100644
--- a/browser/app/macbuild/Contents/MacOS-files.in
+++ b/browser/app/macbuild/Contents/MacOS-files.in
@@ -5,6 +5,5 @@
/gtest/***
/pk12util
/ssltunnel
-/webapprt-stub
/xpcshell
/XUL
diff --git a/browser/components/loop/LoopRooms.jsm b/browser/components/loop/LoopRooms.jsm
index 92718ffd0659..0dbc67587bee 100644
--- a/browser/components/loop/LoopRooms.jsm
+++ b/browser/components/loop/LoopRooms.jsm
@@ -106,6 +106,11 @@ const checkForParticipantsUpdate = function(room, updatedRoom) {
let LoopRoomsInternal = {
rooms: new Map(),
+ get sessionType() {
+ return MozLoopService.userProfile ? LOOP_SESSION_TYPE.FXA :
+ LOOP_SESSION_TYPE.GUEST;
+ },
+
/**
* Fetch a list of rooms that the currently registered user is a member of.
*
@@ -131,10 +136,8 @@ let LoopRoomsInternal = {
}
// Fetch the rooms from the server.
- let sessionType = MozLoopService.userProfile ? LOOP_SESSION_TYPE.FXA :
- LOOP_SESSION_TYPE.GUEST;
let url = "/rooms" + (version ? "?version=" + encodeURIComponent(version) : "");
- let response = yield MozLoopService.hawkRequest(sessionType, url, "GET");
+ let response = yield MozLoopService.hawkRequest(this.sessionType, url, "GET");
let roomsList = JSON.parse(response.body);
if (!Array.isArray(roomsList)) {
throw new Error("Missing array of rooms in response.");
@@ -188,9 +191,7 @@ let LoopRoomsInternal = {
return;
}
- let sessionType = MozLoopService.userProfile ? LOOP_SESSION_TYPE.FXA :
- LOOP_SESSION_TYPE.GUEST;
- MozLoopService.hawkRequest(sessionType, "/rooms/" + encodeURIComponent(roomToken), "GET")
+ MozLoopService.hawkRequest(this.sessionType, "/rooms/" + encodeURIComponent(roomToken), "GET")
.then(response => {
let data = JSON.parse(response.body);
@@ -227,10 +228,7 @@ let LoopRoomsInternal = {
return;
}
- let sessionType = MozLoopService.userProfile ? LOOP_SESSION_TYPE.FXA :
- LOOP_SESSION_TYPE.GUEST;
-
- MozLoopService.hawkRequest(sessionType, "/rooms", "POST", room)
+ MozLoopService.hawkRequest(this.sessionType, "/rooms", "POST", room)
.then(response => {
let data = JSON.parse(response.body);
extend(room, data);
@@ -252,6 +250,28 @@ let LoopRoomsInternal = {
MozLoopService.openChatWindow(windowData);
},
+ /**
+ * Deletes a room.
+ *
+ * @param {String} roomToken The room token.
+ * @param {Function} callback Function that will be invoked once the operation
+ * finished. The first argument passed will be an
+ * `Error` object or `null`.
+ */
+ delete: function(roomToken, callback) {
+ // XXX bug 1092954: Before deleting a room, the client should check room
+ // membership and forceDisconnect() all current participants.
+ let room = this.rooms.get(roomToken);
+ let url = "/rooms/" + encodeURIComponent(roomToken);
+ MozLoopService.hawkRequest(this.sessionType, url, "DELETE")
+ .then(response => {
+ this.rooms.delete(roomToken);
+ eventEmitter.emit("delete", room);
+ callback(null, room);
+ }, error => callback(error)).catch(error => callback(error));
+ },
+
+
/**
* Callback used to indicate changes to rooms data on the LoopServer.
*
@@ -273,7 +293,7 @@ Object.freeze(LoopRoomsInternal);
* At this point the following events may be subscribed to:
* - 'add[:{room-id}]': A new room object was successfully added to the data
* store.
- * - 'remove[:{room-id}]': A room was successfully removed from the data store.
+ * - 'delete[:{room-id}]': A room was successfully removed from the data store.
* - 'update[:{room-id}]': A room object was successfully updated with changed
* properties in the data store.
* - 'joined[:{room-id}]': A participant joined a room.
@@ -298,6 +318,10 @@ this.LoopRooms = {
return LoopRoomsInternal.open(roomToken);
},
+ delete: function(roomToken, callback) {
+ return LoopRoomsInternal.delete(roomToken, callback);
+ },
+
promise: function(method, ...params) {
return new Promise((resolve, reject) => {
this[method](...params, (error, result) => {
diff --git a/browser/components/loop/content/js/panel.js b/browser/components/loop/content/js/panel.js
index 0bdd248ffdef..82542501d73d 100644
--- a/browser/components/loop/content/js/panel.js
+++ b/browser/components/loop/content/js/panel.js
@@ -467,8 +467,8 @@ loop.panel = (function(_, mozL10n) {
*/
var RoomEntry = React.createClass({displayName: 'RoomEntry',
propTypes: {
- openRoom: React.PropTypes.func.isRequired,
- room: React.PropTypes.instanceOf(loop.store.Room).isRequired
+ dispatcher: React.PropTypes.instanceOf(loop.Dispatcher).isRequired,
+ room: React.PropTypes.instanceOf(loop.store.Room).isRequired
},
getInitialState: function() {
@@ -480,9 +480,11 @@ loop.panel = (function(_, mozL10n) {
(nextState.urlCopied !== this.state.urlCopied);
},
- handleClickRoom: function(event) {
+ handleClickRoomUrl: function(event) {
event.preventDefault();
- this.props.openRoom(this.props.room);
+ this.props.dispatcher.dispatch(new sharedActions.OpenRoom({
+ roomToken: this.props.room.roomToken
+ }));
},
handleCopyButtonClick: function(event) {
@@ -491,6 +493,14 @@ loop.panel = (function(_, mozL10n) {
this.setState({urlCopied: true});
},
+ handleDeleteButtonClick: function(event) {
+ event.preventDefault();
+ // XXX We should prompt end user for confirmation; see bug 1092953.
+ this.props.dispatcher.dispatch(new sharedActions.DeleteRoom({
+ roomToken: this.props.room.roomToken
+ }));
+ },
+
handleMouseLeave: function(event) {
this.setState({urlCopied: false});
},
@@ -507,20 +517,22 @@ loop.panel = (function(_, mozL10n) {
"room-active": this._isActive()
});
var copyButtonClasses = React.addons.classSet({
- 'copy-link': true,
- 'checked': this.state.urlCopied
+ "copy-link": true,
+ "checked": this.state.urlCopied
});
return (
React.DOM.div({className: roomClasses, onMouseLeave: this.handleMouseLeave},
React.DOM.h2(null,
React.DOM.span({className: "room-notification"}),
- room.roomName,
+ room.roomName,
React.DOM.button({className: copyButtonClasses,
- onClick: this.handleCopyButtonClick})
+ onClick: this.handleCopyButtonClick}),
+ React.DOM.button({className: "delete-link",
+ onClick: this.handleDeleteButtonClick})
),
React.DOM.p(null,
- React.DOM.a({ref: "room", href: "#", onClick: this.handleClickRoom},
+ React.DOM.a({href: "#", onClick: this.handleClickRoomUrl},
room.roomUrl
)
)
@@ -581,12 +593,6 @@ loop.panel = (function(_, mozL10n) {
}));
},
- openRoom: function(room) {
- this.props.dispatcher.dispatch(new sharedActions.OpenRoom({
- roomToken: room.roomToken
- }));
- },
-
render: function() {
if (this.state.error) {
// XXX Better end user reporting of errors.
@@ -598,7 +604,11 @@ loop.panel = (function(_, mozL10n) {
React.DOM.h1(null, this._getListHeading()),
React.DOM.div({className: "room-list"},
this.state.rooms.map(function(room, i) {
- return RoomEntry({key: i, room: room, openRoom: this.openRoom});
+ return RoomEntry({
+ key: room.roomToken,
+ dispatcher: this.props.dispatcher,
+ room: room}
+ );
}, this)
),
React.DOM.p(null,
diff --git a/browser/components/loop/content/js/panel.jsx b/browser/components/loop/content/js/panel.jsx
index 956ed9c182f9..5143fc5b5e18 100644
--- a/browser/components/loop/content/js/panel.jsx
+++ b/browser/components/loop/content/js/panel.jsx
@@ -467,8 +467,8 @@ loop.panel = (function(_, mozL10n) {
*/
var RoomEntry = React.createClass({
propTypes: {
- openRoom: React.PropTypes.func.isRequired,
- room: React.PropTypes.instanceOf(loop.store.Room).isRequired
+ dispatcher: React.PropTypes.instanceOf(loop.Dispatcher).isRequired,
+ room: React.PropTypes.instanceOf(loop.store.Room).isRequired
},
getInitialState: function() {
@@ -480,9 +480,11 @@ loop.panel = (function(_, mozL10n) {
(nextState.urlCopied !== this.state.urlCopied);
},
- handleClickRoom: function(event) {
+ handleClickRoomUrl: function(event) {
event.preventDefault();
- this.props.openRoom(this.props.room);
+ this.props.dispatcher.dispatch(new sharedActions.OpenRoom({
+ roomToken: this.props.room.roomToken
+ }));
},
handleCopyButtonClick: function(event) {
@@ -491,6 +493,14 @@ loop.panel = (function(_, mozL10n) {
this.setState({urlCopied: true});
},
+ handleDeleteButtonClick: function(event) {
+ event.preventDefault();
+ // XXX We should prompt end user for confirmation; see bug 1092953.
+ this.props.dispatcher.dispatch(new sharedActions.DeleteRoom({
+ roomToken: this.props.room.roomToken
+ }));
+ },
+
handleMouseLeave: function(event) {
this.setState({urlCopied: false});
},
@@ -507,20 +517,22 @@ loop.panel = (function(_, mozL10n) {
"room-active": this._isActive()
});
var copyButtonClasses = React.addons.classSet({
- 'copy-link': true,
- 'checked': this.state.urlCopied
+ "copy-link": true,
+ "checked": this.state.urlCopied
});
return (
- {room.roomName}
+ {room.roomName}
-
+
{room.roomUrl}
@@ -581,12 +593,6 @@ loop.panel = (function(_, mozL10n) {
}));
},
- openRoom: function(room) {
- this.props.dispatcher.dispatch(new sharedActions.OpenRoom({
- roomToken: room.roomToken
- }));
- },
-
render: function() {
if (this.state.error) {
// XXX Better end user reporting of errors.
@@ -598,7 +604,11 @@ loop.panel = (function(_, mozL10n) {
{this._getListHeading()}
{
this.state.rooms.map(function(room, i) {
- return ;
+ return ;
}, this)
}
diff --git a/browser/components/loop/content/shared/css/panel.css b/browser/components/loop/content/shared/css/panel.css
index 4654bb6b303d..9c87f11793a5 100644
--- a/browser/components/loop/content/shared/css/panel.css
+++ b/browser/components/loop/content/shared/css/panel.css
@@ -222,37 +222,48 @@ body {
text-decoration: underline;
}
-.room-list > .room-entry > h2 > .copy-link {
+@keyframes drop-and-fade-in {
+ 0% {opacity: 0; top: -15px;}
+ 25% {opacity: 0; top: -15px;}
+ 100% {opacity: 1; top: 0px;}
+}
+
+.room-list > .room-entry > h2 > button {
display: inline-block;
+ position: relative;
width: 24px;
height: 24px;
border: none;
- margin: .1em .5em; /* relative to _this_ line's font, not the document's */
+ margin: .1em .1em .1em .5em; /* relative to _this_ line's font, not the document's */
background-color: transparent; /* override browser default for button tags */
+ top: -15px;
}
-@keyframes drop-and-fade-in {
- from { opacity: 0; transform: translateY(-10px); }
- to { opacity: 100; transform: translateY(0); }
+.room-list > .room-entry:hover > h2 > button {
+ animation: drop-and-fade-in 0.250s;
+ animation-fill-mode: forwards;
+ cursor: pointer;
}
.room-list > .room-entry:hover > h2 > .copy-link {
- background: transparent url(../img/svg/copy-16x16.svg);
- cursor: pointer;
- animation: drop-and-fade-in 0.4s;
- animation-fill-mode: forwards;
+ background-image: url(../img/icons-16x16.svg#copy);
+}
+
+.room-list > .room-entry:hover > h2 > .delete-link {
+ background-image: url(../img/icons-16x16.svg#trash);
}
/* scale this up to 1.1x and then back to the original size */
@keyframes pulse {
0%, 100% { transform: scale(1.0); }
- 50% { transform: scale(1.1); }
+ 50% { transform: scale(1.1); }
}
.room-list > .room-entry > h2 > .copy-link.checked {
- background: transparent url(../img/svg/checkmark-16x16.svg);
- animation: pulse .250s;
+ background: transparent url(../img/icons-16x16.svg#checkmark);
+ animation: pulse .150s;
animation-timing-function: ease-in-out;
+ top: 0px;
}
.room-list > .room-entry > h2 {
diff --git a/browser/components/loop/content/shared/img/icons-16x16.svg b/browser/components/loop/content/shared/img/icons-16x16.svg
index d62e062dd013..3d508fa36bfe 100644
--- a/browser/components/loop/content/shared/img/icons-16x16.svg
+++ b/browser/components/loop/content/shared/img/icons-16x16.svg
@@ -87,6 +87,37 @@ use[id$="-red"] {
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
+
@@ -98,6 +129,8 @@ use[id$="-red"] {
+
+
@@ -113,6 +146,7 @@ use[id$="-red"] {
+
diff --git a/browser/components/loop/content/shared/img/svg/checkmark-16x16.svg b/browser/components/loop/content/shared/img/svg/checkmark-16x16.svg
deleted file mode 100644
index 2ac67b1da317..000000000000
--- a/browser/components/loop/content/shared/img/svg/checkmark-16x16.svg
+++ /dev/null
@@ -1,10 +0,0 @@
-
-
-
diff --git a/browser/components/loop/content/shared/img/svg/copy-16x16.svg b/browser/components/loop/content/shared/img/svg/copy-16x16.svg
deleted file mode 100644
index 2b68a345bf5b..000000000000
--- a/browser/components/loop/content/shared/img/svg/copy-16x16.svg
+++ /dev/null
@@ -1,28 +0,0 @@
-
-
-
diff --git a/browser/components/loop/content/shared/js/actions.js b/browser/components/loop/content/shared/js/actions.js
index c444b8b461ed..52f1d2866baf 100644
--- a/browser/components/loop/content/shared/js/actions.js
+++ b/browser/components/loop/content/shared/js/actions.js
@@ -158,6 +158,22 @@ loop.shared.actions = (function() {
error: Error
}),
+ /**
+ * Deletes a room.
+ * XXX: should move to some roomActions module - refs bug 1079284
+ */
+ DeleteRoom: Action.define("deleteRoom", {
+ roomToken: String
+ }),
+
+ /**
+ * Room deletion error.
+ * XXX: should move to some roomActions module - refs bug 1079284
+ */
+ DeleteRoomError: Action.define("deleteRoomError", {
+ error: Error
+ }),
+
/**
* Retrieves room list.
* XXX: should move to some roomActions module - refs bug 1079284
diff --git a/browser/components/loop/content/shared/js/roomListStore.js b/browser/components/loop/content/shared/js/roomListStore.js
index 5c366121edc5..f281e304f913 100644
--- a/browser/components/loop/content/shared/js/roomListStore.js
+++ b/browser/components/loop/content/shared/js/roomListStore.js
@@ -71,6 +71,8 @@ loop.store = loop.store || {};
this._dispatcher.register(this, [
"createRoom",
"createRoomError",
+ "deleteRoom",
+ "deleteRoomError",
"getAllRooms",
"getAllRoomsError",
"openRoom",
@@ -139,7 +141,7 @@ loop.store = loop.store || {};
// Rooms event registration
this._mozLoop.rooms.on("add", this._onRoomAdded.bind(this));
this._mozLoop.rooms.on("update", this._onRoomUpdated.bind(this));
- this._mozLoop.rooms.on("remove", this._onRoomRemoved.bind(this));
+ this._mozLoop.rooms.on("delete", this._onRoomRemoved.bind(this));
},
/**
@@ -181,7 +183,7 @@ loop.store = loop.store || {};
},
/**
- * Executed when a room is removed.
+ * Executed when a room is deleted.
*
* @param {String} eventName The event name (unused).
* @param {Object} removedRoomData The removed room data.
@@ -194,7 +196,6 @@ loop.store = loop.store || {};
}));
},
-
/**
* Maps and sorts the raw room list received from the mozLoop API.
*
@@ -267,7 +268,7 @@ loop.store = loop.store || {};
this._mozLoop.rooms.create(roomCreationData, function(err) {
this.setStoreState({pendingCreation: false});
if (err) {
- this._dispatchAction(new sharedActions.CreateRoomError({error: err}));
+ this._dispatchAction(new sharedActions.CreateRoomError({error: err}));
}
}.bind(this));
},
@@ -284,6 +285,28 @@ loop.store = loop.store || {};
});
},
+ /**
+ * Creates a new room.
+ *
+ * @param {sharedActions.DeleteRoom} actionData The action data.
+ */
+ deleteRoom: function(actionData) {
+ this._mozLoop.rooms.delete(actionData.roomToken, function(err) {
+ if (err) {
+ this._dispatchAction(new sharedActions.DeleteRoomError({error: err}));
+ }
+ }.bind(this));
+ },
+
+ /**
+ * Executed when a room deletion error occurs.
+ *
+ * @param {sharedActions.DeleteRoomError} actionData The action data.
+ */
+ deleteRoomError: function(actionData) {
+ this.setStoreState({error: actionData.error});
+ },
+
/**
* Gather the list of all available rooms from the MozLoop API.
*/
diff --git a/browser/components/loop/jar.mn b/browser/components/loop/jar.mn
index 8e70b628b27d..d7b8046428c2 100644
--- a/browser/components/loop/jar.mn
+++ b/browser/components/loop/jar.mn
@@ -49,8 +49,6 @@ browser.jar:
content/browser/loop/shared/img/svg/glyph-account-16x16.svg (content/shared/img/svg/glyph-account-16x16.svg)
content/browser/loop/shared/img/svg/glyph-signin-16x16.svg (content/shared/img/svg/glyph-signin-16x16.svg)
content/browser/loop/shared/img/svg/glyph-signout-16x16.svg (content/shared/img/svg/glyph-signout-16x16.svg)
- content/browser/loop/shared/img/svg/copy-16x16.svg (content/shared/img/svg/copy-16x16.svg)
- content/browser/loop/shared/img/svg/checkmark-16x16.svg (content/shared/img/svg/checkmark-16x16.svg)
content/browser/loop/shared/img/audio-call-avatar.svg (content/shared/img/audio-call-avatar.svg)
content/browser/loop/shared/img/beta-ribbon.svg (content/shared/img/beta-ribbon.svg)
content/browser/loop/shared/img/icons-10x10.svg (content/shared/img/icons-10x10.svg)
diff --git a/browser/components/loop/test/desktop-local/panel_test.js b/browser/components/loop/test/desktop-local/panel_test.js
index 134cea6954eb..007a373c3625 100644
--- a/browser/components/loop/test/desktop-local/panel_test.js
+++ b/browser/components/loop/test/desktop-local/panel_test.js
@@ -639,7 +639,7 @@ describe("loop.panel", function() {
});
describe("loop.panel.RoomEntry", function() {
- var buttonNode, roomData, roomEntry, roomStore, dispatcher;
+ var dispatcher, roomData;
beforeEach(function() {
dispatcher = new loop.Dispatcher();
@@ -656,52 +656,104 @@ describe("loop.panel", function() {
],
ctime: 1405517418
};
- roomStore = new loop.store.Room(roomData);
- roomEntry = mountRoomEntry();
- buttonNode = roomEntry.getDOMNode().querySelector("button.copy-link");
});
- function mountRoomEntry() {
- return TestUtils.renderIntoDocument(loop.panel.RoomEntry({
- openRoom: sandbox.stub(),
- room: roomStore
- }));
+ function mountRoomEntry(props) {
+ return TestUtils.renderIntoDocument(loop.panel.RoomEntry(props));
}
- it("should not display copy-link button by default", function() {
- expect(buttonNode).to.not.equal(null);
- });
+ describe("Copy button", function() {
+ var roomEntry, copyButton;
- it("should copy the URL when the click event fires", function() {
- TestUtils.Simulate.click(buttonNode);
-
- sinon.assert.calledOnce(navigator.mozLoop.copyString);
- sinon.assert.calledWithExactly(navigator.mozLoop.copyString,
- roomData.roomUrl);
- });
-
- it("should set state.urlCopied when the click event fires", function() {
- TestUtils.Simulate.click(buttonNode);
-
- expect(roomEntry.state.urlCopied).to.equal(true);
- });
-
- it("should switch to displaying a check icon when the URL has been copied",
- function() {
- TestUtils.Simulate.click(buttonNode);
-
- expect(buttonNode.classList.contains("checked")).eql(true);
+ beforeEach(function() {
+ roomEntry = mountRoomEntry({
+ dispatcher: dispatcher,
+ deleteRoom: sandbox.stub(),
+ room: new loop.store.Room(roomData)
+ });
+ copyButton = roomEntry.getDOMNode().querySelector("button.copy-link");
});
- it("should not display a check icon after mouse leaves the entry",
- function() {
- var roomNode = roomEntry.getDOMNode();
- TestUtils.Simulate.click(buttonNode);
-
- TestUtils.SimulateNative.mouseOut(roomNode);
-
- expect(buttonNode.classList.contains("checked")).eql(false);
+ it("should not display a copy button by default", function() {
+ expect(copyButton).to.not.equal(null);
});
+
+ it("should copy the URL when the click event fires", function() {
+ TestUtils.Simulate.click(copyButton);
+
+ sinon.assert.calledOnce(navigator.mozLoop.copyString);
+ sinon.assert.calledWithExactly(navigator.mozLoop.copyString,
+ roomData.roomUrl);
+ });
+
+ it("should set state.urlCopied when the click event fires", function() {
+ TestUtils.Simulate.click(copyButton);
+
+ expect(roomEntry.state.urlCopied).to.equal(true);
+ });
+
+ it("should switch to displaying a check icon when the URL has been copied",
+ function() {
+ TestUtils.Simulate.click(copyButton);
+
+ expect(copyButton.classList.contains("checked")).eql(true);
+ });
+
+ it("should not display a check icon after mouse leaves the entry",
+ function() {
+ var roomNode = roomEntry.getDOMNode();
+ TestUtils.Simulate.click(copyButton);
+
+ TestUtils.SimulateNative.mouseOut(roomNode);
+
+ expect(copyButton.classList.contains("checked")).eql(false);
+ });
+ });
+
+ describe("Delete button click", function() {
+ var roomEntry, deleteButton;
+
+ beforeEach(function() {
+ roomEntry = mountRoomEntry({
+ dispatcher: dispatcher,
+ room: new loop.store.Room(roomData)
+ });
+ deleteButton = roomEntry.getDOMNode().querySelector("button.delete-link");
+ });
+
+ it("should not display a delete button by default", function() {
+ expect(deleteButton).to.not.equal(null);
+ });
+
+ it("should call the delete function when clicked", function() {
+ sandbox.stub(dispatcher, "dispatch");
+
+ TestUtils.Simulate.click(deleteButton);
+
+ sinon.assert.calledOnce(dispatcher.dispatch);
+ sinon.assert.calledWithExactly(dispatcher.dispatch,
+ new sharedActions.DeleteRoom({roomToken: roomData.roomToken}));
+ });
+ });
+
+ describe("Room URL click", function() {
+ var roomEntry;
+
+ it("should dispatch an OpenRoom action", function() {
+ sandbox.stub(dispatcher, "dispatch");
+ roomEntry = mountRoomEntry({
+ dispatcher: dispatcher,
+ room: new loop.store.Room(roomData)
+ });
+ var urlLink = roomEntry.getDOMNode().querySelector("p > a");
+
+ TestUtils.Simulate.click(urlLink);
+
+ sinon.assert.calledOnce(dispatcher.dispatch);
+ sinon.assert.calledWithExactly(dispatcher.dispatch,
+ new sharedActions.OpenRoom({roomToken: roomData.roomToken}));
+ });
+ });
});
describe("loop.panel.RoomList", function() {
@@ -775,20 +827,6 @@ describe("loop.panel", function() {
var buttonNode = view.getDOMNode().querySelector("button[disabled]");
expect(buttonNode).to.not.equal(null);
});
-
- describe("#openRoom", function() {
- it("should dispatch an OpenRoom action", function() {
- var view = createTestComponent();
- var dispatch = sandbox.stub(dispatcher, "dispatch");
-
- view.openRoom({roomToken: "42cba"});
-
- sinon.assert.calledOnce(dispatch);
- sinon.assert.calledWithExactly(dispatch, new sharedActions.OpenRoom({
- roomToken: "42cba"
- }));
- });
- });
});
describe('loop.panel.ToSView', function() {
diff --git a/browser/components/loop/test/shared/roomListStore_test.js b/browser/components/loop/test/shared/roomListStore_test.js
index 9d3db3005b16..a5a9fb690ce5 100644
--- a/browser/components/loop/test/shared/roomListStore_test.js
+++ b/browser/components/loop/test/shared/roomListStore_test.js
@@ -135,9 +135,9 @@ describe("loop.store.RoomListStore", function () {
});
});
- describe("remove", function() {
- it("should remove a room from the list", function() {
- fakeMozLoop.rooms.trigger("remove", "remove", {
+ describe("delete", function() {
+ it("should delete a room from the list", function() {
+ fakeMozLoop.rooms.trigger("delete", "delete", {
roomToken: "_nxD4V4FflQ"
});
diff --git a/browser/components/loop/test/xpcshell/test_looprooms.js b/browser/components/loop/test/xpcshell/test_looprooms.js
index de3003af5110..f221595b4305 100644
--- a/browser/components/loop/test/xpcshell/test_looprooms.js
+++ b/browser/components/loop/test/xpcshell/test_looprooms.js
@@ -262,6 +262,15 @@ add_task(function* test_createRoom() {
compareRooms(room, kCreateRoomProps);
});
+// Test if deleting a room works as expected.
+add_task(function* test_deleteRoom() {
+ let roomToken = "QzBbvGmIZWU";
+ let deletedRoom = yield LoopRooms.promise("delete", roomToken);
+ Assert.equal(deletedRoom.roomToken, roomToken);
+ let rooms = yield LoopRooms.promise("getAll");
+ Assert.ok(!rooms.some((room) => room.roomToken == roomToken));
+});
+
// Test if opening a new room window works correctly.
add_task(function* test_openRoom() {
let openedUrl;
diff --git a/browser/components/loop/ui/ui-showcase.css b/browser/components/loop/ui/ui-showcase.css
index 5d8abffa09a2..5f4a0ec1484b 100644
--- a/browser/components/loop/ui/ui-showcase.css
+++ b/browser/components/loop/ui/ui-showcase.css
@@ -162,3 +162,24 @@
/* Removes the fake video image for ended conversations */
background: none;
}
+
+/* SVG icons showcase */
+
+.svg-icon-entry {
+ width: 180px;
+ float: left;
+}
+
+.svg-icon-entry > p {
+ float: left;
+ margin-right: .5rem;
+}
+
+.svg-icon {
+ display: inline-block;
+ width: 16px;
+ height: 16px;
+ background-repeat: no-repeat;
+ background-size: 16px 16px;
+ background-position: center;
+}
diff --git a/browser/components/loop/ui/ui-showcase.js b/browser/components/loop/ui/ui-showcase.js
index d3094b981f8e..d0cd1dfd11cc 100644
--- a/browser/components/loop/ui/ui-showcase.js
+++ b/browser/components/loop/ui/ui-showcase.js
@@ -101,6 +101,41 @@
detailsButtonLabel: "Retry",
});
+ var SVGIcon = React.createClass({displayName: 'SVGIcon',
+ render: function() {
+ return (
+ React.DOM.span({className: "svg-icon", style: {
+ "background-image": "url(/content/shared/img/icons-16x16.svg#" + this.props.shapeId + ")"
+ }})
+ );
+ }
+ });
+
+ var SVGIcons = React.createClass({displayName: 'SVGIcons',
+ shapes: [
+ "audio", "audio-hover", "audio-active", "block",
+ "block-red", "block-hover", "block-active", "contacts", "contacts-hover",
+ "contacts-active", "copy", "checkmark", "google", "google-hover",
+ "google-active", "history", "history-hover", "history-active",
+ "precall", "precall-hover", "precall-active", "settings", "settings-hover",
+ "settings-active", "tag", "tag-hover", "tag-active", "trash", "unblock",
+ "unblock-hover", "unblock-active", "video", "video-hover", "video-active"
+ ],
+
+ render: function() {
+ return (
+ React.DOM.div({className: "svg-icon-list"},
+ this.shapes.map(function(shapeId, i) {
+ return React.DOM.div({className: "svg-icon-entry"},
+ React.DOM.p(null, SVGIcon({key: i, shapeId: shapeId})),
+ React.DOM.p(null, shapeId)
+ );
+ }, this)
+ )
+ );
+ }
+ });
+
var Example = React.createClass({displayName: 'Example',
makeId: function(prefix) {
return (prefix || "") + this.props.summary.toLowerCase().replace(/\s/g, "-");
@@ -490,6 +525,12 @@
UnsupportedDeviceView(null)
)
)
+ ),
+
+ Section({name: "SVG icons preview"},
+ Example({summary: "16x16"},
+ SVGIcons(null)
+ )
)
)
diff --git a/browser/components/loop/ui/ui-showcase.jsx b/browser/components/loop/ui/ui-showcase.jsx
index 6fda09c81c14..030254c4e0b3 100644
--- a/browser/components/loop/ui/ui-showcase.jsx
+++ b/browser/components/loop/ui/ui-showcase.jsx
@@ -101,6 +101,41 @@
detailsButtonLabel: "Retry",
});
+ var SVGIcon = React.createClass({
+ render: function() {
+ return (
+
+ );
+ }
+ });
+
+ var SVGIcons = React.createClass({
+ shapes: [
+ "audio", "audio-hover", "audio-active", "block",
+ "block-red", "block-hover", "block-active", "contacts", "contacts-hover",
+ "contacts-active", "copy", "checkmark", "google", "google-hover",
+ "google-active", "history", "history-hover", "history-active",
+ "precall", "precall-hover", "precall-active", "settings", "settings-hover",
+ "settings-active", "tag", "tag-hover", "tag-active", "trash", "unblock",
+ "unblock-hover", "unblock-active", "video", "video-hover", "video-active"
+ ],
+
+ render: function() {
+ return (
+
{
+ this.shapes.map(function(shapeId, i) {
+ return
;
+ }, this)
+ }
+ );
+ }
+ });
+
var Example = React.createClass({
makeId: function(prefix) {
return (prefix || "") + this.props.summary.toLowerCase().replace(/\s/g, "-");
@@ -492,6 +527,12 @@
+
+
);
}
diff --git a/browser/installer/package-manifest.in b/browser/installer/package-manifest.in
index 7cbeb3b8c7df..125354ff90a7 100644
--- a/browser/installer/package-manifest.in
+++ b/browser/installer/package-manifest.in
@@ -856,11 +856,7 @@ bin/libfreebl_32int64_3.so
#ifdef XP_WIN
@BINPATH@/webapp-uninstaller@BIN_SUFFIX@
#endif
-#ifdef XP_MACOSX
-@APPNAME@/Contents/MacOS/webapprt-stub@BIN_SUFFIX@
-#else
@BINPATH@/webapprt-stub@BIN_SUFFIX@
-#endif
@BINPATH@/webapprt/webapprt.ini
@BINPATH@/webapprt/chrome.manifest
@BINPATH@/webapprt/chrome/webapprt@JAREXT@
diff --git a/build/win32/mozconfig.vs2013-win64 b/build/win32/mozconfig.vs2013-win64
index d62635f3e973..0adf6cc05e67 100644
--- a/build/win32/mozconfig.vs2013-win64
+++ b/build/win32/mozconfig.vs2013-win64
@@ -4,18 +4,18 @@ export WIN32_REDIST_DIR=${_VSPATH}/VC/redist/x86/Microsoft.VC120.CRT
## moz tools location for 64-bit builders ##
export MOZ_TOOLS=C:/mozilla-build/moztools
-## includes: win8 sdk includes, winrt headers for metro, msvc std library, directx sdk for d3d9 ##
-export INCLUDE=/c/Program\ Files\ \(x86\)/Windows\ Kits/8.0/include/shared:/c/Program\ Files\ \(x86\)/Windows\ Kits/8.0/include/um:/c/Program\ Files\ \(x86\)/Windows\ Kits/8.0/include/winrt:/c/Program\ Files\ \(x86\)/Windows\ Kits/8.0/include/winrt/wrl:/c/Program\ Files\ \(x86\)/Windows\ Kits/8.0/include/winrt/wrl/wrappers:${_VSPATH}/vc/include:${_VSPATH}/vc/atlmfc/include:/c/tools/sdks/dx10/include
+## includes: win8.1 sdk includes, winrt headers for metro, msvc std library, directx sdk for d3d9 ##
+export INCLUDE=/c/Program\ Files\ \(x86\)/Windows\ Kits/8.1/include/shared:/c/Program\ Files\ \(x86\)/Windows\ Kits/8.1/include/um:/c/Program\ Files\ \(x86\)/Windows\ Kits/8.1/include/winrt:/c/Program\ Files\ \(x86\)/Windows\ Kits/8.1/include/winrt/wrl:/c/Program\ Files\ \(x86\)/Windows\ Kits/8.1/include/winrt/wrl/wrappers:${_VSPATH}/vc/include:${_VSPATH}/vc/atlmfc/include:/c/tools/sdks/dx10/include
-## libs: win8 sdk x86 (32-bit) libs, msvc (32-bit) std library, msvc atl libs, directx sdk (32-bit) for d3d9 ##
-export LIBPATH=/c/Program\ Files\ \(x86\)/Windows\ Kits/8.0/Lib/win8/um/x86:${_VSPATH}/vc/lib:${_VSPATH}/vc/atlmfc/lib:/c/tools/sdks/dx10/lib
-export LIB=/c/Program\ Files\ \(x86\)/Windows\ Kits/8.0/Lib/win8/um/x86:${_VSPATH}/vc/lib:${_VSPATH}/vc/atlmfc/lib:/c/tools/sdks/dx10/lib
+## libs: win8.1 sdk x86 (32-bit) libs, msvc (32-bit) std library, msvc atl libs, directx sdk (32-bit) for d3d9 ##
+export LIBPATH=/c/Program\ Files\ \(x86\)/Windows\ Kits/8.1/Lib/winv6.3/um/x86:${_VSPATH}/vc/lib:${_VSPATH}/vc/atlmfc/lib:/c/tools/sdks/dx10/lib
+export LIB=/c/Program\ Files\ \(x86\)/Windows\ Kits/8.1/Lib/winv6.3/um/x86:${_VSPATH}/vc/lib:${_VSPATH}/vc/atlmfc/lib:/c/tools/sdks/dx10/lib
-## paths: win8 sdk x86 (32-bit) tools, msvc (64-bit compiling 32-bit) build toolchain, moz tools ##
-export PATH="/c/Program Files (x86)/Windows Kits/8.0/bin/x86:${_VSPATH}/Common7/IDE:${_VSPATH}/VC/BIN/amd64_x86:${_VSPATH}/VC/BIN/amd64:${_VSPATH}/Common7/Tools:${_VSPATH}/VC/VCPackages:/c/mozilla-build/moztools:${PATH}"
+## paths: win8.1 sdk x86 (32-bit) tools, msvc (64-bit compiling 32-bit) build toolchain, moz tools ##
+export PATH="/c/Program Files (x86)/Windows Kits/8.1/bin/x86:${_VSPATH}/Common7/IDE:${_VSPATH}/VC/BIN/amd64_x86:${_VSPATH}/VC/BIN/amd64:${_VSPATH}/Common7/Tools:${_VSPATH}/VC/VCPackages:/c/mozilla-build/moztools:${PATH}"
## WindowsSDKDir ##
-export WINDOWSSDKDIR="/c/Program Files (x86)/Windows Kits/8.0/"
+export WINDOWSSDKDIR="/c/Program Files (x86)/Windows Kits/8.1/"
. $topsrcdir/build/mozconfig.vs-common
diff --git a/build/win64/mozconfig.vs2013 b/build/win64/mozconfig.vs2013
index f4d48fc81674..52fa311b0497 100644
--- a/build/win64/mozconfig.vs2013
+++ b/build/win64/mozconfig.vs2013
@@ -1,18 +1,18 @@
_VSPATH="/c/tools/vs2013"
export WIN32_REDIST_DIR=${_VSPATH}/VC/redist/x64/Microsoft.VC120.CRT
-## includes: win8 sdk includes, winrt headers for metro, msvc 10 std library, directx sdk for d3d9 ##
-export INCLUDE=/c/Program\ Files\ \(x86\)/Windows\ Kits/8.0/include/shared:/c/Program\ Files\ \(x86\)/Windows\ Kits/8.0/include/um:/c/Program\ Files\ \(x86\)/Windows\ Kits/8.0/include/winrt:/c/Program\ Files\ \(x86\)/Windows\ Kits/8.0/include/winrt/wrl:/c/Program\ Files\ \(x86\)/Windows\ Kits/8.0/include/winrt/wrl/wrappers:${_VSPATH}/vc/include:${_VSPATH}/vc/atlmfc/include:/c/tools/sdks/dx10/include
+## includes: win8.1 sdk includes, winrt headers for metro, msvc std library, directx sdk for d3d9 ##
+export INCLUDE=/c/Program\ Files\ \(x86\)/Windows\ Kits/8.1/include/shared:/c/Program\ Files\ \(x86\)/Windows\ Kits/8.1/include/um:/c/Program\ Files\ \(x86\)/Windows\ Kits/8.1/include/winrt:/c/Program\ Files\ \(x86\)/Windows\ Kits/8.1/include/winrt/wrl:/c/Program\ Files\ \(x86\)/Windows\ Kits/8.1/include/winrt/wrl/wrappers:${_VSPATH}/vc/include:${_VSPATH}/vc/atlmfc/include:/c/tools/sdks/dx10/include
-## libs: win8 sdk x64 (64-bit) libs, msvc 10 (64-bit) std library, msvc 10 atl libs, directx sdk (64-bit) for d3d9 ##
-export LIBPATH=/c/Program\ Files\ \(x86\)/Windows\ Kits/8.0/Lib/win8/um/x64:${_VSPATH}/vc/lib/amd64:${_VSPATH}/vc/atlmfc/lib/amd64:/c/tools/sdks/dx10/lib/x64
-export LIB=/c/Program\ Files\ \(x86\)/Windows\ Kits/8.0/Lib/win8/um/x64:${_VSPATH}/vc/lib/amd64:${_VSPATH}/vc/atlmfc/lib/amd64:/c/tools/sdks/dx10/lib/x64
+## libs: win8.1 sdk x64 (64-bit) libs, msvc (64-bit) std library, msvc atl libs, directx sdk (64-bit) for d3d9 ##
+export LIBPATH=/c/Program\ Files\ \(x86\)/Windows\ Kits/8.1/Lib/winv6.3/um/x64:${_VSPATH}/vc/lib/amd64:${_VSPATH}/vc/atlmfc/lib/amd64:/c/tools/sdks/dx10/lib/x64
+export LIB=/c/Program\ Files\ \(x86\)/Windows\ Kits/8.1/Lib/winv6.3/um/x64:${_VSPATH}/vc/lib/amd64:${_VSPATH}/vc/atlmfc/lib/amd64:/c/tools/sdks/dx10/lib/x64
-## paths: win8 sdk x64 (64-bit) tools, msvc 10 (64-bit) build toolchain, moz tools ##
-export PATH="/c/Program Files (x86)/Windows Kits/8.0/bin/x64:${_VSPATH}/Common7/IDE:${_VSPATH}/VC/BIN/amd64:${_VSPATH}/VC/BIN/x86_amd64:${_VSPATH}/VC/BIN:${_VSPATH}/Common7/Tools:${_VSPATH}/VC/VCPackages:${PATH}"
+## paths: win8.1 sdk x64 (64-bit) tools, msvc (64-bit) build toolchain, moz tools ##
+export PATH="/c/Program Files (x86)/Windows Kits/8.1/bin/x64:${_VSPATH}/Common7/IDE:${_VSPATH}/VC/BIN/amd64:${_VSPATH}/VC/BIN/x86_amd64:${_VSPATH}/VC/BIN:${_VSPATH}/Common7/Tools:${_VSPATH}/VC/VCPackages:${PATH}"
## WindowsSDKDir ##
-export WINDOWSSDKDIR="/c/Program Files (x86)/Windows Kits/8.0/"
+export WINDOWSSDKDIR="/c/Program Files (x86)/Windows Kits/8.1/"
. $topsrcdir/build/mozconfig.vs-common
diff --git a/docshell/test/navigation/mochitest.ini b/docshell/test/navigation/mochitest.ini
index b7514ba66cbe..ad906f146aae 100644
--- a/docshell/test/navigation/mochitest.ini
+++ b/docshell/test/navigation/mochitest.ini
@@ -44,7 +44,7 @@ skip-if = (buildapp == 'b2g' && toolkit != 'gonk') #Bug 931116, b2g desktop spec
[test_popup-navigates-children.html]
skip-if = buildapp == 'b2g' # b2g(Needs multiple window.open support, also uses docshelltreenode) b2g-debug(Needs multiple window.open support, also uses docshelltreenode) b2g-desktop(Needs multiple window.open support, also uses docshelltreenode)
[test_reserved.html]
-skip-if = (buildapp == 'b2g' && (toolkit != 'gonk' || debug))
+skip-if = (buildapp == 'b2g' && (toolkit != 'gonk' || debug)) || android_version == '10' #too slow on Android 2.3 aws only; bug 1030403
[test_sessionhistory.html]
skip-if = (buildapp == 'b2g' && (toolkit != 'gonk' || debug)) || toolkit == 'android' #RANDOM # b2g-debug(Perma-orange on debug emulator builds) b2g-desktop(Bug 931116, b2g desktop specific, initial triage)
[test_sibling-matching-parent.html]
diff --git a/dom/canvas/test/webgl-mochitest.ini b/dom/canvas/test/webgl-mochitest.ini
index ece220bbd5ef..a48356ab0a69 100644
--- a/dom/canvas/test/webgl-mochitest.ini
+++ b/dom/canvas/test/webgl-mochitest.ini
@@ -11,6 +11,7 @@ support-files =
[webgl-mochitest/test_fb_param_crash.html]
[webgl-mochitest/test_highp_fs.html]
[webgl-mochitest/test_no_arr_points.html]
+skip-if = android_version == '10' #Android 2.3 aws only; bug 1030942
[webgl-mochitest/test_noprog_draw.html]
[webgl-mochitest/test_privileged_exts.html]
[webgl-mochitest/test_texsubimage_float.html]
diff --git a/dom/html/test/mochitest.ini b/dom/html/test/mochitest.ini
index 69c55e93fe7d..4384aaec9ae1 100644
--- a/dom/html/test/mochitest.ini
+++ b/dom/html/test/mochitest.ini
@@ -395,7 +395,7 @@ skip-if = (buildapp == 'b2g' && toolkit != 'gonk') #Bug 931116, b2g desktop spec
[test_bug658746.html]
[test_bug659596.html]
[test_bug659743.xml]
-skip-if = (buildapp == 'b2g' && toolkit != 'gonk') #Bug 931116, b2g desktop specific, initial triage
+skip-if = (buildapp == 'b2g' && toolkit != 'gonk') || android_version == '10' #Bug 931116, b2g desktop specific, initial triage #Android 2.3 aws only; bug 1031103
[test_bug660663.html]
[test_bug660959-1.html]
[test_bug660959-2.html]
diff --git a/dom/ipc/ContentChild.cpp b/dom/ipc/ContentChild.cpp
index bf7e4cd900ca..40990de58979 100644
--- a/dom/ipc/ContentChild.cpp
+++ b/dom/ipc/ContentChild.cpp
@@ -1907,6 +1907,17 @@ ContentChild::RecvGeolocationUpdate(const GeoPosition& somewhere)
return true;
}
+bool
+ContentChild::RecvGeolocationError(const uint16_t& errorCode)
+{
+ nsCOMPtr
gs = do_GetService("@mozilla.org/geolocation/service;1");
+ if (!gs) {
+ return true;
+ }
+ gs->NotifyError(errorCode);
+ return true;
+}
+
bool
ContentChild::RecvUpdateDictionaryList(const InfallibleTArray& aDictionaries)
{
diff --git a/dom/ipc/ContentChild.h b/dom/ipc/ContentChild.h
index 60ec6598ea77..20a5d3e279aa 100644
--- a/dom/ipc/ContentChild.h
+++ b/dom/ipc/ContentChild.h
@@ -305,6 +305,8 @@ public:
virtual bool RecvGeolocationUpdate(const GeoPosition& somewhere) MOZ_OVERRIDE;
+ virtual bool RecvGeolocationError(const uint16_t& errorCode) MOZ_OVERRIDE;
+
virtual bool RecvUpdateDictionaryList(const InfallibleTArray& aDictionaries) MOZ_OVERRIDE;
virtual bool RecvAddPermission(const IPC::Permission& permission) MOZ_OVERRIDE;
diff --git a/dom/ipc/ContentParent.cpp b/dom/ipc/ContentParent.cpp
index 128cfe9dd20d..8050f60c8545 100755
--- a/dom/ipc/ContentParent.cpp
+++ b/dom/ipc/ContentParent.cpp
@@ -93,6 +93,7 @@
#include "nsICycleCollectorListener.h"
#include "nsIDocument.h"
#include "nsIDOMGeoGeolocation.h"
+#include "nsIDOMGeoPositionError.h"
#include "mozilla/dom/WakeLock.h"
#include "nsIDOMWindow.h"
#include "nsIExternalProtocolService.h"
@@ -2590,6 +2591,7 @@ NS_INTERFACE_MAP_BEGIN_CYCLE_COLLECTION(ContentParent)
NS_INTERFACE_MAP_ENTRY(nsIContentParent)
NS_INTERFACE_MAP_ENTRY(nsIObserver)
NS_INTERFACE_MAP_ENTRY(nsIDOMGeoPositionCallback)
+ NS_INTERFACE_MAP_ENTRY(nsIDOMGeoPositionErrorCallback)
NS_INTERFACE_MAP_ENTRY_AMBIGUOUS(nsISupports, nsIObserver)
NS_INTERFACE_MAP_END
@@ -3689,7 +3691,7 @@ ContentParent::RecvFilePathUpdateNotify(const nsString& aType,
}
static int32_t
-AddGeolocationListener(nsIDOMGeoPositionCallback* watcher, bool highAccuracy)
+AddGeolocationListener(nsIDOMGeoPositionCallback* watcher, nsIDOMGeoPositionErrorCallback* errorCallBack, bool highAccuracy)
{
nsCOMPtr geo = do_GetService("@mozilla.org/geolocation;1");
if (!geo) {
@@ -3701,7 +3703,7 @@ AddGeolocationListener(nsIDOMGeoPositionCallback* watcher, bool highAccuracy)
options->mMaximumAge = 0;
options->mEnableHighAccuracy = highAccuracy;
int32_t retval = 1;
- geo->WatchPosition(watcher, nullptr, options, &retval);
+ geo->WatchPosition(watcher, errorCallBack, options, &retval);
return retval;
}
@@ -3722,7 +3724,7 @@ ContentParent::RecvAddGeolocationListener(const IPC::Principal& aPrincipal,
// To ensure no geolocation updates are skipped, we always force the
// creation of a new listener.
RecvRemoveGeolocationListener();
- mGeolocationWatchID = AddGeolocationListener(this, aHighAccuracy);
+ mGeolocationWatchID = AddGeolocationListener(this, this, aHighAccuracy);
return true;
}
@@ -3747,7 +3749,7 @@ ContentParent::RecvSetGeolocationHigherAccuracy(const bool& aEnable)
// so this check allows us to forgo securing privileges.
if (mGeolocationWatchID != -1) {
RecvRemoveGeolocationListener();
- mGeolocationWatchID = AddGeolocationListener(this, aEnable);
+ mGeolocationWatchID = AddGeolocationListener(this, this, aEnable);
}
return true;
}
@@ -3759,6 +3761,17 @@ ContentParent::HandleEvent(nsIDOMGeoPosition* postion)
return NS_OK;
}
+NS_IMETHODIMP
+ContentParent::HandleEvent(nsIDOMGeoPositionError* postionError)
+{
+ int16_t errorCode;
+ nsresult rv;
+ rv = postionError->GetCode(&errorCode);
+ NS_ENSURE_SUCCESS(rv,rv);
+ unused << SendGeolocationError(errorCode);
+ return NS_OK;
+}
+
nsConsoleService *
ContentParent::GetConsoleService()
{
diff --git a/dom/ipc/ContentParent.h b/dom/ipc/ContentParent.h
index fc96b196fc07..5ab32d06ffe6 100644
--- a/dom/ipc/ContentParent.h
+++ b/dom/ipc/ContentParent.h
@@ -22,6 +22,7 @@
#include "nsIObserver.h"
#include "nsIThreadInternal.h"
#include "nsIDOMGeoPositionCallback.h"
+#include "nsIDOMGeoPositionErrorCallback.h"
#include "PermissionMessageUtils.h"
#define CHILD_PROCESS_SHUTDOWN_MESSAGE NS_LITERAL_STRING("child-process-shutdown")
@@ -68,6 +69,7 @@ class ContentParent MOZ_FINAL : public PContentParent
, public nsIContentParent
, public nsIObserver
, public nsIDOMGeoPositionCallback
+ , public nsIDOMGeoPositionErrorCallback
, public mozilla::LinkedListElement
{
typedef mozilla::ipc::GeckoChildProcessHost GeckoChildProcessHost;
@@ -160,6 +162,7 @@ public:
NS_DECL_CYCLE_COLLECTING_ISUPPORTS
NS_DECL_NSIOBSERVER
NS_DECL_NSIDOMGEOPOSITIONCALLBACK
+ NS_DECL_NSIDOMGEOPOSITIONERRORCALLBACK
/**
* MessageManagerCallback methods that we override.
diff --git a/dom/ipc/PContent.ipdl b/dom/ipc/PContent.ipdl
index ed1ada4546d6..e9945b39cdb6 100644
--- a/dom/ipc/PContent.ipdl
+++ b/dom/ipc/PContent.ipdl
@@ -449,6 +449,8 @@ child:
GeolocationUpdate(GeoPosition somewhere);
+ GeolocationError(uint16_t errorCode);
+
UpdateDictionaryList(nsString[] dictionaries);
// nsIPermissionManager messages
diff --git a/dom/media/tests/mochitest/mochitest.ini b/dom/media/tests/mochitest/mochitest.ini
index 09870566e1a0..0cc509376c34 100644
--- a/dom/media/tests/mochitest/mochitest.ini
+++ b/dom/media/tests/mochitest/mochitest.ini
@@ -1,5 +1,5 @@
[DEFAULT]
-skip-if = (os == 'win' && contentSandbox != 'off') # contentSandbox(Bug 1042735)
+skip-if = (os == 'win' && contentSandbox != 'off') || android_version == '10' # contentSandbox(Bug 1042735) #Android 2.3 only; bug 981881
support-files =
head.js
constraints.js
diff --git a/dom/permission/tests/mochitest-bt.ini b/dom/permission/tests/mochitest-bt.ini
index a4b6389d370c..f0a61bf2cace 100644
--- a/dom/permission/tests/mochitest-bt.ini
+++ b/dom/permission/tests/mochitest-bt.ini
@@ -1 +1,2 @@
[test_bluetooth.html]
+skip-if = (toolkit == 'gonk' && debug) # bug 1093079
diff --git a/dom/tests/unit/test_geolocation_position_unavailable.js b/dom/tests/unit/test_geolocation_position_unavailable.js
new file mode 100644
index 000000000000..77c1d4717202
--- /dev/null
+++ b/dom/tests/unit/test_geolocation_position_unavailable.js
@@ -0,0 +1,36 @@
+const Cc = Components.classes;
+const Ci = Components.interfaces;
+const Cu = Components.utils;
+const Cr = Components.results;
+
+
+function successCallback() {
+ do_check_true(false);
+ do_test_finished();
+}
+
+function errorCallback(err) {
+ do_check_eq(Ci.nsIDOMGeoPositionError.POSITION_UNAVAILABLE, err.code);
+ do_test_finished();
+}
+
+function run_test()
+{
+ do_test_pending();
+
+ if (Cc["@mozilla.org/xre/app-info;1"].getService(Ci.nsIXULRuntime)
+ .processType == Ci.nsIXULRuntime.PROCESS_TYPE_DEFAULT) {
+ // XPCShell does not get a profile by default. The geolocation service
+ // depends on the settings service which uses IndexedDB and IndexedDB
+ // needs a place where it can store databases.
+ do_get_profile();
+
+ var prefs = Cc["@mozilla.org/preferences-service;1"].getService(Ci.nsIPrefBranch);
+ prefs.setBoolPref("geo.wifi.scan", false);
+ prefs.setCharPref("geo.wifi.uri", "UrlNotUsedHere:");
+ prefs.setBoolPref("dom.testing.ignore_ipc_principal", true);
+ }
+
+ geolocation = Cc["@mozilla.org/geolocation;1"].getService(Ci.nsISupports);
+ geolocation.getCurrentPosition(successCallback, errorCallback);
+}
diff --git a/dom/tests/unit/test_geolocation_position_unavailable_wrap.js b/dom/tests/unit/test_geolocation_position_unavailable_wrap.js
new file mode 100644
index 000000000000..585c7511a791
--- /dev/null
+++ b/dom/tests/unit/test_geolocation_position_unavailable_wrap.js
@@ -0,0 +1,13 @@
+const Cc = Components.classes;
+const Ci = Components.interfaces;
+const Cu = Components.utils;
+
+
+function run_test() {
+ var prefs = Cc["@mozilla.org/preferences-service;1"].getService(Ci.nsIPrefBranch);
+ prefs.setBoolPref("geo.wifi.scan", false);
+
+ prefs.setCharPref("geo.wifi.uri", "UrlNotUsedHere");
+ prefs.setBoolPref("dom.testing.ignore_ipc_principal", true);
+ run_test_in_child("./test_geolocation_position_unavailable.js");
+}
diff --git a/dom/tests/unit/xpcshell.ini b/dom/tests/unit/xpcshell.ini
index 4db9a9eb71b3..5eed85620e63 100644
--- a/dom/tests/unit/xpcshell.ini
+++ b/dom/tests/unit/xpcshell.ini
@@ -18,4 +18,8 @@ skip-if = os == "mac" || os == "android"
skip-if = os == "android"
[test_geolocation_reset_accuracy_wrap.js]
skip-if = os == "mac" || os == "android"
+[test_geolocation_position_unavailable.js]
+skip-if = os == "android"
+[test_geolocation_position_unavailable_wrap.js]
+skip-if = os == "mac" || os == "android"
[test_PromiseDebugging.js]
diff --git a/ipc/glue/MessageChannel.cpp b/ipc/glue/MessageChannel.cpp
index 2703f8411626..579a1809489c 100644
--- a/ipc/glue/MessageChannel.cpp
+++ b/ipc/glue/MessageChannel.cpp
@@ -747,7 +747,7 @@ MessageChannel::SendAndWait(Message* aMsg, Message* aReply)
MOZ_ASSERT(mRecvd->type() == replyType, "wrong reply type");
MOZ_ASSERT(mRecvd->seqno() == replySeqno);
- *aReply = *mRecvd;
+ *aReply = Move(*mRecvd);
mRecvd = nullptr;
return true;
}
@@ -838,10 +838,10 @@ MessageChannel::Call(Message* aMsg, Message* aReply)
if ((it = mOutOfTurnReplies.find(mInterruptStack.top().seqno()))
!= mOutOfTurnReplies.end())
{
- recvd = it->second;
+ recvd = Move(it->second);
mOutOfTurnReplies.erase(it);
} else if (!mPending.empty()) {
- recvd = mPending.front();
+ recvd = Move(mPending.front());
mPending.pop_front();
} else {
// because of subtleties with nested event loops, it's possible
@@ -882,7 +882,7 @@ MessageChannel::Call(Message* aMsg, Message* aReply)
if ((mSide == ChildSide && recvd.seqno() > outcall.seqno()) ||
(mSide != ChildSide && recvd.seqno() < outcall.seqno()))
{
- mOutOfTurnReplies[recvd.seqno()] = recvd;
+ mOutOfTurnReplies[recvd.seqno()] = Move(recvd);
continue;
}
@@ -896,8 +896,9 @@ MessageChannel::Call(Message* aMsg, Message* aReply)
// this frame and return the reply.
mInterruptStack.pop();
- if (!recvd.is_reply_error()) {
- *aReply = recvd;
+ bool is_reply_error = recvd.is_reply_error();
+ if (!is_reply_error) {
+ *aReply = Move(recvd);
}
// If we have no more pending out calls waiting on replies, then
@@ -906,7 +907,7 @@ MessageChannel::Call(Message* aMsg, Message* aReply)
"still have pending replies with no pending out-calls",
true);
- return !recvd.is_reply_error();
+ return !is_reply_error;
}
// Dispatch an Interrupt in-call. Snapshot the current stack depth while we
@@ -1017,7 +1018,7 @@ MessageChannel::OnMaybeDequeueOne()
if (IsOnCxxStack() && recvd.is_interrupt() && recvd.is_reply()) {
// We probably just received a reply in a nested loop for an
// Interrupt call sent before entering that loop.
- mOutOfTurnReplies[recvd.seqno()] = recvd;
+ mOutOfTurnReplies[recvd.seqno()] = Move(recvd);
return false;
}
diff --git a/layout/style/test/mochitest.ini b/layout/style/test/mochitest.ini
index 50d950977216..8d669e1ed44f 100644
--- a/layout/style/test/mochitest.ini
+++ b/layout/style/test/mochitest.ini
@@ -157,7 +157,7 @@ skip-if = toolkit == 'android'
[test_initial_storage.html]
[test_keyframes_rules.html]
[test_media_queries.html]
-skip-if = (toolkit == 'gonk' && debug) #debug-only failure; timed out
+skip-if = (toolkit == 'gonk' && debug) || android_version == '10' #debug-only failure; timed out #Android 2.3 aws only; bug 1030419
[test_media_queries_dynamic.html]
[test_media_queries_dynamic_xbl.html]
[test_media_query_list.html]
@@ -170,7 +170,6 @@ skip-if = (toolkit == 'gonk' && debug) #debug-only failure; timed out
[test_parse_url.html]
[test_parser_diagnostics_unprintables.html]
[test_pixel_lengths.html]
-skip-if = true # bug 891840 - intermittent crashes
[test_pointer-events.html]
[test_position_sticky.html]
support-files = file_position_sticky.html
@@ -201,6 +200,7 @@ skip-if = (toolkit == 'gonk' && debug) || toolkit == 'android' #bug 775227 #debu
[test_transitions_and_restyles.html]
[test_transitions_and_zoom.html]
[test_transitions_cancel_near_end.html]
+skip-if = android_version == '10' #Android 2.3 aws only; bug 1030432
[test_transitions_computed_values.html]
[test_transitions_computed_value_combinations.html]
[test_transitions_events.html]
diff --git a/security/pkix/lib/pkixcert.cpp b/security/pkix/lib/pkixcert.cpp
index 1ce0dbf595f7..73a7eca99715 100644
--- a/security/pkix/lib/pkixcert.cpp
+++ b/security/pkix/lib/pkixcert.cpp
@@ -222,6 +222,10 @@ BackCert::RememberExtension(Reader& extnID, const Input& extnValue,
static const uint8_t id_pe_authorityInfoAccess[] = {
0x2b, 0x06, 0x01, 0x05, 0x05, 0x07, 0x01, 0x01
};
+ // python DottedOIDToCode.py id-pkix-ocsp-nocheck 1.3.6.1.5.5.7.48.1.5
+ static const uint8_t id_pkix_ocsp_nocheck[] = {
+ 0x2b, 0x06, 0x01, 0x05, 0x05, 0x07, 0x30, 0x01, 0x05
+ };
// python DottedOIDToCode.py Netscape-certificate-type 2.16.840.1.113730.1.1
static const uint8_t Netscape_certificate_type[] = {
0x60, 0x86, 0x48, 0x01, 0x86, 0xf8, 0x42, 0x01, 0x01
@@ -237,6 +241,17 @@ BackCert::RememberExtension(Reader& extnID, const Input& extnValue,
// ignore the extension.
Input dummyPolicyConstraints;
+ // We don't need to save the contents of this extension if it is present. We
+ // just need to handle its presence (it is essentially ignored right now).
+ Input dummyOCSPNocheck;
+
+ // For compatibility reasons, for some extensions we have to allow empty
+ // extension values. This would normally interfere with our duplicate
+ // extension checking code. However, as long as the extensions we allow to
+ // have empty values are also the ones we implicitly allow duplicates of,
+ // this will work fine.
+ bool emptyValueAllowed = false;
+
// RFC says "Conforming CAs MUST mark this extension as non-critical" for
// both authorityKeyIdentifier and subjectKeyIdentifier, and we do not use
// them for anything, so we totally ignore them here.
@@ -259,6 +274,17 @@ BackCert::RememberExtension(Reader& extnID, const Input& extnValue,
out = &inhibitAnyPolicy;
} else if (extnID.MatchRest(id_pe_authorityInfoAccess)) {
out = &authorityInfoAccess;
+ } else if (extnID.MatchRest(id_pkix_ocsp_nocheck) && critical) {
+ // We need to make sure we don't reject delegated OCSP response signing
+ // certificates that contain the id-pkix-ocsp-nocheck extension marked as
+ // critical when validating OCSP responses. Without this, an application
+ // that implements soft-fail OCSP might ignore a valid Revoked or Unknown
+ // response, and an application that implements hard-fail OCSP might fail
+ // to connect to a server given a valid Good response.
+ out = &dummyOCSPNocheck;
+ // We allow this extension to have an empty value.
+ // See http://comments.gmane.org/gmane.ietf.x509/30947
+ emptyValueAllowed = true;
} else if (extnID.MatchRest(Netscape_certificate_type) && critical) {
out = &criticalNetscapeCertificateType;
}
@@ -266,7 +292,7 @@ BackCert::RememberExtension(Reader& extnID, const Input& extnValue,
if (out) {
// Don't allow an empty value for any extension we understand. This way, we
// can test out->GetLength() != 0 or out->Init() to check for duplicates.
- if (extnValue.GetLength() == 0) {
+ if (extnValue.GetLength() == 0 && !emptyValueAllowed) {
return Result::ERROR_EXTENSION_VALUE_INVALID;
}
if (out->Init(extnValue) != Success) {
diff --git a/security/pkix/test/gtest/pkixcert_extension_tests.cpp b/security/pkix/test/gtest/pkixcert_extension_tests.cpp
index c32f584cb79e..ae3632021858 100644
--- a/security/pkix/test/gtest/pkixcert_extension_tests.cpp
+++ b/security/pkix/test/gtest/pkixcert_extension_tests.cpp
@@ -23,6 +23,7 @@
*/
#include "pkix/pkix.h"
+#include "pkixder.h"
#include "pkixgtest.h"
#include "pkixtestutil.h"
@@ -107,7 +108,144 @@ private:
}
};
-class pkixcert_extension : public ::testing::Test
+// python DottedOIDToCode.py --tlv unknownExtensionOID 1.3.6.1.4.1.13769.666.666.666.1.500.9.3
+static const uint8_t tlv_unknownExtensionOID[] = {
+ 0x06, 0x12, 0x2b, 0x06, 0x01, 0x04, 0x01, 0xeb, 0x49, 0x85, 0x1a, 0x85, 0x1a,
+ 0x85, 0x1a, 0x01, 0x83, 0x74, 0x09, 0x03
+};
+
+// python DottedOIDToCode.py --tlv id-pe-authorityInformationAccess 1.3.6.1.5.5.7.1.1
+static const uint8_t tlv_id_pe_authorityInformationAccess[] = {
+ 0x06, 0x08, 0x2b, 0x06, 0x01, 0x05, 0x05, 0x07, 0x01, 0x01
+};
+
+// python DottedOIDToCode.py --tlv wrongExtensionOID 1.3.6.6.1.5.5.7.1.1
+// (there is an extra "6" that shouldn't be in this OID)
+static const uint8_t tlv_wrongExtensionOID[] = {
+ 0x06, 0x09, 0x2b, 0x06, 0x06, 0x01, 0x05, 0x05, 0x07, 0x01, 0x01
+};
+
+// python DottedOIDToCode.py --tlv id-ce-unknown 2.5.29.55
+// (this is a made-up OID for testing "id-ce"-prefixed OIDs that mozilla::pkix
+// doesn't handle)
+static const uint8_t tlv_id_ce_unknown[] = {
+ 0x06, 0x03, 0x55, 0x1d, 0x37
+};
+
+// python DottedOIDToCode.py --tlv id-ce-inhibitAnyPolicy 2.5.29.54
+static const uint8_t tlv_id_ce_inhibitAnyPolicy[] = {
+ 0x06, 0x03, 0x55, 0x1d, 0x36
+};
+
+// python DottedOIDToCode.py --tlv id-pkix-ocsp-nocheck 1.3.6.1.5.5.7.48.1.5
+static const uint8_t tlv_id_pkix_ocsp_nocheck[] = {
+ 0x06, 0x09, 0x2b, 0x06, 0x01, 0x05, 0x05, 0x07, 0x30, 0x01, 0x05
+};
+
+template
+inline ByteString
+BytesToByteString(const uint8_t (&bytes)[L])
+{
+ return ByteString(bytes, L);
+}
+
+struct ExtensionTestcase
+{
+ ByteString extension;
+ Result expectedResult;
+};
+
+static const ExtensionTestcase EXTENSION_TESTCASES[] =
+{
+ // Tests that a non-critical extension not in the id-ce or id-pe arcs (which
+ // is thus unknown to us) verifies successfully even if empty (extensions we
+ // know about aren't normally allowed to be empty).
+ { TLV(der::SEQUENCE,
+ BytesToByteString(tlv_unknownExtensionOID) +
+ TLV(der::OCTET_STRING, ByteString())),
+ Success
+ },
+
+ // Tests that a critical extension not in the id-ce or id-pe arcs (which is
+ // thus unknown to us) is detected and that verification fails with the
+ // appropriate error.
+ { TLV(der::SEQUENCE,
+ BytesToByteString(tlv_unknownExtensionOID) +
+ Boolean(true) +
+ TLV(der::OCTET_STRING, ByteString())),
+ Result::ERROR_UNKNOWN_CRITICAL_EXTENSION
+ },
+
+ // Tests that a id-pe-authorityInformationAccess critical extension
+ // is detected and that verification succeeds.
+ // XXX: According to RFC 5280 an AIA that consists of an empty sequence is
+ // not legal, but we accept it and that is not what we're testing here.
+ { TLV(der::SEQUENCE,
+ BytesToByteString(tlv_id_pe_authorityInformationAccess) +
+ Boolean(true) +
+ TLV(der::OCTET_STRING, TLV(der::SEQUENCE, ByteString()))),
+ Success
+ },
+
+ // Tests that an incorrect OID for id-pe-authorityInformationAccess
+ // (when marked critical) is detected and that verification fails.
+ // (Until bug 1020993 was fixed, this wrong value was used for
+ // id-pe-authorityInformationAccess.)
+ { TLV(der::SEQUENCE,
+ BytesToByteString(tlv_wrongExtensionOID) +
+ Boolean(true) +
+ TLV(der::OCTET_STRING, ByteString())),
+ Result::ERROR_UNKNOWN_CRITICAL_EXTENSION
+ },
+
+ // We know about some id-ce extensions (OID arc 2.5.29), but not all of them.
+ // Tests that an unknown id-ce extension is detected and that verification
+ // fails.
+ { TLV(der::SEQUENCE,
+ BytesToByteString(tlv_id_ce_unknown) +
+ Boolean(true) +
+ TLV(der::OCTET_STRING, ByteString())),
+ Result::ERROR_UNKNOWN_CRITICAL_EXTENSION
+ },
+
+ // Tests that a certificate with a known critical id-ce extension (in this
+ // case, OID 2.5.29.54, which is id-ce-inhibitAnyPolicy), verifies
+ // successfully.
+ { TLV(der::SEQUENCE,
+ BytesToByteString(tlv_id_ce_inhibitAnyPolicy) +
+ Boolean(true) +
+ TLV(der::OCTET_STRING, Integer(0))),
+ Success
+ },
+
+ // Tests that a certificate with the id-pkix-ocsp-nocheck extension (marked
+ // critical) verifies successfully.
+ // RFC 6960:
+ // ext-ocsp-nocheck EXTENSION ::= { SYNTAX NULL IDENTIFIED
+ // BY id-pkix-ocsp-nocheck }
+ { TLV(der::SEQUENCE,
+ BytesToByteString(tlv_id_pkix_ocsp_nocheck) +
+ Boolean(true) +
+ TLV(der::OCTET_STRING, TLV(der::NULLTag, ByteString()))),
+ Success
+ },
+
+ // Tests that a certificate with another representation of the
+ // id-pkix-ocsp-nocheck extension (marked critical) verifies successfully.
+ // According to http://comments.gmane.org/gmane.ietf.x509/30947,
+ // some code creates certificates where value of the extension is
+ // an empty OCTET STRING.
+ { TLV(der::SEQUENCE,
+ BytesToByteString(tlv_id_pkix_ocsp_nocheck) +
+ Boolean(true) +
+ TLV(der::OCTET_STRING, ByteString())),
+ Success
+ },
+};
+
+class pkixcert_extension
+ : public ::testing::Test
+ , public ::testing::WithParamInterface
{
protected:
static TrustEverythingTrustDomain trustDomain;
@@ -115,29 +253,15 @@ protected:
/*static*/ TrustEverythingTrustDomain pkixcert_extension::trustDomain;
-// Tests that a critical extension not in the id-ce or id-pe arcs (which is
-// thus unknown to us) is detected and that verification fails with the
-// appropriate error.
-TEST_F(pkixcert_extension, UnknownCriticalExtension)
+TEST_P(pkixcert_extension, ExtensionHandledProperly)
{
- static const uint8_t unknownCriticalExtensionBytes[] = {
- 0x30, 0x19, // SEQUENCE (length = 25)
- 0x06, 0x12, // OID (length = 18)
- // 1.3.6.1.4.1.13769.666.666.666.1.500.9.3
- 0x2b, 0x06, 0x01, 0x04, 0x01, 0xeb, 0x49, 0x85, 0x1a,
- 0x85, 0x1a, 0x85, 0x1a, 0x01, 0x83, 0x74, 0x09, 0x03,
- 0x01, 0x01, 0xff, // BOOLEAN (length = 1) TRUE
- 0x04, 0x00 // OCTET STRING (length = 0)
- };
- static const ByteString
- unknownCriticalExtension(unknownCriticalExtensionBytes,
- sizeof(unknownCriticalExtensionBytes));
- const char* certCN = "Cert With Unknown Critical Extension";
- ByteString cert(CreateCertWithOneExtension(certCN, unknownCriticalExtension));
+ const ExtensionTestcase& testcase(GetParam());
+ const char* cn = "Cert Extension Test";
+ ByteString cert(CreateCertWithOneExtension(cn, testcase.extension));
ASSERT_FALSE(ENCODING_FAILED(cert));
Input certInput;
ASSERT_EQ(Success, certInput.Init(cert.data(), cert.length()));
- ASSERT_EQ(Result::ERROR_UNKNOWN_CRITICAL_EXTENSION,
+ ASSERT_EQ(testcase.expectedResult,
BuildCertChain(trustDomain, certInput, Now(),
EndEntityOrCA::MustBeEndEntity,
KeyUsage::noParticularKeyUsageRequired,
@@ -146,172 +270,24 @@ TEST_F(pkixcert_extension, UnknownCriticalExtension)
nullptr/*stapledOCSPResponse*/));
}
-// Tests that a non-critical extension not in the id-ce or id-pe arcs (which is
-// thus unknown to us) verifies successfully.
-TEST_F(pkixcert_extension, UnknownNonCriticalExtension)
-{
- static const uint8_t unknownNonCriticalExtensionBytes[] = {
- 0x30, 0x16, // SEQUENCE (length = 22)
- 0x06, 0x12, // OID (length = 18)
- // 1.3.6.1.4.1.13769.666.666.666.1.500.9.3
- 0x2b, 0x06, 0x01, 0x04, 0x01, 0xeb, 0x49, 0x85, 0x1a,
- 0x85, 0x1a, 0x85, 0x1a, 0x01, 0x83, 0x74, 0x09, 0x03,
- 0x04, 0x00 // OCTET STRING (length = 0)
- };
- static const ByteString
- unknownNonCriticalExtension(unknownNonCriticalExtensionBytes,
- sizeof(unknownNonCriticalExtensionBytes));
- const char* certCN = "Cert With Unknown NonCritical Extension";
- ByteString cert(CreateCertWithOneExtension(certCN,
- unknownNonCriticalExtension));
- ASSERT_FALSE(ENCODING_FAILED(cert));
- Input certInput;
- ASSERT_EQ(Success, certInput.Init(cert.data(), cert.length()));
- ASSERT_EQ(Success,
- BuildCertChain(trustDomain, certInput, Now(),
- EndEntityOrCA::MustBeEndEntity,
- KeyUsage::noParticularKeyUsageRequired,
- KeyPurposeId::anyExtendedKeyUsage,
- CertPolicyId::anyPolicy,
- nullptr/*stapledOCSPResponse*/));
-}
-
-// Tests that an incorrect OID for id-pe-authorityInformationAccess
-// (when marked critical) is detected and that verification fails.
-// (Until bug 1020993 was fixed, the code checked for this OID.)
-TEST_F(pkixcert_extension, WrongOIDCriticalExtension)
-{
- static const uint8_t wrongOIDCriticalExtensionBytes[] = {
- 0x30, 0x10, // SEQUENCE (length = 16)
- 0x06, 0x09, // OID (length = 9)
- // 1.3.6.6.1.5.5.7.1.1 (there is an extra "6" that shouldn't be there)
- 0x2b, 0x06, 0x06, 0x01, 0x05, 0x05, 0x07, 0x01, 0x01,
- 0x01, 0x01, 0xff, // BOOLEAN (length = 1) TRUE
- 0x04, 0x00 // OCTET STRING (length = 0)
- };
- static const ByteString
- wrongOIDCriticalExtension(wrongOIDCriticalExtensionBytes,
- sizeof(wrongOIDCriticalExtensionBytes));
- const char* certCN = "Cert With Critical Wrong OID Extension";
- ByteString cert(CreateCertWithOneExtension(certCN,
- wrongOIDCriticalExtension));
- ASSERT_FALSE(ENCODING_FAILED(cert));
- Input certInput;
- ASSERT_EQ(Success, certInput.Init(cert.data(), cert.length()));
- ASSERT_EQ(Result::ERROR_UNKNOWN_CRITICAL_EXTENSION,
- BuildCertChain(trustDomain, certInput, Now(),
- EndEntityOrCA::MustBeEndEntity,
- KeyUsage::noParticularKeyUsageRequired,
- KeyPurposeId::anyExtendedKeyUsage,
- CertPolicyId::anyPolicy,
- nullptr/*stapledOCSPResponse*/));
-}
-
-// Tests that a id-pe-authorityInformationAccess critical extension
-// is detected and that verification succeeds.
-TEST_F(pkixcert_extension, CriticalAIAExtension)
-{
- // XXX: According to RFC 5280 an AIA that consists of an empty sequence is
- // not legal, but we accept it and that is not what we're testing here.
- static const uint8_t criticalAIAExtensionBytes[] = {
- 0x30, 0x11, // SEQUENCE (length = 17)
- 0x06, 0x08, // OID (length = 8)
- // 1.3.6.1.5.5.7.1.1
- 0x2b, 0x06, 0x01, 0x05, 0x05, 0x07, 0x01, 0x01,
- 0x01, 0x01, 0xff, // BOOLEAN (length = 1) TRUE
- 0x04, 0x02, // OCTET STRING (length = 2)
- 0x30, 0x00, // SEQUENCE (length = 0)
- };
- static const ByteString
- criticalAIAExtension(criticalAIAExtensionBytes,
- sizeof(criticalAIAExtensionBytes));
- const char* certCN = "Cert With Critical AIA Extension";
- ByteString cert(CreateCertWithOneExtension(certCN, criticalAIAExtension));
- ASSERT_FALSE(ENCODING_FAILED(cert));
- Input certInput;
- ASSERT_EQ(Success, certInput.Init(cert.data(), cert.length()));
- ASSERT_EQ(Success,
- BuildCertChain(trustDomain, certInput, Now(),
- EndEntityOrCA::MustBeEndEntity,
- KeyUsage::noParticularKeyUsageRequired,
- KeyPurposeId::anyExtendedKeyUsage,
- CertPolicyId::anyPolicy,
- nullptr/*stapledOCSPResponse*/));
-}
-
-// We know about some id-ce extensions (OID arc 2.5.29), but not all of them.
-// Tests that an unknown id-ce extension is detected and that verification
-// fails.
-TEST_F(pkixcert_extension, UnknownCriticalCEExtension)
-{
- static const uint8_t unknownCriticalCEExtensionBytes[] = {
- 0x30, 0x0a, // SEQUENCE (length = 10)
- 0x06, 0x03, // OID (length = 3)
- 0x55, 0x1d, 0x37, // 2.5.29.55
- 0x01, 0x01, 0xff, // BOOLEAN (length = 1) TRUE
- 0x04, 0x00 // OCTET STRING (length = 0)
- };
- static const ByteString
- unknownCriticalCEExtension(unknownCriticalCEExtensionBytes,
- sizeof(unknownCriticalCEExtensionBytes));
- const char* certCN = "Cert With Unknown Critical id-ce Extension";
- ByteString cert(CreateCertWithOneExtension(certCN,
- unknownCriticalCEExtension));
- ASSERT_FALSE(ENCODING_FAILED(cert));
- Input certInput;
- ASSERT_EQ(Success, certInput.Init(cert.data(), cert.length()));
- ASSERT_EQ(Result::ERROR_UNKNOWN_CRITICAL_EXTENSION,
- BuildCertChain(trustDomain, certInput, Now(),
- EndEntityOrCA::MustBeEndEntity,
- KeyUsage::noParticularKeyUsageRequired,
- KeyPurposeId::anyExtendedKeyUsage,
- CertPolicyId::anyPolicy,
- nullptr/*stapledOCSPResponse*/));
-}
-
-// Tests that a certificate with a known critical id-ce extension (in this case,
-// OID 2.5.29.54, which is id-ce-inhibitAnyPolicy), verifies successfully.
-TEST_F(pkixcert_extension, KnownCriticalCEExtension)
-{
- static const uint8_t criticalCEExtensionBytes[] = {
- 0x30, 0x0d, // SEQUENCE (length = 13)
- 0x06, 0x03, // OID (length = 3)
- 0x55, 0x1d, 0x36, // 2.5.29.54 (id-ce-inhibitAnyPolicy)
- 0x01, 0x01, 0xff, // BOOLEAN (length = 1) TRUE
- 0x04, 0x03, // OCTET STRING (length = 3)
- 0x02, 0x01, 0x00, // INTEGER (length = 1, value = 0)
- };
- static const ByteString
- criticalCEExtension(criticalCEExtensionBytes,
- sizeof(criticalCEExtensionBytes));
- const char* certCN = "Cert With Known Critical id-ce Extension";
- ByteString cert(CreateCertWithOneExtension(certCN, criticalCEExtension));
- ASSERT_FALSE(ENCODING_FAILED(cert));
- Input certInput;
- ASSERT_EQ(Success, certInput.Init(cert.data(), cert.length()));
- ASSERT_EQ(Success,
- BuildCertChain(trustDomain, certInput, Now(),
- EndEntityOrCA::MustBeEndEntity,
- KeyUsage::noParticularKeyUsageRequired,
- KeyPurposeId::anyExtendedKeyUsage,
- CertPolicyId::anyPolicy,
- nullptr/*stapledOCSPResponse*/));
-}
+INSTANTIATE_TEST_CASE_P(pkixcert_extension,
+ pkixcert_extension,
+ testing::ValuesIn(EXTENSION_TESTCASES));
// Two subjectAltNames must result in an error.
TEST_F(pkixcert_extension, DuplicateSubjectAltName)
{
- static const uint8_t DER_BYTES[] = {
- 0x30, 22, // SEQUENCE (length = 22)
- 0x06, 3, // OID (length = 3)
- 0x55, 0x1d, 0x11, // 2.5.29.17
- 0x04, 15, // OCTET STRING (length = 15)
- 0x30, 13, // GeneralNames (SEQUENCE) (length = 13)
- 0x82, 11, // [2] (dNSName) (length = 11)
- 'e', 'x', 'a', 'm', 'p', 'l', 'e', '.', 'c', 'o', 'm'
+ // python DottedOIDToCode.py --tlv id-ce-subjectAltName 2.5.29.17
+ static const uint8_t tlv_id_ce_subjectAltName[] = {
+ 0x06, 0x03, 0x55, 0x1d, 0x11
};
- static const ByteString DER(DER_BYTES, sizeof(DER_BYTES));
- static const ByteString extensions[] = { DER, DER, ByteString() };
+
+ ByteString subjectAltName(
+ TLV(der::SEQUENCE,
+ BytesToByteString(tlv_id_ce_subjectAltName) +
+ TLV(der::OCTET_STRING, TLV(der::SEQUENCE, DNSName("example.com")))));
+ static const ByteString extensions[] = { subjectAltName, subjectAltName,
+ ByteString() };
static const char* certCN = "Cert With Duplicate subjectAltName";
ByteString cert(CreateCertWithExtensions(certCN, extensions));
ASSERT_FALSE(ENCODING_FAILED(cert));
diff --git a/security/pkix/test/lib/pkixtestutil.cpp b/security/pkix/test/lib/pkixtestutil.cpp
index d722cd9076be..27f0c0b52a69 100644
--- a/security/pkix/test/lib/pkixtestutil.cpp
+++ b/security/pkix/test/lib/pkixtestutil.cpp
@@ -183,7 +183,7 @@ BitString(const ByteString& rawBytes, bool corrupt)
return TLV(der::BIT_STRING, prefixed);
}
-static ByteString
+ByteString
Boolean(bool value)
{
ByteString encodedValue;
@@ -191,7 +191,7 @@ Boolean(bool value)
return TLV(der::BOOLEAN, encodedValue);
}
-static ByteString
+ByteString
Integer(long value)
{
if (value < 0 || value > 127) {
diff --git a/security/pkix/test/lib/pkixtestutil.h b/security/pkix/test/lib/pkixtestutil.h
index 71b68ad3c06a..50bf48e51255 100644
--- a/security/pkix/test/lib/pkixtestutil.h
+++ b/security/pkix/test/lib/pkixtestutil.h
@@ -111,6 +111,8 @@ mozilla::pkix::Time YMDHMS(int16_t year, int16_t month, int16_t day,
int16_t hour, int16_t minutes, int16_t seconds);
ByteString TLV(uint8_t tag, const ByteString& value);
+ByteString Boolean(bool value);
+ByteString Integer(long value);
ByteString CN(const ByteString&, uint8_t encodingTag = 0x0c /*UTF8String*/);
diff --git a/testing/config/mozharness/android_arm_config.py b/testing/config/mozharness/android_arm_config.py
index 053a1904d761..19b42a031cce 100644
--- a/testing/config/mozharness/android_arm_config.py
+++ b/testing/config/mozharness/android_arm_config.py
@@ -33,6 +33,7 @@ config = {
"--apk=%(installer_path)s", "--no-logfiles",
"--symbols-path=%(symbols_path)s",
"--manifest=tests/xpcshell.ini",
+ "--log-raw=%(raw_log_file)s",
],
},
}, # end suite_definitions
diff --git a/testing/config/mozharness/android_panda_config.py b/testing/config/mozharness/android_panda_config.py
index ef57e90d40b4..8b6523062ecd 100644
--- a/testing/config/mozharness/android_panda_config.py
+++ b/testing/config/mozharness/android_panda_config.py
@@ -61,7 +61,8 @@ config = {
"--local-lib-dir=../fennec",
"--apk=../%(apk_name)s",
"--no-logfiles",
- "--symbols-path=%(symbols_path)s"
+ "--symbols-path=%(symbols_path)s",
+ "--log-raw=%(raw_log_file)s",
],
"jittest_options": [
"bin/js",
diff --git a/testing/config/mozharness/android_x86_config.py b/testing/config/mozharness/android_x86_config.py
index 68d0b03d704a..7c0477026f4b 100644
--- a/testing/config/mozharness/android_x86_config.py
+++ b/testing/config/mozharness/android_x86_config.py
@@ -33,6 +33,7 @@ config = {
"--apk=%(installer_path)s", "--no-logfiles",
"--symbols-path=%(symbols_path)s",
"--manifest=tests/xpcshell.ini",
+ "--log-raw=%(raw_log_file)s",
],
},
}, # end suite_definitions
diff --git a/testing/config/mozharness/b2g_emulator_config.py b/testing/config/mozharness/b2g_emulator_config.py
index 04d7feb19384..91b6cf13bfba 100644
--- a/testing/config/mozharness/b2g_emulator_config.py
+++ b/testing/config/mozharness/b2g_emulator_config.py
@@ -47,6 +47,7 @@ config = {
"--logdir=%(logcat_dir)s", "--manifest=tests/xpcshell.ini", "--use-device-libs",
"--testing-modules-dir=%(modules_dir)s", "--symbols-path=%(symbols_path)s",
"--busybox=%(busybox)s", "--total-chunks=%(total_chunks)s", "--this-chunk=%(this_chunk)s",
+ "--log-raw=%(raw_log_file)s",
],
"cppunittest_options": [
diff --git a/testing/config/mozharness/linux_config.py b/testing/config/mozharness/linux_config.py
index f799918a4c4d..c47b5e62f5b1 100644
--- a/testing/config/mozharness/linux_config.py
+++ b/testing/config/mozharness/linux_config.py
@@ -24,7 +24,8 @@ config = {
],
"xpcshell_options": [
"--symbols-path=%(symbols_path)s",
- "--test-plugin-path=%(test_plugin_path)s"
+ "--test-plugin-path=%(test_plugin_path)s",
+ "--log-raw=%(raw_log_file)s",
],
"cppunittest_options": [
"--symbols-path=%(symbols_path)s",
diff --git a/testing/config/mozharness/mac_config.py b/testing/config/mozharness/mac_config.py
index 483159ae5de4..2c44f6bca806 100644
--- a/testing/config/mozharness/mac_config.py
+++ b/testing/config/mozharness/mac_config.py
@@ -23,7 +23,8 @@ config = {
],
"xpcshell_options": [
"--symbols-path=%(symbols_path)s",
- "--test-plugin-path=%(test_plugin_path)s"
+ "--test-plugin-path=%(test_plugin_path)s",
+ "--log-raw=%(raw_log_file)s",
],
"cppunittest_options": [
"--symbols-path=%(symbols_path)s",
diff --git a/testing/config/mozharness/windows_config.py b/testing/config/mozharness/windows_config.py
index 483159ae5de4..2c44f6bca806 100644
--- a/testing/config/mozharness/windows_config.py
+++ b/testing/config/mozharness/windows_config.py
@@ -23,7 +23,8 @@ config = {
],
"xpcshell_options": [
"--symbols-path=%(symbols_path)s",
- "--test-plugin-path=%(test_plugin_path)s"
+ "--test-plugin-path=%(test_plugin_path)s",
+ "--log-raw=%(raw_log_file)s",
],
"cppunittest_options": [
"--symbols-path=%(symbols_path)s",
diff --git a/testing/mochitest/android23.json b/testing/mochitest/android23.json
index b6b788b5f1c3..d2c9122d77fc 100644
--- a/testing/mochitest/android23.json
+++ b/testing/mochitest/android23.json
@@ -1,12 +1,6 @@
{
"runtests": {},
"excludetests": {
- "dom/html/test/test_bug659743.xml": "Android 2.3 aws only; bug 1031103",
- "docshell/test/navigation/test_reserved.html": "too slow on Android 2.3 aws only; bug 1030403",
- "dom/canvas/test/webgl-conformance": "bug 865443 - separate suite -- mochitest-gl",
- "dom/canvas/test/webgl-mochitest/test_no_arr_points.html": "Android 2.3 aws only; bug 1030942",
- "dom/media/tests/mochitest": "Android 2.3 only; bug 981881",
- "layout/style/test/test_media_queries.html": "Android 2.3 aws only; bug 1030419",
- "layout/style/test/test_transitions_cancel_near_end.html": "Android 2.3 aws only; bug 1030432"
+ "dom/canvas/test/webgl-conformance": "bug 865443 - separate suite -- mochitest-gl"
}
}
diff --git a/testing/mochitest/mach_commands.py b/testing/mochitest/mach_commands.py
index f3851448ac68..581323a03b67 100644
--- a/testing/mochitest/mach_commands.py
+++ b/testing/mochitest/mach_commands.py
@@ -92,7 +92,7 @@ class MochitestRunner(MozbuildObject):
appname = 'webapprt-stub' + mozinfo.info.get('bin_suffix', '')
if sys.platform.startswith('darwin'):
appname = os.path.join(self.distdir, self.substs['MOZ_MACBUNDLE_NAME'],
- 'Contents', 'MacOS', appname)
+ 'Contents', 'Resources', appname)
else:
appname = os.path.join(self.distdir, 'bin', appname)
return appname
diff --git a/testing/mozbase/mozdevice/mozdevice/adb.py b/testing/mozbase/mozdevice/mozdevice/adb.py
index e69244947e3a..8070c699b5dc 100644
--- a/testing/mozbase/mozdevice/mozdevice/adb.py
+++ b/testing/mozbase/mozdevice/mozdevice/adb.py
@@ -114,7 +114,7 @@ class ADBCommand(object):
from mozdevice import ADBCommand
try:
- adbcommand = ADBCommand(...)
+ adbcommand = ADBCommand()
except NotImplementedError:
print "ADBCommand can not be instantiated."
@@ -280,7 +280,7 @@ class ADBHost(ADBCommand):
from mozdevice import ADBHost
- adbhost = ADBHost(...)
+ adbhost = ADBHost()
adbhost.start_server()
"""
@@ -442,7 +442,7 @@ class ADBDevice(ADBCommand):
from mozdevice import ADBDevice
- adbdevice = ADBDevice(...)
+ adbdevice = ADBDevice()
print adbdevice.list_files("/mnt/sdcard")
if adbdevice.process_exist("org.mozilla.fennec"):
print "Fennec is running"
diff --git a/testing/mozharness/README.txt b/testing/mozharness/README.txt
deleted file mode 100644
index a4b534a419d3..000000000000
--- a/testing/mozharness/README.txt
+++ /dev/null
@@ -1,2 +0,0 @@
-mozharness.json is a manifest file that is currently only used on try.
-It allows you to lock mozharness to a repository and a revision.
diff --git a/testing/mozharness/mozharness.json b/testing/mozharness/mozharness.json
deleted file mode 100644
index 0908d77c9e3e..000000000000
--- a/testing/mozharness/mozharness.json
+++ /dev/null
@@ -1,4 +0,0 @@
-{
- "repo": "http://hg.mozilla.org/build/mozharness",
- "revision": "production"
-}
diff --git a/testing/mozharness/repository_from_code.py b/testing/mozharness/repository_from_code.py
deleted file mode 100644
index addfe69fd29a..000000000000
--- a/testing/mozharness/repository_from_code.py
+++ /dev/null
@@ -1,121 +0,0 @@
-#! /usr/bin/env python
-# 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/.
-
-#
-# Script name: repository_manifest.py
-# Purpose: Reads from a json file a repository and revision to use.
-# If none is found we fall back to the default values.
-# Author(s): Zambrano Gasparnian, Armen
-# Target: Python 2.7.x
-#
-from optparse import OptionParser
-import json
-import re
-import urllib2
-import urlparse
-import sys
-import os
-
-def main():
- '''
- Determine which repository and revision mozharness.json indicates.
- If none is found we fall back to the default repository
- '''
- parser = OptionParser()
- parser.add_option("--repository-manifest-url", dest="repository_manifest_url", type="string",
- help="It indicates from where to download the talos.json file.")
- (options, args) = parser.parse_args()
-
- # 1) check that the url was passed
- if options.repository_manifest_url == None:
- print "You need to specify --repository-manifest-url."
- sys.exit(1)
-
- # 2) try to download the talos.json file
- try:
- jsonFilename = download_file(options.talos_json_url)
- except Exception, e:
- print "ERROR: We tried to download the talos.json file but something failed."
- print "ERROR: %s" % str(e)
- sys.exit(1)
-
- # 3) download the necessary files
- print "INFO: talos.json URL: %s" % options.talos_json_url
- try:
- key = 'talos.zip'
- entity = get_value(jsonFilename, key)
- if passesRestrictions(options.talos_json_url, entity["url"]):
- # the key is at the same time the filename e.g. talos.zip
- print "INFO: Downloading %s as %s" % (entity["url"], os.path.join(entity["path"], key))
- download_file(entity["url"], entity["path"], key)
- else:
- print "ERROR: You have tried to download a file " + \
- "from: %s " % entity["url"] + \
- "which is a location different than http://talos-bundles.pvt.build.mozilla.org/"
- print "ERROR: This is only allowed for the certain branches."
- sys.exit(1)
- except Exception, e:
- print "ERROR: %s" % str(e)
- sys.exit(1)
-
-def passesRestrictions(talosJsonUrl, fileUrl):
- '''
- Only certain branches are exempted from having to host their downloadable files
- in talos-bundles.pvt.build.mozilla.org
- '''
- if talosJsonUrl.startswith("http://hg.mozilla.org/try/") or \
- talosJsonUrl.startswith("https://hg.mozilla.org/try/") or \
- talosJsonUrl.startswith("http://hg.mozilla.org/projects/pine/") or \
- talosJsonUrl.startswith("https://hg.mozilla.org/projects/pine/") or \
- talosJsonUrl.startswith("http://hg.mozilla.org/projects/ash/") or \
- talosJsonUrl.startswith("https://hg.mozilla.org/projects/ash/"):
- return True
- else:
- p = re.compile('^http://talos-bundles.pvt.build.mozilla.org/')
- m = p.match(fileUrl)
- if m == None:
- return False
- return True
-
-def get_filename_from_url(url):
- '''
- This returns the filename of the file we're trying to download
- '''
- parsed = urlparse.urlsplit(url.rstrip('/'))
- if parsed.path != '':
- return parsed.path.rsplit('/', 1)[-1]
- else:
- print "ERROR: We were trying to download a file from %s " + \
- "but the URL seems to be incorrect."
- sys.exit(1)
-
-def download_file(url, path="", saveAs=None):
- '''
- It downloads a file from URL to the indicated path
- '''
- req = urllib2.Request(url)
- f = urllib2.urlopen(req)
- if path != "" and not os.path.isdir(path):
- try:
- os.makedirs(path)
- print "INFO: directory %s created" % path
- except Exception, e:
- print "ERROR: %s" % str(e)
- sys.exit(1)
- filename = saveAs if saveAs else get_filename_from_url(url)
- local_file = open(os.path.join(path, filename), 'wb')
- local_file.write(f.read())
- local_file.close()
- return filename
-
-def get_value(json_filename, key):
- '''
- It loads up a JSON file and returns the value for the given string
- '''
- f = open(json_filename, 'r')
- return json.load(f)[key]
-
-if __name__ == '__main__':
- main()
diff --git a/testing/testsuite-targets.mk b/testing/testsuite-targets.mk
index 2143ed000956..a1b0b3af2e8d 100644
--- a/testing/testsuite-targets.mk
+++ b/testing/testsuite-targets.mk
@@ -169,7 +169,7 @@ endif
$(CHECK_TEST_ERROR)
ifeq ($(OS_ARCH),Darwin)
-webapprt_stub_path = $(TARGET_DIST)/$(MOZ_MACBUNDLE_NAME)/Contents/MacOS/webapprt-stub$(BIN_SUFFIX)
+webapprt_stub_path = $(TARGET_DIST)/$(MOZ_MACBUNDLE_NAME)/Contents/Resources/webapprt-stub$(BIN_SUFFIX)
endif
ifeq ($(OS_ARCH),WINNT)
webapprt_stub_path = $(TARGET_DIST)/bin/webapprt-stub$(BIN_SUFFIX)
diff --git a/toolkit/webapps/MacNativeApp.js b/toolkit/webapps/MacNativeApp.js
index 0e12503f5985..dadd6c43ed45 100644
--- a/toolkit/webapps/MacNativeApp.js
+++ b/toolkit/webapps/MacNativeApp.js
@@ -222,7 +222,8 @@ NativeApp.prototype = {
_copyPrebuiltFiles: function(aDir) {
let destDir = getFile(aDir, this.macOSDir);
- let stub = getFile(this.runtimeFolder, "webapprt-stub");
+ let stub = getFile(OS.Path.join(OS.Path.dirname(this.runtimeFolder),
+ "Resources"), "webapprt-stub");
stub.copyTo(destDir, "webapprt");
},
diff --git a/toolkit/webapps/tests/test_webapp_runtime_executable_update.xul b/toolkit/webapps/tests/test_webapp_runtime_executable_update.xul
index 9886fc061311..1400a262d84d 100644
--- a/toolkit/webapps/tests/test_webapp_runtime_executable_update.xul
+++ b/toolkit/webapps/tests/test_webapp_runtime_executable_update.xul
@@ -94,7 +94,7 @@ let runTest = Task.async(function*() {
let fakeInstallDir;
if (MAC) {
- fakeInstallDir = getFile(testAppInfo.installPath, "Contents", "MacOS");
+ fakeInstallDir = getFile(testAppInfo.installPath, "Contents", "Resources");
} else {
fakeInstallDir = getFile(OS.Constants.Path.profileDir, "fakeInstallDir");
fakeInstallDir.createUnique(Ci.nsIFile.DIRECTORY_TYPE, 0o755);
diff --git a/webapprt/mac/webapprt.mm b/webapprt/mac/webapprt.mm
index dea620e4d44c..4e2299ad207b 100644
--- a/webapprt/mac/webapprt.mm
+++ b/webapprt/mac/webapprt.mm
@@ -166,7 +166,7 @@ main(int argc, char **argv)
//we know the firefox path, so copy the new webapprt here
NSString *newWebRTPath =
- [NSString stringWithFormat: @"%@%s%s", firefoxPath, APP_MACOS_PATH,
+ [NSString stringWithFormat: @"%@%s%s", firefoxPath, APP_RESOURCES_PATH,
WEBAPPRT_EXECUTABLE];
NSLog(@"### Firefox webapprt path: %@", newWebRTPath);
if (![fileClerk fileExistsAtPath:newWebRTPath]) {