mirror of
https://gitlab.winehq.org/wine/wine-gecko.git
synced 2024-09-13 09:24:08 -07:00
Bug 770490 - Infrastructure to run reftests on B2G, r=jgriffin
This commit is contained in:
parent
de807f4c93
commit
b4d43b25cb
@ -35,16 +35,19 @@ class B2GRemoteAutomation(Automation):
|
||||
_devicemanager = None
|
||||
|
||||
def __init__(self, deviceManager, appName='', remoteLog=None,
|
||||
marionette=None):
|
||||
marionette=None, context_chrome=True):
|
||||
self._devicemanager = deviceManager
|
||||
self._appName = appName
|
||||
self._remoteProfile = None
|
||||
self._remoteLog = remoteLog
|
||||
self.marionette = marionette
|
||||
self.context_chrome = context_chrome
|
||||
self._is_emulator = False
|
||||
|
||||
# Default our product to b2g
|
||||
self._product = "b2g"
|
||||
# Default log finish to mochitest standard
|
||||
self.logFinish = 'INFO SimpleTest FINISHED'
|
||||
Automation.__init__(self)
|
||||
|
||||
def setEmulator(self, is_emulator):
|
||||
@ -121,7 +124,7 @@ class B2GRemoteAutomation(Automation):
|
||||
|
||||
def waitForFinish(self, proc, utilityPath, timeout, maxTime, startTime,
|
||||
debuggerInfo, symbolsPath):
|
||||
""" Wait for mochitest to finish (as evidenced by a signature string
|
||||
""" Wait for tests to finish (as evidenced by a signature string
|
||||
in logcat), or for a given amount of time to elapse with no
|
||||
output.
|
||||
"""
|
||||
@ -135,7 +138,7 @@ class B2GRemoteAutomation(Automation):
|
||||
if currentlog:
|
||||
done = time.time() + timeout
|
||||
print currentlog
|
||||
if 'INFO SimpleTest FINISHED' in currentlog:
|
||||
if hasattr(self, 'logFinish') and self.logFinish in currentlog:
|
||||
return 0
|
||||
else:
|
||||
if time.time() > done:
|
||||
@ -162,6 +165,8 @@ class B2GRemoteAutomation(Automation):
|
||||
return (serial, status)
|
||||
|
||||
def restartB2G(self):
|
||||
# TODO hangs in subprocess.Popen without this delay
|
||||
time.sleep(5)
|
||||
self._devicemanager.checkCmd(['shell', 'stop', 'b2g'])
|
||||
# Wait for a bit to make sure B2G has completely shut down.
|
||||
time.sleep(10)
|
||||
@ -194,11 +199,11 @@ class B2GRemoteAutomation(Automation):
|
||||
|
||||
def Process(self, cmd, stdout=None, stderr=None, env=None, cwd=None):
|
||||
# On a desktop or fennec run, the Process method invokes a gecko
|
||||
# process in which to run mochitests. For B2G, we simply
|
||||
# process in which to the tests. For B2G, we simply
|
||||
# reboot the device (which was configured with a test profile
|
||||
# already), wait for B2G to start up, and then navigate to the
|
||||
# test url using Marionette. There doesn't seem to be any way
|
||||
# to pass env variables into the B2G process, but this doesn't
|
||||
# to pass env variables into the B2G process, but this doesn't
|
||||
# seem to matter.
|
||||
|
||||
# reboot device so it starts up with the mochitest profile
|
||||
@ -239,11 +244,27 @@ class B2GRemoteAutomation(Automation):
|
||||
if 'b2g' not in session:
|
||||
raise Exception("bad session value %s returned by start_session" % session)
|
||||
|
||||
# Start the tests by navigating to the mochitest url, by setting it
|
||||
# as the 'src' attribute to the homescreen mozbrowser element
|
||||
# provided by B2G's shell.js.
|
||||
self.marionette.set_context("chrome")
|
||||
self.marionette.execute_script("document.getElementById('homescreen').src='%s';" % self.testURL)
|
||||
if self.context_chrome:
|
||||
self.marionette.set_context(self.marionette.CONTEXT_CHROME)
|
||||
|
||||
# start the tests
|
||||
if hasattr(self, 'testURL'):
|
||||
# Start the tests by navigating to the mochitest url, by setting it
|
||||
# as the 'src' attribute to the homescreen mozbrowser element
|
||||
# provided by B2G's shell.js.
|
||||
self.marionette.execute_script("document.getElementById('homescreen').src='%s';" % self.testURL)
|
||||
# run the script that starts the tests
|
||||
elif hasattr(self, 'testScript'):
|
||||
if os.path.isfile(self.testScript):
|
||||
script = open(self.testScript, 'r')
|
||||
self.marionette.execute_script(script.read())
|
||||
script.close()
|
||||
else:
|
||||
# assume testScript is a string
|
||||
self.marionette.execute_script(self.testScript)
|
||||
else:
|
||||
# assumes the tests are started on startup automatically
|
||||
pass
|
||||
|
||||
return instance
|
||||
|
||||
|
@ -24,7 +24,7 @@ include backgrounds/reftest.list
|
||||
include bidi/reftest.list
|
||||
|
||||
# border-image
|
||||
skip-if(Android) include border-image/reftest.list
|
||||
skip-if(Android||B2G) include border-image/reftest.list
|
||||
|
||||
# border-radius/
|
||||
include border-radius/reftest.list
|
||||
@ -39,10 +39,10 @@ include box-ordinal/reftest.list
|
||||
include box-properties/reftest.list
|
||||
|
||||
# box-shadow/
|
||||
skip-if(Android) include box-shadow/reftest.list
|
||||
skip-if(Android||B2G) include box-shadow/reftest.list
|
||||
|
||||
# bugs/
|
||||
skip-if(Android) include bugs/reftest.list
|
||||
skip-if(Android||B2G) include bugs/reftest.list
|
||||
|
||||
# canvas 2D
|
||||
include canvas/reftest.list
|
||||
@ -57,10 +57,10 @@ include css-charset/reftest.list
|
||||
include css-default/reftest.list
|
||||
|
||||
# css :disable tests
|
||||
skip-if(Android) include css-disabled/reftest.list
|
||||
skip-if(Android||B2G) include css-disabled/reftest.list
|
||||
|
||||
# css :enable tests
|
||||
skip-if(Android) include css-enabled/reftest.list
|
||||
skip-if(Android||B2G) include css-enabled/reftest.list
|
||||
|
||||
# css @import tests
|
||||
include css-import/reftest.list
|
||||
@ -87,10 +87,10 @@ include css-required/reftest.list
|
||||
include css-optional/reftest.list
|
||||
|
||||
# css valid
|
||||
skip-if(Android) include css-valid/reftest.list
|
||||
skip-if(Android||B2G) include css-valid/reftest.list
|
||||
|
||||
# css invalid
|
||||
skip-if(Android) include css-invalid/reftest.list
|
||||
skip-if(Android||B2G) include css-invalid/reftest.list
|
||||
|
||||
# css-submit-invalid
|
||||
include css-submit-invalid/reftest.list
|
||||
@ -105,10 +105,10 @@ include css-selectors/reftest.list
|
||||
include css-transitions/reftest.list
|
||||
|
||||
# css :-moz-ui-invalid
|
||||
skip-if(Android) include css-ui-invalid/reftest.list
|
||||
skip-if(Android||B2G) include css-ui-invalid/reftest.list
|
||||
|
||||
# css :-moz-ui-valid
|
||||
skip-if(Android) include css-ui-valid/reftest.list
|
||||
skip-if(Android||B2G) include css-ui-valid/reftest.list
|
||||
|
||||
# css values and units
|
||||
include css-valuesandunits/reftest.list
|
||||
@ -138,7 +138,7 @@ include dom/reftest.list
|
||||
include generated-content/reftest.list
|
||||
|
||||
# first-letter/
|
||||
skip-if(Android) include first-letter/reftest.list
|
||||
skip-if(Android||B2G) include first-letter/reftest.list
|
||||
|
||||
# first-line/
|
||||
include first-line/reftest.list
|
||||
@ -159,7 +159,7 @@ include font-inflation/reftest.list
|
||||
include font-matching/reftest.list
|
||||
|
||||
# forms
|
||||
skip-if(Android) include forms/reftest.list
|
||||
skip-if(Android||B2G) include forms/reftest.list
|
||||
|
||||
# gfx
|
||||
include ../../gfx/tests/reftest/reftest.list
|
||||
@ -204,7 +204,7 @@ include margin-collapsing/reftest.list
|
||||
include marquee/reftest.list
|
||||
|
||||
# native-theme/
|
||||
skip-if(Android) include native-theme/reftest.list
|
||||
skip-if(Android||B2G) include native-theme/reftest.list
|
||||
|
||||
# netwerk/
|
||||
include ../../netwerk/test/reftest/reftest.list
|
||||
@ -232,7 +232,7 @@ include ../../dom/plugins/test/reftest/reftest.list
|
||||
|
||||
# position-dynamic-changes/
|
||||
# Disabled on Native Fennec for now, because running them takes too long
|
||||
skip-if(Android&&!browserIsRemote) include position-dynamic-changes/reftest.list # Bug 762181
|
||||
skip-if((Android||B2G)&&!browserIsRemote) include position-dynamic-changes/reftest.list # Bug 762181
|
||||
|
||||
# printing
|
||||
include printing/reftest.list
|
||||
@ -275,7 +275,7 @@ include text-decoration/reftest.list
|
||||
include text-indent/reftest.list
|
||||
|
||||
# text-shadow/
|
||||
skip-if(Android) include text-shadow/reftest.list
|
||||
skip-if(Android||B2G) include text-shadow/reftest.list
|
||||
|
||||
# theme (pinstripe)
|
||||
include ../../toolkit/themes/pinstripe/reftests/reftest.list
|
||||
|
@ -25,6 +25,11 @@ DEFINES += -DBOOTSTRAP
|
||||
DIST_FILES += bootstrap.js
|
||||
endif
|
||||
|
||||
ifeq ($(MOZ_BUILD_APP),b2g)
|
||||
DEFINES += -DBOOTSTRAP
|
||||
DEFINES += -DREFTEST_B2G
|
||||
endif
|
||||
|
||||
# Used in install.rdf
|
||||
USE_EXTENSION_MANIFEST=1
|
||||
else
|
||||
@ -52,10 +57,13 @@ endif
|
||||
_HARNESS_FILES = \
|
||||
$(srcdir)/runreftest.py \
|
||||
$(srcdir)/remotereftest.py \
|
||||
$(srcdir)/runreftestb2g.py \
|
||||
$(srcdir)/b2g_start_script.js \
|
||||
automation.py \
|
||||
$(topsrcdir)/build/mobile/devicemanager.py \
|
||||
$(topsrcdir)/build/mobile/devicemanagerADB.py \
|
||||
$(topsrcdir)/build/mobile/devicemanagerSUT.py \
|
||||
$(topsrcdir)/build/mobile/b2gautomation.py \
|
||||
$(topsrcdir)/build/automationutils.py \
|
||||
$(topsrcdir)/build/mobile/remoteautomation.py \
|
||||
$(topsrcdir)/testing/mochitest/server.js \
|
||||
|
30
layout/tools/reftest/b2g_start_script.js
Normal file
30
layout/tools/reftest/b2g_start_script.js
Normal file
@ -0,0 +1,30 @@
|
||||
function setDefaultPrefs() {
|
||||
// This code sets the preferences for extension-based reftest; for
|
||||
// command-line based reftest they are set in function handler_handle in
|
||||
// reftest-cmdline.js. These two locations should stay in sync.
|
||||
//
|
||||
// FIXME: These should be in only one place.
|
||||
var prefs = Components.classes["@mozilla.org/preferences-service;1"].
|
||||
getService(Components.interfaces.nsIPrefService);
|
||||
var branch = prefs.getDefaultBranch("");
|
||||
branch.setBoolPref("gfx.color_management.force_srgb", true);
|
||||
branch.setBoolPref("browser.dom.window.dump.enabled", true);
|
||||
branch.setIntPref("ui.caretBlinkTime", -1);
|
||||
branch.setBoolPref("dom.send_after_paint_to_content", true);
|
||||
// no slow script dialogs
|
||||
branch.setIntPref("dom.max_script_run_time", 0);
|
||||
branch.setIntPref("dom.max_chrome_script_run_time", 0);
|
||||
branch.setIntPref("hangmonitor.timeout", 0);
|
||||
// Ensure autoplay is enabled for all platforms.
|
||||
branch.setBoolPref("media.autoplay.enabled", true);
|
||||
// Disable updates
|
||||
branch.setBoolPref("app.update.enabled", false);
|
||||
}
|
||||
|
||||
// Load into any existing windows
|
||||
let wm = Components.classes["@mozilla.org/appshell/window-mediator;1"]
|
||||
.getService(Components.interfaces.nsIWindowMediator);
|
||||
let win = wm.getMostRecentWindow('');
|
||||
setDefaultPrefs();
|
||||
Components.utils.import("chrome://reftest/content/reftest.jsm");
|
||||
OnRefTestLoad(win);
|
@ -1,6 +1,6 @@
|
||||
reftest.jar:
|
||||
% content reftest %content/
|
||||
content/reftest-content.js (reftest-content.js)
|
||||
* content/reftest-content.js (reftest-content.js)
|
||||
#ifdef BOOTSTRAP
|
||||
* content/reftest.jsm (reftest.js)
|
||||
#else
|
||||
|
@ -75,7 +75,7 @@ var gClearingForAssertionCheck = false;
|
||||
|
||||
const TYPE_SCRIPT = 'script'; // test contains individual test results
|
||||
|
||||
function markupDocumentViewer() {
|
||||
function markupDocumentViewer() {
|
||||
return docShell.contentViewer.QueryInterface(CI.nsIMarkupDocumentViewer);
|
||||
}
|
||||
|
||||
@ -119,7 +119,9 @@ function PaintWaitFinishedListener(event)
|
||||
|
||||
function OnInitialLoad()
|
||||
{
|
||||
#ifndef REFTEST_B2G
|
||||
removeEventListener("load", OnInitialLoad, true);
|
||||
#endif
|
||||
|
||||
gDebug = CC[DEBUG_CONTRACTID].getService(CI.nsIDebug2);
|
||||
|
||||
@ -132,7 +134,7 @@ function OnInitialLoad()
|
||||
|
||||
addEventListener("MozPaintWait", PaintWaitListener, true);
|
||||
addEventListener("MozPaintWaitFinished", PaintWaitFinishedListener, true);
|
||||
|
||||
|
||||
LogWarning("Using browser remote="+ gBrowserIsRemote +"\n");
|
||||
}
|
||||
|
||||
@ -170,11 +172,16 @@ function resetZoom() {
|
||||
}
|
||||
|
||||
function doPrintMode(contentRootElement) {
|
||||
#if REFTEST_B2G
|
||||
// nsIPrintSettings not available in B2G
|
||||
return false;
|
||||
#else
|
||||
// use getAttribute because className works differently in HTML and SVG
|
||||
return contentRootElement &&
|
||||
contentRootElement.hasAttribute('class') &&
|
||||
contentRootElement.getAttribute('class').split(/\s+/)
|
||||
.indexOf("reftest-print") != -1;
|
||||
#endif
|
||||
}
|
||||
|
||||
function setupPrintMode() {
|
||||
@ -289,7 +296,7 @@ function WaitForTestEnd(contentRootElement, inPrintMode) {
|
||||
} catch (e) {
|
||||
LogWarning("flushWindow failed: " + e + "\n");
|
||||
}
|
||||
|
||||
|
||||
if (!afterPaintWasPending && utils.isMozAfterPaintPending) {
|
||||
LogInfo("FlushRendering generated paint for window " + win.location.href);
|
||||
anyPendingPaintsGeneratedInDescendants = true;
|
||||
@ -380,7 +387,7 @@ function WaitForTestEnd(contentRootElement, inPrintMode) {
|
||||
}
|
||||
|
||||
state = STATE_WAITING_FOR_REFTEST_WAIT_REMOVAL;
|
||||
var hasReftestWait = shouldWaitForReftestWaitRemoval(contentRootElement);
|
||||
var hasReftestWait = shouldWaitForReftestWaitRemoval(contentRootElement);
|
||||
// Notify the test document that now is a good time to test some invalidation
|
||||
LogInfo("MakeProgress: dispatching MozReftestInvalidate");
|
||||
if (contentRootElement) {
|
||||
@ -459,12 +466,18 @@ function WaitForTestEnd(contentRootElement, inPrintMode) {
|
||||
MakeProgress();
|
||||
}
|
||||
|
||||
#if REFTEST_B2G
|
||||
function OnDocumentLoad()
|
||||
{
|
||||
var currentDoc = content.document;
|
||||
#else
|
||||
function OnDocumentLoad(event)
|
||||
{
|
||||
var currentDoc = content.document;
|
||||
if (event.target != currentDoc)
|
||||
// Ignore load events for subframes.
|
||||
return;
|
||||
#endif
|
||||
|
||||
if (gClearingForAssertionCheck &&
|
||||
currentDoc.location.href == BLANK_URL_FOR_CLEARING) {
|
||||
@ -750,7 +763,7 @@ function SendInitCanvasWithSnapshot()
|
||||
// browser though, it doesn't wrt correctness whether this request
|
||||
// is sync or async.
|
||||
var ret = sendSyncMessage("reftest:InitCanvasWithSnapshot")[0];
|
||||
|
||||
|
||||
gHaveCanvasSnapshot = ret.painted;
|
||||
return ret.painted;
|
||||
}
|
||||
@ -780,7 +793,7 @@ function SendUpdateCanvasForEvent(event)
|
||||
{
|
||||
var win = content;
|
||||
var scale = markupDocumentViewer().fullZoom;
|
||||
|
||||
|
||||
var rects = [ ];
|
||||
var rectList = event.clientRects;
|
||||
for (var i = 0; i < rectList.length; ++i) {
|
||||
@ -803,5 +816,9 @@ function SendUpdateCanvasForEvent(event)
|
||||
sendAsyncMessage("reftest:UpdateCanvasForInvalidation", { rects: rects });
|
||||
}
|
||||
}
|
||||
|
||||
#if REFTEST_B2G
|
||||
OnInitialLoad();
|
||||
OnDocumentLoad();
|
||||
#else
|
||||
addEventListener("load", OnInitialLoad, true);
|
||||
#endif
|
||||
|
@ -35,7 +35,7 @@ const NS_DIRECTORY_SERVICE_CONTRACTID =
|
||||
const NS_OBSERVER_SERVICE_CONTRACTID =
|
||||
"@mozilla.org/observer-service;1";
|
||||
|
||||
Components.utils.import("resource://gre/modules/FileUtils.jsm");
|
||||
Components.utils.import("resource://gre/modules/FileUtils.jsm");
|
||||
|
||||
var gLoadTimeout = 0;
|
||||
var gTimeoutHook = null;
|
||||
@ -109,7 +109,7 @@ const TYPE_SCRIPT = 'script'; // test contains individual test results
|
||||
|
||||
// The order of these constants matters, since when we have a status
|
||||
// listed for a *manifest*, we combine the status with the status for
|
||||
// the test by using the *larger*.
|
||||
// the test by using the *larger*.
|
||||
// FIXME: In the future, we may also want to use this rule for combining
|
||||
// statuses that are on the same line (rather than making the last one
|
||||
// win).
|
||||
@ -206,7 +206,7 @@ function OnRefTestLoad(win)
|
||||
.getService(CI.nsIProperties)
|
||||
.get("ProfD", CI.nsIFile);
|
||||
gCrashDumpDir.append("minidumps");
|
||||
|
||||
|
||||
var env = CC["@mozilla.org/process/environment;1"].
|
||||
getService(CI.nsIEnvironment);
|
||||
gVerbose = !!env.get("MOZ_REFTEST_VERBOSE");
|
||||
@ -218,7 +218,7 @@ function OnRefTestLoad(win)
|
||||
} catch (e) {
|
||||
gBrowserIsRemote = false;
|
||||
}
|
||||
|
||||
|
||||
if (win === undefined || win == null) {
|
||||
win = window;
|
||||
}
|
||||
@ -235,7 +235,11 @@ function OnRefTestLoad(win)
|
||||
gBrowser.setAttribute("style", "min-width: 800px; min-height: 1000px; max-width: 800px; max-height: 1000px");
|
||||
|
||||
#if BOOTSTRAP
|
||||
#if REFTEST_B2G
|
||||
var doc = gContainingWindow.document.getElementsByTagName("window")[0];
|
||||
#else
|
||||
var doc = gContainingWindow.document.getElementById('main-window');
|
||||
#endif
|
||||
while (doc.hasChildNodes()) {
|
||||
doc.removeChild(doc.firstChild);
|
||||
}
|
||||
@ -260,27 +264,31 @@ function InitAndStartRefTests()
|
||||
} catch(e) {
|
||||
gDumpLog("REFTEST TEST-UNEXPECTED-FAIL | | EXCEPTION: " + e + "\n");
|
||||
}
|
||||
|
||||
|
||||
/* set the gLoadTimeout */
|
||||
try {
|
||||
gLoadTimeout = prefs.getIntPref("reftest.timeout");
|
||||
} catch(e) {
|
||||
} catch(e) {
|
||||
gLoadTimeout = 5 * 60 * 1000; //5 minutes as per bug 479518
|
||||
}
|
||||
|
||||
|
||||
/* Get the logfile for android tests */
|
||||
try {
|
||||
var logFile = prefs.getCharPref("reftest.logFile");
|
||||
if (logFile) {
|
||||
try {
|
||||
var f = FileUtils.File(logFile);
|
||||
var mfl = FileUtils.openFileOutputStream(f, FileUtils.MODE_WRONLY | FileUtils.MODE_CREATE);
|
||||
var mfl = FileUtils.openFileOutputStream(f, FileUtils.MODE_WRONLY | FileUtils.MODE_CREATE);
|
||||
// Set to mirror to stdout as well as the file
|
||||
gDumpLog = function (msg) {
|
||||
#if BOOTSTRAP
|
||||
//NOTE: on android-xul, we have a libc crash if we do a dump with %7s in the string
|
||||
#if REFTEST_B2G
|
||||
dump(msg);
|
||||
#else
|
||||
dump(msg);
|
||||
//NOTE: on android-xul, we have a libc crash if we do a dump with %7s in the string
|
||||
#endif
|
||||
#else
|
||||
dump(msg);
|
||||
#endif
|
||||
mfl.write(msg, msg.length);
|
||||
};
|
||||
@ -291,10 +299,10 @@ function InitAndStartRefTests()
|
||||
}
|
||||
}
|
||||
} catch(e) {}
|
||||
|
||||
|
||||
try {
|
||||
gRemote = prefs.getBoolPref("reftest.remote");
|
||||
} catch(e) {
|
||||
} catch(e) {
|
||||
gRemote = false;
|
||||
}
|
||||
|
||||
@ -374,22 +382,22 @@ function StartTests()
|
||||
} catch(e) {
|
||||
gDumpLog("REFTEST TEST-UNEXPECTED-FAIL | | EXCEPTION: " + e + "\n");
|
||||
}
|
||||
|
||||
|
||||
try {
|
||||
gNoCanvasCache = prefs.getIntPref("reftest.nocache");
|
||||
} catch(e) {
|
||||
} catch(e) {
|
||||
gNoCanvasCache = false;
|
||||
}
|
||||
|
||||
try {
|
||||
gRunSlowTests = prefs.getIntPref("reftest.skipslowtests");
|
||||
} catch(e) {
|
||||
} catch(e) {
|
||||
gRunSlowTests = false;
|
||||
}
|
||||
|
||||
try {
|
||||
uri = prefs.getCharPref("reftest.uri");
|
||||
} catch(e) {
|
||||
} catch(e) {
|
||||
uri = "";
|
||||
}
|
||||
|
||||
@ -415,7 +423,6 @@ function StartTests()
|
||||
DoneTests();
|
||||
}
|
||||
#endif
|
||||
|
||||
try {
|
||||
ReadTopManifest(uri);
|
||||
BuildUseCounts();
|
||||
@ -480,19 +487,26 @@ function BuildConditionSandbox(aURL) {
|
||||
}
|
||||
|
||||
|
||||
#if REFTEST_B2G
|
||||
// XXX nsIGfxInfo isn't available in B2G
|
||||
sandbox.d2d = false;
|
||||
sandbox.azureQuartz = false;
|
||||
sandbox.azureSkia = false;
|
||||
sandbox.contentSameGfxBackendAsCanvas = false;
|
||||
#else
|
||||
var gfxInfo = (NS_GFXINFO_CONTRACTID in CC) && CC[NS_GFXINFO_CONTRACTID].getService(CI.nsIGfxInfo);
|
||||
try {
|
||||
sandbox.d2d = gfxInfo.D2DEnabled;
|
||||
} catch (e) {
|
||||
sandbox.d2d = false;
|
||||
}
|
||||
|
||||
var info = gfxInfo.getInfo();
|
||||
sandbox.azureQuartz = info.AzureCanvasBackend == "quartz";
|
||||
sandbox.azureSkia = info.AzureCanvasBackend == "skia";
|
||||
// true if we are using the same Azure backend for rendering canvas and content
|
||||
sandbox.contentSameGfxBackendAsCanvas = info.AzureContentBackend == info.AzureCanvasBackend
|
||||
|| (info.AzureContentBackend == "none" && info.AzureCanvasBackend == "cairo");
|
||||
#endif
|
||||
|
||||
sandbox.layersGPUAccelerated =
|
||||
gWindowUtils.layerManagerType != "Basic";
|
||||
@ -500,7 +514,8 @@ function BuildConditionSandbox(aURL) {
|
||||
gWindowUtils.layerManagerType == "OpenGL";
|
||||
|
||||
// Shortcuts for widget toolkits.
|
||||
sandbox.Android = xr.OS == "Android";
|
||||
sandbox.B2G = xr.widgetToolkit == "gonk";
|
||||
sandbox.Android = xr.OS == "Android" && !sandbox.B2G;
|
||||
sandbox.cocoaWidget = xr.widgetToolkit == "cocoa";
|
||||
sandbox.gtk2Widget = xr.widgetToolkit == "gtk2";
|
||||
sandbox.qtWidget = xr.widgetToolkit == "qt";
|
||||
@ -599,7 +614,6 @@ function BuildConditionSandbox(aURL) {
|
||||
dump("REFTEST INFO | " + JSON.stringify(sandbox) + " \n");
|
||||
gDumpedConditionSandbox = true;
|
||||
}
|
||||
|
||||
return sandbox;
|
||||
}
|
||||
|
||||
@ -624,7 +638,7 @@ function ReadManifest(aURL, inherited_status)
|
||||
var inputStream = channel.open();
|
||||
if (channel instanceof Components.interfaces.nsIHttpChannel
|
||||
&& channel.responseStatus != 200) {
|
||||
gDumpLog("REFTEST TEST-UNEXPECTED-FAIL | | HTTP ERROR : " +
|
||||
gDumpLog("REFTEST TEST-UNEXPECTED-FAIL | | HTTP ERROR : " +
|
||||
channel.responseStatus + "\n");
|
||||
}
|
||||
var streamBuf = getStreamContent(inputStream);
|
||||
@ -633,7 +647,6 @@ function ReadManifest(aURL, inherited_status)
|
||||
|
||||
// Build the sandbox for fails-if(), etc., condition evaluation.
|
||||
var sandbox = BuildConditionSandbox(aURL);
|
||||
|
||||
var lineNo = 0;
|
||||
var urlprefix = "";
|
||||
for each (var str in lines) {
|
||||
@ -1180,10 +1193,12 @@ function DoneTests()
|
||||
let appStartup = CC["@mozilla.org/toolkit/app-startup;1"].getService(CI.nsIAppStartup);
|
||||
appStartup.quit(CI.nsIAppStartup.eForceQuit);
|
||||
}
|
||||
if (gServer)
|
||||
if (gServer) {
|
||||
gServer.stop(onStopped);
|
||||
else
|
||||
}
|
||||
else {
|
||||
onStopped();
|
||||
}
|
||||
}
|
||||
|
||||
function UpdateCanvasCache(url, canvas)
|
||||
|
@ -51,7 +51,7 @@ class RemoteOptions(ReftestOptions):
|
||||
self.add_option("--remote-webserver", action="store",
|
||||
type = "string", dest = "remoteWebServer",
|
||||
help = "IP Address of the webserver hosting the reftest content")
|
||||
defaults["remoteWebServer"] = automation.getLanIp()
|
||||
defaults["remoteWebServer"] = automation.getLanIp()
|
||||
|
||||
self.add_option("--http-port", action = "store",
|
||||
type = "string", dest = "httpPort",
|
||||
@ -114,23 +114,23 @@ class RemoteOptions(ReftestOptions):
|
||||
# Neither remoteAppPath nor app are set -- error
|
||||
print "ERROR: You must specify either appPath or app"
|
||||
return None
|
||||
|
||||
|
||||
if (options.xrePath == None):
|
||||
print "ERROR: You must specify the path to the controller xre directory"
|
||||
return None
|
||||
else:
|
||||
# Ensure xrepath is a full path
|
||||
options.xrePath = os.path.abspath(options.xrePath)
|
||||
|
||||
|
||||
# Default to <deviceroot>/reftest/reftest.log
|
||||
if (options.remoteLogFile == None):
|
||||
options.remoteLogFile = 'reftest.log'
|
||||
|
||||
options.localLogName = options.remoteLogFile
|
||||
options.remoteLogFile = options.remoteTestRoot + '/' + options.remoteLogFile
|
||||
|
||||
|
||||
# Ensure that the options.logfile (which the base class uses) is set to
|
||||
# the remote setting when running remote. Also, if the user set the
|
||||
# the remote setting when running remote. Also, if the user set the
|
||||
# log file name there, use that instead of reusing the remotelogfile as above.
|
||||
if (options.logFile):
|
||||
# If the user specified a local logfile name use that
|
||||
@ -168,7 +168,7 @@ class ReftestServer:
|
||||
|
||||
def start(self):
|
||||
"Run the Refest server, returning the process ID of the server."
|
||||
|
||||
|
||||
env = self._automation.environment(xrePath = self._xrePath)
|
||||
env["XPCOM_DEBUG_BREAK"] = "warn"
|
||||
if self._automation.IS_WIN32:
|
||||
@ -177,7 +177,7 @@ class ReftestServer:
|
||||
args = ["-g", self._xrePath,
|
||||
"-v", "170",
|
||||
"-f", os.path.join(self.scriptDir, "reftest/components/httpd.js"),
|
||||
"-e", "const _PROFILE_PATH = '%(profile)s';const _SERVER_PORT = '%(port)s'; const _SERVER_ADDR ='%(server)s';" %
|
||||
"-e", "const _PROFILE_PATH = '%(profile)s';const _SERVER_PORT = '%(port)s'; const _SERVER_ADDR ='%(server)s';" %
|
||||
{"profile" : self._profileDir.replace('\\', '\\\\'), "port" : self.httpPort, "server" : self.webServer },
|
||||
"-f", os.path.join(self.scriptDir, "server.js")]
|
||||
|
||||
@ -211,16 +211,17 @@ class ReftestServer:
|
||||
return 1
|
||||
|
||||
def stop(self):
|
||||
try:
|
||||
c = urllib2.urlopen(self.shutdownURL)
|
||||
c.read()
|
||||
c.close()
|
||||
if hasattr(self, '_process'):
|
||||
try:
|
||||
c = urllib2.urlopen(self.shutdownURL)
|
||||
c.read()
|
||||
c.close()
|
||||
|
||||
rtncode = self._process.poll()
|
||||
if (rtncode == None):
|
||||
self._process.terminate()
|
||||
except:
|
||||
self._process.kill()
|
||||
rtncode = self._process.poll()
|
||||
if (rtncode == None):
|
||||
self._process.terminate()
|
||||
except:
|
||||
self._process.kill()
|
||||
|
||||
class RemoteReftest(RefTest):
|
||||
remoteApp = ''
|
||||
@ -279,7 +280,7 @@ class RemoteReftest(RefTest):
|
||||
xpcshell = "xpcshell"
|
||||
if (os.name == "nt"):
|
||||
xpcshell += ".exe"
|
||||
|
||||
|
||||
if (options.utilityPath):
|
||||
paths.insert(0, options.utilityPath)
|
||||
options.utilityPath = self.findPath(paths, xpcshell)
|
||||
@ -299,7 +300,7 @@ class RemoteReftest(RefTest):
|
||||
options.xrePath = remoteXrePath
|
||||
options.utilityPath = remoteUtilityPath
|
||||
return 0
|
||||
|
||||
|
||||
def stopWebServer(self, options):
|
||||
self.server.stop()
|
||||
|
||||
@ -333,7 +334,7 @@ user_pref("capability.principal.codebase.p2.id", "http://%s:%s");
|
||||
def copyExtraFilesToProfile(self, options, profileDir):
|
||||
RefTest.copyExtraFilesToProfile(self, options, profileDir)
|
||||
if (self._devicemanager.pushDir(profileDir, options.remoteProfile) == None):
|
||||
raise devicemanager.FileError("Failed to copy extra files to device")
|
||||
raise devicemanager.FileError("Failed to copy extra files to device")
|
||||
|
||||
def getManifestPath(self, path):
|
||||
return path
|
||||
|
517
layout/tools/reftest/runreftestb2g.py
Normal file
517
layout/tools/reftest/runreftestb2g.py
Normal file
@ -0,0 +1,517 @@
|
||||
# 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/.
|
||||
|
||||
import ConfigParser
|
||||
import os
|
||||
import re
|
||||
import sys
|
||||
import tempfile
|
||||
import time
|
||||
import urllib
|
||||
import traceback
|
||||
|
||||
# We need to know our current directory so that we can serve our test files from it.
|
||||
SCRIPT_DIRECTORY = os.path.abspath(os.path.realpath(os.path.dirname(sys.argv[0])))
|
||||
sys.path.insert(0, SCRIPT_DIRECTORY)
|
||||
|
||||
from automation import Automation
|
||||
from b2gautomation import B2GRemoteAutomation
|
||||
from runreftest import RefTest
|
||||
from runreftest import ReftestOptions
|
||||
from remotereftest import ReftestServer
|
||||
|
||||
from mozprofile import Profile
|
||||
from mozrunner import Runner
|
||||
|
||||
import devicemanagerADB
|
||||
import manifestparser
|
||||
|
||||
from marionette import Marionette
|
||||
|
||||
|
||||
class B2GOptions(ReftestOptions):
|
||||
|
||||
def __init__(self, automation, **kwargs):
|
||||
defaults = {}
|
||||
ReftestOptions.__init__(self, automation)
|
||||
|
||||
self.add_option("--b2gpath", action="store",
|
||||
type = "string", dest = "b2gPath",
|
||||
help = "path to B2G repo or qemu dir")
|
||||
defaults["b2gPath"] = None
|
||||
|
||||
self.add_option("--marionette", action="store",
|
||||
type = "string", dest = "marionette",
|
||||
help = "host:port to use when connecting to Marionette")
|
||||
defaults["marionette"] = None
|
||||
|
||||
self.add_option("--emulator", action="store",
|
||||
type="string", dest = "emulator",
|
||||
help = "Architecture of emulator to use: x86 or arm")
|
||||
defaults["emulator"] = None
|
||||
self.add_option("--emulator-res", action="store",
|
||||
type="string", dest = "emulator_res",
|
||||
help = "Emulator resolution of the format '<width>x<height>'")
|
||||
defaults["emulator_res"] = None
|
||||
|
||||
self.add_option("--no-window", action="store_true",
|
||||
dest = "noWindow",
|
||||
help = "Pass --no-window to the emulator")
|
||||
defaults["noWindow"] = False
|
||||
|
||||
self.add_option("--adbpath", action="store",
|
||||
type = "string", dest = "adbPath",
|
||||
help = "path to adb")
|
||||
defaults["adbPath"] = "adb"
|
||||
|
||||
self.add_option("--deviceIP", action="store",
|
||||
type = "string", dest = "deviceIP",
|
||||
help = "ip address of remote device to test")
|
||||
defaults["deviceIP"] = None
|
||||
|
||||
self.add_option("--devicePort", action="store",
|
||||
type = "string", dest = "devicePort",
|
||||
help = "port of remote device to test")
|
||||
defaults["devicePort"] = 20701
|
||||
|
||||
self.add_option("--remote-logfile", action="store",
|
||||
type = "string", dest = "remoteLogFile",
|
||||
help = "Name of log file on the device relative to the device root. PLEASE ONLY USE A FILENAME.")
|
||||
defaults["remoteLogFile"] = None
|
||||
|
||||
self.add_option("--remote-webserver", action = "store",
|
||||
type = "string", dest = "remoteWebServer",
|
||||
help = "ip address where the remote web server is hosted at")
|
||||
defaults["remoteWebServer"] = None
|
||||
|
||||
self.add_option("--http-port", action = "store",
|
||||
type = "string", dest = "httpPort",
|
||||
help = "ip address where the remote web server is hosted at")
|
||||
defaults["httpPort"] = automation.DEFAULT_HTTP_PORT
|
||||
|
||||
self.add_option("--ssl-port", action = "store",
|
||||
type = "string", dest = "sslPort",
|
||||
help = "ip address where the remote web server is hosted at")
|
||||
defaults["sslPort"] = automation.DEFAULT_SSL_PORT
|
||||
|
||||
self.add_option("--pidfile", action = "store",
|
||||
type = "string", dest = "pidFile",
|
||||
help = "name of the pidfile to generate")
|
||||
defaults["pidFile"] = ""
|
||||
defaults["remoteTestRoot"] = None
|
||||
defaults["logFile"] = "reftest.log"
|
||||
defaults["autorun"] = True
|
||||
defaults["closeWhenDone"] = True
|
||||
defaults["testPath"] = ""
|
||||
|
||||
self.set_defaults(**defaults)
|
||||
|
||||
def verifyRemoteOptions(self, options):
|
||||
options.remoteTestRoot = self._automation._devicemanager.getDeviceRoot() + "/reftest"
|
||||
options.remoteProfile = options.remoteTestRoot + "/profile"
|
||||
|
||||
productRoot = options.remoteTestRoot + "/" + self._automation._product
|
||||
if options.utilityPath == self._automation.DIST_BIN:
|
||||
options.utilityPath = productRoot + "/bin"
|
||||
|
||||
if options.remoteWebServer == None:
|
||||
if os.name != "nt":
|
||||
options.remoteWebServer = self._automation.getLanIp()
|
||||
else:
|
||||
print "ERROR: you must specify a --remote-webserver=<ip address>\n"
|
||||
return None
|
||||
|
||||
options.webServer = options.remoteWebServer
|
||||
|
||||
#if not options.emulator and not options.deviceIP:
|
||||
# print "ERROR: you must provide a device IP"
|
||||
# return None
|
||||
|
||||
if options.remoteLogFile == None:
|
||||
options.remoteLogFile = "reftest.log"
|
||||
|
||||
options.localLogName = options.remoteLogFile
|
||||
options.remoteLogFile = options.remoteTestRoot + '/' + options.remoteLogFile
|
||||
|
||||
# Ensure that the options.logfile (which the base class uses) is set to
|
||||
# the remote setting when running remote. Also, if the user set the
|
||||
# log file name there, use that instead of reusing the remotelogfile as above.
|
||||
if (options.logFile):
|
||||
# If the user specified a local logfile name use that
|
||||
options.localLogName = options.logFile
|
||||
options.logFile = options.remoteLogFile
|
||||
|
||||
# Only reset the xrePath if it wasn't provided
|
||||
if options.xrePath == None:
|
||||
options.xrePath = options.utilityPath
|
||||
options.xrePath = os.path.abspath(options.xrePath)
|
||||
|
||||
if options.pidFile != "":
|
||||
f = open(options.pidFile, 'w')
|
||||
f.write("%s" % os.getpid())
|
||||
f.close()
|
||||
|
||||
return options
|
||||
|
||||
|
||||
class ProfileConfigParser(ConfigParser.RawConfigParser):
|
||||
"""Subclass of RawConfigParser that outputs .ini files in the exact
|
||||
format expected for profiles.ini, which is slightly different
|
||||
than the default format.
|
||||
"""
|
||||
|
||||
def optionxform(self, optionstr):
|
||||
return optionstr
|
||||
|
||||
def write(self, fp):
|
||||
if self._defaults:
|
||||
fp.write("[%s]\n" % ConfigParser.DEFAULTSECT)
|
||||
for (key, value) in self._defaults.items():
|
||||
fp.write("%s=%s\n" % (key, str(value).replace('\n', '\n\t')))
|
||||
fp.write("\n")
|
||||
for section in self._sections:
|
||||
fp.write("[%s]\n" % section)
|
||||
for (key, value) in self._sections[section].items():
|
||||
if key == "__name__":
|
||||
continue
|
||||
if (value is not None) or (self._optcre == self.OPTCRE):
|
||||
key = "=".join((key, str(value).replace('\n', '\n\t')))
|
||||
fp.write("%s\n" % (key))
|
||||
fp.write("\n")
|
||||
|
||||
|
||||
class B2GReftest(RefTest):
|
||||
|
||||
_automation = None
|
||||
_devicemanager = None
|
||||
localProfile = None
|
||||
remoteApp = ''
|
||||
profile = None
|
||||
|
||||
def __init__(self, automation, devicemanager, options, scriptDir):
|
||||
self._automation = automation
|
||||
RefTest.__init__(self, self._automation)
|
||||
self._devicemanager = devicemanager
|
||||
self.runSSLTunnel = False
|
||||
self.remoteTestRoot = options.remoteTestRoot
|
||||
self.remoteProfile = options.remoteProfile
|
||||
self._automation.setRemoteProfile(self.remoteProfile)
|
||||
self.localLogName = options.localLogName
|
||||
self.remoteLogFile = options.remoteLogFile
|
||||
self.userJS = '/data/local/user.js'
|
||||
self.testDir = '/data/local/tests'
|
||||
self.remoteMozillaPath = '/data/b2g/mozilla'
|
||||
self.remoteProfilesIniPath = os.path.join(self.remoteMozillaPath, 'profiles.ini')
|
||||
self.originalProfilesIni = None
|
||||
self.scriptDir = scriptDir
|
||||
self.SERVER_STARTUP_TIMEOUT = 90
|
||||
if self._automation.IS_DEBUG_BUILD:
|
||||
self.SERVER_STARTUP_TIMEOUT = 180
|
||||
|
||||
def cleanup(self, profileDir):
|
||||
# Pull results back from device
|
||||
if (self.remoteLogFile):
|
||||
try:
|
||||
self._devicemanager.getFile(self.remoteLogFile, self.localLogName)
|
||||
except:
|
||||
print "ERROR: We were not able to retrieve the info from %s" % self.remoteLogFile
|
||||
sys.exit(5)
|
||||
|
||||
# Restore the original profiles.ini.
|
||||
if self.originalProfilesIni:
|
||||
try:
|
||||
if not self._automation._is_emulator:
|
||||
self.restoreProfilesIni()
|
||||
os.remove(self.originalProfilesIni)
|
||||
except:
|
||||
pass
|
||||
|
||||
if not self._automation._is_emulator:
|
||||
self._devicemanager.removeFile(self.remoteLogFile)
|
||||
self._devicemanager.removeDir(self.remoteProfile)
|
||||
self._devicemanager.removeDir(self.remoteTestRoot)
|
||||
|
||||
# Restore the original user.js.
|
||||
self._devicemanager.checkCmdAs(['shell', 'rm', '-f', self.userJS])
|
||||
if self._devicemanager.useDDCopy:
|
||||
self._devicemanager.checkCmdAs(['shell', 'dd', 'if=%s.orig' % self.userJS, 'of=%s' % self.userJS])
|
||||
else:
|
||||
self._devicemanager.checkCmdAs(['shell', 'cp', '%s.orig' % self.userJS, self.userJS])
|
||||
|
||||
# We've restored the original profile, so reboot the device so that
|
||||
# it gets picked up.
|
||||
self._automation.rebootDevice()
|
||||
|
||||
RefTest.cleanup(self, profileDir)
|
||||
if getattr(self, 'pidFile', '') != '':
|
||||
try:
|
||||
os.remove(self.pidFile)
|
||||
os.remove(self.pidFile + ".xpcshell.pid")
|
||||
except:
|
||||
print "Warning: cleaning up pidfile '%s' was unsuccessful from the test harness" % self.pidFile
|
||||
|
||||
def findPath(self, paths, filename = None):
|
||||
for path in paths:
|
||||
p = path
|
||||
if filename:
|
||||
p = os.path.join(p, filename)
|
||||
if os.path.exists(self.getFullPath(p)):
|
||||
return path
|
||||
return None
|
||||
|
||||
def startWebServer(self, options):
|
||||
""" Create the webserver on the host and start it up """
|
||||
remoteXrePath = options.xrePath
|
||||
remoteProfilePath = self.remoteProfile
|
||||
remoteUtilityPath = options.utilityPath
|
||||
localAutomation = Automation()
|
||||
localAutomation.IS_WIN32 = False
|
||||
localAutomation.IS_LINUX = False
|
||||
localAutomation.IS_MAC = False
|
||||
localAutomation.UNIXISH = False
|
||||
hostos = sys.platform
|
||||
if hostos in ['mac', 'darwin']:
|
||||
localAutomation.IS_MAC = True
|
||||
elif hostos in ['linux', 'linux2']:
|
||||
localAutomation.IS_LINUX = True
|
||||
localAutomation.UNIXISH = True
|
||||
elif hostos in ['win32', 'win64']:
|
||||
localAutomation.BIN_SUFFIX = ".exe"
|
||||
localAutomation.IS_WIN32 = True
|
||||
|
||||
paths = [options.xrePath,
|
||||
localAutomation.DIST_BIN,
|
||||
self._automation._product,
|
||||
os.path.join('..', self._automation._product)]
|
||||
options.xrePath = self.findPath(paths)
|
||||
if options.xrePath == None:
|
||||
print "ERROR: unable to find xulrunner path for %s, please specify with --xre-path" % (os.name)
|
||||
sys.exit(1)
|
||||
paths.append("bin")
|
||||
paths.append(os.path.join("..", "bin"))
|
||||
|
||||
xpcshell = "xpcshell"
|
||||
if (os.name == "nt"):
|
||||
xpcshell += ".exe"
|
||||
|
||||
if (options.utilityPath):
|
||||
paths.insert(0, options.utilityPath)
|
||||
options.utilityPath = self.findPath(paths, xpcshell)
|
||||
if options.utilityPath == None:
|
||||
print "ERROR: unable to find utility path for %s, please specify with --utility-path" % (os.name)
|
||||
sys.exit(1)
|
||||
|
||||
options.serverProfilePath = tempfile.mkdtemp()
|
||||
self.server = ReftestServer(localAutomation, options, self.scriptDir)
|
||||
retVal = self.server.start()
|
||||
if retVal:
|
||||
return retVal
|
||||
|
||||
if (options.pidFile != ""):
|
||||
f = open(options.pidFile + ".xpcshell.pid", 'w')
|
||||
f.write("%s" % self.server._process.pid)
|
||||
f.close()
|
||||
|
||||
retVal = self.server.ensureReady(self.SERVER_STARTUP_TIMEOUT)
|
||||
if retVal:
|
||||
return retVal
|
||||
|
||||
options.xrePath = remoteXrePath
|
||||
options.utilityPath = remoteUtilityPath
|
||||
options.profilePath = remoteProfilePath
|
||||
return 0
|
||||
|
||||
def stopWebServer(self, options):
|
||||
if hasattr(self, 'server'):
|
||||
self.server.stop()
|
||||
|
||||
|
||||
def restoreProfilesIni(self):
|
||||
# restore profiles.ini on the device to its previous state
|
||||
if not self.originalProfilesIni or not os.access(self.originalProfilesIni, os.F_OK):
|
||||
raise DMError('Unable to install original profiles.ini; file not found: %s',
|
||||
self.originalProfilesIni)
|
||||
|
||||
self._devicemanager.pushFile(self.originalProfilesIni, self.remoteProfilesIniPath)
|
||||
|
||||
def updateProfilesIni(self, profilePath):
|
||||
# update profiles.ini on the device to point to the test profile
|
||||
self.originalProfilesIni = tempfile.mktemp()
|
||||
self._devicemanager.getFile(self.remoteProfilesIniPath, self.originalProfilesIni)
|
||||
|
||||
config = ProfileConfigParser()
|
||||
config.read(self.originalProfilesIni)
|
||||
for section in config.sections():
|
||||
if 'Profile' in section:
|
||||
config.set(section, 'IsRelative', 0)
|
||||
config.set(section, 'Path', profilePath)
|
||||
|
||||
newProfilesIni = tempfile.mktemp()
|
||||
with open(newProfilesIni, 'wb') as configfile:
|
||||
config.write(configfile)
|
||||
|
||||
self._devicemanager.pushFile(newProfilesIni, self.remoteProfilesIniPath)
|
||||
try:
|
||||
os.remove(newProfilesIni)
|
||||
except:
|
||||
pass
|
||||
|
||||
|
||||
def createReftestProfile(self, options, profileDir, reftestlist):
|
||||
print "profileDir: " + str(profileDir)
|
||||
retVal = RefTest.createReftestProfile(self, options, profileDir, reftestlist, server=options.remoteWebServer)
|
||||
|
||||
# Turn off the locale picker screen
|
||||
fhandle = open(os.path.join(profileDir, "user.js"), 'a')
|
||||
fhandle.write("""
|
||||
user_pref("browser.homescreenURL", "data:text/html,<h1>reftests should start soon</h1>");
|
||||
user_pref("browser.manifestURL", "dummy (bug 772307)");
|
||||
user_pref("browser.firstrun.show.localepicker", false);
|
||||
user_pref("browser.dom.window.dump.enabled", true);
|
||||
user_pref("font.size.inflation.emPerLine", 0);
|
||||
user_pref("font.size.inflation.minTwips", 0);
|
||||
user_pref("reftest.remote", true);
|
||||
user_pref("toolkit.telemetry.prompted", true);
|
||||
user_pref("reftest.uri", "%s");
|
||||
""" % reftestlist)
|
||||
|
||||
#workaround for jsreftests.
|
||||
if getattr(options, 'enablePrivilege', False):
|
||||
fhandle.write("""
|
||||
user_pref("capability.principal.codebase.p2.granted", "UniversalXPConnect");
|
||||
user_pref("capability.principal.codebase.p2.id", "http://%s:%s");
|
||||
""" % (options.remoteWebServer, options.httpPort))
|
||||
|
||||
# Close the file
|
||||
fhandle.close()
|
||||
|
||||
# Copy the profile to the device.
|
||||
self._devicemanager.removeDir(self.remoteProfile)
|
||||
if self._devicemanager.pushDir(profileDir, self.remoteProfile) == None:
|
||||
raise devicemanager.FileError("Unable to copy profile to device.")
|
||||
|
||||
# In B2G, user.js is always read from /data/local, not the profile
|
||||
# directory. Backup the original user.js first so we can restore it.
|
||||
self._devicemanager.checkCmdAs(['shell', 'rm', '-f', '%s.orig' % self.userJS])
|
||||
if self._devicemanager.useDDCopy:
|
||||
self._devicemanager.checkCmdAs(['shell', 'dd', 'if=%s' % self.userJS, 'of=%s.orig' % self.userJS])
|
||||
else:
|
||||
self._devicemanager.checkCmdAs(['shell', 'cp', self.userJS, '%s.orig' % self.userJS])
|
||||
self._devicemanager.pushFile(os.path.join(profileDir, "user.js"), self.userJS)
|
||||
|
||||
self.updateProfilesIni(self.remoteProfile)
|
||||
|
||||
options.profilePath = self.remoteProfile
|
||||
return retVal
|
||||
|
||||
def copyExtraFilesToProfile(self, options, profileDir):
|
||||
RefTest.copyExtraFilesToProfile(self, options, profileDir)
|
||||
if (self._devicemanager.pushDir(profileDir, options.remoteProfile) == None):
|
||||
raise devicemanager.FileError("Failed to copy extra files to device")
|
||||
|
||||
def getManifestPath(self, path):
|
||||
return path
|
||||
|
||||
|
||||
def main(args=sys.argv[1:]):
|
||||
auto = B2GRemoteAutomation(None, "fennec", context_chrome=True)
|
||||
parser = B2GOptions(auto)
|
||||
options, args = parser.parse_args(args)
|
||||
|
||||
# create our Marionette instance
|
||||
kwargs = {}
|
||||
if options.emulator:
|
||||
kwargs['emulator'] = options.emulator
|
||||
auto.setEmulator(True)
|
||||
if options.noWindow:
|
||||
kwargs['noWindow'] = True
|
||||
if options.emulator_res:
|
||||
kwargs['emulator_res'] = options.emulator_res
|
||||
if options.b2gPath:
|
||||
kwargs['homedir'] = options.b2gPath
|
||||
if options.marionette:
|
||||
host,port = options.marionette.split(':')
|
||||
kwargs['host'] = host
|
||||
kwargs['port'] = int(port)
|
||||
marionette = Marionette(**kwargs)
|
||||
auto.marionette = marionette
|
||||
|
||||
# create the DeviceManager
|
||||
kwargs = {'adbPath': options.adbPath}
|
||||
if options.deviceIP:
|
||||
kwargs.update({'host': options.deviceIP,
|
||||
'port': options.devicePort})
|
||||
dm = devicemanagerADB.DeviceManagerADB(**kwargs)
|
||||
auto.setDeviceManager(dm)
|
||||
|
||||
options = parser.verifyRemoteOptions(options)
|
||||
if (options == None):
|
||||
print "ERROR: Invalid options specified, use --help for a list of valid options"
|
||||
sys.exit(1)
|
||||
|
||||
# TODO fix exception
|
||||
if not options.ignoreWindowSize:
|
||||
parts = dm.getInfo('screen')['screen'][0].split()
|
||||
width = int(parts[0].split(':')[1])
|
||||
height = int(parts[1].split(':')[1])
|
||||
if (width < 1366 or height < 1050):
|
||||
print "ERROR: Invalid screen resolution %sx%s, please adjust to 1366x1050 or higher" % (width, height)
|
||||
return 1
|
||||
|
||||
auto.setProduct("b2g")
|
||||
auto.testScript = os.path.join(SCRIPT_DIRECTORY, 'b2g_start_script.js')
|
||||
auto.logFinish = "REFTEST TEST-START | Shutdown"
|
||||
|
||||
reftest = B2GReftest(auto, dm, options, SCRIPT_DIRECTORY)
|
||||
# Create /data/local/tests, to force its use by DeviceManagerADB;
|
||||
# B2G won't run correctly with the profile installed to /mnt/sdcard.
|
||||
dm.mkDirs(reftest.testDir)
|
||||
|
||||
logParent = os.path.dirname(options.remoteLogFile)
|
||||
dm.mkDir(logParent);
|
||||
auto.setRemoteLog(options.remoteLogFile)
|
||||
auto.setServerInfo(options.webServer, options.httpPort, options.sslPort)
|
||||
|
||||
# Dynamically build the reftest URL if possible, beware that args[0] should exist 'inside' the webroot
|
||||
manifest = args[0]
|
||||
if os.path.exists(os.path.join(SCRIPT_DIRECTORY, args[0])):
|
||||
manifest = "http://%s:%s/%s" % (options.remoteWebServer, options.httpPort, args[0])
|
||||
elif os.path.exists(args[0]):
|
||||
manifestPath = os.path.abspath(args[0]).split(SCRIPT_DIRECTORY)[1].strip('/')
|
||||
manifest = "http://%s:%s/%s" % (options.remoteWebServer, options.httpPort, manifestPath)
|
||||
else:
|
||||
print "ERROR: Could not find test manifest '%s'" % manifest
|
||||
return 1
|
||||
|
||||
# Start the webserver
|
||||
retVal = 1
|
||||
try:
|
||||
retVal = reftest.startWebServer(options)
|
||||
if retVal:
|
||||
return retVal
|
||||
procName = options.app.split('/')[-1]
|
||||
if (dm.processExist(procName)):
|
||||
dm.killProcess(procName)
|
||||
|
||||
cmdlineArgs = ["-reftest", manifest]
|
||||
if getattr(options, 'bootstrap', False):
|
||||
cmdlineArgs = []
|
||||
|
||||
retVal = reftest.runTests(manifest, options, cmdlineArgs)
|
||||
except:
|
||||
print "TEST-UNEXPECTED-FAIL | %s | Exception caught while running tests." % sys.exc_info()[1]
|
||||
traceback.print_exc()
|
||||
reftest.stopWebServer(options)
|
||||
try:
|
||||
reftest.cleanup(None)
|
||||
except:
|
||||
pass
|
||||
return 1
|
||||
|
||||
reftest.stopWebServer(options)
|
||||
return retVal
|
||||
|
||||
if __name__ == "__main__":
|
||||
sys.exit(main())
|
||||
|
@ -159,6 +159,11 @@ REMOTE_REFTEST = rm -f ./$@.log && $(PYTHON) _tests/reftest/remotereftest.py \
|
||||
--app=$(TEST_PACKAGE_NAME) --deviceIP=${TEST_DEVICE} --xre-path=${MOZ_HOST_BIN} \
|
||||
$(SYMBOLS_PATH) $(EXTRA_TEST_ARGS) $(1) | tee ./$@.log
|
||||
|
||||
RUN_REFTEST_B2G = rm -f ./$@.log && $(PYTHON) _tests/reftest/runreftestb2g.py \
|
||||
--remote-webserver=10.0.2.2 --b2gpath=${B2G_PATH} --adbpath=${ADB_PATH} \
|
||||
--xre-path=${MOZ_HOST_BIN} $(SYMBOLS_PATH) --ignore-window-size \
|
||||
$(EXTRA_TEST_ARGS) $(1) | tee ./$@.log
|
||||
|
||||
ifeq ($(OS_ARCH),WINNT) #{
|
||||
# GPU-rendered shadow layers are unsupported here
|
||||
OOP_CONTENT = --setpref=browser.tabs.remote=true --setpref=layers.acceleration.disabled=true
|
||||
@ -186,6 +191,22 @@ reftest-remote:
|
||||
$(CHECK_TEST_ERROR); \
|
||||
fi
|
||||
|
||||
reftest-b2g: TEST_PATH?=layout/reftests/reftest.list
|
||||
reftest-b2g:
|
||||
@if [ ! -f ${MOZ_HOST_BIN}/xpcshell ]; then \
|
||||
echo "please set the MOZ_HOST_BIN environment variable"; \
|
||||
elif [ "${B2G_PATH}" = "" -o "${ADB_PATH}" = "" ]; then \
|
||||
echo "please set the B2G_PATH and ADB_PATH environment variables"; \
|
||||
else \
|
||||
ln -s $(abspath $(topsrcdir)) _tests/reftest/tests; \
|
||||
if [ "${REFTEST_PATH}" != "" ]; then \
|
||||
$(call RUN_REFTEST_B2G,tests/${REFTEST_PATH}); \
|
||||
else \
|
||||
$(call RUN_REFTEST_B2G,tests/$(TEST_PATH)); \
|
||||
fi; \
|
||||
$(CHECK_TEST_ERROR); \
|
||||
fi
|
||||
|
||||
reftest-ipc: TEST_PATH?=layout/reftests/reftest.list
|
||||
reftest-ipc:
|
||||
$(call RUN_REFTEST,$(topsrcdir)/$(TEST_PATH) $(OOP_CONTENT))
|
||||
|
Loading…
Reference in New Issue
Block a user