Bug 793672 - Allow to get notifications for arbitrary observer topics through RDP with the profiler actor. r=past

This commit is contained in:
Mike Hommey 2012-10-06 10:37:58 +02:00
parent cbb20704b2
commit 958dbfdb59
2 changed files with 61 additions and 13 deletions

View File

@ -164,10 +164,10 @@ const ThreadStateTypes = {
* by the client.
*/
const UnsolicitedNotifications = {
"eventNotification": "eventNotification",
"newScript": "newScript",
"tabDetached": "tabDetached",
"tabNavigated": "tabNavigated",
"profilerStateChanged": "profilerStateChanged"
"tabNavigated": "tabNavigated"
};
/**

View File

@ -10,19 +10,18 @@
*/
function ProfilerActor(aConnection)
{
this._conn = aConnection;
this._profiler = Cc["@mozilla.org/tools/profiler;1"].getService(Ci.nsIProfiler);
this._started = false;
Cu.import("resource://gre/modules/Services.jsm");
Services.obs.addObserver(this, "profiler-started", false);
Services.obs.addObserver(this, "profiler-stopped", false);
this._observedEvents = [];
}
ProfilerActor.prototype = {
actorPrefix: "profiler",
disconnect: function() {
for (var event of this._observedEvents) {
Services.obs.removeObserver(this, event);
}
if (this._profiler && this._started) {
this._profiler.StopProfiler();
}
@ -64,12 +63,59 @@ ProfilerActor.prototype = {
var sharedLibraries = this._profiler.getSharedLibraryInformation();
return { "sharedLibraryInformation": sharedLibraries }
},
observe: function(aSubject, aTopic, aData) {
if (aTopic == "profiler-started") {
this.conn.send({ from: this.actorID, type: "profilerStateChanged", isActive: true });
} else if (aTopic == "profiler-stopped") {
this.conn.send({ from: this.actorID, type: "profilerStateChanged", isActive: false });
onRegisterEventNotifications: function(aRequest) {
let registered = [];
for (var event of aRequest.events) {
if (this._observedEvents.indexOf(event) != -1)
continue;
Services.obs.addObserver(this, event, false);
this._observedEvents.push(event);
registered.push(event);
}
return { registered: registered }
},
onUnregisterEventNotifications: function(aRequest) {
let unregistered = [];
for (var event of aRequest.events) {
let idx = this._observedEvents.indexOf(event);
if (idx == -1)
continue;
Services.obs.removeObserver(this, event);
this._observedEvents.splice(idx, 1);
unregistered.push(event);
}
return { unregistered: unregistered }
},
observe: function(aSubject, aTopic, aData) {
function unWrapper(obj) {
if (obj && typeof obj == "object" && ("wrappedJSObject" in obj)) {
obj = obj.wrappedJSObject;
if (("wrappedJSObject" in obj) && (obj.wrappedJSObject == obj)) {
/* If the object defines wrappedJSObject as itself, which is the
* typical idiom for wrapped JS objects, JSON.stringify won't be
* able to work because the object is cyclic.
* But removing the wrappedJSObject property will break aSubject
* for possible other observers of the same topic, so we need
* to restore wrappedJSObject afterwards */
delete obj.wrappedJSObject;
return { unwrapped: obj,
fixup: function() {
this.unwrapped.wrappedJSObject = this.unwrapped;
}
}
}
}
return { unwrapped: obj, fixup: function() { } }
}
var subject = unWrapper(aSubject);
var data = unWrapper(aData);
this.conn.send({ from: this.actorID,
type: "eventNotification",
event: aTopic,
subject: subject.unwrapped,
data: data.unwrapped });
data.fixup();
subject.fixup();
},
};
@ -84,7 +130,9 @@ ProfilerActor.prototype.requestTypes = {
"isActive": ProfilerActor.prototype.onIsActive,
"getResponsivenessTimes": ProfilerActor.prototype.onGetResponsivenessTimes,
"getFeatures": ProfilerActor.prototype.onGetFeatures,
"getSharedLibraryInformation": ProfilerActor.prototype.onGetSharedLibraryInformation
"getSharedLibraryInformation": ProfilerActor.prototype.onGetSharedLibraryInformation,
"registerEventNotifications": ProfilerActor.prototype.onRegisterEventNotifications,
"unregisterEventNotifications": ProfilerActor.prototype.onUnregisterEventNotifications
};
DebuggerServer.addGlobalActor(ProfilerActor, "profilerActor");