Bug 959130 - Stop using OS.File for startup read in CrashMonitor.jsm. r=ttaubert
authorSteven MacLeod <smacleod@mozilla.com>
Mon, 03 Feb 2014 15:14:16 +0100
changeset 182630 75303a3ddc0c1f6ec245252c85d6075b8f73b986
parent 182629 13d1ff429b44e99b17a709810633d0bc638d2665
child 182631 c092abc72367a3d17f25d52c117db45b3dc40634
push id3343
push userffxbld
push dateMon, 17 Mar 2014 21:55:32 +0000
treeherdermozilla-beta@2f7d3415f79f [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersttaubert
bugs959130
milestone29.0a1
first release with
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
last release without
nightly linux32
nightly linux64
nightly mac
nightly win32
nightly win64
Bug 959130 - Stop using OS.File for startup read in CrashMonitor.jsm. r=ttaubert
toolkit/components/crashmonitor/CrashMonitor.jsm
--- a/toolkit/components/crashmonitor/CrashMonitor.jsm
+++ b/toolkit/components/crashmonitor/CrashMonitor.jsm
@@ -29,22 +29,25 @@
  * checkpoint file tells us that the corresponding stage was reached
  * during the last run, the absence of a notification after a crash
  * does not necessarily tell us that the checkpoint wasn't reached.
  */
 
 this.EXPORTED_SYMBOLS = [ "CrashMonitor" ];
 
 const Cu = Components.utils;
+const Cr = Components.results;
 
 Cu.import("resource://gre/modules/Services.jsm");
 Cu.import("resource://gre/modules/osfile.jsm");
 Cu.import("resource://gre/modules/Promise.jsm");
 Cu.import("resource://gre/modules/Task.jsm");
 Cu.import("resource://gre/modules/AsyncShutdown.jsm");
+Cu.import("resource://gre/modules/NetUtil.jsm");
+Cu.import("resource://gre/modules/FileUtils.jsm");
 
 const NOTIFICATIONS = [
   "final-ui-startup",
   "sessionstore-windows-restored",
   "quit-application-granted",
   "quit-application",
   "profile-change-net-teardown",
   "profile-change-teardown",
@@ -88,35 +91,52 @@ let CrashMonitorInternal = {
   path: OS.Path.join(OS.Constants.Path.profileDir, "sessionCheckpoints.json"),
 
   /**
    * Load checkpoints from previous session asynchronously.
    *
    * @return {Promise} A promise that resolves/rejects once loading is complete
    */
   loadPreviousCheckpoints: function () {
-    let promise = Task.spawn(function () {
-      let notifications;
+    let deferred = Promise.defer();
+    CrashMonitorInternal.previousCheckpoints = deferred.promise;
+
+    let file = FileUtils.File(CrashMonitorInternal.path);
+    NetUtil.asyncFetch(file, function(inputStream, status) {
+      if (!Components.isSuccessCode(status)) {
+        if (status != Cr.NS_ERROR_FILE_NOT_FOUND) {
+          Cu.reportError("Error while loading crash monitor data: " + status);
+        }
+
+        deferred.resolve(null);
+        return;
+      }
+
+      let data = NetUtil.readInputStreamToString(inputStream,
+        inputStream.available(), { charset: "UTF-8" });
+
+      let notifications = null;
       try {
-        let decoder = new TextDecoder();
-        let data = yield OS.File.read(CrashMonitorInternal.path);
-        let contents = decoder.decode(data);
-        notifications = JSON.parse(contents);
-      } catch (ex if ex instanceof OS.File.Error && ex.becauseNoSuchFile) {
-        // If checkpoint file cannot be read
-        throw new Task.Result(null);
+        notifications = JSON.parse(data);
       } catch (ex) {
-        Cu.reportError("Error while loading crash monitor data: " + ex);
-        throw new Task.Result(null);
+        Cu.reportError("Error while parsing crash monitor data: " + ex);
+        deferred.resolve(null);
       }
-      throw new Task.Result(Object.freeze(notifications));
+
+      try {
+        deferred.resolve(Object.freeze(notifications));
+      } catch (ex) {
+        // The only exception we reject from is if notifications is not
+        // an object. This happens when the checkpoints file contained
+        // just a numeric string.
+        deferred.reject(ex);
+      }
     });
 
-    CrashMonitorInternal.previousCheckpoints = promise;
-    return promise;
+    return deferred.promise;
   }
 };
 
 this.CrashMonitor = {
 
   /**
    * Notifications received during previous session.
    *