Bug 960671 - Part 1: Add attach/detch RDP requests to the MemoryActor. r=past

This commit is contained in:
Nick Fitzgerald 2014-07-30 11:47:00 +02:00
parent 0692009b1d
commit aab6e2e516
6 changed files with 227 additions and 56 deletions

View File

@ -4,9 +4,37 @@
"use strict";
const {Cc, Ci, Cu} = require("chrome");
const { Cc, Ci, Cu } = require("chrome");
let protocol = require("devtools/server/protocol");
let {method, RetVal} = protocol;
let { method, RetVal } = protocol;
const { reportException } = require("devtools/toolkit/DevToolsUtils");
/**
* A method decorator that ensures the actor is in the expected state before
* proceeding. If the actor is not in the expected state, the decorated method
* returns a rejected promise.
*
* @param String expectedState
* The expected state.
*
* @param Function method
* The actor method to proceed with when the actor is in the expected
* state.
*
* @returns Function
* The decorated method.
*/
function expectState(expectedState, method) {
return function(...args) {
if (this.state !== expectedState) {
const msg = "Wrong State: Expected '" + expectedState + "', but current "
+ "state is '" + this.state + "'";
return Promise.reject(new Error(msg));
}
return method.apply(this, args);
};
}
/**
* An actor that returns memory usage data for its parent actor's window.
@ -17,18 +45,59 @@ let {method, RetVal} = protocol;
let MemoryActor = protocol.ActorClass({
typeName: "memory",
initialize: function(conn, tabActor) {
get dbg() {
if (!this._dbg) {
this._dbg = this.parent.makeDebugger();
}
return this._dbg;
},
initialize: function(conn, parent) {
protocol.Actor.prototype.initialize.call(this, conn);
this.tabActor = tabActor;
this.parent = parent;
this._mgr = Cc["@mozilla.org/memory-reporter-manager;1"]
.getService(Ci.nsIMemoryReporterManager);
this.state = "detached";
this._dbg = null;
},
destroy: function() {
this._mgr = null;
if (this.state === "attached") {
this.detach();
}
protocol.Actor.prototype.destroy.call(this);
},
/**
* Attach to this MemoryActor.
*/
attach: method(expectState("detached", function() {
this.dbg.addDebuggees();
this.dbg.enabled = true;
this.state = "attached";
}), {
request: {},
response: {
type: "attached"
}
}),
/**
* Detach from this MemoryActor.
*/
detach: method(expectState("attached", function() {
this.dbg.removeAllDebuggees();
this.dbg.enabled = false;
this._dbg = null;
this.state = "detached";
}), {
request: {},
response: {
type: "detached"
}
}),
/**
* A method that returns a detailed breakdown of the memory consumption of the
* associated window.
@ -49,7 +118,7 @@ let MemoryActor = protocol.ActorClass({
let nonJSMilliseconds = {};
try {
this._mgr.sizeOfTab(this.tabActor.window, jsObjectsSize, jsStringsSize, jsOtherSize,
this._mgr.sizeOfTab(this.parent.window, jsObjectsSize, jsStringsSize, jsOtherSize,
domSize, styleSize, otherSize, totalSize, jsMilliseconds, nonJSMilliseconds);
result.total = totalSize.value;
result.domSize = domSize.value;
@ -61,9 +130,7 @@ let MemoryActor = protocol.ActorClass({
result.jsMilliseconds = jsMilliseconds.value.toFixed(1);
result.nonJSMilliseconds = nonJSMilliseconds.value.toFixed(1);
} catch (e) {
console.error(e);
let url = this.tabActor.url;
console.error("Error getting size of " + url);
reportException("MemoryActor.prototype.measure", e);
}
return result;

View File

@ -7,6 +7,7 @@ support-files =
nonchrome_unsafeDereference.html
inspector_getImageData.html
large-image.jpg
memory-helpers.js
small-image.gif
Debugger.Source.prototype.element.js
Debugger.Source.prototype.element-2.js
@ -66,6 +67,8 @@ skip-if = buildapp == 'mulet'
[test_inspector_getImageData.html]
skip-if = buildapp == 'mulet'
[test_memory.html]
[test_memory_attach_01.html]
[test_memory_attach_02.html]
[test_preference.html]
[test_connectToChild.html]
skip-if = buildapp == 'mulet'

View File

@ -0,0 +1,54 @@
let Cu = Components.utils;
let Cc = Components.classes;
let Ci = Components.interfaces;
Cu.import("resource://gre/modules/Services.jsm");
// Always log packets when running tests.
Services.prefs.setBoolPref("devtools.debugger.log", true);
SimpleTest.registerCleanupFunction(function() {
Services.prefs.clearUserPref("devtools.debugger.log");
});
Cu.import("resource://gre/modules/devtools/dbg-client.jsm");
Cu.import("resource://gre/modules/devtools/dbg-server.jsm");
Cu.import("resource://gre/modules/Task.jsm");
Cu.import("resource://gre/modules/devtools/Loader.jsm");
let { require } = devtools;
let { MemoryFront } = require("devtools/server/actors/memory");
function startServerAndGetSelectedTabMemory() {
DebuggerServer.init(() => true);
DebuggerServer.addBrowserActors();
var client = new DebuggerClient(DebuggerServer.connectPipe());
return new Promise((resolve, reject) => {
client.connect(response => {
if (response.error) {
reject(new Error(response.error + ": " + response.message));
return;
}
client.listTabs(response => {
if (response.error) {
reject(new Error(response.error + ": " + response.message));
return;
}
var form = response.tabs[response.selected];
var memory = MemoryFront(client, form);
resolve({ memory, client });
});
});
});
}
function destroyServerAndFinish(client) {
client.close(() => {
DebuggerServer.destroy();
SimpleTest.finish()
});
}

View File

@ -11,59 +11,26 @@ Bug 923275 - Add a memory monitor widget to the developer toolbar
</head>
<body>
<pre id="test">
<script src="memory-helpers.js" type="application/javascript;version=1.8"></script>
<script>
window.onload = function() {
var Cu = Components.utils;
var Cc = Components.classes;
var Ci = Components.interfaces;
Cu.import("resource://gre/modules/Services.jsm");
// Always log packets when running tests.
Services.prefs.setBoolPref("devtools.debugger.log", true);
SimpleTest.registerCleanupFunction(function() {
Services.prefs.clearUserPref("devtools.debugger.log");
});
Cu.import("resource://gre/modules/devtools/Loader.jsm");
Cu.import("resource://gre/modules/devtools/dbg-client.jsm");
Cu.import("resource://gre/modules/devtools/dbg-server.jsm");
SimpleTest.waitForExplicitFinish();
var {MemoryFront} = devtools.require("devtools/server/actors/memory");
DebuggerServer.init(function () { return true; });
DebuggerServer.addBrowserActors();
var client = new DebuggerClient(DebuggerServer.connectPipe());
client.connect(function onConnect() {
client.listTabs(function onListTabs(aResponse) {
var form = aResponse.tabs[aResponse.selected];
var front = MemoryFront(client, form);
front.measure().then(measurement => {
ok(measurement.total > 0, "total memory is valid");
ok(measurement.domSize > 0, "domSize is valid");
ok(measurement.styleSize > 0, "styleSize is valid");
ok(measurement.jsObjectsSize > 0, "jsObjectsSize is valid");
ok(measurement.jsStringsSize > 0, "jsStringsSize is valid");
ok(measurement.jsOtherSize > 0, "jsOtherSize is valid");
ok(measurement.otherSize > 0, "otherSize is valid");
ok(measurement.jsMilliseconds, "jsMilliseconds is valid");
ok(measurement.nonJSMilliseconds, "nonJSMilliseconds is valid");
client.close(() => {
DebuggerServer.destroy();
SimpleTest.finish()
});
});
});
Task.spawn(function* () {
var { memory, client } = yield startServerAndGetSelectedTabMemory();
var measurement = yield memory.measure();
ok(measurement.total > 0, "total memory is valid");
ok(measurement.domSize > 0, "domSize is valid");
ok(measurement.styleSize > 0, "styleSize is valid");
ok(measurement.jsObjectsSize > 0, "jsObjectsSize is valid");
ok(measurement.jsStringsSize > 0, "jsStringsSize is valid");
ok(measurement.jsOtherSize > 0, "jsOtherSize is valid");
ok(measurement.otherSize > 0, "otherSize is valid");
ok(measurement.jsMilliseconds, "jsMilliseconds is valid");
ok(measurement.nonJSMilliseconds, "nonJSMilliseconds is valid");
destroyServerAndFinish(client);
});
}
};
</script>
</pre>
</body>

View File

@ -0,0 +1,31 @@
<!DOCTYPE HTML>
<html>
<!--
Bug 960671 - Test attaching and detaching from a memory actor.
-->
<head>
<meta charset="utf-8">
<title>Memory monitoring actor test</title>
<script type="application/javascript" src="chrome://mochikit/content/tests/SimpleTest/SimpleTest.js"></script>
<link rel="stylesheet" type="text/css" href="chrome://mochikit/content/tests/SimpleTest/test.css">
</head>
<body>
<pre id="test">
<script src="memory-helpers.js" type="application/javascript;version=1.8"></script>
<script>
window.onload = function() {
SimpleTest.waitForExplicitFinish();
Task.spawn(function* () {
var { memory, client } = yield startServerAndGetSelectedTabMemory();
yield memory.attach();
ok(true, "Shouldn't have gotten an error attaching.");
yield memory.detach();
ok(true, "Shouldn't have gotten an error detaching.");
destroyServerAndFinish(client);
});
};
</script>
</pre>
</body>
</html>

View File

@ -0,0 +1,49 @@
<!DOCTYPE HTML>
<html>
<!--
Bug 960671 - Test attaching and detaching while in the wrong state.
-->
<head>
<meta charset="utf-8">
<title>Memory monitoring actor test</title>
<script type="application/javascript" src="chrome://mochikit/content/tests/SimpleTest/SimpleTest.js"></script>
<link rel="stylesheet" type="text/css" href="chrome://mochikit/content/tests/SimpleTest/test.css">
</head>
<body>
<pre id="test">
<script src="memory-helpers.js" type="application/javascript;version=1.8"></script>
<script>
window.onload = function() {
SimpleTest.waitForExplicitFinish();
Task.spawn(function* () {
var { memory, client } = yield startServerAndGetSelectedTabMemory();
var e = null;
try {
yield memory.detach();
}
catch (ee) {
e = ee;
}
ok(e, "Should have hit the wrongState error");
yield memory.attach();
e = null;
try {
yield memory.attach();
}
catch (ee) {
e = ee;
}
ok(e, "Should have hit the wrongState error");
yield memory.detach();
destroyServerAndFinish(client);
});
};
</script>
</pre>
</body>
</html>