Bug 1620656 - Remove 'geckoview' telemetry support. r=chutten,geckoview-reviewers,aklotz
authorAlessio Placitelli <alessio.placitelli@gmail.com>
Tue, 16 Jun 2020 12:22:55 +0000
changeset 535863 5409134fc766cfea378963fa5a37ac9c56515fdd
parent 535862 89a54069f124b175a0069affaaa1f55ff83214de
child 535864 d009c756c86bb07bdfdad89772d9d810c71a9c98
push id119111
push useraplacitelli@mozilla.com
push dateTue, 16 Jun 2020 12:26:25 +0000
treeherderautoland@dfab5bc68cde [default view] [failures only]
perfherder[talos] [build metrics] [platform microbench] (compared to previous push)
reviewerschutten, geckoview-reviewers, aklotz
bugs1620656
milestone79.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 1620656 - Remove 'geckoview' telemetry support. r=chutten,geckoview-reviewers,aklotz This removes the support for the 'geckoview' telemetry in the core and in the JSM files. It also cleans up testing and the configurations. Differential Revision: https://phabricator.services.mozilla.com/D79521
mobile/android/app/geckoview-prefs.js
mobile/android/components/geckoview/GeckoViewStartup.jsm
modules/libpref/init/StaticPrefList.yaml
toolkit/components/build/components.conf
toolkit/components/processsingleton/ContentProcessSingleton.jsm
toolkit/components/telemetry/core/Telemetry.cpp
toolkit/components/telemetry/core/TelemetryCommon.cpp
toolkit/components/telemetry/core/TelemetryCommon.h
toolkit/components/telemetry/core/nsITelemetry.idl
toolkit/components/telemetry/docs/collection/events.rst
toolkit/components/telemetry/docs/collection/histograms.rst
toolkit/components/telemetry/docs/collection/scalars.rst
toolkit/components/telemetry/docs/internals/geckoview.rst
toolkit/components/telemetry/docs/internals/preferences.rst
toolkit/components/telemetry/geckoview/GeckoViewTelemetryController.jsm
toolkit/components/telemetry/geckoview/TelemetryGeckoViewPersistence.cpp
toolkit/components/telemetry/geckoview/TelemetryGeckoViewPersistence.h
toolkit/components/telemetry/geckoview/TelemetryGeckoViewTesting.cpp
toolkit/components/telemetry/geckoview/TelemetryGeckoViewTesting.h
toolkit/components/telemetry/geckoview/gtest/TestGeckoView.cpp
toolkit/components/telemetry/geckoview/gtest/moz.build
toolkit/components/telemetry/geckoview/nsITelemetryGeckoViewTesting.idl
toolkit/components/telemetry/moz.build
toolkit/components/telemetry/tests/unit/head.js
toolkit/components/telemetry/tests/unit/head_GeckoView.js
toolkit/components/telemetry/tests/unit/test_GeckoView.js
toolkit/components/telemetry/tests/unit/test_GeckoView_ScalarSemantics.js
toolkit/components/telemetry/tests/unit/test_GeckoView_content_histograms.js
toolkit/components/telemetry/tests/unit/test_GeckoView_content_scalars.js
toolkit/components/telemetry/tests/unit/test_TelemetryScalars.js
toolkit/components/telemetry/tests/unit/xpcshell.ini
--- a/mobile/android/app/geckoview-prefs.js
+++ b/mobile/android/app/geckoview-prefs.js
@@ -16,18 +16,16 @@
 #include mobile.js
 
 pref("privacy.trackingprotection.pbmode.enabled", false);
 
 pref("dom.ipc.keepProcessesAlive.web", 1);
 pref("dom.ipc.processCount", 1);
 pref("dom.ipc.processPrelaunch.enabled", false);
 
-// Tell Telemetry that we're in GeckoView mode.
-pref("toolkit.telemetry.isGeckoViewMode", true);
 // Disable the Telemetry Event Ping
 pref("toolkit.telemetry.eventping.enabled", false);
 // Don't create the hidden window during startup.
 pref("toolkit.lazyHiddenWindow", true);
 
 pref("geckoview.console.enabled", false);
 
 #ifdef RELEASE_OR_BETA
--- a/mobile/android/components/geckoview/GeckoViewStartup.jsm
+++ b/mobile/android/components/geckoview/GeckoViewStartup.jsm
@@ -10,18 +10,16 @@ const { XPCOMUtils } = ChromeUtils.impor
 );
 const { GeckoViewUtils } = ChromeUtils.import(
   "resource://gre/modules/GeckoViewUtils.jsm"
 );
 
 XPCOMUtils.defineLazyModuleGetters(this, {
   ActorManagerParent: "resource://gre/modules/ActorManagerParent.jsm",
   EventDispatcher: "resource://gre/modules/Messaging.jsm",
-  GeckoViewTelemetryController:
-    "resource://gre/modules/GeckoViewTelemetryController.jsm",
   Preferences: "resource://gre/modules/Preferences.jsm",
   SafeBrowsing: "resource://gre/modules/SafeBrowsing.jsm",
   Services: "resource://gre/modules/Services.jsm",
 });
 
 const { debug, warn } = GeckoViewUtils.initLogging("Startup"); // eslint-disable-line no-unused-vars
 
 const JSWINDOWACTORS = {
@@ -196,21 +194,16 @@ class GeckoViewStartup {
             name: "devtools.debugger.remote-enabled",
             default: false,
           },
           {
             handler: _ => this.GeckoViewRemoteDebugger,
           }
         );
 
-        // This initializes Telemetry for GeckoView only in the parent process.
-        // The Telemetry initialization for the content process is performed in
-        // ContentProcessSingleton.js for consistency with Desktop Telemetry.
-        GeckoViewTelemetryController.setup();
-
         ChromeUtils.import("resource://gre/modules/NotificationDB.jsm");
 
         // Initialize safe browsing module. This is required for content
         // blocking features and manages blocklist downloads and updates.
         SafeBrowsing.init();
 
         // Listen for global EventDispatcher messages
         EventDispatcher.instance.registerListener(this, [
--- a/modules/libpref/init/StaticPrefList.yaml
+++ b/modules/libpref/init/StaticPrefList.yaml
@@ -8993,21 +8993,16 @@
 # subsystem. Batch the remote accumulations for a period of time before sending
 # them all at once. This value was chosen as a balance between data timeliness
 # and performance (see bug 1218576).
 - name: toolkit.telemetry.ipcBatchTimeout
   type: uint32_t
   value: 2000
   mirror: always
 
-- name: toolkit.telemetry.isGeckoViewMode
-  type: RelaxedAtomicBool
-  value: false
-  mirror: always
-
 - name: toolkit.telemetry.geckoview.batchDurationMS
   type: RelaxedAtomicUint32
   value: 5000
   mirror: always
 
 - name: toolkit.telemetry.geckoview.maxBatchStalenessMS
   type: RelaxedAtomicUint32
   value: 60000
--- a/toolkit/components/build/components.conf
+++ b/toolkit/components/build/components.conf
@@ -183,18 +183,8 @@ if MOZ_HAS_TERMINATOR:
     Classes += [
         {
             'cid': '{2e59cc70-f83a-412f-89d4-453885837217}',
             'contract_ids': ['@mozilla.org/toolkit/shutdown-terminator;1'],
             'type': 'mozilla::nsTerminator',
             'headers': ['nsTerminator.h'],
         },
     ]
-
-if defined('ENABLE_TESTS'):
-    Classes += [
-        {
-            'cid': '{aaa3f7f2-8ef0-41ec-8d03-aed667cf7fa2}',
-            'contract_ids': ['@mozilla.org/telemetry/geckoview-testing;1'],
-            'type': 'TelemetryGeckoViewTestingImpl',
-            'headers': ['/toolkit/components/telemetry/geckoview/TelemetryGeckoViewTesting.h'],
-        },
-    ]
--- a/toolkit/components/processsingleton/ContentProcessSingleton.jsm
+++ b/toolkit/components/processsingleton/ContentProcessSingleton.jsm
@@ -5,41 +5,31 @@
 "use strict";
 
 const { Services } = ChromeUtils.import("resource://gre/modules/Services.jsm");
 const { XPCOMUtils } = ChromeUtils.import(
   "resource://gre/modules/XPCOMUtils.jsm"
 );
 
 XPCOMUtils.defineLazyModuleGetters(this, {
-  GeckoViewTelemetryController:
-    "resource://gre/modules/GeckoViewTelemetryController.jsm",
   TelemetryController: "resource://gre/modules/TelemetryController.jsm",
 });
 
 function ContentProcessSingleton() {}
 ContentProcessSingleton.prototype = {
   classID: Components.ID("{ca2a8470-45c7-11e4-916c-0800200c9a66}"),
   QueryInterface: ChromeUtils.generateQI([
     Ci.nsIObserver,
     Ci.nsISupportsWeakReference,
   ]),
 
   observe(subject, topic, data) {
     switch (topic) {
       case "app-startup": {
         Services.obs.addObserver(this, "xpcom-shutdown");
-        // Initialize Telemetry in the content process: use a different
-        // controller depending on the platform.
-        if (
-          Services.prefs.getBoolPref("toolkit.telemetry.isGeckoViewMode", false)
-        ) {
-          GeckoViewTelemetryController.setup();
-          return;
-        }
         // Initialize Firefox Desktop Telemetry.
         TelemetryController.observe(null, topic, null);
         break;
       }
       case "xpcom-shutdown":
         Services.obs.removeObserver(this, "xpcom-shutdown");
         break;
     }
--- a/toolkit/components/telemetry/core/Telemetry.cpp
+++ b/toolkit/components/telemetry/core/Telemetry.cpp
@@ -1274,25 +1274,16 @@ already_AddRefed<nsITelemetry> Telemetry
   nsCOMPtr<nsITelemetry> ret = telemetry;
 
   telemetry->mCanRecordBase = useTelemetry;
   telemetry->mCanRecordExtended = useTelemetry;
 
   telemetry->InitMemoryReporter();
   InitHistogramRecordingEnabled();  // requires sTelemetry to exist
 
-#if defined(MOZ_TELEMETRY_GECKOVIEW)
-  // We only want to add persistence for GeckoView, but both
-  // GV and Fennec are on Android. So just init persistence if this
-  // is Android but not Fennec.
-  if (GetCurrentProduct() == SupportedProduct::Geckoview) {
-    TelemetryGeckoViewPersistence::InitPersistence();
-  }
-#endif
-
   return ret.forget();
 }
 
 void TelemetryImpl::ShutdownTelemetry() {
   // No point in collecting IO beyond this point
   ClearIOReporting();
   {
     auto lock = sTelemetry.Lock();
@@ -1302,22 +1293,16 @@ void TelemetryImpl::ShutdownTelemetry() 
   // Lastly, de-initialise the TelemetryHistogram and TelemetryScalar global
   // states, so as to release any heap storage that would otherwise be kept
   // alive by it.
   TelemetryHistogram::DeInitializeGlobalState();
   TelemetryScalar::DeInitializeGlobalState();
   TelemetryEvent::DeInitializeGlobalState();
   TelemetryOrigin::DeInitializeGlobalState();
   TelemetryIPCAccumulator::DeInitializeGlobalState();
-
-#if defined(MOZ_TELEMETRY_GECKOVIEW)
-  if (GetCurrentProduct() == SupportedProduct::Geckoview) {
-    TelemetryGeckoViewPersistence::DeInitPersistence();
-  }
-#endif
 }
 
 void TelemetryImpl::StoreSlowSQL(const nsACString& sql, uint32_t delay,
                                  SanitizedState state) {
   auto lock = sTelemetry.Lock();
   auto telemetry = lock.ref();
   AutoHashtable<SlowSQLEntryType>* slowSQLMap = nullptr;
   if (state == Sanitized)
@@ -1756,34 +1741,16 @@ TelemetryImpl::RegisterBuiltinEvents(con
 
 NS_IMETHODIMP
 TelemetryImpl::ClearEvents() {
   TelemetryEvent::ClearEvents();
   return NS_OK;
 }
 
 NS_IMETHODIMP
-TelemetryImpl::ClearProbes() {
-#if defined(MOZ_TELEMETRY_GECKOVIEW)
-  // We only support this in GeckoView.
-  if (GetCurrentProduct() != SupportedProduct::Geckoview) {
-    MOZ_ASSERT(false, "ClearProbes is only supported on GeckoView");
-    return NS_ERROR_FAILURE;
-  }
-
-  // TODO: supporting clear for histograms will come from bug 1457127.
-  TelemetryScalar::ClearScalars();
-  TelemetryGeckoViewPersistence::ClearPersistenceData();
-  return NS_OK;
-#else
-  return NS_ERROR_FAILURE;
-#endif
-}
-
-NS_IMETHODIMP
 TelemetryImpl::SetEventRecordingEnabled(const nsACString& aCategory,
                                         bool aEnabled) {
   TelemetryEvent::SetEventRecordingEnabled(aCategory, aEnabled);
   return NS_OK;
 }
 
 NS_IMETHODIMP
 TelemetryImpl::GetOriginSnapshot(bool aClear, JSContext* aCx,
--- a/toolkit/components/telemetry/core/TelemetryCommon.cpp
+++ b/toolkit/components/telemetry/core/TelemetryCommon.cpp
@@ -180,18 +180,16 @@ JSString* ToJSString(JSContext* cx, cons
 JSString* ToJSString(JSContext* cx, const nsAString& aStr) {
   return JS_NewUCStringCopyN(cx, aStr.Data(), aStr.Length());
 }
 
 SupportedProduct GetCurrentProduct() {
 #if defined(MOZ_WIDGET_ANDROID)
   if (mozilla::StaticPrefs::toolkit_telemetry_geckoview_streaming()) {
     return SupportedProduct::GeckoviewStreaming;
-  } else if (mozilla::StaticPrefs::toolkit_telemetry_isGeckoViewMode()) {
-    return SupportedProduct::Geckoview;
   } else {
     return SupportedProduct::Fennec;
   }
 #elif defined(MOZ_THUNDERBIRD)
   return SupportedProduct::Thunderbird;
 #else
   return SupportedProduct::Firefox;
 #endif
--- a/toolkit/components/telemetry/core/TelemetryCommon.h
+++ b/toolkit/components/telemetry/core/TelemetryCommon.h
@@ -32,17 +32,19 @@ enum class RecordedProcessType : uint16_
 MOZ_MAKE_ENUM_CLASS_BITWISE_OPERATORS(RecordedProcessType);
 static_assert(static_cast<uint16_t>(RecordedProcessType::Main) == 1,
               "Main process type must be equal to 1 to allow easy matching in "
               "CanRecordInProcess");
 
 enum class SupportedProduct : uint8_t {
   Firefox = (1 << 0),
   Fennec = (1 << 1),
-  Geckoview = (1 << 2),
+  // Note that `1 << 2` (former GeckoView) is missing in the representation
+  // but isn't necessary to be maintained, but we see no point in filling it
+  // at this time.
   GeckoviewStreaming = (1 << 3),
   Thunderbird = (1 << 4),
 };
 MOZ_MAKE_ENUM_CLASS_BITWISE_OPERATORS(SupportedProduct);
 
 template <class EntryType>
 class AutoHashtable : public nsTHashtable<EntryType> {
  public:
--- a/toolkit/components/telemetry/core/nsITelemetry.idl
+++ b/toolkit/components/telemetry/core/nsITelemetry.idl
@@ -620,28 +620,16 @@ interface nsITelemetry : nsISupports
    * Get a list of all registered stores.
    *
    * The list is deduplicated, but unordered.
    */
   [implicit_jscontext]
   jsval getAllStores();
 
   /**
-   * Reset the storage for all the collection primitives so that GeckoView
-   * can issue a single Clear signal for histograms, scalars, events, ...
-   *
-   * This is needed for supporting the current implementation of GeckoView
-   * measurement persistence: all the measurements are stored in a single file and
-   * they can't be cleared independently.
-   *
-   * Please note that this is only intended to be used by GeckoViewTelemetryController.
-   */
-  void clearProbes();
-
-  /**
    * Does early, cheap initialization for native telemetry data providers.
    * Currently, this includes only MemoryTelemetry.
    */
   void earlyInit();
 
   /**
    * Does late, expensive initialization for native telemetry data providers.
    * Currently, this includes only MemoryTelemetry.
--- a/toolkit/components/telemetry/docs/collection/events.rst
+++ b/toolkit/components/telemetry/docs/collection/events.rst
@@ -128,17 +128,16 @@ The following event properties are valid
 
   - ``expiry_version`` *(required, string)*: The version number in which the event expires, e.g. ``"50"``, or ``"never"``. A version number of type "N" is automatically converted to "N.0a1" in order to expire the event also in the development channels. For events that never expire the value ``never`` can be used.
 
 - ``extra_keys`` *(optional, object)*: An object that specifies valid keys for the ``extra`` argument and a description - see the example above.
 - ``products`` *(required, list of strings)*: A list of products the event can be recorded on. Currently supported values are:
 
   - ``firefox`` - Collected in Firefox Desktop for submission via Firefox Telemetry.
   - ``fennec`` - Collected in Firefox for Android for submission via Firefox Mobile Telemetry.
-  - ``geckoview`` - *deprecated* Will be removed in Firefox 79. (see `bug 1620395 <https://bugzilla.mozilla.org/show_bug.cgi?id=1620395>`__)
 
 - ``operating_systems`` *(optional, list of strings)*: This field restricts recording to certain operating systems only. It defaults to ``all``. Currently supported values are:
 
    - ``mac``
    - ``linux``
    - ``windows``
    - ``android``
    - ``unix``
@@ -330,16 +329,17 @@ 4. ``TelemetryTestUtils.assertEvents(exp
    If you only need to check the number of events recorded, you can use
    ``TelemetryTestUtils.assertNumberOfEvents(expectedNum, filter, options);``.
    Both utilities have `helpful inline documentation <https://hg.mozilla.org/mozilla-central/file/tip/toolkit/components/telemetry/tests/utils/TelemetryTestUtils.jsm>`_.
 
 
 Version History
 ===============
 
+- Firefox 79:  ``geckoview`` support removed (see `bug 1620395 <https://bugzilla.mozilla.org/show_bug.cgi?id=1620395>`__).
 - Firefox 52: Initial event support (`bug 1302663 <https://bugzilla.mozilla.org/show_bug.cgi?id=1302663>`_).
 - Firefox 53: Event recording disabled by default (`bug 1329139 <https://bugzilla.mozilla.org/show_bug.cgi?id=1329139>`_).
 - Firefox 54: Added child process events (`bug 1313326 <https://bugzilla.mozilla.org/show_bug.cgi?id=1313326>`_).
 - Firefox 56: Added support for recording new probes from add-ons (`bug 1302681 <bug https://bugzilla.mozilla.org/show_bug.cgi?id=1302681>`_).
 - Firefox 58:
 
    - Ignore re-registering existing events for a category instead of failing (`bug 1408975 <https://bugzilla.mozilla.org/show_bug.cgi?id=1408975>`_).
    - Removed support for the ``expiry_date`` property, as it was unused (`bug 1414638 <https://bugzilla.mozilla.org/show_bug.cgi?id=1414638>`_).
--- a/toolkit/components/telemetry/docs/collection/histograms.rst
+++ b/toolkit/components/telemetry/docs/collection/histograms.rst
@@ -231,17 +231,16 @@ Optional. This is one of:
     Every new or changed data collection in Firefox needs a `data collection review <https://wiki.mozilla.org/Firefox/Data_Collection>`__ from a Data Steward.
 
 ``products``
 -------------
 Required. This field is a list of products this histogram can be recorded on. Currently-supported values are:
 
 - ``firefox`` - Collected in Firefox Desktop for submission via Firefox Telemetry.
 - ``fennec`` - Collected in Firefox for Android for submission via Firefox Mobile Telemetry.
-- ``geckoview`` - *deprecated* Will be removed in Firefox 79. (see `bug 1620395 <https://bugzilla.mozilla.org/show_bug.cgi?id=1620395>`__)
 
 ``record_into_store``
 ---------------------
 
 Optional. This field is a list of stores this histogram should be recorded into.
 If this field is left out it defaults to ``[main]``.
 
 Changing a histogram
--- a/toolkit/components/telemetry/docs/collection/scalars.rst
+++ b/toolkit/components/telemetry/docs/collection/scalars.rst
@@ -158,17 +158,16 @@ Required Fields
 - ``description``: A single or multi-line string describing what data the probe collects and when it gets collected.
 - ``expires``: The version number in which the scalar expires, e.g. "30"; a version number of type "N" is automatically converted to "N.0a1" in order to expire the scalar also in the development channels. A telemetry probe acting on an expired scalar will print a warning into the browser console. For scalars that never expire the value ``never`` can be used.
 - ``kind``: A string representing the scalar type. Allowed values are ``uint``, ``string`` and ``boolean``.
 - ``notification_emails``: A list of email addresses to notify with alerts of expiring probes. More importantly, these are used by the data steward to verify that the probe is still useful.
 - ``products``: A list of products the scalar can be recorded on. Currently supported values are:
 
   - ``firefox`` - Collected in Firefox Desktop for submission via Firefox Telemetry.
   - ``fennec`` - Collected in Firefox for Android for submission via Firefox Mobile Telemetry.
-  - ``geckoview`` - *deprecated* Will be removed in Firefox 79. (see `bug 1620395 <https://bugzilla.mozilla.org/show_bug.cgi?id=1620395>`__)
 
 - ``record_in_processes``: A list of processes the scalar is allowed to record in. Currently supported values are:
 
   - ``main``;
   - ``content``;
   - ``gpu``;
   - ``all_children`` (record in all the child processes);
   - ``all`` (record in all the processes).
@@ -304,16 +303,17 @@ Native code can take advantage of Scalar
 
 The ``ScalarID`` enum is automatically generated by the build process, with an example being available `here <https://dxr.mozilla.org/mozilla-central/search?q=path%3ATelemetryScalarEnums.h&redirect=false>`_ .
 
 Other examples can be found in the `test coverage <https://dxr.mozilla.org/mozilla-central/source/toolkit/components/telemetry/tests/gtest/TestScalars.cpp>`_ for the scalars C++ API.
 
 Version History
 ===============
 
+- Firefox 79:  ``geckoview`` support removed (see `bug 1620395 <https://bugzilla.mozilla.org/show_bug.cgi?id=1620395>`__).
 - Firefox 50: Initial scalar support (`bug 1276195 <https://bugzilla.mozilla.org/show_bug.cgi?id=1276195>`_).
 - Firefox 51: Added keyed scalars (`bug 1277806 <https://bugzilla.mozilla.org/show_bug.cgi?id=1277806>`_).
 - Firefox 53: Added child process scalars (`bug 1278556 <https://bugzilla.mozilla.org/show_bug.cgi?id=1278556>`_).
 - Firefox 58
 
   - Added support for recording new scalars from add-ons (`bug 1393801 <bug https://bugzilla.mozilla.org/show_bug.cgi?id=1393801>`_).
   - Ignore re-registering existing scalars for a category instead of failing (`bug 1409323 <https://bugzilla.mozilla.org/show_bug.cgi?id=1409323>`_).
 
deleted file mode 100644
--- a/toolkit/components/telemetry/docs/internals/geckoview.rst
+++ /dev/null
@@ -1,177 +0,0 @@
-GeckoView
-=========
-
-Supporting GeckoView in the Telemetry core means enabling GeckoView to easily add and
-record Telemetry. Since GeckoView can be embedded and have a short life cycle, due to
-the OS killing the application to spare memory or the user completing a short task and
-then bailing out, we need to support measurements across different sessions. The current
-GeckoView support is limited to :doc:`scalars <../collection/scalars>` and
-:doc:`histograms <../collection/histograms>`.
-
-Overview
---------
-GeckoView does not make use of the same `JavaScript modules <https://dxr.mozilla.org/mozilla-central/search?q=path%3Atoolkit%2Fcomponents%2Ftelemetry+ext%3Ajsm+-path%3Ageckoview&redirect=false>`_
-used in Firefox Desktop. Instead, Telemetry gets setup on this product by `GeckoViewTelemetryController.jsm <https://dxr.mozilla.org/mozilla-central/rev/1800b8895c08bc0c60302775dc0a4b5ea4deb310/toolkit/components/telemetry/geckoview/GeckoViewTelemetryController.jsm>`_ .
-
-More importantly, users do not need to worry about handling measurements' persistence across
-sessions: this means measurements accumulate across application sessions until cleared. In
-contrast with Firefox Desktop, for which Telemetry defines a strict :doc:`session <../concepts/sessions>`
-model, for GeckoView, the Telemetry module does not define it: it just provides accumulation
-and storage.
-Defining a session model is the responsibility of the application.
-
-Persistence
------------
-Measurement persistence across sessions is guaranteed by an automatic serialization and deserialization
-process performed, behind the scenes, by the Telemetry core. As soon as Telemetry starts up, it
-checks for the existence of the persisted measurements file (``gv_measurements.json``) in the
-Android's application `data dir <https://developer.android.com/reference/android/content/pm/ApplicationInfo.html#dataDir>`_. If that file is found, it is parsed and the values of the
-contained measurements are loaded in memory.
-
-.. note::
-
-  While it's possible to request a snapshot of the measurements using the GeckoView API before
-  the persisted measurements are loaded from the disk, the requests will only be served once
-  the state of the persisted measurements is restored from the disk. The
-  ``internal-telemetry-geckoview-load-complete`` topic is broadcasted to signal that loading
-  is complete.
-
-Once the measurements are restored, their values will be dumped again to the persisted
-measurements file after the update interval expires. This interval is defined by the
-``toolkit.telemetry.geckoPersistenceTimeout`` preference (defaults to 1 minute), see the
-:doc:`preferences docs <preferences>`.
-
-Scalar Semantics
-~~~~~~~~~~~~~~~~
-
-Data collection can start very early during the application life cycle and might overlap with the persistence deserialization.
-The Telemetry Core therefore takes additional steps to preserve the semantics of scalar operations.
-
-During deserialization of persisted measurements operations on scalar probes are not applied immediately, but recorded into a pending operations list.
-Once deserialization is finished, the pending operations are applied in the order they were recorded.
-This avoids any data race between operations and scalar values are always in a consistent state.
-Snapshots requests will only be fulfilled after the deserialization finished and all pending operations are applied.
-Consumers of the recorded data should therefore never see inconsistent data.
-
-An example:
-
-1. Scalar deserialization is started
-2. "test" scalar is incremented by "10" by the application -> The operation ``[test, add, 10]`` is recorded into the list.
-3. The state of the "test" scalar is loaded off the persistence file, and the value "14" is set.
-4. Deserialization is finished and the pending operations are applied.
-
-   * The "test" scalar is incremented by "10", the value is now "24"
-5. "test" scalar is incremented via "scalarAdd" by 1. Its value is "25"
-
-To stop growing unbounded in memory while waiting for scalar deserialization to finish, pending operations are applied
-immediately if the array reaches a high water mark of 10000 elements.
-At that point the deserialization is considered done and following scalar operatins will be applied immediately.
-In the case of the deserialization still being in progress, it might overwrite recorded values,
-leading to inconsistent data.
-
-The persistence file format
----------------------------
-All the supported measurements are serialized to the persistence file using the JSON format.
-The top level entries in the file are the measurement types. Each measurement section contains
-an entry for all the supported processes. Finally, each process section contains the measurement
-specific data required to restore its state in memory.
-
-.. code-block:: js
-
-    {
-      "scalars": {
-        "content": {
-          "telemetry.test.all_processes_uint": 37,
-          "<other scalar>": ...
-        },
-        "<other process>": {
-          ...
-        }
-      },
-      "keyedScalars": {
-        "parent": {
-          "telemetry.test.keyed_unsigned_int": {
-            "testKey": 73,
-            "<other key>: ..."
-          }
-        }
-      },
-      "histograms": {
-        "parent": {
-          "TELEMETRY_TEST_MULTIPRODUCT": {
-            "sum": 31303,
-            "counts": [
-              3, 5, 7, ...
-            ]
-          },
-          "<other histogram>:" {
-            "sum": ...,
-            "counts" [
-              // the count for each histogram's bucket
-            ]
-          }
-        },
-        "<other process>": {
-          ...
-        }
-      },
-      "keyedHistograms": {
-        "content": {
-          "TELEMETRY_TEST_MULTIPRODUCT_KEYED": {
-            "niceKey": {
-              "sum": 13001,
-              "counts": [
-                1, 2, 3, ...
-              ]
-            },
-            "<other key>": {
-              ..
-            }
-          },
-          "<other keyed histogram>": {
-            ...
-          }
-        },
-        "<other process>": {
-          ...
-        }
-      }
-    }
-
-The internal C++ API
---------------------
-The following API is only exposed to the rest of the Telemetry core and the gtest suite.
-
-.. code-block:: cpp
-
-    /**
-     * Initializes the GeckoView persistence.
-     * This loads any measure that was previously persisted and then kicks
-     * off the persistence timer that regularly serializes telemetry measurements
-     * to the disk (off the main thread).
-     *
-     * Note: while this code should only be used in GeckoView, it's also
-     * compiled on other platforms for test-coverage.
-     */
-    void InitPersistence();
-
-    /**
-     * Shuts down the GeckoView persistence.
-     */
-    void DeInitPersistence();
-
-    /**
-     * Clears any GeckoView persisted data.
-     * This physically deletes persisted data files.
-     */
-    void ClearPersistenceData();
-
-Version history
----------------
-
-
-- Firefox 62:
-
-  - Initial GeckoView support and scalar persistence (`bug 1453591 <https://bugzilla.mozilla.org/show_bug.cgi?id=1453591>`_).
-  - Persistence support for histograms (`bug 1457127 <https://bugzilla.mozilla.org/show_bug.cgi?id=1457127>`_).
-  - Preserve the semantics of scalar operations when restoring the persisted state (`bug 1454606 <https://bugzilla.mozilla.org/show_bug.cgi?id=1454606>`_)
--- a/toolkit/components/telemetry/docs/internals/preferences.rst
+++ b/toolkit/components/telemetry/docs/internals/preferences.rst
@@ -230,24 +230,16 @@ Data-choices notification
 
 ``datareporting.policy.minimumPolicyVersion.channel-NAME``
 
   This is the only channel-specific version that we currently use for the minimum policy version.
 
 GeckoView
 ---------
 
-``toolkit.telemetry.isGeckoViewMode``
-
-   Whether or not Telemetry needs to run in :doc:`GeckoView <../internals/geckoview>` mode. If true, and ``toolkit.telemetry.geckoview.streaming`` is false,  measurements persistence is enabled. Defaults to false on all products except GeckoView.
-
-``toolkit.telemetry.geckoPersistenceTimeout``
-
-   The interval that governs how frequently measurements are saved to disk, in milliseconds. Defaults to 60000 (60 seconds).
-
 ``toolkit.telemetry.geckoview.streaming``
 
    Whether the GeckoView mode we're running in is the variety that uses the :doc:`GeckoView Streaming Telemetry API <../internals/geckoview-streaming>` or not.
    Defaults to false.
 
 ``toolkit.telemetry.geckoview.batchDurationMS``
 
    The duration in milliseconds over which :doc:`GeckoView Streaming Telemetry <../internals/geckoview-streaming>` will batch accumulations before passing it on to its delegate.
deleted file mode 100644
--- a/toolkit/components/telemetry/geckoview/GeckoViewTelemetryController.jsm
+++ /dev/null
@@ -1,147 +0,0 @@
-/* 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 { XPCOMUtils } = ChromeUtils.import(
-  "resource://gre/modules/XPCOMUtils.jsm"
-);
-const { GeckoViewUtils } = ChromeUtils.import(
-  "resource://gre/modules/GeckoViewUtils.jsm"
-);
-
-XPCOMUtils.defineLazyModuleGetters(this, {
-  EventDispatcher: "resource://gre/modules/Messaging.jsm",
-  Services: "resource://gre/modules/Services.jsm",
-  TelemetryUtils: "resource://gre/modules/TelemetryUtils.jsm",
-});
-
-const { debug, warn } = GeckoViewUtils.initLogging(
-  "GeckoView.TelemetryController"
-); // eslint-disable-line no-unused-vars
-
-var EXPORTED_SYMBOLS = ["GeckoViewTelemetryController"];
-
-// Persistent data loading topic - see TelemetryGeckoViewPersistence.cpp.
-const LOAD_COMPLETE_TOPIC = "internal-telemetry-geckoview-load-complete";
-
-const GeckoViewTelemetryController = {
-  /**
-   * Setup the Telemetry recording flags. This must be called
-   * in all the processes that need to collect Telemetry.
-   */
-  setup() {
-    TelemetryUtils.setTelemetryRecordingFlags();
-
-    debug`setup -
-           canRecordPrereleaseData ${Services.telemetry.canRecordPrereleaseData},
-           canRecordReleaseData ${Services.telemetry.canRecordReleaseData}`;
-
-    if (GeckoViewUtils.IS_PARENT_PROCESS) {
-      // Prevent dispatching snapshots before persistent data has been loaded.
-      this._loadComplete = new Promise(resolve => {
-        Services.obs.addObserver(function observer(aSubject, aTopic, aData) {
-          if (aTopic !== LOAD_COMPLETE_TOPIC) {
-            warn`Received unexpected topic ${aTopic}`;
-            return;
-          }
-          debug`observed ${aTopic} - ready to handle telemetry requests`;
-          // Loading data has completed, discard this observer.
-          Services.obs.removeObserver(observer, LOAD_COMPLETE_TOPIC);
-          resolve();
-        }, LOAD_COMPLETE_TOPIC);
-      });
-
-      try {
-        EventDispatcher.instance.registerListener(this, [
-          "GeckoView:TelemetrySnapshots",
-        ]);
-      } catch (e) {
-        warn`Failed registering GeckoView:TelemetrySnapshots listener: ${e}`;
-      }
-    }
-  },
-
-  /**
-   * Handle GeckoView:TelemetrySnapshots requests.
-   * Match with RuntimeTelemetry.getSnapshots.
-   *
-   * @param aEvent Name of the event to dispatch.
-   * @param aData Optional object containing data for the event.
-   * @param aCallback Optional callback implementing nsIAndroidEventCallback.
-   */
-  onEvent(aEvent, aData, aCallback) {
-    debug`onEvent: aEvent=${aEvent}, aData=${aData}`;
-
-    if (aEvent !== "GeckoView:TelemetrySnapshots") {
-      warn`Received unexpected event ${aEvent}`;
-      return;
-    }
-
-    // Handle this request when loading has completed.
-    this._loadComplete.then(() =>
-      this.retrieveSnapshots(aData.clear, aCallback)
-    );
-  },
-
-  /**
-   * Retrieve snapshots and forward them to the callback.
-   *
-   * @param aClear True if snapshot data should be cleared after retrieving.
-   * @param aCallback Callback implementing nsIAndroidEventCallback.
-   */
-  retrieveSnapshots(aClear, aCallback) {
-    debug`retrieveSnapshots`;
-
-    const histograms = Services.telemetry.getSnapshotForHistograms(
-      "main",
-      /* clear */ false
-    );
-    const keyedHistograms = Services.telemetry.getSnapshotForKeyedHistograms(
-      "main",
-      /* clear */ false
-    );
-    const scalars = Services.telemetry.getSnapshotForScalars(
-      "main",
-      /* clear */ false
-    );
-    const keyedScalars = Services.telemetry.getSnapshotForKeyedScalars(
-      "main",
-      /* clear */ false
-    );
-
-    const snapshots = {
-      histograms,
-      keyedHistograms,
-      scalars,
-      keyedScalars,
-    };
-
-    if (
-      !snapshots.histograms ||
-      !snapshots.keyedHistograms ||
-      !snapshots.scalars ||
-      !snapshots.keyedScalars
-    ) {
-      aCallback.onError(`Failed retrieving snapshots!`);
-      return;
-    }
-
-    let processSnapshots = {};
-    for (let [name, snapshot] of Object.entries(snapshots)) {
-      for (let [processName, processSnapshot] of Object.entries(snapshot)) {
-        if (!(processName in processSnapshots)) {
-          processSnapshots[processName] = {};
-        }
-        processSnapshots[processName][name] = processSnapshot;
-      }
-    }
-
-    if (aClear) {
-      Services.telemetry.clearProbes();
-    }
-
-    aCallback.onSuccess(processSnapshots);
-  },
-};
deleted file mode 100644
--- a/toolkit/components/telemetry/geckoview/TelemetryGeckoViewPersistence.cpp
+++ /dev/null
@@ -1,587 +0,0 @@
-/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
-/* vim: set ts=8 sts=2 et sw=2 tw=80: */
-/* 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/. */
-
-#include "TelemetryGeckoViewPersistence.h"
-
-#include "core/TelemetryHistogram.h"
-#include "core/TelemetryScalar.h"
-#include "jsapi.h"
-#include "js/JSON.h"
-#include "mozilla/dom/ScriptSettings.h"  // for AutoJSAPI
-#include "mozilla/dom/SimpleGlobalObject.h"
-#include "mozilla/ErrorNames.h"
-#include "mozilla/JSONWriter.h"
-#include "mozilla/Path.h"
-#include "mozilla/Preferences.h"
-#include "mozilla/ScopeExit.h"
-#include "mozilla/StaticPtr.h"
-#include "nsDirectoryServiceDefs.h"
-#include "nsIFile.h"
-#include "nsIInputStream.h"
-#include "nsIObserverService.h"
-#include "nsIOutputStream.h"
-#include "nsISafeOutputStream.h"
-#include "nsIThread.h"
-#include "nsITimer.h"
-#include "nsLocalFile.h"
-#include "nsNetUtil.h"
-#include "nsThreadUtils.h"
-#include "nsXULAppAPI.h"
-#include "prenv.h"
-#include "prio.h"
-#include "xpcpublic.h"
-
-using mozilla::GetErrorName;
-using mozilla::MakeScopeExit;
-using mozilla::Preferences;
-using mozilla::StaticRefPtr;
-using mozilla::TaskCategory;
-using mozilla::dom::AutoJSAPI;
-using mozilla::dom::SimpleGlobalObject;
-
-using PathChar = mozilla::filesystem::Path::value_type;
-using PathCharPtr = const PathChar*;
-
-// Enable logging by default on Debug builds.
-#ifdef DEBUG
-// If we're building for Android, use the provided logging facility.
-#  ifdef MOZ_WIDGET_ANDROID
-#    include <android/log.h>
-#    define ANDROID_LOG(fmt, ...) \
-      __android_log_print(ANDROID_LOG_DEBUG, "Telemetry", fmt, ##__VA_ARGS__)
-#  else
-// If we're building for other platforms (e.g. for running test coverage), try
-// to print something anyway.
-#    define ANDROID_LOG(...) printf_stderr("\n**** TELEMETRY: " __VA_ARGS__)
-#  endif  // MOZ_WIDGET_ANDROID
-#else
-// No-op on Release builds.
-#  define ANDROID_LOG(...)
-#endif  // DEBUG
-
-// The Gecko runtime can be killed at anytime. Moreover, we can
-// have very short lived sessions. The persistence timeout governs
-// how frequently measurements are saved to disk.
-const uint32_t kDefaultPersistenceTimeoutMs = 60 * 1000;  // 60s
-
-// The name of the persistence file used for saving the
-// measurements.
-const char16_t kPersistenceFileName[] = u"gv_measurements.json";
-
-// This topic is notified and propagated up to the application to
-// make sure it knows that data loading has complete and that snapshotting
-// can now be performed.
-const char kLoadCompleteTopic[] = "internal-telemetry-geckoview-load-complete";
-
-// The timer used for persisting measurements data.
-nsITimer* gPersistenceTimer;
-// The worker thread to perform persistence.
-StaticRefPtr<nsIThread> gPersistenceThread;
-
-namespace {
-
-void PersistenceThreadPersist();
-
-/**
-+ * The helper class used by mozilla::JSONWriter to
-+ * serialize the JSON structure to a file.
-+ */
-class StreamingJSONWriter : public mozilla::JSONWriteFunc {
- public:
-  nsresult Open(nsCOMPtr<nsIFile> aOutFile) {
-    MOZ_ASSERT(!mStream, "Open must not be called twice");
-    nsresult rv =
-        NS_NewSafeLocalFileOutputStream(getter_AddRefs(mStream), aOutFile);
-    NS_ENSURE_SUCCESS(rv, rv);
-    return NS_OK;
-  }
-
-  nsresult Close() {
-    MOZ_ASSERT(mStream, "Close must be called on an already opened stream");
-    // We don't need to care too much about checking if count matches
-    // the length of aData: Finish() will do that for us and fail if
-    // Write did not persist all the data or mStream->Close() failed.
-    // Note that |nsISafeOutputStream| will write to a temp file and only
-    // overwrite the destination if no error was reported.
-    nsCOMPtr<nsISafeOutputStream> safeStream = do_QueryInterface(mStream);
-    MOZ_ASSERT(safeStream);
-    return safeStream->Finish();
-  }
-
-  void Write(const char* aStr) override {
-    uint32_t count;
-    mozilla::Unused << mStream->Write(aStr, strlen(aStr), &count);
-  }
-
-  void Write(const char* aStr, size_t aLen) override {
-    uint32_t count;
-    mozilla::Unused << mStream->Write(aStr, aLen, &count);
-  }
-
- private:
-  nsCOMPtr<nsIOutputStream> mStream;
-};
-
-/**
- * Get the path to the Android Data dir.
- *
- * @param {nsTString<PathChar>} aOutDir - the variable holding the path.
- * @return {nsresult} NS_OK if the data dir path was found, a failure value
- *                    otherwise.
- */
-nsresult GetAndroidDataDir(nsTString<PathChar>& aOutDir) {
-  // This relies on the Java environment to set the location of the
-  // cache directory. If that happens, the following variable is set.
-  // This should always be the case.
-  const char* dataDir = PR_GetEnv("MOZ_ANDROID_DATA_DIR");
-  if (!dataDir || !*dataDir) {
-    ANDROID_LOG(
-        "GetAndroidDataDir - Cannot find the data directory in the "
-        "environment.");
-    return NS_ERROR_FAILURE;
-  }
-
-  aOutDir.AssignASCII(dataDir);
-  return NS_OK;
-}
-
-/**
- * Get the path to the persistence file in the Android Data dir.
- *
- * @param {nsCOMPtr<nsIFile>} aOutFile - the nsIFile pointer holding the file
- *                                       info.
- * @return {nsresult} NS_OK if the persistence file was found, a failure value
- *                          otherwise.
- */
-nsresult GetPersistenceFile(nsCOMPtr<nsIFile>& aOutFile) {
-  nsTString<PathChar> dataDir;
-  nsresult rv = GetAndroidDataDir(dataDir);
-  NS_ENSURE_SUCCESS(rv, rv);
-
-  // Append the extension to the filename.
-  nsAutoString fileName;
-  fileName.Assign(kPersistenceFileName);
-
-  aOutFile = new nsLocalFile(dataDir);
-  aOutFile->Append(fileName);
-  ANDROID_LOG("GetPersistenceFile -  %s", aOutFile->HumanReadablePath().get());
-  return NS_OK;
-}
-
-/**
- * Read and parses JSON content from a file.
- *
- * @param {nsCOMPtr<nsIFile>} aFile - the nsIFile handle to the file.
- * @param {nsACString} fileContent - the content of the file.
- * @return {nsresult} NS_OK if the file was correctly read, an error code
- *                          otherwise.
- */
-nsresult ReadFromFile(const nsCOMPtr<nsIFile>& aFile, nsACString& fileContent) {
-  int64_t fileSize = 0;
-  nsresult rv = aFile->GetFileSize(&fileSize);
-  if (NS_FAILED(rv)) {
-    return rv;
-  }
-
-  nsCOMPtr<nsIInputStream> inStream;
-  rv = NS_NewLocalFileInputStream(getter_AddRefs(inStream), aFile, PR_RDONLY);
-  NS_ENSURE_SUCCESS(rv, rv);
-
-  // Make sure to close the stream.
-  auto scopedStreamClose = MakeScopeExit([inStream] { inStream->Close(); });
-
-  rv = NS_ReadInputStreamToString(inStream, fileContent, fileSize);
-  NS_ENSURE_SUCCESS(rv, rv);
-
-  return NS_OK;
-}
-
-/**
- * Arms the persistence timer and instructs to run the persistence
- * task off the main thread.
- */
-void MainThreadArmPersistenceTimer() {
-  MOZ_ASSERT(NS_IsMainThread());
-  ANDROID_LOG("MainThreadArmPersistenceTimer");
-
-  // We won't have a persistence timer the first time this runs, so take
-  // care of that.
-  if (!gPersistenceTimer) {
-    gPersistenceTimer = NS_NewTimer().take();
-    if (!gPersistenceTimer) {
-      ANDROID_LOG("MainThreadArmPersistenceTimer - Timer creation failed.");
-      return;
-    }
-  }
-
-  // Define the callback for the persistence timer: it will dispatch the
-  // persistence task off the main thread. Once finished, it will trigger the
-  // timer again.
-  nsTimerCallbackFunc timerCallback = [](nsITimer* aTimer, void* aClosure) {
-    gPersistenceThread->Dispatch(
-        NS_NewRunnableFunction("PersistenceThreadPersist",
-                               []() -> void { ::PersistenceThreadPersist(); }));
-  };
-
-  uint32_t timeout =
-      Preferences::GetUint("toolkit.telemetry.geckoPersistenceTimeout",
-                           kDefaultPersistenceTimeoutMs);
-
-  // Schedule the timer to automatically run and reschedule
-  // every |kPersistenceTimeoutMs|.
-  gPersistenceTimer->InitWithNamedFuncCallback(
-      timerCallback, nullptr, timeout, nsITimer::TYPE_ONE_SHOT_LOW_PRIORITY,
-      "TelemetryGeckoViewPersistence::Persist");
-}
-
-/**
- * Parse the string data into a JSON structure, using
- * the native JS JSON parser.
- */
-void MainThreadParsePersistedProbes(const nsACString& aProbeData) {
-  // We're required to run on the main thread since we're using JS.
-  MOZ_ASSERT(NS_IsMainThread());
-  ANDROID_LOG("MainThreadParsePersistedProbes");
-
-  // We need a JS context to run the parsing stuff in.
-  JS::Rooted<JSObject*> cleanGlobal(
-      mozilla::dom::RootingCx(),
-      SimpleGlobalObject::Create(
-          SimpleGlobalObject::GlobalType::BindingDetail));
-  if (!cleanGlobal) {
-    ANDROID_LOG(
-        "MainThreadParsePersistedProbes - Failed to create a JS global object");
-    return;
-  }
-
-  AutoJSAPI jsapi;
-  if (NS_WARN_IF(!jsapi.Init(cleanGlobal))) {
-    ANDROID_LOG("MainThreadParsePersistedProbes - Failed to get JS API");
-    return;
-  }
-
-  // Parse the JSON using the JS API.
-  JS::RootedValue data(jsapi.cx());
-  NS_ConvertUTF8toUTF16 utf16Content(aProbeData);
-  if (!JS_ParseJSON(jsapi.cx(), utf16Content.BeginReading(),
-                    utf16Content.Length(), &data)) {
-    ANDROID_LOG(
-        "MainThreadParsePersistedProbes - Failed to parse the persisted JSON");
-    return;
-  }
-
-  // Get the data for the scalars.
-  JS::RootedObject dataObj(jsapi.cx(), &data.toObject());
-  JS::RootedValue scalarData(jsapi.cx());
-  if (JS_GetProperty(jsapi.cx(), dataObj, "scalars", &scalarData)) {
-    // If the data is an object, try to parse its properties. If not,
-    // silently skip and try to load the other sections.
-    if (!scalarData.isObject() ||
-        NS_FAILED(TelemetryScalar::DeserializePersistedScalars(jsapi.cx(),
-                                                               scalarData))) {
-      ANDROID_LOG(
-          "MainThreadParsePersistedProbes - Failed to parse 'scalars'.");
-      MOZ_ASSERT(!JS_IsExceptionPending(jsapi.cx()),
-                 "Parsers must suppress exceptions themselves");
-    }
-  } else {
-    // Getting the "scalars" property failed, suppress the exception
-    // and continue.
-    JS_ClearPendingException(jsapi.cx());
-  }
-
-  JS::RootedValue keyedScalarData(jsapi.cx());
-  if (JS_GetProperty(jsapi.cx(), dataObj, "keyedScalars", &keyedScalarData)) {
-    // If the data is an object, try to parse its properties. If not,
-    // silently skip and try to load the other sections.
-    if (!keyedScalarData.isObject() ||
-        NS_FAILED(TelemetryScalar::DeserializePersistedKeyedScalars(
-            jsapi.cx(), keyedScalarData))) {
-      ANDROID_LOG(
-          "MainThreadParsePersistedProbes - Failed to parse 'keyedScalars'.");
-      MOZ_ASSERT(!JS_IsExceptionPending(jsapi.cx()),
-                 "Parsers must suppress exceptions themselves");
-    }
-  } else {
-    // Getting the "keyedScalars" property failed, suppress the exception
-    // and continue.
-    JS_ClearPendingException(jsapi.cx());
-  }
-
-  // Get the data for the histograms.
-  JS::RootedValue histogramData(jsapi.cx());
-  if (JS_GetProperty(jsapi.cx(), dataObj, "histograms", &histogramData)) {
-    // If the data is an object, try to parse its properties. If not,
-    // silently skip and try to load the other sections.
-    nsresult rv = NS_OK;
-    if (!histogramData.isObject() ||
-        NS_FAILED(rv = TelemetryHistogram::DeserializeHistograms(
-                      jsapi.cx(), histogramData))) {
-      nsAutoCString errorName;
-      GetErrorName(rv, errorName);
-      ANDROID_LOG(
-          "MainThreadParsePersistedProbes - Failed to parse 'histograms', %s.",
-          errorName.get());
-      MOZ_ASSERT(!JS_IsExceptionPending(jsapi.cx()),
-                 "Parsers must suppress exceptions themselves");
-    }
-  } else {
-    // Getting the "histogramData" property failed, suppress the exception
-    // and continue.
-    JS_ClearPendingException(jsapi.cx());
-  }
-
-  // Get the data for the keyed histograms.
-  JS::RootedValue keyedHistogramData(jsapi.cx());
-  if (JS_GetProperty(jsapi.cx(), dataObj, "keyedHistograms",
-                     &keyedHistogramData)) {
-    // If the data is an object, try to parse its properties. If not,
-    // silently skip and try to load the other sections.
-    nsresult rv = NS_OK;
-    if (!keyedHistogramData.isObject() ||
-        NS_FAILED(rv = TelemetryHistogram::DeserializeKeyedHistograms(
-                      jsapi.cx(), keyedHistogramData))) {
-      nsAutoCString errorName;
-      GetErrorName(rv, errorName);
-      ANDROID_LOG(
-          "MainThreadParsePersistedProbes - Failed to parse 'keyedHistograms', "
-          "%s.",
-          errorName.get());
-      MOZ_ASSERT(!JS_IsExceptionPending(jsapi.cx()),
-                 "Parsers must suppress exceptions themselves");
-    }
-  } else {
-    // Getting the "keyedHistogramData" property failed, suppress the exception
-    // and continue.
-    JS_ClearPendingException(jsapi.cx());
-  }
-}
-
-/**
- * The persistence worker function, meant to be run off the main thread.
- */
-void PersistenceThreadPersist() {
-  MOZ_ASSERT(XRE_IsParentProcess(),
-             "We must only persist from the parent process.");
-  MOZ_ASSERT(!NS_IsMainThread(),
-             "This function must be called off the main thread.");
-  ANDROID_LOG("PersistenceThreadPersist");
-
-  // If the function completes or fails, make sure to spin up the persistence
-  // timer again.
-  auto scopedArmTimer = MakeScopeExit([&] {
-    NS_DispatchToMainThread(NS_NewRunnableFunction(
-        "MainThreadArmPersistenceTimer",
-        []() -> void { MainThreadArmPersistenceTimer(); }));
-  });
-
-  nsCOMPtr<nsIFile> persistenceFile;
-  if (NS_FAILED(GetPersistenceFile(persistenceFile))) {
-    ANDROID_LOG(
-        "PersistenceThreadPersist - Failed to get the persistence file.");
-    return;
-  }
-
-  // Open the persistence file.
-  mozilla::UniquePtr<StreamingJSONWriter> jsonWriter =
-      mozilla::MakeUnique<StreamingJSONWriter>();
-
-  if (!jsonWriter || NS_FAILED(jsonWriter->Open(persistenceFile))) {
-    ANDROID_LOG(
-        "PersistenceThreadPersist - There was an error opening the persistence "
-        "file.");
-    return;
-  }
-
-  // Build the JSON structure: give up the ownership of jsonWriter.
-  mozilla::JSONWriter w(std::move(jsonWriter));
-  w.Start();
-
-  w.StartObjectProperty("scalars");
-  if (NS_FAILED(TelemetryScalar::SerializeScalars(w))) {
-    ANDROID_LOG("Persist - Failed to persist scalars.");
-  }
-  w.EndObject();
-
-  w.StartObjectProperty("keyedScalars");
-  if (NS_FAILED(TelemetryScalar::SerializeKeyedScalars(w))) {
-    ANDROID_LOG("Persist - Failed to persist keyed scalars.");
-  }
-  w.EndObject();
-
-  w.StartObjectProperty("histograms");
-  if (NS_FAILED(TelemetryHistogram::SerializeHistograms(w))) {
-    ANDROID_LOG("Persist - Failed to persist histograms.");
-  }
-  w.EndObject();
-
-  w.StartObjectProperty("keyedHistograms");
-  if (NS_FAILED(TelemetryHistogram::SerializeKeyedHistograms(w))) {
-    ANDROID_LOG("Persist - Failed to persist keyed histograms.");
-  }
-  w.EndObject();
-
-  // End the building process.
-  w.End();
-
-  // Android can kill us while we are writing to disk and, if that happens,
-  // we end up with a corrupted json overwriting the old session data.
-  // Luckily, |StreamingJSONWriter::Close| is smart enough to write to a
-  // temporary file and only overwrite the original file if nothing bad
-  // happened.
-  nsresult rv = static_cast<StreamingJSONWriter*>(w.WriteFunc())->Close();
-  if (NS_FAILED(rv)) {
-    ANDROID_LOG(
-        "PersistenceThreadPersist - There was an error writing to the "
-        "persistence file.");
-    return;
-  }
-}
-
-/**
- * This function loads the persisted metrics from a JSON file
- * and adds them to the related storage. After it completes,
- * it spins up the persistence timer.
- *
- * Please note that this function is meant to be run off the
- * main-thread.
- */
-void PersistenceThreadLoadData() {
-  MOZ_ASSERT(XRE_IsParentProcess(),
-             "We must only persist from the parent process.");
-  MOZ_ASSERT(!NS_IsMainThread(), "We must perform I/O off the main thread.");
-  ANDROID_LOG("PersistenceThreadLoadData");
-
-  // If the function completes or fails, make sure to spin up the persistence
-  // timer.
-  nsAutoCString fileContent;
-  auto scopedArmTimer = MakeScopeExit([&] {
-    NS_DispatchToMainThread(NS_NewRunnableFunction(
-        "MainThreadArmPersistenceTimer", [fileContent]() -> void {
-          // Try to parse the probes if the file was not empty.
-          if (!fileContent.IsEmpty()) {
-            MainThreadParsePersistedProbes(fileContent);
-          }
-
-          TelemetryScalar::ApplyPendingOperations();
-
-          // Arm the timer.
-          MainThreadArmPersistenceTimer();
-          // Notify that we're good to take snapshots!
-          nsCOMPtr<nsIObserverService> os =
-              mozilla::services::GetObserverService();
-          if (os) {
-            os->NotifyObservers(nullptr, kLoadCompleteTopic, nullptr);
-          }
-        }));
-  });
-
-  // Attempt to load the persistence file. This could fail if we're not able
-  // to allocate enough memory for the content. See bug 1460911.
-  nsCOMPtr<nsIFile> persistenceFile;
-  if (NS_FAILED(GetPersistenceFile(persistenceFile)) ||
-      NS_FAILED(ReadFromFile(persistenceFile, fileContent))) {
-    ANDROID_LOG("PersistenceThreadLoadData - Failed to load cache file at %s",
-                persistenceFile->HumanReadablePath().get());
-    return;
-  }
-}
-
-}  // anonymous namespace
-
-// This namespace exposes testing only helpers to simplify writing
-// gtest cases.
-namespace TelemetryGeckoViewTesting {
-
-void TestDispatchPersist() {
-  gPersistenceThread->Dispatch(NS_NewRunnableFunction(
-      "Persist", []() -> void { ::PersistenceThreadPersist(); }));
-}
-
-}  // namespace TelemetryGeckoViewTesting
-
-void TelemetryGeckoViewPersistence::InitPersistence() {
-  MOZ_ASSERT(NS_IsMainThread());
-
-  if (gPersistenceThread) {
-    ANDROID_LOG("Init must only be called once.");
-    return;
-  }
-
-  // Only register the persistence timer in the parent process in
-  // order to persist data for all the processes.
-  if (!XRE_IsParentProcess()) {
-    ANDROID_LOG("InitPersistence - Bailing out on child process.");
-    return;
-  }
-
-  ANDROID_LOG("InitPersistence");
-
-  // Spawn a new thread for handling GeckoView Telemetry persistence I/O.
-  // We just spawn it once and re-use it later.
-  nsCOMPtr<nsIThread> thread;
-  nsresult rv = NS_NewNamedThread("TelemetryGVIO", getter_AddRefs(thread));
-  if (NS_WARN_IF(NS_FAILED(rv))) {
-    ANDROID_LOG("InitPersistence -  Failed to instantiate the worker thread.");
-    return;
-  }
-
-  gPersistenceThread = ToRefPtr(std::move(thread));
-
-  // From now on all scalar operations should be recorded.
-  TelemetryScalar::DeserializationStarted();
-
-  // Trigger the loading of the persistence data. After the function
-  // completes it will automatically arm the persistence timer.
-  gPersistenceThread->Dispatch(NS_NewRunnableFunction(
-      "PersistenceThreadLoadData", &PersistenceThreadLoadData));
-}
-
-void TelemetryGeckoViewPersistence::DeInitPersistence() {
-  MOZ_ASSERT(NS_IsMainThread());
-
-  // Bail out if this is not the parent process.
-  if (!XRE_IsParentProcess()) {
-    ANDROID_LOG("DeInitPersistence - Bailing out.");
-    return;
-  }
-
-  // Even though we need to implement this function, it might end up
-  // not being called: Android might kill us without notice to reclaim
-  // our memory in case some other foreground application needs it.
-  ANDROID_LOG("DeInitPersistence");
-
-  if (gPersistenceThread) {
-    gPersistenceThread->Shutdown();
-    gPersistenceThread = nullptr;
-  }
-
-  if (gPersistenceTimer) {
-    // Always make sure the timer is canceled.
-    MOZ_ALWAYS_SUCCEEDS(gPersistenceTimer->Cancel());
-    NS_RELEASE(gPersistenceTimer);
-  }
-}
-
-void TelemetryGeckoViewPersistence::ClearPersistenceData() {
-  // This can be run on any thread, as we just dispatch the persistence
-  // task to the persistence thread.
-  MOZ_ASSERT(gPersistenceThread);
-
-  ANDROID_LOG("ClearPersistenceData");
-
-  // Trigger clearing the persisted measurements off the main thread.
-  gPersistenceThread->Dispatch(
-      NS_NewRunnableFunction("ClearPersistedData", []() -> void {
-        nsCOMPtr<nsIFile> persistenceFile;
-        if (NS_FAILED(GetPersistenceFile(persistenceFile)) ||
-            NS_FAILED(persistenceFile->Remove(false))) {
-          ANDROID_LOG(
-              "ClearPersistenceData - Failed to remove the persistence file.");
-          return;
-        }
-      }));
-}
deleted file mode 100644
--- a/toolkit/components/telemetry/geckoview/TelemetryGeckoViewPersistence.h
+++ /dev/null
@@ -1,36 +0,0 @@
-/* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*- */
-/* vim: set ts=8 sts=2 et sw=2 tw=80: */
-/* 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/. */
-
-#ifndef GeckoViewTelemetryPersistence_h__
-#define GeckoViewTelemetryPersistence_h__
-
-namespace TelemetryGeckoViewPersistence {
-
-/**
- * Initializes the GeckoView persistence.
- * This loads any measure that was previously persisted and then kicks
- * off the persistence timer that regularly serializes telemetry measurements
- * to the disk (off the main thread).
- *
- * Note: while this code should only be used in GeckoView, it's also
- * compiled on other platforms for test-coverage.
- */
-void InitPersistence();
-
-/**
- * Shuts down the GeckoView persistence.
- */
-void DeInitPersistence();
-
-/**
- * Clears any GeckoView persisted data.
- * This physically deletes persisted data files.
- */
-void ClearPersistenceData();
-
-}  // namespace TelemetryGeckoViewPersistence
-
-#endif  // GeckoViewTelemetryPersistence_h__
deleted file mode 100644
--- a/toolkit/components/telemetry/geckoview/TelemetryGeckoViewTesting.cpp
+++ /dev/null
@@ -1,46 +0,0 @@
-/* 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/. */
-
-#include "TelemetryGeckoViewTesting.h"
-#include "TelemetryGeckoViewPersistence.h"
-#include "core/TelemetryScalar.h"
-
-namespace TelemetryGeckoViewTesting {
-// This is defined in TelemetryGeckoViewPersistence.cpp
-void TestDispatchPersist();
-}  // namespace TelemetryGeckoViewTesting
-
-NS_IMPL_ISUPPORTS(TelemetryGeckoViewTestingImpl, nsITelemetryGeckoViewTesting)
-
-// We don't need |aCx|. It's there to make these test functions harder
-// to call from C++.
-NS_IMETHODIMP
-TelemetryGeckoViewTestingImpl::InitPersistence(JSContext*) {
-  TelemetryGeckoViewPersistence::InitPersistence();
-  return NS_OK;
-}
-
-NS_IMETHODIMP
-TelemetryGeckoViewTestingImpl::DeInitPersistence(JSContext*) {
-  TelemetryGeckoViewPersistence::DeInitPersistence();
-  return NS_OK;
-}
-
-NS_IMETHODIMP
-TelemetryGeckoViewTestingImpl::ClearPersistenceData(JSContext*) {
-  TelemetryGeckoViewPersistence::ClearPersistenceData();
-  return NS_OK;
-}
-
-NS_IMETHODIMP
-TelemetryGeckoViewTestingImpl::ForcePersist(JSContext*) {
-  TelemetryGeckoViewTesting::TestDispatchPersist();
-  return NS_OK;
-}
-
-NS_IMETHODIMP
-TelemetryGeckoViewTestingImpl::DeserializationStarted(JSContext*) {
-  TelemetryScalar::DeserializationStarted();
-  return NS_OK;
-}
deleted file mode 100644
--- a/toolkit/components/telemetry/geckoview/TelemetryGeckoViewTesting.h
+++ /dev/null
@@ -1,14 +0,0 @@
-/* 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/. */
-
-#include "nsITelemetryGeckoViewTesting.h"
-
-class TelemetryGeckoViewTestingImpl final
-    : public nsITelemetryGeckoViewTesting {
-  ~TelemetryGeckoViewTestingImpl() = default;
-
- public:
-  NS_DECL_ISUPPORTS
-  NS_DECL_NSITELEMETRYGECKOVIEWTESTING
-};
deleted file mode 100644
--- a/toolkit/components/telemetry/geckoview/gtest/TestGeckoView.cpp
+++ /dev/null
@@ -1,601 +0,0 @@
-/* vim:set ts=2 sw=2 sts=2 et: */
-/* Any copyright is dedicated to the Public Domain.
- * http://creativecommons.org/publicdomain/zero/1.0/
- */
-
-#include "gtest/gtest.h"
-#include "mozilla/JSONWriter.h"
-#include "nsDirectoryServiceDefs.h"
-#include "nsIObserver.h"
-#include "nsIObserverService.h"
-#include "nsIOutputStream.h"
-#include "nsJSUtils.h"
-#include "nsNetUtil.h"
-#include "nsPrintfCString.h"
-#include "nsThreadUtils.h"
-#include "prenv.h"
-#include "mozilla/Telemetry.h"
-#include "TelemetryFixture.h"
-#include "TelemetryGeckoViewPersistence.h"
-#include "core/TelemetryScalar.h"
-#include "TelemetryTestHelpers.h"
-
-using namespace mozilla;
-using namespace TelemetryTestHelpers;
-
-const char kSampleData[] = R"({
-  "scalars": {
-    "content": {
-      "telemetry.test.all_processes_uint": 37
-    }
-  },
-  "keyedScalars": {
-    "parent": {
-      "telemetry.test.keyed_unsigned_int": {
-        "testKey": 73
-      }
-    }
-  }
-})";
-
-const char16_t kPersistedFilename[] = u"gv_measurements.json";
-const char kDataLoadedTopic[] = "internal-telemetry-geckoview-load-complete";
-
-namespace {
-
-/**
- * Using gtest assertion macros requires the containing function to return
- * a void type. For this reason, all the functions below are using that return
- * type.
- */
-void GetMockedDataDir(nsAString& aMockedDir) {
-  // Get the OS temporary directory.
-  nsCOMPtr<nsIFile> tmpDir;
-  nsresult rv = NS_GetSpecialDirectory(NS_OS_TEMP_DIR, getter_AddRefs(tmpDir));
-  ASSERT_EQ(NS_SUCCEEDED(rv), true);
-  // Return the mocked dir.
-  rv = tmpDir->GetPath(aMockedDir);
-  ASSERT_EQ(NS_SUCCEEDED(rv), true);
-}
-
-void MockAndroidDataDir() {
-  // Get the OS temporary directory.
-  nsAutoString mockedPath;
-  GetMockedDataDir(mockedPath);
-
-  // Set the environment variable to mock.
-  // Note: we intentionally leak it with |ToNewCString| as PR_SetEnv forces
-  // us to!
-  nsAutoCString mockedEnv(nsPrintfCString(
-      "MOZ_ANDROID_DATA_DIR=%s", NS_ConvertUTF16toUTF8(mockedPath).get()));
-  ASSERT_EQ(PR_SetEnv(ToNewCString(mockedEnv)), PR_SUCCESS);
-}
-
-void WritePersistenceFile(const nsACString& aData) {
-  // Write the file to the temporary directory.
-  nsCOMPtr<nsIFile> file;
-  nsresult rv = NS_GetSpecialDirectory(NS_OS_TEMP_DIR, getter_AddRefs(file));
-  ASSERT_EQ(NS_SUCCEEDED(rv), true);
-
-  // Append the filename and the extension.
-  nsAutoString fileName;
-  fileName.Append(kPersistedFilename);
-  file->Append(fileName);
-
-  nsCOMPtr<nsIOutputStream> stream;
-  rv = NS_NewLocalFileOutputStream(getter_AddRefs(stream), file);
-  ASSERT_EQ(NS_SUCCEEDED(rv), true);
-
-  uint32_t count;
-  rv = stream->Write(aData.Data(), aData.Length(), &count);
-  // Make sure we wrote correctly.
-  ASSERT_EQ(NS_SUCCEEDED(rv), true);
-  ASSERT_EQ(count, aData.Length());
-
-  stream->Close();
-}
-
-void RemovePersistenceFile() {
-  nsCOMPtr<nsIFile> file;
-  nsresult rv = NS_GetSpecialDirectory(NS_OS_TEMP_DIR, getter_AddRefs(file));
-  ASSERT_EQ(NS_SUCCEEDED(rv), true);
-
-  // Append the filename and the extension.
-  nsAutoString fileName;
-  fileName.Append(kPersistedFilename);
-  file->Append(fileName);
-
-  bool exists = true;
-  rv = file->Exists(&exists);
-  ASSERT_EQ(NS_OK, rv) << "nsIFile::Exists cannot fail";
-
-  if (exists) {
-    rv = file->Remove(false);
-    ASSERT_EQ(NS_OK, rv) << "nsIFile::Remove cannot delete the requested file";
-  }
-}
-
-void CheckPersistenceFileExists(bool& aFileExists) {
-  nsCOMPtr<nsIFile> file;
-  nsresult rv = NS_GetSpecialDirectory(NS_OS_TEMP_DIR, getter_AddRefs(file));
-  ASSERT_EQ(NS_OK, rv)
-      << "NS_GetSpecialDirectory must return a valid directory";
-
-  // Append the filename and the extension.
-  nsAutoString fileName;
-  fileName.Append(kPersistedFilename);
-  file->Append(fileName);
-
-  rv = file->Exists(&aFileExists);
-  ASSERT_EQ(NS_OK, rv) << "nsIFile::Exists must not fail";
-}
-
-/**
- * A helper class to wait for the internal "data loaded"
- * topic.
- */
-class DataLoadedObserver final : public nsIObserver {
-  ~DataLoadedObserver() = default;
-
- public:
-  NS_DECL_ISUPPORTS
-
-  explicit DataLoadedObserver() : mDataLoaded(false) {
-    // The following line can fail to fetch the observer service. However,
-    // since we're test code, we're fine with crashing due to that.
-    nsCOMPtr<nsIObserverService> observerService =
-        mozilla::services::GetObserverService();
-    observerService->AddObserver(this, kDataLoadedTopic, false);
-  }
-
-  void WaitForNotification() {
-    mozilla::SpinEventLoopUntil([&]() { return mDataLoaded; });
-  }
-
-  NS_IMETHOD Observe(nsISupports* aSubject, const char* aTopic,
-                     const char16_t* aData) override {
-    if (!strcmp(aTopic, kDataLoadedTopic)) {
-      nsCOMPtr<nsIObserverService> observerService =
-          mozilla::services::GetObserverService();
-      observerService->RemoveObserver(this, kDataLoadedTopic);
-      mDataLoaded = true;
-    }
-
-    return NS_OK;
-  }
-
- private:
-  bool mDataLoaded;
-};
-
-NS_IMPL_ISUPPORTS(DataLoadedObserver, nsIObserver)
-
-}  // namespace
-
-/**
- * A GeckoView specific test fixture. Please note that this
- * can't live in the above anonymous namespace.
- */
-class TelemetryGeckoViewFixture : public TelemetryTestFixture {
- protected:
-  virtual void SetUp() {
-    TelemetryTestFixture::SetUp();
-    MockAndroidDataDir();
-  }
-};
-
-namespace TelemetryGeckoViewTesting {
-
-void TestDispatchPersist();
-
-}  // namespace TelemetryGeckoViewTesting
-
-/**
- * Test that corrupted JSON files don't crash the Telemetry core.
- */
-TEST_F(TelemetryGeckoViewFixture, CorruptedPersistenceFiles) {
-  AutoJSContextWithGlobal cx(mCleanGlobal);
-
-  // Try to load a corrupted file.
-  WritePersistenceFile(NS_LITERAL_CSTRING("{"));
-  TelemetryGeckoViewPersistence::InitPersistence();
-  TelemetryGeckoViewPersistence::DeInitPersistence();
-
-  // Cleanup/remove the files.
-  RemovePersistenceFile();
-}
-
-/**
- * Test that valid and empty JSON files don't crash the Telemetry core.
- */
-TEST_F(TelemetryGeckoViewFixture, EmptyPersistenceFiles) {
-  AutoJSContextWithGlobal cx(mCleanGlobal);
-
-  // Try to load an empty file/corrupted file.
-  WritePersistenceFile(EmptyCString());
-  TelemetryGeckoViewPersistence::InitPersistence();
-  TelemetryGeckoViewPersistence::DeInitPersistence();
-
-  // Cleanup/remove the files.
-  RemovePersistenceFile();
-}
-
-/**
- * Test that we're able to clear the persistence storage.
- */
-TEST_F(TelemetryGeckoViewFixture, ClearPersistenceFiles) {
-  AutoJSContextWithGlobal cx(mCleanGlobal);
-
-  bool fileExists = false;
-  CheckPersistenceFileExists(fileExists);
-  ASSERT_FALSE(fileExists)
-  << "No persisted measurements must exist on the disk";
-
-  WritePersistenceFile(nsDependentCString(kSampleData));
-  CheckPersistenceFileExists(fileExists);
-  ASSERT_TRUE(fileExists)
-  << "We should have written the test persistence file to disk";
-
-  // Init the persistence: this will trigger the measurements to be written
-  // to disk off-the-main thread.
-  TelemetryGeckoViewPersistence::InitPersistence();
-  TelemetryGeckoViewPersistence::ClearPersistenceData();
-  TelemetryGeckoViewPersistence::DeInitPersistence();
-
-  CheckPersistenceFileExists(fileExists);
-  ASSERT_FALSE(fileExists)
-  << "ClearPersistenceData must remove the persistence file";
-}
-
-/**
- * Test that the data loaded topic gets notified correctly.
- */
-TEST_F(TelemetryGeckoViewFixture, CheckDataLoadedTopic) {
-  AutoJSContextWithGlobal cx(mCleanGlobal);
-
-  bool fileExists = false;
-  CheckPersistenceFileExists(fileExists);
-  ASSERT_FALSE(fileExists)
-  << "No persisted measurements must exist on the disk";
-
-  // Check that the data loaded topic is notified after attempting the load
-  // if no measurement file exists.
-  RefPtr<DataLoadedObserver> loadingFinished = new DataLoadedObserver();
-  TelemetryGeckoViewPersistence::InitPersistence();
-  loadingFinished->WaitForNotification();
-  TelemetryGeckoViewPersistence::DeInitPersistence();
-
-  // Check that the topic is triggered when the measuements file exists.
-  WritePersistenceFile(nsDependentCString(kSampleData));
-  CheckPersistenceFileExists(fileExists);
-  ASSERT_TRUE(fileExists)
-  << "The persisted measurements must exist on the disk";
-
-  // Check that the data loaded topic is triggered when the measurement file
-  // exists.
-  loadingFinished = new DataLoadedObserver();
-  TelemetryGeckoViewPersistence::InitPersistence();
-  loadingFinished->WaitForNotification();
-  TelemetryGeckoViewPersistence::DeInitPersistence();
-
-  // Cleanup/remove the files.
-  RemovePersistenceFile();
-}
-
-/**
- * Test that we can correctly persist the scalar data.
- */
-TEST_F(TelemetryGeckoViewFixture, PersistScalars) {
-  AutoJSContextWithGlobal cx(mCleanGlobal);
-
-  Unused << mTelemetry->ClearScalars();
-
-  bool fileExists = false;
-  CheckPersistenceFileExists(fileExists);
-  ASSERT_FALSE(fileExists)
-  << "No persisted measurements must exist on the disk";
-
-  RefPtr<DataLoadedObserver> loadingFinished = new DataLoadedObserver();
-
-  // Init the persistence: this will trigger the measurements to be written
-  // to disk off-the-main thread.
-  TelemetryGeckoViewPersistence::InitPersistence();
-  loadingFinished->WaitForNotification();
-
-  // Set some scalars: we can only test the parent process as we don't support
-  // other processes in gtests.
-  const uint32_t kExpectedUintValue = 37;
-  const uint32_t kExpectedKeyedUintValue = 73;
-  Telemetry::ScalarSet(Telemetry::ScalarID::TELEMETRY_TEST_ALL_PROCESSES_UINT,
-                       kExpectedUintValue);
-  Telemetry::ScalarSet(Telemetry::ScalarID::TELEMETRY_TEST_KEYED_UNSIGNED_INT,
-                       NS_LITERAL_STRING("gv_key"), kExpectedKeyedUintValue);
-
-  // Dispatch the persisting task: we don't wait for the timer to expire
-  // as we need a reliable and reproducible way to kick this off. We ensure
-  // that the task runs by shutting down the persistence: this shuts down the
-  // thread which executes the task as the last action.
-  TelemetryGeckoViewTesting::TestDispatchPersist();
-  TelemetryGeckoViewPersistence::DeInitPersistence();
-
-  CheckPersistenceFileExists(fileExists);
-  ASSERT_TRUE(fileExists)
-  << "The persisted measurements must exist on the disk";
-
-  // Clear the in-memory scalars again. They will be restored from the disk.
-  Unused << mTelemetry->ClearScalars();
-
-  // Load the persisted file again.
-  TelemetryGeckoViewPersistence::InitPersistence();
-  TelemetryGeckoViewPersistence::DeInitPersistence();
-
-  // Get a snapshot of the keyed and plain scalars.
-  JS::RootedValue scalarsSnapshot(cx.GetJSContext());
-  JS::RootedValue keyedScalarsSnapshot(cx.GetJSContext());
-  GetScalarsSnapshot(false, cx.GetJSContext(), &scalarsSnapshot);
-  GetScalarsSnapshot(true, cx.GetJSContext(), &keyedScalarsSnapshot);
-
-  // Verify that the scalars were correctly persisted and restored.
-  CheckUintScalar("telemetry.test.all_processes_uint", cx.GetJSContext(),
-                  scalarsSnapshot, kExpectedUintValue);
-  CheckKeyedUintScalar("telemetry.test.keyed_unsigned_int", "gv_key",
-                       cx.GetJSContext(), keyedScalarsSnapshot,
-                       kExpectedKeyedUintValue);
-
-  // Cleanup/remove the files.
-  RemovePersistenceFile();
-}
-
-/**
- * Test that we can correctly persist the histogram data.
- */
-TEST_F(TelemetryGeckoViewFixture, PersistHistograms) {
-  AutoJSContextWithGlobal cx(mCleanGlobal);
-
-  // Clear the histogram data.
-  GetAndClearHistogram(cx.GetJSContext(), mTelemetry,
-                       NS_LITERAL_CSTRING("TELEMETRY_TEST_MULTIPRODUCT"),
-                       false /* is_keyed */);
-  GetAndClearHistogram(cx.GetJSContext(), mTelemetry,
-                       NS_LITERAL_CSTRING("TELEMETRY_TEST_KEYED_COUNT"),
-                       true /* is_keyed */);
-
-  bool fileExists = false;
-  CheckPersistenceFileExists(fileExists);
-  ASSERT_FALSE(fileExists)
-  << "No persisted measurements must exist on the disk";
-
-  RefPtr<DataLoadedObserver> loadingFinished = new DataLoadedObserver();
-
-  // Init the persistence: this will trigger the measurements to be written
-  // to disk off-the-main thread.
-  TelemetryGeckoViewPersistence::InitPersistence();
-  loadingFinished->WaitForNotification();
-
-  // Set some histograms: we can only test the parent process as we don't
-  // support other processes in gtests.
-  const uint32_t kExpectedUintValue = 37;
-  const nsTArray<uint32_t> keyedSamples({5, 10, 15});
-  const uint32_t kExpectedKeyedSum = 5 + 10 + 15;
-  Telemetry::Accumulate(Telemetry::TELEMETRY_TEST_MULTIPRODUCT,
-                        kExpectedUintValue);
-  Telemetry::Accumulate(Telemetry::TELEMETRY_TEST_KEYED_COUNT,
-                        NS_LITERAL_CSTRING("gv_key"), keyedSamples);
-
-  // Dispatch the persisting task: we don't wait for the timer to expire
-  // as we need a reliable and reproducible way to kick off this. We ensure
-  // that the task runs by shutting down the persistence: this shuts down the
-  // thread which executes the task as the last action.
-  TelemetryGeckoViewTesting::TestDispatchPersist();
-  TelemetryGeckoViewPersistence::DeInitPersistence();
-
-  CheckPersistenceFileExists(fileExists);
-  ASSERT_TRUE(fileExists)
-  << "The persisted measurements must exist on the disk";
-
-  // Clear the in-memory histograms again. They will be restored from the disk.
-  GetAndClearHistogram(cx.GetJSContext(), mTelemetry,
-                       NS_LITERAL_CSTRING("TELEMETRY_TEST_MULTIPRODUCT"),
-                       false /* is_keyed */);
-  GetAndClearHistogram(cx.GetJSContext(), mTelemetry,
-                       NS_LITERAL_CSTRING("TELEMETRY_TEST_KEYED_COUNT"),
-                       true /* is_keyed */);
-
-  // Load the persisted file again.
-  TelemetryGeckoViewPersistence::InitPersistence();
-  TelemetryGeckoViewPersistence::DeInitPersistence();
-
-  // Get a snapshot of the keyed and plain histograms.
-  JS::RootedValue snapshot(cx.GetJSContext());
-  JS::RootedValue keyedSnapshot(cx.GetJSContext());
-  GetSnapshots(cx.GetJSContext(), mTelemetry, "TELEMETRY_TEST_MULTIPRODUCT",
-               &snapshot, false /* is_keyed */);
-  GetSnapshots(cx.GetJSContext(), mTelemetry, "TELEMETRY_TEST_KEYED_COUNT",
-               &keyedSnapshot, true /* is_keyed */);
-
-  // Validate the loaded histogram data.
-  JS::RootedValue histogram(cx.GetJSContext());
-  GetProperty(cx.GetJSContext(), "TELEMETRY_TEST_MULTIPRODUCT", snapshot,
-              &histogram);
-
-  // Get "sum" property from histogram
-  JS::RootedValue sum(cx.GetJSContext());
-  GetProperty(cx.GetJSContext(), "sum", histogram, &sum);
-
-  // Check that the "sum" stored in the histogram matches with |kExpectedValue|
-  uint32_t uSum = 0;
-  JS::ToUint32(cx.GetJSContext(), sum, &uSum);
-  ASSERT_EQ(uSum, kExpectedUintValue)
-      << "The histogram is not returning the expected value";
-
-  // Validate the keyed histogram data.
-  GetProperty(cx.GetJSContext(), "TELEMETRY_TEST_KEYED_COUNT", keyedSnapshot,
-              &histogram);
-
-  // Get "testkey" property from histogram and check that it stores the correct
-  // data.
-  JS::RootedValue expectedKeyData(cx.GetJSContext());
-  GetProperty(cx.GetJSContext(), "gv_key", histogram, &expectedKeyData);
-  ASSERT_FALSE(expectedKeyData.isUndefined())
-  << "Cannot find the expected key in the keyed histogram data";
-  GetProperty(cx.GetJSContext(), "sum", expectedKeyData, &sum);
-  JS::ToUint32(cx.GetJSContext(), sum, &uSum);
-  ASSERT_EQ(uSum, kExpectedKeyedSum)
-      << "The histogram is not returning the expected sum for 'gv_key'";
-
-  // Cleanup/remove the files.
-  RemovePersistenceFile();
-}
-
-TEST_F(TelemetryGeckoViewFixture, EmptyPendingOperations) {
-  AutoJSContextWithGlobal cx(mCleanGlobal);
-
-  Unused << mTelemetry->ClearScalars();
-
-  // Force loading mode
-  TelemetryScalar::DeserializationStarted();
-
-  // Do nothing explicitely
-
-  // Force pending operations to be applied and end load mode.
-  // It should not crash and don't change any scalars.
-  TelemetryScalar::ApplyPendingOperations();
-
-  // Check that the snapshot is empty
-  JS::RootedValue scalarsSnapshot(cx.GetJSContext());
-  GetScalarsSnapshot(false, cx.GetJSContext(), &scalarsSnapshot);
-
-  ASSERT_TRUE(scalarsSnapshot.isUndefined())
-  << "Scalars snapshot should not contain any data.";
-}
-
-TEST_F(TelemetryGeckoViewFixture, SimpleAppendOperation) {
-  AutoJSContextWithGlobal cx(mCleanGlobal);
-
-  Unused << mTelemetry->ClearScalars();
-
-  // Set an initial value, so we can test that it is not overwritten.
-  uint32_t initialValue = 1;
-  Telemetry::ScalarSet(Telemetry::ScalarID::TELEMETRY_TEST_UNSIGNED_INT_KIND,
-                       initialValue);
-
-  // Force loading mode
-  TelemetryScalar::DeserializationStarted();
-
-  // Add to a scalar
-  uint32_t value = 37;
-  Telemetry::ScalarAdd(Telemetry::ScalarID::TELEMETRY_TEST_UNSIGNED_INT_KIND,
-                       value);
-
-  // Verify that this was not yet applied.
-  JS::RootedValue scalarsSnapshot(cx.GetJSContext());
-  GetScalarsSnapshot(false, cx.GetJSContext(), &scalarsSnapshot);
-
-  CheckUintScalar("telemetry.test.unsigned_int_kind", cx.GetJSContext(),
-                  scalarsSnapshot, initialValue);
-
-  // Force pending operations to be applied and end load mode
-  TelemetryScalar::ApplyPendingOperations();
-
-  // Verify recorded operations are applied
-  GetScalarsSnapshot(false, cx.GetJSContext(), &scalarsSnapshot);
-  CheckUintScalar("telemetry.test.unsigned_int_kind", cx.GetJSContext(),
-                  scalarsSnapshot, initialValue + value);
-}
-
-TEST_F(TelemetryGeckoViewFixture, ApplyPendingOperationsAfterLoad) {
-  AutoJSContextWithGlobal cx(mCleanGlobal);
-
-  Unused << mTelemetry->ClearScalars();
-
-  const char persistedData[] = R"({
- "scalars": {
-  "parent": {
-   "telemetry.test.unsigned_int_kind": 14
-  }
- }
-})";
-
-  // Force loading mode
-  TelemetryScalar::DeserializationStarted();
-
-  // Add to a scalar, this should be recorded
-  uint32_t addValue = 10;
-  Telemetry::ScalarAdd(Telemetry::ScalarID::TELEMETRY_TEST_UNSIGNED_INT_KIND,
-                       addValue);
-
-  // Load persistence file
-  RefPtr<DataLoadedObserver> loadingFinished = new DataLoadedObserver();
-  WritePersistenceFile(nsDependentCString(persistedData));
-  TelemetryGeckoViewPersistence::InitPersistence();
-  loadingFinished->WaitForNotification();
-
-  // At this point all pending operations should have been applied.
-
-  // Increment again, now directly applied
-  uint32_t val = 1;
-  Telemetry::ScalarAdd(Telemetry::ScalarID::TELEMETRY_TEST_UNSIGNED_INT_KIND,
-                       val);
-
-  JS::RootedValue scalarsSnapshot(cx.GetJSContext());
-  GetScalarsSnapshot(false, cx.GetJSContext(), &scalarsSnapshot);
-
-  uint32_t expectedValue = 25;
-  CheckUintScalar("telemetry.test.unsigned_int_kind", cx.GetJSContext(),
-                  scalarsSnapshot, expectedValue);
-}
-
-TEST_F(TelemetryGeckoViewFixture, MultipleAppendOperations) {
-  AutoJSContextWithGlobal cx(mCleanGlobal);
-
-  Unused << mTelemetry->ClearScalars();
-
-  // Force loading mode
-  TelemetryScalar::DeserializationStarted();
-
-  // Modify all kinds of scalars
-  uint32_t startValue = 35;
-  uint32_t expectedValue = 40;
-  Telemetry::ScalarSet(Telemetry::ScalarID::TELEMETRY_TEST_UNSIGNED_INT_KIND,
-                       startValue);
-  Telemetry::ScalarSetMaximum(
-      Telemetry::ScalarID::TELEMETRY_TEST_UNSIGNED_INT_KIND, startValue + 2);
-  Telemetry::ScalarAdd(Telemetry::ScalarID::TELEMETRY_TEST_UNSIGNED_INT_KIND,
-                       3);
-
-  Telemetry::ScalarSet(Telemetry::ScalarID::TELEMETRY_TEST_BOOLEAN_KIND, true);
-  Telemetry::ScalarSet(Telemetry::ScalarID::TELEMETRY_TEST_STRING_KIND,
-                       NS_LITERAL_STRING("Star Wars VI"));
-
-  // Modify all kinds of keyed scalars
-  Telemetry::ScalarSet(Telemetry::ScalarID::TELEMETRY_TEST_KEYED_UNSIGNED_INT,
-                       NS_LITERAL_STRING("chewbacca"), startValue);
-  Telemetry::ScalarSetMaximum(
-      Telemetry::ScalarID::TELEMETRY_TEST_KEYED_UNSIGNED_INT,
-      NS_LITERAL_STRING("chewbacca"), startValue + 2);
-  Telemetry::ScalarAdd(Telemetry::ScalarID::TELEMETRY_TEST_KEYED_UNSIGNED_INT,
-                       NS_LITERAL_STRING("chewbacca"), 3);
-
-  Telemetry::ScalarSet(Telemetry::ScalarID::TELEMETRY_TEST_KEYED_BOOLEAN_KIND,
-                       NS_LITERAL_STRING("chewbacca"), true);
-
-  // Force pending operations to be applied and end load mode
-  TelemetryScalar::ApplyPendingOperations();
-
-  JS::RootedValue scalarsSnapshot(cx.GetJSContext());
-  JS::RootedValue keyedScalarsSnapshot(cx.GetJSContext());
-  GetScalarsSnapshot(false, cx.GetJSContext(), &scalarsSnapshot);
-  GetScalarsSnapshot(true, cx.GetJSContext(), &keyedScalarsSnapshot);
-
-  CheckUintScalar("telemetry.test.unsigned_int_kind", cx.GetJSContext(),
-                  scalarsSnapshot, expectedValue);
-  CheckBoolScalar("telemetry.test.boolean_kind", cx.GetJSContext(),
-                  scalarsSnapshot, true);
-  CheckStringScalar("telemetry.test.string_kind", cx.GetJSContext(),
-                    scalarsSnapshot, "Star Wars VI");
-
-  CheckKeyedUintScalar("telemetry.test.keyed_unsigned_int", "chewbacca",
-                       cx.GetJSContext(), keyedScalarsSnapshot, expectedValue);
-  CheckKeyedBoolScalar("telemetry.test.keyed_boolean_kind", "chewbacca",
-                       cx.GetJSContext(), keyedScalarsSnapshot, true);
-}
--- a/toolkit/components/telemetry/geckoview/gtest/moz.build
+++ b/toolkit/components/telemetry/geckoview/gtest/moz.build
@@ -9,22 +9,16 @@ Library('telemetrygeckoviewtest')
 LOCAL_INCLUDES += [
     '../',
     '../..',
     '../../..',
     '/toolkit/components/telemetry/tests/gtest',
     '/xpcom/io',
 ]
 
-DEFINES['MOZ_TELEMETRY_GECKOVIEW'] = True
-
-UNIFIED_SOURCES = [
-    'TestGeckoView.cpp',
-]
-
 # GeckoView Streaming Telemetry is only available on Android.
 if CONFIG['MOZ_WIDGET_TOOLKIT'] == 'android':
   UNIFIED_SOURCES += [
     'TestGeckoViewStreaming.cpp',
   ]
 
 # We need the following line otherwise including
 # "TelemetryHistogram.h" in tests will fail due to
deleted file mode 100644
--- a/toolkit/components/telemetry/geckoview/nsITelemetryGeckoViewTesting.idl
+++ /dev/null
@@ -1,44 +0,0 @@
-/* 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/. */
-
-#include "nsISupports.idl"
-
-/**
- * This is an internal interface used only for testing purposes.
- *
- * THIS IS NOT AN API TO BE USED BY EXTENSIONS! ONLY USED BY MOZILLA TESTS.
- */
-[scriptable, builtinclass, uuid(019feb07-e5dd-48e6-aa59-fc98bcb65e7f)]
-interface nsITelemetryGeckoViewTesting : nsISupports
-{
-  /**
-   * The following methods map to the functions with the
-   * same name from TelemetryGeckoViewPersistence.cpp.
-   * Even though [implicit_jscontext] it's not needed on the methods,
-   * it's there to make it harder to call them from C++: this IDL is only
-   * meant to be used in xpcshell tests (JS).
-   */
-  [implicit_jscontext]
-  void initPersistence();
-  [implicit_jscontext]
-  void deInitPersistence();
-  [implicit_jscontext]
-  void clearPersistenceData();
-
-  /**
-   * Enqueues a persist action into the Telemetry persistence thread:
-   * measurements might be written to the disk after it returns.
-   */
-  [implicit_jscontext]
-  void forcePersist();
-
-  /**
-   * The following method maps to the function with the same name from TelemetryScalar.cpp.
-   *
-   * It marks deserialization as in progress.
-   * After this, all scalar operations are recorded into the pending operations list.
-   */
-  [implicit_jscontext]
-  void deserializationStarted();
-};
--- a/toolkit/components/telemetry/moz.build
+++ b/toolkit/components/telemetry/moz.build
@@ -23,18 +23,18 @@ SPHINX_TREES['/toolkit/components/teleme
 
 with Files('docs/**'):
     SCHEDULES.exclusive = ['docs']
 
 if CONFIG['CC_TYPE'] in ('clang', 'gcc'):
     CXXFLAGS += ['-Wno-error=shadow']
 
 if CONFIG['ENABLE_TESTS']:
-    # We need to use a separate directory for GeckoView gtests. See
-    # the comment below near MOZ_TELEMETRY_GECKOVIEW.
+    # We used to need GeckoView tests as a separate directory. This
+    # is no longer true and we could probably move it to tests/gtest.
     DIRS += [
         'geckoview/gtest',
         'tests/gtest'
     ]
 
 TEST_DIRS += ['tests']
 
 XPCSHELL_TESTS_MANIFESTS += ['tests/unit/xpcshell.ini']
@@ -70,17 +70,16 @@ SOURCES += [
     'core/Stopwatch.cpp',
     'core/Telemetry.cpp',
     'core/TelemetryCommon.cpp',
     'core/TelemetryEvent.cpp',
     'core/TelemetryHistogram.cpp',
     'core/TelemetryOrigin.cpp',
     'core/TelemetryScalar.cpp',
     'geckoview/streaming/GeckoViewStreamingTelemetry.cpp',
-    'geckoview/TelemetryGeckoViewPersistence.cpp',
     'other/CombinedStacks.cpp',
     'other/ProcessedStack.cpp',
     'other/TelemetryIOInterposeObserver.cpp',
 ]
 
 if CONFIG['OS_ARCH'] == 'WINNT':
     SOURCES += [
         'other/UntrustedModules.cpp',
@@ -224,36 +223,10 @@ GeneratedFile('TelemetryProcessData.h',
 # While this currently only applies to Android, in the medium-term it
 # is going to generate code for Firefox as well (project FOG).
 # Prior art for this was in bug 1063728, within SpiderMonkey tests.
 GeneratedFile(
     'glean_checks',
     script='build_scripts/run_glean_parser.py',
     inputs=['geckoview/streaming/metrics.yaml'])
 
-# Add support for GeckoView: please note that building GeckoView
-# implies having an Android build. The packaging step decides
-# which files to include. As a consequence, we can simply only
-# include the GeckoView files on all Android builds.
-if CONFIG['MOZ_WIDGET_TOOLKIT'] == 'android':
-    # Introduce this define to conditionally enable Telemetry GV code in the various
-    # C++ modules. We need this trick in order to run gtest coverage on Treeherder
-    # on platforms other than Android, since gtests on Android are not supported
-    # yet (see bug 1318091).
-    DEFINES['MOZ_TELEMETRY_GECKOVIEW'] = True
-
-    EXTRA_JS_MODULES += [
-        'geckoview/GeckoViewTelemetryController.jsm',
-    ]
-
-# Include the GeckoView testing IDL if we're building tests
-# as well. This will be used in xpcshell tests.
-if CONFIG['ENABLE_TESTS']:
-    XPIDL_SOURCES += [
-        'geckoview/nsITelemetryGeckoViewTesting.idl'
-    ]
-
-    SOURCES += [
-        'geckoview/TelemetryGeckoViewTesting.cpp'
-    ]
-
 with Files('**'):
     BUG_COMPONENT = ('Toolkit', 'Telemetry')
--- a/toolkit/components/telemetry/tests/unit/head.js
+++ b/toolkit/components/telemetry/tests/unit/head.js
@@ -521,19 +521,16 @@ if (runningInParent) {
   Services.prefs.setBoolPref(
     TelemetryUtils.Preferences.HealthPingEnabled,
     false
   );
 
   // Speed up child process accumulations
   Services.prefs.setIntPref(TelemetryUtils.Preferences.IPCBatchTimeout, 10);
 
-  // Ensure we're not in a GeckoView-like environment by default
-  Services.prefs.setBoolPref("toolkit.telemetry.isGeckoViewMode", false);
-
   // Make sure ecosystem telemetry is disabled, no matter which build
   // Individual tests will enable it when appropriate
   Services.prefs.setBoolPref(
     TelemetryUtils.Preferences.EcosystemTelemetryEnabled,
     false
   );
 
   // Non-unified Telemetry (e.g. Fennec on Android) needs the preference to be set
deleted file mode 100644
--- a/toolkit/components/telemetry/tests/unit/head_GeckoView.js
+++ /dev/null
@@ -1,93 +0,0 @@
-/* Any copyright is dedicated to the Public Domain.
-   http://creativecommons.org/publicdomain/zero/1.0/
-*/
-"use strict";
-
-ChromeUtils.import("resource://gre/modules/PromiseUtils.jsm", this);
-ChromeUtils.import("resource://gre/modules/Services.jsm", this);
-ChromeUtils.import("resource://gre/modules/TelemetryUtils.jsm", this);
-ChromeUtils.import("resource://testing-common/ContentTaskUtils.jsm", this);
-
-const Telemetry = Services.telemetry;
-const TelemetryGeckoView = Cc[
-  "@mozilla.org/telemetry/geckoview-testing;1"
-].createInstance(Ci.nsITelemetryGeckoViewTesting);
-
-/**
- * Run a file in the content process.
- * @param aFileName - The file to execute in the content process.
- * @return {Promise} A promise resolved after the execution in the other process
- *         finishes.
- */
-async function run_in_child(aFileName) {
-  const PREF_GECKOVIEW_MODE = "toolkit.telemetry.isGeckoViewMode";
-  // We don't ship GeckoViewTelemetryController.jsm outside of Android. If
-  // |toolkit.telemetry.isGeckoViewMode| is true, this makes Gecko crash on
-  // other platforms because ContentProcessSingleton.js requires it. Work
-  // around this by temporarily setting the pref to false.
-  const currentValue = Services.prefs.getBoolPref(PREF_GECKOVIEW_MODE, false);
-  Services.prefs.setBoolPref(PREF_GECKOVIEW_MODE, false);
-  await run_test_in_child(aFileName);
-  Services.prefs.setBoolPref(PREF_GECKOVIEW_MODE, currentValue);
-}
-
-/**
- * Builds a promise to wait for the GeckoView data loading to finish.
- * @return {Promise} A promise resolved when the data loading finishes.
- */
-function waitGeckoViewLoadComplete() {
-  return new Promise(resolve => {
-    Services.obs.addObserver(function observe() {
-      Services.obs.removeObserver(
-        observe,
-        "internal-telemetry-geckoview-load-complete"
-      );
-      resolve();
-    }, "internal-telemetry-geckoview-load-complete");
-  });
-}
-
-/**
- * This function waits until the desired histogram is reported into the
- * snapshot of the relevant process.
- * @param aHistogramName - The name of the histogram to look for.
- * @param aProcessName - The name of the process to look in.
- * @param aKeyed - Whether or not to look in keyed snapshots.
- */
-async function waitForHistogramSnapshotData(
-  aHistogramName,
-  aProcessName,
-  aKeyed
-) {
-  await ContentTaskUtils.waitForCondition(() => {
-    const data = aKeyed
-      ? Telemetry.getSnapshotForKeyedHistograms("main", false)
-      : Telemetry.getSnapshotForHistograms("main", false);
-
-    return aProcessName in data && aHistogramName in data[aProcessName];
-  });
-}
-
-/**
- * This function waits until the desired scalar is reported into the
- * snapshot of the relevant process.
- * @param aScalarName - The name of the scalar to look for.
- * @param aProcessName - The name of the process to look in.
- * @param aKeyed - Whether or not to look in keyed snapshots.
- */
-async function waitForScalarSnapshotData(aScalarName, aProcessName, aKeyed) {
-  await ContentTaskUtils.waitForCondition(() => {
-    const data = aKeyed
-      ? Telemetry.getSnapshotForKeyedScalars("main", false)
-      : Telemetry.getSnapshotForScalars("main", false);
-
-    return aProcessName in data && aScalarName in data[aProcessName];
-  });
-}
-
-if (runningInParent) {
-  Services.prefs.setBoolPref(
-    TelemetryUtils.Preferences.OverridePreRelease,
-    true
-  );
-}
deleted file mode 100644
--- a/toolkit/components/telemetry/tests/unit/test_GeckoView.js
+++ /dev/null
@@ -1,145 +0,0 @@
-/* Any copyright is dedicated to the Public Domain.
-   http://creativecommons.org/publicdomain/zero/1.0/
-*/
-"use strict";
-
-ChromeUtils.import("resource://gre/modules/PromiseUtils.jsm", this);
-ChromeUtils.import("resource://gre/modules/Services.jsm", this);
-ChromeUtils.import("resource://testing-common/ContentTaskUtils.jsm", this);
-
-add_task(async function setup() {
-  // Init the profile.
-  let profileDir = do_get_profile(true);
-
-  // Set geckoview mode.
-  Services.prefs.setBoolPref("toolkit.telemetry.isGeckoViewMode", true);
-
-  // Set the ANDROID_DATA_DIR to the profile dir.
-  let env = Cc["@mozilla.org/process/environment;1"].getService(
-    Ci.nsIEnvironment
-  );
-  env.set("MOZ_ANDROID_DATA_DIR", profileDir.path);
-});
-
-add_task(async function test_persistContentHistograms() {
-  // Get and clear the histograms.
-  let plainHist = Telemetry.getHistogramById("TELEMETRY_TEST_MULTIPRODUCT");
-  plainHist.clear();
-  let keyedHist = Telemetry.getKeyedHistogramById("TELEMETRY_TEST_KEYED_COUNT");
-  keyedHist.clear();
-
-  TelemetryGeckoView.initPersistence();
-
-  // Set the histograms in parent.
-  plainHist.add(37);
-  keyedHist.add("parent-test-key", 73);
-
-  // Set content histograms and wait for the execution in the other
-  // process to finish.
-  await run_in_child("test_GeckoView_content_histograms.js");
-
-  // Wait for the data to be collected by the parent process.
-  await waitForHistogramSnapshotData(
-    "TELEMETRY_TEST_MULTIPRODUCT",
-    "content",
-    false /* aKeyed */
-  );
-  await waitForHistogramSnapshotData(
-    "TELEMETRY_TEST_KEYED_COUNT",
-    "content",
-    true /* aKeyed */
-  );
-
-  // Force persisting the measurements to file.
-  TelemetryGeckoView.forcePersist();
-  TelemetryGeckoView.deInitPersistence();
-
-  // Clear the histograms for all processes.
-  Telemetry.getSnapshotForHistograms("main", true /* clear */);
-  Telemetry.getSnapshotForKeyedHistograms("main", true /* clear */);
-
-  // Start the persistence system again, to unpersist the data.
-  let loadPromise = waitGeckoViewLoadComplete();
-  TelemetryGeckoView.initPersistence();
-  // Wait for the load to finish.
-  await loadPromise;
-
-  // Validate the snapshot data.
-  const snapshot = Telemetry.getSnapshotForHistograms(
-    "main",
-    false /* clear */
-  );
-  Assert.ok(
-    "parent" in snapshot,
-    "The snapshot object must have a 'parent' entry."
-  );
-  Assert.ok(
-    "content" in snapshot,
-    "The snapshot object must have a 'content' entry."
-  );
-  Assert.ok(
-    "TELEMETRY_TEST_MULTIPRODUCT" in snapshot.parent,
-    "The TELEMETRY_TEST_MULTIPRODUCT histogram must exist in the parent section."
-  );
-  Assert.equal(
-    snapshot.parent.TELEMETRY_TEST_MULTIPRODUCT.sum,
-    37,
-    "The TELEMETRY_TEST_MULTIPRODUCT must have the expected value in the parent section."
-  );
-  Assert.ok(
-    "TELEMETRY_TEST_MULTIPRODUCT" in snapshot.content,
-    "The TELEMETRY_TEST_MULTIPRODUCT histogram must exist in the content section."
-  );
-  Assert.equal(
-    snapshot.content.TELEMETRY_TEST_MULTIPRODUCT.sum,
-    73,
-    "The TELEMETRY_TEST_MULTIPRODUCT must have the expected value in the content section."
-  );
-
-  const keyedSnapshot = Telemetry.getSnapshotForKeyedHistograms(
-    "main",
-    false /* clear */
-  );
-  Assert.ok(
-    "parent" in keyedSnapshot,
-    "The keyed snapshot object must have a 'parent' entry."
-  );
-  Assert.ok(
-    "content" in keyedSnapshot,
-    "The keyed snapshot object must have a 'content' entry."
-  );
-  const parentData = keyedSnapshot.parent;
-  Assert.ok(
-    "TELEMETRY_TEST_KEYED_COUNT" in parentData,
-    "The TELEMETRY_TEST_KEYED_COUNT histogram must exist in the parent section."
-  );
-  Assert.ok(
-    "parent-test-key" in parentData.TELEMETRY_TEST_KEYED_COUNT,
-    "The histogram in the parent process should have the expected key."
-  );
-  Assert.equal(
-    parentData.TELEMETRY_TEST_KEYED_COUNT["parent-test-key"].sum,
-    73,
-    "The TELEMETRY_TEST_KEYED_COUNT must have the expected value in the parent section."
-  );
-  const contentData = keyedSnapshot.content;
-  Assert.ok(
-    "TELEMETRY_TEST_KEYED_COUNT" in contentData,
-    "The TELEMETRY_TEST_KEYED_COUNT histogram must exist in the content section."
-  );
-  Assert.ok(
-    "content-test-key" in contentData.TELEMETRY_TEST_KEYED_COUNT,
-    "The histogram in the content process should have the expected key."
-  );
-  Assert.equal(
-    contentData.TELEMETRY_TEST_KEYED_COUNT["content-test-key"].sum,
-    37,
-    "The TELEMETRY_TEST_KEYED_COUNT must have the expected value in the content section."
-  );
-
-  TelemetryGeckoView.deInitPersistence();
-});
-
-add_task(async function cleanup() {
-  Services.prefs.clearUserPref("toolkit.telemetry.isGeckoViewMode");
-});
deleted file mode 100644
--- a/toolkit/components/telemetry/tests/unit/test_GeckoView_ScalarSemantics.js
+++ /dev/null
@@ -1,196 +0,0 @@
-/* Any copyright is dedicated to the Public Domain.
-   http://creativecommons.org/publicdomain/zero/1.0/
-*/
-"use strict";
-
-ChromeUtils.import("resource://gre/modules/PromiseUtils.jsm", this);
-ChromeUtils.import("resource://gre/modules/Services.jsm", this);
-ChromeUtils.import("resource://testing-common/ContentTaskUtils.jsm", this);
-
-const CONTENT_ONLY_UINT_SCALAR = "telemetry.test.content_only_uint";
-const ALL_PROCESSES_UINT_SCALAR = "telemetry.test.all_processes_uint";
-const DEFAULT_PRODUCTS_SCALAR = "telemetry.test.default_products";
-const CHILD_KEYED_UNSIGNED_INT = "telemetry.test.child_keyed_unsigned_int";
-
-add_task(async function setup() {
-  // Init the profile.
-  let profileDir = do_get_profile(true);
-
-  // Set geckoview mode.
-  Services.prefs.setBoolPref("toolkit.telemetry.isGeckoViewMode", true);
-
-  // Set the ANDROID_DATA_DIR to the profile dir.
-  let env = Cc["@mozilla.org/process/environment;1"].getService(
-    Ci.nsIEnvironment
-  );
-  env.set("MOZ_ANDROID_DATA_DIR", profileDir.path);
-});
-
-add_task(async function test_MultiprocessScalarSemantics() {
-  /**
-   * To mitigate races during deserialization of persisted data
-   * scalar operations will be recorded and applied after the deserialization is finished.
-   *
-   * This test ensures it works acording to the semantics and follows the documentation example:
-   *
-   *  * Scalar deserialization is started
-   *  * “test” scalar is incremented by “10” by the application -> The operation [test, add, 10] is recorded into the list.
-   *  * The state of the “test” scalar is loaded off the persistence file, and the value “14” is set.
-   *  * Deserialization is finished and the pending operations are applied.
-   *  * The “test” scalar is incremented by “10”, the value is now “24”
-   */
-
-  Telemetry.clearScalars();
-
-  let loadPromise = waitGeckoViewLoadComplete();
-  TelemetryGeckoView.initPersistence();
-  await loadPromise;
-
-  // Set something in the parent
-  Telemetry.scalarSet(ALL_PROCESSES_UINT_SCALAR, 34);
-
-  // Set scalars in the child process.
-  // The child will then wait for a signal to continue.
-  let child = run_in_child("test_GeckoView_content_scalars.js");
-
-  // Wait for the data to be collected by the parent process.
-  await waitForScalarSnapshotData(
-    ALL_PROCESSES_UINT_SCALAR,
-    "parent",
-    false /* aKeyed */
-  );
-  await waitForScalarSnapshotData(
-    CONTENT_ONLY_UINT_SCALAR,
-    "content",
-    false /* aKeyed */
-  );
-  await waitForScalarSnapshotData(
-    ALL_PROCESSES_UINT_SCALAR,
-    "content",
-    false /* aKeyed */
-  );
-  await waitForScalarSnapshotData(
-    CHILD_KEYED_UNSIGNED_INT,
-    "content",
-    true /* aKeyed */
-  );
-
-  let snapshot = Telemetry.getSnapshotForScalars("main", false /* clear */);
-  let keyedSnapshot = Telemetry.getSnapshotForKeyedScalars(
-    "main",
-    false /* clear */
-  );
-  Assert.equal(
-    snapshot.content[CONTENT_ONLY_UINT_SCALAR],
-    14,
-    `The ${CONTENT_ONLY_UINT_SCALAR} scalar must have the expected value in the content section.`
-  );
-  Assert.equal(
-    snapshot.content[ALL_PROCESSES_UINT_SCALAR],
-    24,
-    `The ${ALL_PROCESSES_UINT_SCALAR} scalar must have the expected value in the content section.`
-  );
-  Assert.equal(
-    snapshot.parent[ALL_PROCESSES_UINT_SCALAR],
-    34,
-    `The ${ALL_PROCESSES_UINT_SCALAR} scalar must have the expected value in the parent section.`
-  );
-  Assert.equal(
-    keyedSnapshot.content[CHILD_KEYED_UNSIGNED_INT].chewbacca,
-    44,
-    `The ${CHILD_KEYED_UNSIGNED_INT} keyed scalar must have the expected value in the content section.`
-  );
-
-  // Force persisting the measurements to file.
-  TelemetryGeckoView.forcePersist();
-  TelemetryGeckoView.deInitPersistence();
-
-  // Clear all data from memory.
-  Telemetry.clearScalars();
-
-  // Mark deserialization as in progress, following operations are recorded and not applied.
-  TelemetryGeckoView.deserializationStarted();
-
-  // Modify a scalar in the parent process.
-  Telemetry.scalarAdd(ALL_PROCESSES_UINT_SCALAR, 10);
-
-  // Let child know to progress and wait for it to finish.
-  do_send_remote_message("child-scalar-semantics");
-  await child;
-
-  // Start the persistence system again, to unpersist the data.
-  loadPromise = waitGeckoViewLoadComplete();
-  TelemetryGeckoView.initPersistence();
-  // Wait for the load to finish.
-  await loadPromise;
-
-  // Wait for the data to be collected by the parent process.
-  // We only wait for the new data, as the rest will be in there from the persistence load.
-  await waitForScalarSnapshotData(
-    DEFAULT_PRODUCTS_SCALAR,
-    "content",
-    false /* aKeyed */
-  );
-
-  // Validate the snapshot data.
-  snapshot = Telemetry.getSnapshotForScalars("main", false /* clear */);
-  keyedSnapshot = Telemetry.getSnapshotForKeyedScalars(
-    "main",
-    false /* clear */
-  );
-
-  Assert.ok(
-    "parent" in snapshot,
-    "The snapshot object must have a 'content' entry."
-  );
-  Assert.ok(
-    "content" in snapshot,
-    "The snapshot object must have a 'content' entry."
-  );
-  Assert.ok(
-    "content" in keyedSnapshot,
-    "The keyed snapshot object must have a 'content' entry."
-  );
-
-  Assert.ok(
-    ALL_PROCESSES_UINT_SCALAR in snapshot.parent,
-    `The ${ALL_PROCESSES_UINT_SCALAR} scalar must exist in the parent section.`
-  );
-  Assert.ok(
-    CONTENT_ONLY_UINT_SCALAR in snapshot.content,
-    `The ${CONTENT_ONLY_UINT_SCALAR} scalar must exist in the content section.`
-  );
-  Assert.ok(
-    ALL_PROCESSES_UINT_SCALAR in snapshot.content,
-    `The ${ALL_PROCESSES_UINT_SCALAR} scalar must exist in the content section.`
-  );
-
-  Assert.equal(
-    snapshot.content[CONTENT_ONLY_UINT_SCALAR],
-    24,
-    `The ${CONTENT_ONLY_UINT_SCALAR} must have the expected value in the content section.`
-  );
-  Assert.equal(
-    snapshot.content[ALL_PROCESSES_UINT_SCALAR],
-    34,
-    `The ${ALL_PROCESSES_UINT_SCALAR} must have the expected value in the content section.`
-  );
-
-  Assert.equal(
-    snapshot.parent[ALL_PROCESSES_UINT_SCALAR],
-    44,
-    `The ${ALL_PROCESSES_UINT_SCALAR} must have the expected value in the parent section.`
-  );
-
-  Assert.equal(
-    keyedSnapshot.content[CHILD_KEYED_UNSIGNED_INT].chewbacca,
-    54,
-    `The ${CHILD_KEYED_UNSIGNED_INT} keyed scalar must have the expected value in the content section.`
-  );
-
-  TelemetryGeckoView.deInitPersistence();
-});
-
-add_task(async function cleanup() {
-  Services.prefs.clearUserPref("toolkit.telemetry.isGeckoViewMode");
-});
deleted file mode 100644
--- a/toolkit/components/telemetry/tests/unit/test_GeckoView_content_histograms.js
+++ /dev/null
@@ -1,17 +0,0 @@
-/* Any copyright is dedicated to the Public Domain.
-   http://creativecommons.org/publicdomain/zero/1.0/
-*/
-"use strict";
-
-ChromeUtils.import("resource://gre/modules/Services.jsm", this);
-
-// Note: this test file is only supposed to be run by
-// test_GeckoView.js. It assumes to be in the content
-// process.
-function run_test() {
-  // Get the histograms and set some values in the content process.
-  Services.telemetry.getHistogramById("TELEMETRY_TEST_MULTIPRODUCT").add(73);
-  Services.telemetry
-    .getKeyedHistogramById("TELEMETRY_TEST_KEYED_COUNT")
-    .add("content-test-key", 37);
-}
deleted file mode 100644
--- a/toolkit/components/telemetry/tests/unit/test_GeckoView_content_scalars.js
+++ /dev/null
@@ -1,30 +0,0 @@
-/* Any copyright is dedicated to the Public Domain.
-   http://creativecommons.org/publicdomain/zero/1.0/
-*/
-"use strict";
-
-ChromeUtils.import("resource://gre/modules/Services.jsm", this);
-
-const CONTENT_ONLY_UINT_SCALAR = "telemetry.test.content_only_uint";
-const ALL_PROCESSES_UINT_SCALAR = "telemetry.test.all_processes_uint";
-const DEFAULT_PRODUCTS_SCALAR = "telemetry.test.default_products";
-const CHILD_KEYED_UNSIGNED_INT = "telemetry.test.child_keyed_unsigned_int";
-
-// Note: this test file is only supposed to be run by
-// test_GeckoView_ScalarSemantics.js.
-// It assumes to be in the content process.
-add_task(async function run_child() {
-  // Set initial values in content process.
-  Services.telemetry.scalarSet(CONTENT_ONLY_UINT_SCALAR, 14);
-  Services.telemetry.scalarSet(ALL_PROCESSES_UINT_SCALAR, 24);
-  Services.telemetry.keyedScalarSet(CHILD_KEYED_UNSIGNED_INT, "chewbacca", 44);
-
-  // Wait for the parent to inform us to continue.
-  await do_await_remote_message("child-scalar-semantics");
-
-  // Modifications to probes will be recorded and applied later.
-  Services.telemetry.scalarAdd(CONTENT_ONLY_UINT_SCALAR, 10);
-  Services.telemetry.scalarAdd(ALL_PROCESSES_UINT_SCALAR, 10);
-  Services.telemetry.keyedScalarAdd(CHILD_KEYED_UNSIGNED_INT, "chewbacca", 10);
-  Services.telemetry.scalarSet(DEFAULT_PRODUCTS_SCALAR, 1);
-});
--- a/toolkit/components/telemetry/tests/unit/test_TelemetryScalars.js
+++ b/toolkit/components/telemetry/tests/unit/test_TelemetryScalars.js
@@ -1083,70 +1083,8 @@ add_task(
       "The desktop-only scalar must not be persisted."
     );
     Assert.ok(
       !(DESKTOP_ONLY_KEYED_SCALAR in keyedScalars),
       "The desktop-only keyed scalar must not be persisted."
     );
   }
 );
-
-add_task(
-  {
-    skip_if: () => !gIsAndroid,
-  },
-  async function test_geckoviewSpecificScalar() {
-    const DEFAULT_PRODUCT_SCALAR = "telemetry.test.default_products";
-    const DESKTOP_ONLY_SCALAR = "telemetry.test.desktop_only";
-    const MULTIPRODUCT_SCALAR = "telemetry.test.multiproduct";
-    const MOBILE_ONLY_SCALAR = "telemetry.test.mobile_only";
-    const GECKOVIEW_ONLY_SCALAR = "telemetry.test.geckoview_only";
-
-    Telemetry.clearScalars();
-
-    // Fake a geckoview-like environment
-    Services.prefs.setBoolPref("toolkit.telemetry.isGeckoViewMode", true);
-
-    // Try to set the mobile and multiproduct scalars
-    let expectedValue = 11714;
-    Telemetry.scalarAdd(GECKOVIEW_ONLY_SCALAR, expectedValue);
-    Telemetry.scalarAdd(MOBILE_ONLY_SCALAR, expectedValue);
-    Telemetry.scalarAdd(MULTIPRODUCT_SCALAR, expectedValue);
-    Telemetry.scalarSet(DEFAULT_PRODUCT_SCALAR, expectedValue);
-
-    // Try to set the desktop-only scalar to some value. We will not be recording the value,
-    // but we shouldn't throw.
-    Telemetry.scalarSet(DESKTOP_ONLY_SCALAR, 11715);
-    Telemetry.scalarSetMaximum(DESKTOP_ONLY_SCALAR, 11715);
-
-    // Get a snapshot of the scalars.
-    const scalars = TelemetryTestUtils.getProcessScalars("parent");
-
-    Assert.equal(
-      scalars[GECKOVIEW_ONLY_SCALAR],
-      expectedValue,
-      "The geckoview-only scalar must contain the right value"
-    );
-    Assert.equal(
-      scalars[MOBILE_ONLY_SCALAR],
-      expectedValue,
-      "The mobile-only scalar must contain the right value"
-    );
-    Assert.equal(
-      scalars[MULTIPRODUCT_SCALAR],
-      expectedValue,
-      "The multiproduct scalar must contain the right value"
-    );
-    Assert.equal(
-      scalars[DEFAULT_PRODUCT_SCALAR],
-      expectedValue,
-      "The default products scalar must contain the right value"
-    );
-
-    Assert.ok(
-      !(DESKTOP_ONLY_SCALAR in scalars),
-      "The desktop-only scalar must not be persisted."
-    );
-
-    // Reset to original environment
-    Services.prefs.clearUserPref("toolkit.telemetry.isGeckoViewMode");
-  }
-);
--- a/toolkit/components/telemetry/tests/unit/xpcshell.ini
+++ b/toolkit/components/telemetry/tests/unit/xpcshell.ini
@@ -19,26 +19,16 @@ support-files =
   testNoPDBAArch64.dll
   !/toolkit/mozapps/extensions/test/xpcshell/head_addons.js
 generated-files =
   dictionary.xpi
   system.xpi
   restartless.xpi
 
 [test_client_id.js]
-[test_GeckoView.js]
-skip-if = os == "android" # Disabled due to crashes (see bug 1331366)
-head = head_GeckoView.js
-support-files =
-  test_GeckoView_content_histograms.js
-[test_GeckoView_ScalarSemantics.js]
-skip-if = os == "android" # Disabled due to crashes (see bug 1331366)
-head = head_GeckoView.js
-support-files =
-  test_GeckoView_content_scalars.js
 [test_MigratePendingPings.js]
 [test_TelemetryHistograms.js]
 [test_SubsessionChaining.js]
 tags = addons
 [test_TelemetryEnvironment.js]
 skip-if = os == "android"
 tags = addons
 [test_PingAPI.js]