Bug 1329692 - Ship updated Firefox system add-on to change app.update.url preference for Websense with new endpoint version check. r=felipc, r=bsmedberg for data a=gchang
authorRobert Strong <robert.bugzilla@gmail.com>
Fri, 17 Feb 2017 14:04:46 -0800
changeset 378632 9352ff3f0da2997e2174bc9e9142e341b5bfc3c6
parent 378631 8adddacf61038c048989e2a80fa34629b5d7371b
child 378633 94debbbf7e5a08a93acfac75f2d7436df6d10cbf
push id1419
push userjlund@mozilla.com
push dateMon, 10 Apr 2017 20:44:07 +0000
treeherdermozilla-release@5e6801b73ef6 [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewersfelipc, bsmedberg, gchang
bugs1329692
milestone53.0a2
Bug 1329692 - Ship updated Firefox system add-on to change app.update.url preference for Websense with new endpoint version check. r=felipc, r=bsmedberg for data a=gchang
browser/extensions/aushelper/bootstrap.js
browser/extensions/aushelper/install.rdf.in
toolkit/components/telemetry/Histograms.json
toolkit/components/telemetry/Scalars.yaml
--- a/browser/extensions/aushelper/bootstrap.js
+++ b/browser/extensions/aushelper/bootstrap.js
@@ -3,32 +3,58 @@
  * 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/. */
 
 const {classes: Cc, interfaces: Ci, utils: Cu} = Components;
 
 const APP_UPDATE_URL_PREF = "app.update.url";
 const REPLACE_KEY = "%OS_VERSION%";
 
+const AUSHELPER_CPU_RESULT_CODE_HISTOGRAM_ID = "AUSHELPER_CPU_RESULT_CODE";
+// The system is not vulnerable to Bug 1296630.
+const CPU_NO_BUG1296630 = 1;
+// The system is vulnerable to Bug 1296630.
+const CPU_YES_BUG1296630 = 2;
+// An error occured when checking if the system is vulnerable to Bug 1296630.
+const CPU_ERR_BUG1296630 = 3;
+// It is unknown whether the system is vulnerable to Bug 1296630 (should never happen).
+const CPU_UNKNOWN_BUG1296630 = 4;
+
+const AUSHELPER_CPU_ERROR_CODE_HISTOGRAM_ID = "AUSHELPER_CPU_ERROR_CODE";
+const CPU_SUCCESS = 0;
+const CPU_REG_OPEN_ERROR = 1;
+const CPU_VENDOR_ID_ERROR = 2;
+const CPU_ID_ERROR = 4;
+const CPU_REV_ERROR = 8;
+
+const AUSHELPER_WEBSENSE_REG_VERSION_SCALAR_NAME = "aushelper.websense_reg_version";
+const AUSHELPER_WEBSENSE_REG_EXISTS_HISTOGRAM_ID = "AUSHELPER_WEBSENSE_REG_EXISTS";
+
+const AUSHELPER_WEBSENSE_ERROR_CODE_HISTOGRAM_ID = "AUSHELPER_WEBSENSE_ERROR_CODE";
+const WEBSENSE_SUCCESS = 0;
+const WEBSENSE_REG_OPEN_ERROR = 1;
+const WEBSENSE_REG_READ_ERROR = 2;
+const WEBSENSE_ALREADY_MODIFIED = 4;
+
 Cu.import("resource://gre/modules/Services.jsm");
-Cu.import("resource://gre/modules/TelemetryLog.jsm");
 
 function startup() {
   if (Services.appinfo.OS != "WINNT") {
     return;
   }
 
   const regCPUPath = "HARDWARE\\DESCRIPTION\\System\\CentralProcessor\\0";
   let wrk;
+  let cpuErrorCode = CPU_SUCCESS;
   try {
     wrk = Cc["@mozilla.org/windows-registry-key;1"].createInstance(Ci.nsIWindowsRegKey);
     wrk.open(wrk.ROOT_KEY_LOCAL_MACHINE, regCPUPath, wrk.ACCESS_READ);
   } catch (e) {
-    Cu.reportError("Unable to open registry. Exception: " + e);
-    TelemetryLog.log("AUSHELPER_FATAL_ERROR", [e]);
+    Cu.reportError("AUSHelper - unable to open registry. Exception: " + e);
+    cpuErrorCode |= CPU_REG_OPEN_ERROR;
   }
 
   // If any of the following values are successfully retrieved and they don't
   // match the condition for that value then it is safe to update. Hence why the
   // following checks are somewhat convoluted. The possible values for the
   // variable set by each check is as follows:
   //
   //          | Match | No Match | Error |
@@ -36,44 +62,44 @@ function startup() {
 
   let cpuVendorIDMatch = false;
   try {
     let cpuVendorID = wrk.readStringValue("VendorIdentifier");
     if (cpuVendorID.toLowerCase() == "genuineintel") {
       cpuVendorIDMatch = true;
     }
   } catch (e) {
+    Cu.reportError("AUSHelper - error getting CPU vendor indentifier. Exception: " + e);
     cpuVendorIDMatch = null;
-    Cu.reportError("Error getting CPU vendor indentifier. Exception: " + e);
-    TelemetryLog.log("AUSHELPER_CPU_VENDOR_ID_ERROR", [e]);
+    cpuErrorCode |= CPU_VENDOR_ID_ERROR;
   }
 
   let cpuIDMatch = false;
   try {
     let cpuID = wrk.readStringValue("Identifier");
     if (cpuID.toLowerCase().indexOf("family 6 model 61 stepping 4") != -1) {
       cpuIDMatch = true;
     }
   } catch (e) {
+    Cu.reportError("AUSHelper - error getting CPU indentifier. Exception: " + e);
     cpuIDMatch = null;
-    Cu.reportError("Error getting CPU indentifier. Exception: " + e);
-    TelemetryLog.log("AUSHELPER_CPU_ID_ERROR", [e]);
+    cpuErrorCode |= CPU_ID_ERROR;
   }
 
   let microCodeVersions = [0xe, 0x11, 0x12, 0x13, 0x16, 0x18, 0x19];
   let cpuRevMatch = null;
   try {
     let keyNames = ["Update Revision", "Update Signature"];
     for (let i = 0; i < keyNames.length; ++i) {
       try {
         let regVal = wrk.readBinaryValue(keyNames[i]);
         if (regVal.length == 8) {
           let hexVal = [];
-          // We are only inyterested in the highest byte and return the little
-          // endian value for it.
+          // We are only inyterested in the upper 4 bytes and the little endian
+          // value for it.
           for (let j = 4; j < 8; j++) {
             let c = regVal.charCodeAt(j).toString(16);
             if (c.length == 1) {
               c = "0" + c;
             }
             hexVal.unshift(c);
           }
           cpuRevMatch = false;
@@ -81,49 +107,83 @@ function startup() {
             cpuRevMatch = true;
           }
           break;
         }
       } catch (e) {
         if (i == keyNames.length - 1) {
           // The registry key name's value was not successfully queried.
           cpuRevMatch = null;
-          TelemetryLog.log("AUSHELPER_CPU_REV_ERROR", [e]);
+          cpuErrorCode |= CPU_REV_ERROR;
         }
       }
     }
+    wrk.close();
   } catch (ex) {
+    Cu.reportError("AUSHelper - error getting CPU revision. Exception: " + ex);
     cpuRevMatch = null;
-    Cu.reportError("Error getting CPU revision. Exception: " + ex);
-    TelemetryLog.log("AUSHELPER_CPU_REV_ERROR", [ex]);
+    cpuErrorCode |= CPU_REV_ERROR;
   }
 
-  let resultCode = 3;
-  let newValue = "(unkBug1296630v1)";
+  let cpuResult = CPU_UNKNOWN_BUG1296630;
+  let cpuValue = "(unkBug1296630v1)";
   // The following uses strict equality checks since the values can be true,
   // false, or null.
   if (cpuVendorIDMatch === false || cpuIDMatch === false || cpuRevMatch === false) {
     // Since one of the values is false then the system won't be affected by
     // bug 1296630 according to the conditions set out in bug 1311515.
-    newValue = "(noBug1296630v1)";
-    resultCode = 0;
+    cpuValue = "(noBug1296630v1)";
+    cpuResult = CPU_NO_BUG1296630;
   } else if (cpuVendorIDMatch === null || cpuIDMatch === null || cpuRevMatch === null) {
     // Since one of the values is null we can't say for sure if the system will
     // be affected by bug 1296630.
-    newValue = "(errBug1296630v1)";
-    resultCode = 2;
+    cpuValue = "(errBug1296630v1)";
+    cpuResult = CPU_ERR_BUG1296630;
   } else if (cpuVendorIDMatch === true && cpuIDMatch === true && cpuRevMatch === true) {
     // Since all of the values are true we can say that the system will be
     // affected by bug 1296630.
-    newValue = "(yesBug1296630v1)";
-    resultCode = 1;
+    cpuValue = "(yesBug1296630v1)";
+    cpuResult = CPU_YES_BUG1296630;
   }
 
-  let defaultBranch = Services.prefs.getDefaultBranch("");
-  let curPrefValue = defaultBranch.getCharPref(APP_UPDATE_URL_PREF);
-  let newPrefValue = curPrefValue.replace(REPLACE_KEY + "/", REPLACE_KEY + newValue + "/");
-  defaultBranch.setCharPref(APP_UPDATE_URL_PREF, newPrefValue);
-  TelemetryLog.log("AUSHELPER_RESULT", [resultCode]);
+  Services.telemetry.getHistogramById(AUSHELPER_CPU_RESULT_CODE_HISTOGRAM_ID).add(cpuResult);
+  Services.telemetry.getHistogramById(AUSHELPER_CPU_ERROR_CODE_HISTOGRAM_ID).add(cpuErrorCode);
+
+  const regWebsensePath = "Websense\\Agent";
+  let websenseErrorCode = WEBSENSE_SUCCESS;
+  let websenseVersion = "";
+  try {
+    let regModes = [wrk.ACCESS_READ, wrk.ACCESS_READ | wrk.WOW64_64];
+    for (let i = 0; i < regModes.length; ++i) {
+      wrk.open(wrk.ROOT_KEY_LOCAL_MACHINE, "SOFTWARE", regModes[i]);
+      try {
+        if (wrk.hasChild(regWebsensePath)) {
+          let childKey = wrk.openChild(regWebsensePath, wrk.ACCESS_READ);
+          websenseVersion = childKey.readStringValue("InstallVersion");
+          Services.telemetry.scalarSet(AUSHELPER_WEBSENSE_REG_VERSION_SCALAR_NAME, websenseVersion);
+        }
+        wrk.close();
+      } catch (e) {
+        Cu.reportError("AUSHelper - unable to read registry. Exception: " + e);
+        websenseErrorCode |= WEBSENSE_REG_READ_ERROR;
+      }
+    }
+  } catch (ex) {
+    Cu.reportError("AUSHelper - unable to open registry. Exception: " + ex);
+    websenseErrorCode |= WEBSENSE_REG_OPEN_ERROR;
+  }
+
+  Services.telemetry.getHistogramById(AUSHELPER_WEBSENSE_REG_EXISTS_HISTOGRAM_ID).add(!!websenseVersion);
+  let websenseValue = "(" + (websenseVersion ? "websense-" + websenseVersion : "nowebsense") + ")";
+
+  let branch = Services.prefs.getDefaultBranch("");
+  let curValue = branch.getCharPref(APP_UPDATE_URL_PREF);
+  if (curValue.indexOf(REPLACE_KEY + "/") > -1) {
+    let newValue = curValue.replace(REPLACE_KEY + "/", REPLACE_KEY + cpuValue + websenseValue + "/");
+    branch.setCharPref(APP_UPDATE_URL_PREF, newValue);
+  } else {
+    websenseErrorCode |= WEBSENSE_ALREADY_MODIFIED;
+  }
+  Services.telemetry.getHistogramById(AUSHELPER_WEBSENSE_ERROR_CODE_HISTOGRAM_ID).add(websenseErrorCode);
 }
-
 function shutdown() {}
 function install() {}
 function uninstall() {}
--- a/browser/extensions/aushelper/install.rdf.in
+++ b/browser/extensions/aushelper/install.rdf.in
@@ -5,17 +5,17 @@
 
 #filter substitution
 
 <RDF xmlns="http://www.w3.org/1999/02/22-rdf-syntax-ns#"
      xmlns:em="http://www.mozilla.org/2004/em-rdf#">
 
   <Description about="urn:mozilla:install-manifest">
     <em:id>aushelper@mozilla.org</em:id>
-    <em:version>1.0</em:version>
+    <em:version>2.0</em:version>
     <em:type>2</em:type>
     <em:bootstrap>true</em:bootstrap>
     <em:multiprocessCompatible>true</em:multiprocessCompatible>
 
     <!-- Target Application this extension can install into,
         with minimum and maximum supported versions. -->
     <em:targetApplication>
       <Description>
--- a/toolkit/components/telemetry/Histograms.json
+++ b/toolkit/components/telemetry/Histograms.json
@@ -119,16 +119,51 @@
     "alert_emails": ["padenot@mozilla.com", "kinetik@flim.org"],
     "bug_numbers": [1280630],
     "expires_in_version": "55",
     "kind": "enumerated",
     "n_values": 16,
     "description": "The operating system audio back-end used when successfully opening an audio stream, or whether the failure occurred on the first try or not <https://dxr.mozilla.org/mozilla-central/search?q=AUDIOSTREAM_BACKEND_ID_STR>",
     "releaseChannelCollection": "opt-out"
   },
+  "AUSHELPER_CPU_ERROR_CODE": {
+    "alert_emails": ["application-update-telemetry-alerts@mozilla.com"],
+    "bug_numbers": [1296630],
+    "expires_in_version": "60",
+    "kind": "enumerated",
+    "n_values": 16,
+    "releaseChannelCollection": "opt-out",
+    "description": "The error code from the aushelper system add-on when querying the registry for CPU information for bug 1296630 (see browser/extensions/aushelper/bootstrap.js)."
+  },
+  "AUSHELPER_CPU_RESULT_CODE": {
+    "alert_emails": ["application-update-telemetry-alerts@mozilla.com"],
+    "bug_numbers": [1296630],
+    "expires_in_version": "60",
+    "kind": "enumerated",
+    "n_values": 5,
+    "releaseChannelCollection": "opt-out",
+    "description": "Whether the system is affected by bug 1296630 (1=No, 2=Yes, 3=Error, and 4=Unknown)."
+  },
+  "AUSHELPER_WEBSENSE_ERROR_CODE": {
+    "alert_emails": ["application-update-telemetry-alerts@mozilla.com"],
+    "bug_numbers": [1305847],
+    "expires_in_version": "60",
+    "kind": "enumerated",
+    "n_values": 8,
+    "releaseChannelCollection": "opt-out",
+    "description": "The error code from the aushelper system add-on when gathering information on Websense (see browser/extensions/aushelper/bootstrap.js)."
+  },
+  "AUSHELPER_WEBSENSE_REG_EXISTS": {
+    "alert_emails": ["application-update-telemetry-alerts@mozilla.com"],
+    "bug_numbers": [1305847],
+    "expires_in_version": "60",
+    "kind": "boolean",
+    "releaseChannelCollection": "opt-out",
+    "description": "Whether the system has a Websense InstallVersion registry value (see browser/extensions/aushelper/bootstrap.js)."
+  },
   "BACKGROUNDFILESAVER_THREAD_COUNT": {
     "expires_in_version": "never",
     "kind": "enumerated",
     "n_values": 21,
     "description": "Maximum number of concurrent threads reached during a given download session"
   },
   "BLOCKLIST_SYNC_FILE_LOAD": {
     "alert_emails": ["rvitillo@mozilla.com"],
--- a/toolkit/components/telemetry/Scalars.yaml
+++ b/toolkit/components/telemetry/Scalars.yaml
@@ -1,11 +1,25 @@
 # This file contains a definition of the scalar probes that are recorded in Telemetry.
 # They are submitted with the "main" pings and can be inspected in about:telemetry.
 
+# The following section contains the aushelper system add-on scalars.
+aushelper:
+  websense_reg_version:
+    bug_numbers:
+      - 1305847
+    description: The Websense version from the Windows registry.
+    expires: "60"
+    kind: string
+    notification_emails:
+      - application-update-telemetry-alerts@mozilla.com
+    release_channel_collection: opt-out
+    record_in_processes:
+      - 'main'
+
 # The following section contains the browser engagement scalars.
 browser.engagement:
   max_concurrent_tab_count:
     bug_numbers:
       - 1271304
     description: >
       The count of maximum number of tabs open during a subsession,
       across all windows, including tabs in private windows and restored