Bug 794092 - Initial implementation of Gonk RecoveryService. r=vingtetun r=cjones
authorMarshall Culpepper <marshall.law@gmail.com>
Fri, 28 Sep 2012 17:32:56 -0500
changeset 108525 c19a02de09c4e42951e8061ce13d32fe3e6de697
parent 108524 777564a3cd50c7b441c175a9882f5e921e0892c1
child 108526 de06aeb3c7f393dd03f920f7e38d6e16af1d0897
push id15570
push usermculpepper@mozilla.com
push dateFri, 28 Sep 2012 22:34:04 +0000
treeherdermozilla-inbound@c19a02de09c4 [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersvingtetun, cjones
bugs794092
milestone18.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 794092 - Initial implementation of Gonk RecoveryService. r=vingtetun r=cjones Adopted from Shih-Chiang Chien's original code.
b2g/components/B2GComponents.manifest
b2g/components/Makefile.in
b2g/components/RecoveryService.js
b2g/components/b2g.idl
b2g/installer/package-manifest.in
--- a/b2g/components/B2GComponents.manifest
+++ b/b2g/components/B2GComponents.manifest
@@ -40,8 +40,12 @@ contract @mozilla.org/uriloader/content-
 
 # PaymentGlue.js
 component {8b83eabc-7929-47f4-8b48-4dea8d887e4b} PaymentGlue.js
 contract @mozilla.org/payment/ui-glue;1 {8b83eabc-7929-47f4-8b48-4dea8d887e4b}
 
 # YoutubeProtocolHandler.js
 component {c3f1b945-7e71-49c8-95c7-5ae9cc9e2bad} YoutubeProtocolHandler.js
 contract @mozilla.org/network/protocol;1?name=vnd.youtube {c3f1b945-7e71-49c8-95c7-5ae9cc9e2bad}
+
+# RecoveryService.js
+component {b3caca5d-0bb0-48c6-912b-6be6cbf08832} RecoveryService.js
+contract @mozilla.org/recovery-service;1 {b3caca5d-0bb0-48c6-912b-6be6cbf08832}
--- a/b2g/components/Makefile.in
+++ b/b2g/components/Makefile.in
@@ -22,15 +22,16 @@ EXTRA_PP_COMPONENTS = \
         B2GComponents.manifest \
         ContentHandler.js \
         ContentPermissionPrompt.js \
         DirectoryProvider.js \
         MozKeyboard.js \
         ProcessGlobal.js \
         PaymentGlue.js \
         YoutubeProtocolHandler.js \
+        RecoveryService.js \
         $(NULL)
 
 ifdef MOZ_UPDATER
 EXTRA_PP_COMPONENTS += UpdatePrompt.js
 endif
 
 include $(topsrcdir)/config/rules.mk
new file mode 100644
--- /dev/null
+++ b/b2g/components/RecoveryService.js
@@ -0,0 +1,93 @@
+/* -*- Mode: Java; tab-width: 2; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
+/* vim: set shiftwidth=2 tabstop=2 autoindent cindent expandtab: */
+/* 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/. */
+"use strict";
+
+const {classes: Cc, interfaces: Ci, utils: Cu, results: Cr} = Components;
+
+Cu.import("resource://gre/modules/XPCOMUtils.jsm");
+Cu.import("resource://gre/modules/ctypes.jsm");
+
+const RECOVERYSERVICE_CID = Components.ID("{b3caca5d-0bb0-48c6-912b-6be6cbf08832}");
+const RECOVERYSERVICE_CONTRACTID = "@mozilla.org/recovery-service;1";
+
+function log(msg) {
+  dump("-*- RecoveryService: " + msg + "\n");
+}
+
+#ifdef MOZ_WIDGET_GONK
+let librecovery = (function() {
+  let library = ctypes.open("librecovery.so");
+  let FotaUpdateStatus = new ctypes.StructType("FotaUpdateStatus", [
+                                                { result: ctypes.int },
+                                                { updatePath: ctypes.char.ptr }
+                                              ]);
+
+  return {
+    factoryReset:        library.declare("factoryReset",
+                                         ctypes.default_abi,
+                                         ctypes.int),
+    installFotaUpdate:   library.declare("installFotaUpdate",
+                                         ctypes.default_abi,
+                                         ctypes.int,
+                                         ctypes.char.ptr,
+                                         ctypes.int),
+
+    FotaUpdateStatus:    FotaUpdateStatus,
+    getFotaUpdateStatus: library.declare("getFotaUpdateStatus",
+                                         ctypes.default_abi,
+                                         ctypes.int,
+                                         FotaUpdateStatus.ptr)
+  };
+})();
+#endif
+
+function RecoveryService() {}
+
+RecoveryService.prototype = {
+  classID: RECOVERYSERVICE_CID,
+  QueryInterface: XPCOMUtils.generateQI([Ci.nsIRecoveryService]),
+  classInfo: XPCOMUtils.generateCI({
+    classID: RECOVERYSERVICE_CID,
+    contractID: RECOVERYSERVICE_CONTRACTID,
+    interfaces: [Ci.nsIRecoveryService],
+    classDescription: "B2G Recovery Service"
+  }),
+
+  factoryReset: function RS_factoryReset() {
+#ifdef MOZ_WIDGET_GONK
+    // If this succeeds, then the device reboots and this never returns
+    if (librecovery.factoryReset() != 0) {
+      log("Error: Factory reset failed");
+    }
+#endif
+    throw Cr.NS_ERROR_FAILURE;
+  },
+
+  installFotaUpdate: function RS_installFotaUpdate(updatePath) {
+#ifdef MOZ_WIDGET_GONK
+    // If this succeeds, then the device reboots and this never returns
+    if (librecovery.installFotaUpdate(updatePath, updatePath.length) != 0) {
+      log("Error: FOTA install failed");
+    }
+#endif
+
+    throw Cr.NS_ERROR_FAILURE;
+  },
+
+  getFotaUpdateStatus: function RS_getFotaUpdateStatus() {
+    let status =  Ci.nsIRecoveryService.FOTA_UPDATE_UNKNOWN;
+#ifdef MOZ_WIDGET_GONK
+    let cStatus = librecovery.FotaUpdateStatus();
+    if (librecovery.getFotaUpdateStatus(cStatus.address()) == 0) {
+      status = cStatus.result;
+    }
+
+#endif
+    return status;
+  }
+};
+
+const NSGetFactory = XPCOMUtils.generateNSGetFactory([RecoveryService]);
--- a/b2g/components/b2g.idl
+++ b/b2g/components/b2g.idl
@@ -34,8 +34,42 @@ interface nsIB2GKeyboard : nsISupports
   // for special situations where the value had to be chosen amongst a
   // list (type=month) or a widget (type=date, time, etc.).
   // If the value passed in parameter isn't valid (in the term of HTML5
   // Forms Validation), the value will simply be ignored by the element. 
   void setValue(in jsval value);
 
   attribute nsIDOMEventListener onfocuschange;
 };
+
+[scriptable, uuid(acb93ff8-aa6d-4bc8-bedd-2a6a3b802a74)]
+interface nsIRecoveryService : nsISupports
+{
+  /**
+   * Possible values of fotaStatus.result. These should stay in sync with
+   * librecovery/librecovery.h
+   */
+  const long FOTA_UPDATE_UNKNOWN = 0;
+  const long FOTA_UPDATE_FAIL    = 1;
+  const long FOTA_UPDATE_SUCCESS = 2;
+
+  /**
+   * Uses recovery to wipe the data and cache partitions. If this call is
+   * successful, the device should reboot before the function call ever returns.
+   *
+   * @throws NS_ERROR_FAILURE when rebooting into recovery fails for some reason.
+   */
+  void factoryReset();
+
+  /**
+   * Use recovery to install an OTA update.zip. If this call is
+   * successful, the device should reboot before the function call ever returns.
+   *
+   * @throws NS_ERROR_FAILURE when rebooting into recovery fails for some reason.
+   */
+  void installFotaUpdate(in string updatePath);
+
+  /**
+   * @return The status of the last FOTA update. One of FOTA_UPDATE_UNKNOWN,
+   *         FOTA_UPDATE_FAIL, FOTA_UPDATE_SUCCESS.
+   */
+  long getFotaUpdateStatus();
+};
--- a/b2g/installer/package-manifest.in
+++ b/b2g/installer/package-manifest.in
@@ -703,16 +703,17 @@ bin/components/@DLL_PREFIX@nkgnomevfs@DL
 #endif
 @BINPATH@/components/MozKeyboard.js
 @BINPATH@/components/DirectoryProvider.js
 @BINPATH@/components/ActivitiesGlue.js
 @BINPATH@/components/ProcessGlobal.js
 @BINPATH@/components/ContentHandler.js
 @BINPATH@/components/PaymentGlue.js
 @BINPATH@/components/YoutubeProtocolHandler.js
+@BINPATH@/components/RecoveryService.js
 
 #ifdef XP_MACOSX
 @BINPATH@/@DLL_PREFIX@plugin_child_interpose@DLL_SUFFIX@
 #endif
 
 #ifdef PACKAGE_GAIA
 [gaia]
 @BINPATH@/gaia/*