tor-browser

The Tor Browser
git clone https://git.dasho.dev/tor-browser.git
Log | Files | Refs | README | LICENSE

ContentBlockingPrefs.sys.mjs (20854B)


      1 /* This Source Code Form is subject to the terms of the Mozilla Public
      2 * License, v. 2.0. If a copy of the MPL was not distributed with this
      3 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
      4 
      5 const PREFS_CHANGING_CATEGORY = new Set([
      6  "network.cookie.cookieBehavior",
      7  "network.cookie.cookieBehavior.pbmode",
      8  "network.http.referer.disallowCrossSiteRelaxingDefault",
      9  "network.http.referer.disallowCrossSiteRelaxingDefault.top_navigation",
     10  "privacy.partition.network_state.ocsp_cache",
     11  "privacy.query_stripping.enabled",
     12  "privacy.query_stripping.enabled.pbmode",
     13  "privacy.fingerprintingProtection",
     14  "privacy.fingerprintingProtection.pbmode",
     15 ]);
     16 
     17 /**
     18 * @class ContentBlockingPrefs
     19 *
     20 * Manages how the content blocking and anti-tracking preferences relate to the
     21 * broad Tracking Protection categories (standard, strict and custom).
     22 *
     23 * @typedef {"standard"|"strict"|"custom"} CBCategory
     24 */
     25 export let ContentBlockingPrefs = {
     26  PREF_CB_CATEGORY: "browser.contentblocking.category",
     27  PREF_STRICT_DEF: "browser.contentblocking.features.strict",
     28  PREF_ALLOW_LIST_BASELINE:
     29    "privacy.trackingprotection.allow_list.baseline.enabled",
     30  PREF_ALLOW_LIST_CONVENIENCE:
     31    "privacy.trackingprotection.allow_list.convenience.enabled",
     32  PREF_LNA_ETP_ENABLED: "network.lna.etp.enabled",
     33 
     34  switchingCategory: false,
     35 
     36  /**
     37   * Apply a category preference rule to update preference expectations.   *
     38   *
     39   * @param {string} item - The rule to apply (e.g., "tp", "-fp", "lna")
     40   * @param {string} type - The category type ("strict", "standard")
     41   */
     42  // eslint-disable-next-line complexity
     43  applyCategoryPref(item, type) {
     44    switch (item) {
     45      case "tp":
     46        this.CATEGORY_PREFS[type]["privacy.trackingprotection.enabled"] = true;
     47        break;
     48      case "-tp":
     49        this.CATEGORY_PREFS[type]["privacy.trackingprotection.enabled"] = false;
     50        break;
     51      case "tpPrivate":
     52        this.CATEGORY_PREFS[type]["privacy.trackingprotection.pbmode.enabled"] =
     53          true;
     54        break;
     55      case "-tpPrivate":
     56        this.CATEGORY_PREFS[type]["privacy.trackingprotection.pbmode.enabled"] =
     57          false;
     58        break;
     59      case "fp":
     60        this.CATEGORY_PREFS[type][
     61          "privacy.trackingprotection.fingerprinting.enabled"
     62        ] = true;
     63        break;
     64      case "-fp":
     65        this.CATEGORY_PREFS[type][
     66          "privacy.trackingprotection.fingerprinting.enabled"
     67        ] = false;
     68        break;
     69      case "cryptoTP":
     70        this.CATEGORY_PREFS[type][
     71          "privacy.trackingprotection.cryptomining.enabled"
     72        ] = true;
     73        break;
     74      case "-cryptoTP":
     75        this.CATEGORY_PREFS[type][
     76          "privacy.trackingprotection.cryptomining.enabled"
     77        ] = false;
     78        break;
     79      case "stp":
     80        this.CATEGORY_PREFS[type][
     81          "privacy.trackingprotection.socialtracking.enabled"
     82        ] = true;
     83        break;
     84      case "-stp":
     85        this.CATEGORY_PREFS[type][
     86          "privacy.trackingprotection.socialtracking.enabled"
     87        ] = false;
     88        break;
     89      case "emailTP":
     90        this.CATEGORY_PREFS[type][
     91          "privacy.trackingprotection.emailtracking.enabled"
     92        ] = true;
     93        break;
     94      case "-emailTP":
     95        this.CATEGORY_PREFS[type][
     96          "privacy.trackingprotection.emailtracking.enabled"
     97        ] = false;
     98        break;
     99      case "emailTPPrivate":
    100        this.CATEGORY_PREFS[type][
    101          "privacy.trackingprotection.emailtracking.pbmode.enabled"
    102        ] = true;
    103        break;
    104      case "-emailTPPrivate":
    105        this.CATEGORY_PREFS[type][
    106          "privacy.trackingprotection.emailtracking.pbmode.enabled"
    107        ] = false;
    108        break;
    109      case "consentmanagerSkip":
    110        this.CATEGORY_PREFS[type][
    111          "privacy.trackingprotection.consentmanager.skip.enabled"
    112        ] = true;
    113        break;
    114      case "-consentmanagerSkip":
    115        this.CATEGORY_PREFS[type][
    116          "privacy.trackingprotection.consentmanager.skip.enabled"
    117        ] = false;
    118        break;
    119      case "consentmanagerSkipPrivate":
    120        this.CATEGORY_PREFS[type][
    121          "privacy.trackingprotection.consentmanager.skip.pbmode.enabled"
    122        ] = true;
    123        break;
    124      case "-consentmanagerSkipPrivate":
    125        this.CATEGORY_PREFS[type][
    126          "privacy.trackingprotection.consentmanager.skip.pbmode.enabled"
    127        ] = false;
    128        break;
    129      case "lvl2":
    130        this.CATEGORY_PREFS[type][
    131          "privacy.annotate_channels.strict_list.enabled"
    132        ] = true;
    133        break;
    134      case "-lvl2":
    135        this.CATEGORY_PREFS[type][
    136          "privacy.annotate_channels.strict_list.enabled"
    137        ] = false;
    138        break;
    139      case "rp":
    140        this.CATEGORY_PREFS[type][
    141          "network.http.referer.disallowCrossSiteRelaxingDefault"
    142        ] = true;
    143        break;
    144      case "-rp":
    145        this.CATEGORY_PREFS[type][
    146          "network.http.referer.disallowCrossSiteRelaxingDefault"
    147        ] = false;
    148        break;
    149      case "rpTop":
    150        this.CATEGORY_PREFS[type][
    151          "network.http.referer.disallowCrossSiteRelaxingDefault.top_navigation"
    152        ] = true;
    153        break;
    154      case "-rpTop":
    155        this.CATEGORY_PREFS[type][
    156          "network.http.referer.disallowCrossSiteRelaxingDefault.top_navigation"
    157        ] = false;
    158        break;
    159      case "ocsp":
    160        this.CATEGORY_PREFS[type][
    161          "privacy.partition.network_state.ocsp_cache"
    162        ] = true;
    163        break;
    164      case "-ocsp":
    165        this.CATEGORY_PREFS[type][
    166          "privacy.partition.network_state.ocsp_cache"
    167        ] = false;
    168        break;
    169      case "qps":
    170        this.CATEGORY_PREFS[type]["privacy.query_stripping.enabled"] = true;
    171        break;
    172      case "-qps":
    173        this.CATEGORY_PREFS[type]["privacy.query_stripping.enabled"] = false;
    174        break;
    175      case "qpsPBM":
    176        this.CATEGORY_PREFS[type]["privacy.query_stripping.enabled.pbmode"] =
    177          true;
    178        break;
    179      case "-qpsPBM":
    180        this.CATEGORY_PREFS[type]["privacy.query_stripping.enabled.pbmode"] =
    181          false;
    182        break;
    183      case "fpp":
    184        this.CATEGORY_PREFS[type]["privacy.fingerprintingProtection"] = true;
    185        break;
    186      case "-fpp":
    187        this.CATEGORY_PREFS[type]["privacy.fingerprintingProtection"] = false;
    188        break;
    189      case "fppPrivate":
    190        this.CATEGORY_PREFS[type]["privacy.fingerprintingProtection.pbmode"] =
    191          true;
    192        break;
    193      case "-fppPrivate":
    194        this.CATEGORY_PREFS[type]["privacy.fingerprintingProtection.pbmode"] =
    195          false;
    196        break;
    197      case "cookieBehavior0":
    198        this.CATEGORY_PREFS[type]["network.cookie.cookieBehavior"] =
    199          Ci.nsICookieService.BEHAVIOR_ACCEPT;
    200        break;
    201      case "cookieBehavior1":
    202        this.CATEGORY_PREFS[type]["network.cookie.cookieBehavior"] =
    203          Ci.nsICookieService.BEHAVIOR_REJECT_FOREIGN;
    204        break;
    205      case "cookieBehavior2":
    206        this.CATEGORY_PREFS[type]["network.cookie.cookieBehavior"] =
    207          Ci.nsICookieService.BEHAVIOR_REJECT;
    208        break;
    209      case "cookieBehavior3":
    210        this.CATEGORY_PREFS[type]["network.cookie.cookieBehavior"] =
    211          Ci.nsICookieService.BEHAVIOR_LIMIT_FOREIGN;
    212        break;
    213      case "cookieBehavior4":
    214        this.CATEGORY_PREFS[type]["network.cookie.cookieBehavior"] =
    215          Ci.nsICookieService.BEHAVIOR_REJECT_TRACKER;
    216        break;
    217      case "cookieBehavior5":
    218        this.CATEGORY_PREFS[type]["network.cookie.cookieBehavior"] =
    219          Ci.nsICookieService.BEHAVIOR_REJECT_TRACKER_AND_PARTITION_FOREIGN;
    220        break;
    221      case "cookieBehaviorPBM0":
    222        this.CATEGORY_PREFS[type]["network.cookie.cookieBehavior.pbmode"] =
    223          Ci.nsICookieService.BEHAVIOR_ACCEPT;
    224        break;
    225      case "cookieBehaviorPBM1":
    226        this.CATEGORY_PREFS[type]["network.cookie.cookieBehavior.pbmode"] =
    227          Ci.nsICookieService.BEHAVIOR_REJECT_FOREIGN;
    228        break;
    229      case "cookieBehaviorPBM2":
    230        this.CATEGORY_PREFS[type]["network.cookie.cookieBehavior.pbmode"] =
    231          Ci.nsICookieService.BEHAVIOR_REJECT;
    232        break;
    233      case "cookieBehaviorPBM3":
    234        this.CATEGORY_PREFS[type]["network.cookie.cookieBehavior.pbmode"] =
    235          Ci.nsICookieService.BEHAVIOR_LIMIT_FOREIGN;
    236        break;
    237      case "cookieBehaviorPBM4":
    238        this.CATEGORY_PREFS[type]["network.cookie.cookieBehavior.pbmode"] =
    239          Ci.nsICookieService.BEHAVIOR_REJECT_TRACKER;
    240        break;
    241      case "cookieBehaviorPBM5":
    242        this.CATEGORY_PREFS[type]["network.cookie.cookieBehavior.pbmode"] =
    243          Ci.nsICookieService.BEHAVIOR_REJECT_TRACKER_AND_PARTITION_FOREIGN;
    244        break;
    245      case "3pcd":
    246        this.CATEGORY_PREFS[type][
    247          "network.cookie.cookieBehavior.optInPartitioning"
    248        ] = true;
    249        break;
    250      case "-3pcd":
    251        this.CATEGORY_PREFS[type][
    252          "network.cookie.cookieBehavior.optInPartitioning"
    253        ] = false;
    254        break;
    255      case "btp":
    256        this.CATEGORY_PREFS[type]["privacy.bounceTrackingProtection.mode"] =
    257          Ci.nsIBounceTrackingProtection.MODE_ENABLED;
    258        break;
    259      case "-btp":
    260        // We currently consider MODE_ENABLED_DRY_RUN the "off" state. See
    261        // nsIBounceTrackingProtection.idl for details.
    262        this.CATEGORY_PREFS[type]["privacy.bounceTrackingProtection.mode"] =
    263          Ci.nsIBounceTrackingProtection.MODE_ENABLED_DRY_RUN;
    264        break;
    265      case "lna":
    266        // turn on LNA for etp strict only if network.lna.etp.enabled
    267        // network.lna.etp.enabled is controlled by nimbus
    268        if (Services.prefs.getBoolPref(this.PREF_LNA_ETP_ENABLED, false)) {
    269          this.CATEGORY_PREFS[type]["network.lna.blocking"] = true;
    270        }
    271        break;
    272      case "-lna":
    273        // currently LNA is only enabled with ETP strict mode with pref network.lna.etp.enabled
    274        if (Services.prefs.getBoolPref(this.PREF_LNA_ETP_ENABLED, false)) {
    275          this.CATEGORY_PREFS[type]["network.lna.blocking"] = false;
    276        }
    277        break;
    278      default:
    279        console.error(`Error: Unknown rule observed ${item}`);
    280    }
    281  },
    282 
    283  setPrefExpectations() {
    284    // The prefs inside CATEGORY_PREFS are initial values.
    285    // If the pref remains null, then it will expect the default value.
    286    // The "standard" category is defined as expecting default values of the
    287    // listed prefs. The "strict" category lists all prefs that will be set
    288    // according to the strict feature pref.
    289    this.CATEGORY_PREFS = {
    290      strict: {
    291        "network.cookie.cookieBehavior": null,
    292        "network.cookie.cookieBehavior.pbmode": null,
    293        "privacy.trackingprotection.pbmode.enabled": null,
    294        "privacy.trackingprotection.enabled": null,
    295        "privacy.trackingprotection.socialtracking.enabled": null,
    296        "privacy.trackingprotection.fingerprinting.enabled": null,
    297        "privacy.trackingprotection.cryptomining.enabled": null,
    298        "privacy.trackingprotection.emailtracking.enabled": null,
    299        "privacy.trackingprotection.emailtracking.pbmode.enabled": null,
    300        "privacy.trackingprotection.consentmanager.skip.enabled": null,
    301        "privacy.trackingprotection.consentmanager.skip.pbmode.enabled": null,
    302        "privacy.annotate_channels.strict_list.enabled": null,
    303        "network.http.referer.disallowCrossSiteRelaxingDefault": null,
    304        "network.http.referer.disallowCrossSiteRelaxingDefault.top_navigation":
    305          null,
    306        "privacy.partition.network_state.ocsp_cache": null,
    307        "privacy.query_stripping.enabled": null,
    308        "privacy.query_stripping.enabled.pbmode": null,
    309        "privacy.fingerprintingProtection": null,
    310        "privacy.fingerprintingProtection.pbmode": null,
    311        "network.cookie.cookieBehavior.optInPartitioning": null,
    312        "privacy.bounceTrackingProtection.mode": null,
    313        "network.lna.blocking": null,
    314        [this.PREF_ALLOW_LIST_BASELINE]: true,
    315        [this.PREF_ALLOW_LIST_CONVENIENCE]: false,
    316      },
    317      standard: {
    318        "network.cookie.cookieBehavior": null,
    319        "network.cookie.cookieBehavior.pbmode": null,
    320        "privacy.trackingprotection.pbmode.enabled": null,
    321        "privacy.trackingprotection.enabled": null,
    322        "privacy.trackingprotection.socialtracking.enabled": null,
    323        "privacy.trackingprotection.fingerprinting.enabled": null,
    324        "privacy.trackingprotection.cryptomining.enabled": null,
    325        "privacy.trackingprotection.emailtracking.enabled": null,
    326        "privacy.trackingprotection.emailtracking.pbmode.enabled": null,
    327        "privacy.trackingprotection.consentmanager.skip.enabled": null,
    328        "privacy.trackingprotection.consentmanager.skip.pbmode.enabled": null,
    329        "privacy.annotate_channels.strict_list.enabled": null,
    330        "network.http.referer.disallowCrossSiteRelaxingDefault": null,
    331        "network.http.referer.disallowCrossSiteRelaxingDefault.top_navigation":
    332          null,
    333        "privacy.partition.network_state.ocsp_cache": null,
    334        "privacy.query_stripping.enabled": null,
    335        "privacy.query_stripping.enabled.pbmode": null,
    336        "privacy.fingerprintingProtection": null,
    337        "privacy.fingerprintingProtection.pbmode": null,
    338        "network.cookie.cookieBehavior.optInPartitioning": null,
    339        "privacy.bounceTrackingProtection.mode": null,
    340        "network.lna.blocking": null,
    341        [this.PREF_ALLOW_LIST_BASELINE]: null,
    342        [this.PREF_ALLOW_LIST_CONVENIENCE]: null,
    343      },
    344    };
    345    let type = "strict";
    346    let rulesArray = Services.prefs
    347      .getStringPref(this.PREF_STRICT_DEF)
    348      .split(",");
    349    for (let item of rulesArray) {
    350      this.applyCategoryPref(item, type);
    351    }
    352  },
    353 
    354  /**
    355   * Checks if CB prefs match perfectly with one of our pre-defined categories.
    356   *
    357   * @param {CBCategory} category
    358   */
    359  prefsMatch(category) {
    360    // The category pref must be either unset, or match.
    361    if (
    362      Services.prefs.prefHasUserValue(this.PREF_CB_CATEGORY) &&
    363      Services.prefs.getStringPref(this.PREF_CB_CATEGORY) != category
    364    ) {
    365      return false;
    366    }
    367    for (let pref in this.CATEGORY_PREFS[category]) {
    368      let value = this.CATEGORY_PREFS[category][pref];
    369      // Ignore allow list prefs, since user is allowed to change them in strict mode.
    370      if (
    371        pref == this.PREF_ALLOW_LIST_BASELINE ||
    372        pref == this.PREF_ALLOW_LIST_CONVENIENCE
    373      ) {
    374        continue;
    375      }
    376      if (value == null) {
    377        if (Services.prefs.prefHasUserValue(pref)) {
    378          return false;
    379        }
    380      } else {
    381        let prefType = Services.prefs.getPrefType(pref);
    382        if (
    383          (prefType == Services.prefs.PREF_BOOL &&
    384            Services.prefs.getBoolPref(pref) != value) ||
    385          (prefType == Services.prefs.PREF_INT &&
    386            Services.prefs.getIntPref(pref) != value) ||
    387          (prefType == Services.prefs.PREF_STRING &&
    388            Services.prefs.getStringPref(pref) != value)
    389        ) {
    390          return false;
    391        }
    392      }
    393    }
    394    return true;
    395  },
    396 
    397  matchCBCategory() {
    398    if (this.switchingCategory) {
    399      return;
    400    }
    401    // If PREF_CB_CATEGORY is not set match users to a Content Blocking category. Check if prefs fit
    402    // perfectly into strict or standard, otherwise match with custom. If PREF_CB_CATEGORY has previously been set,
    403    // a change of one of these prefs necessarily puts us in "custom".
    404    if (this.prefsMatch("standard")) {
    405      Services.prefs.setStringPref(this.PREF_CB_CATEGORY, "standard");
    406    } else if (this.prefsMatch("strict")) {
    407      Services.prefs.setStringPref(this.PREF_CB_CATEGORY, "strict");
    408    } else {
    409      Services.prefs.setStringPref(this.PREF_CB_CATEGORY, "custom");
    410    }
    411 
    412    // If there is a custom policy which changes a related pref, then put the user in custom so
    413    // they still have access to other content blocking prefs, and to keep our default definitions
    414    // from changing.
    415    let policy = Services.policies.getActivePolicies();
    416    if (
    417      policy &&
    418      ((policy.EnableTrackingProtection &&
    419        !policy.EnableTrackingProtection.Category) ||
    420        policy.Cookies)
    421    ) {
    422      Services.prefs.setStringPref(this.PREF_CB_CATEGORY, "custom");
    423    }
    424  },
    425 
    426  updateCBCategory(preserveAllowListSettings = false) {
    427    if (
    428      this.switchingCategory ||
    429      !Services.prefs.prefHasUserValue(this.PREF_CB_CATEGORY)
    430    ) {
    431      return;
    432    }
    433    // Turn on switchingCategory flag, to ensure that when the individual prefs that change as a result
    434    // of the category change do not trigger yet another category change.
    435    this.switchingCategory = true;
    436    let value = Services.prefs.getStringPref(this.PREF_CB_CATEGORY);
    437    this.setPrefsToCategory(value, null, preserveAllowListSettings);
    438    this.switchingCategory = false;
    439  },
    440 
    441  /**
    442   * Sets all user-exposed content blocking preferences to values that match the selected category.
    443   *
    444   * @param {CBCategory} category
    445   * @param {boolean} lockPrefs - Whether to lock prefs after setting them
    446   * @param {boolean} preserveAllowListSettings - Whether to preserve existing allow list baseline and
    447   * convenience settings
    448   */
    449  setPrefsToCategory(category, lockPrefs, preserveAllowListSettings) {
    450    // Leave prefs as they were if we are switching to "custom" category.
    451    if (category == "custom") {
    452      return;
    453    }
    454 
    455    let prefBranch = lockPrefs
    456      ? Services.prefs.getDefaultBranch(null)
    457      : Services.prefs.getBranch(null);
    458 
    459    for (let pref in this.CATEGORY_PREFS[category]) {
    460      let value = this.CATEGORY_PREFS[category][pref];
    461      if (!Services.prefs.prefIsLocked(pref)) {
    462        if (value == null) {
    463          Services.prefs.clearUserPref(pref);
    464        } else {
    465          // On initialization, do not update "PREF_ALLOW_LIST_BASELINE" and "PREF_ALLOW_LIST_CONVENIENCE"
    466          // to make sure user's settings are preserved
    467          if (
    468            preserveAllowListSettings &&
    469            (pref == this.PREF_ALLOW_LIST_BASELINE ||
    470              pref == this.PREF_ALLOW_LIST_CONVENIENCE)
    471          ) {
    472            continue;
    473          }
    474          switch (Services.prefs.getPrefType(pref)) {
    475            case Services.prefs.PREF_BOOL:
    476              prefBranch.setBoolPref(pref, value);
    477              break;
    478            case Services.prefs.PREF_INT:
    479              prefBranch.setIntPref(pref, value);
    480              break;
    481            case Services.prefs.PREF_STRING:
    482              prefBranch.setStringPref(pref, value);
    483              break;
    484          }
    485          if (lockPrefs) {
    486            Services.prefs.lockPref(pref);
    487          }
    488        }
    489      }
    490    }
    491  },
    492 
    493  setPrefExpectationsAndUpdate(preserveAllowListSettings = false) {
    494    this.setPrefExpectations();
    495    this.updateCBCategory(preserveAllowListSettings);
    496  },
    497 
    498  observe(subject, topic, data) {
    499    if (topic != "nsPref:changed") {
    500      return;
    501    }
    502 
    503    // We need this early return to avoid updating the CB category prematurely. Specifically when
    504    // user changes the CB category, the observer for hasUserInteractedWithETPSettings is triggered
    505    // before the category is actually changed. If we do not return here, the category may be updated
    506    // incorrectly (for example, to custom when it should be strict).
    507    if (
    508      data ===
    509      "privacy.trackingprotection.allow_list.hasUserInteractedWithETPSettings"
    510    ) {
    511      return;
    512    }
    513 
    514    if (
    515      data.startsWith("privacy.trackingprotection") ||
    516      PREFS_CHANGING_CATEGORY.has(data)
    517    ) {
    518      this.matchCBCategory();
    519    }
    520 
    521    if (data.startsWith("privacy.trackingprotection")) {
    522      this.setPrefExpectations();
    523    } else if (data == this.PREF_CB_CATEGORY) {
    524      this.updateCBCategory();
    525    } else if (data == "browser.contentblocking.features.strict") {
    526      this.setPrefExpectationsAndUpdate();
    527    } else if (data == this.PREF_LNA_ETP_ENABLED) {
    528      // updates tagging of LNA restrictions with ETP strict mode
    529      this.setPrefExpectationsAndUpdate();
    530    }
    531  },
    532 
    533  init() {
    534    this.setPrefExpectationsAndUpdate(true);
    535    this.matchCBCategory();
    536 
    537    for (let prefix of PREF_PREFIXES_TO_OBSERVE) {
    538      Services.prefs.addObserver(prefix, this);
    539    }
    540  },
    541 
    542  uninit() {
    543    for (let prefix of PREF_PREFIXES_TO_OBSERVE) {
    544      Services.prefs.removeObserver(prefix, this);
    545    }
    546  },
    547 };
    548 
    549 const PREF_PREFIXES_TO_OBSERVE = new Set([
    550  "privacy.trackingprotection",
    551  "network.cookie.cookieBehavior",
    552  "network.http.referer.disallowCrossSiteRelaxingDefault",
    553  "privacy.partition.network_state.ocsp_cache",
    554  "privacy.query_stripping.enabled",
    555  "privacy.fingerprintingProtection",
    556  ContentBlockingPrefs.PREF_CB_CATEGORY,
    557  ContentBlockingPrefs.PREF_STRICT_DEF,
    558  ContentBlockingPrefs.PREF_LNA_ETP_ENABLED,
    559 ]);
    560 
    561 ContentBlockingPrefs.QueryInterface = ChromeUtils.generateQI([Ci.nsIObserver]);