diff options
Diffstat (limited to 'modules/libpref/test/unit_ipc')
-rw-r--r-- | modules/libpref/test/unit_ipc/test_existing_prefs.js | 22 | ||||
-rw-r--r-- | modules/libpref/test/unit_ipc/test_initial_prefs.js | 16 | ||||
-rw-r--r-- | modules/libpref/test/unit_ipc/test_large_pref.js | 105 | ||||
-rw-r--r-- | modules/libpref/test/unit_ipc/test_locked_prefs.js | 41 | ||||
-rw-r--r-- | modules/libpref/test/unit_ipc/test_observed_prefs.js | 14 | ||||
-rw-r--r-- | modules/libpref/test/unit_ipc/test_sharedMap.js | 364 | ||||
-rw-r--r-- | modules/libpref/test/unit_ipc/test_sharedMap_static_prefs.js | 80 | ||||
-rw-r--r-- | modules/libpref/test/unit_ipc/test_update_prefs.js | 36 | ||||
-rw-r--r-- | modules/libpref/test/unit_ipc/test_user_default_prefs.js | 73 | ||||
-rw-r--r-- | modules/libpref/test/unit_ipc/xpcshell.ini | 14 |
10 files changed, 765 insertions, 0 deletions
diff --git a/modules/libpref/test/unit_ipc/test_existing_prefs.js b/modules/libpref/test/unit_ipc/test_existing_prefs.js new file mode 100644 index 0000000000..78cfdcd151 --- /dev/null +++ b/modules/libpref/test/unit_ipc/test_existing_prefs.js @@ -0,0 +1,22 @@ +const { Services } = ChromeUtils.import("resource://gre/modules/Services.jsm"); + +function isParentProcess() { + let appInfo = Cc["@mozilla.org/xre/app-info;1"]; + return ( + !appInfo || + Services.appinfo.processType == Ci.nsIXULRuntime.PROCESS_TYPE_DEFAULT + ); +} + +function run_test() { + if (!isParentProcess()) { + do_load_child_test_harness(); + + var pb = Services.prefs; + pb.setBoolPref("Test.IPC.bool.new", true); + pb.setIntPref("Test.IPC.int.new", 23); + pb.setCharPref("Test.IPC.char.new", "hey"); + + run_test_in_child("test_observed_prefs.js"); + } +} diff --git a/modules/libpref/test/unit_ipc/test_initial_prefs.js b/modules/libpref/test/unit_ipc/test_initial_prefs.js new file mode 100644 index 0000000000..0fffd327be --- /dev/null +++ b/modules/libpref/test/unit_ipc/test_initial_prefs.js @@ -0,0 +1,16 @@ +const { Services } = ChromeUtils.import("resource://gre/modules/Services.jsm"); + +function isParentProcess() { + return Services.appinfo.processType == Ci.nsIXULRuntime.PROCESS_TYPE_DEFAULT; +} + +function run_test() { + if (!isParentProcess()) { + const pb = Services.prefs; + pb.setBoolPref("Test.IPC.bool", true); + pb.setIntPref("Test.IPC.int", 23); + pb.setCharPref("Test.IPC.char", "hey"); + + run_test_in_child("test_existing_prefs.js"); + } +} diff --git a/modules/libpref/test/unit_ipc/test_large_pref.js b/modules/libpref/test/unit_ipc/test_large_pref.js new file mode 100644 index 0000000000..4b4a50fcf0 --- /dev/null +++ b/modules/libpref/test/unit_ipc/test_large_pref.js @@ -0,0 +1,105 @@ +/* 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/. */ + +// Large preferences should not be set in the child process. +// Non-string preferences are not tested here, because their behavior +// should not be affected by this filtering. +// +const { Services } = ChromeUtils.import("resource://gre/modules/Services.jsm"); + +function isParentProcess() { + return Services.appinfo.processType == Ci.nsIXULRuntime.PROCESS_TYPE_DEFAULT; +} + +function makeBuffer(length) { + let string = "x"; + while (string.length < length) { + string = string + string; + } + if (string.length > length) { + string = string.substring(length - string.length); + } + return string; +} + +// from prefapi.h +const MAX_ADVISABLE_PREF_LENGTH = 4 * 1024; + +const largeString = makeBuffer(MAX_ADVISABLE_PREF_LENGTH + 1); +const smallString = makeBuffer(4); + +const testValues = [ + { name: "None", value: undefined }, + { name: "Small", value: smallString }, + { name: "Large", value: largeString }, +]; + +function prefName(def, user) { + return "Test.IPC.default" + def.name + "User" + user.name; +} + +function expectedPrefValue(def, user) { + if (user.value) { + return user.value; + } + return def.value; +} + +function run_test() { + const pb = Services.prefs; + let defaultBranch = pb.getDefaultBranch(""); + + let isParent = isParentProcess(); + if (isParent) { + // Preferences with large values will still appear in the shared memory + // snapshot that we share with all processes. They should not, however, be + // sent with the list of changes on top of the snapshot. + // + // So, make sure we've generated the initial snapshot before we set the + // preference values by launching a child process with an empty test. + sendCommand(""); + + // Set all combinations of none, small and large, for default and user prefs. + for (let def of testValues) { + for (let user of testValues) { + let currPref = prefName(def, user); + if (def.value) { + defaultBranch.setCharPref(currPref, def.value); + } + if (user.value) { + pb.setCharPref(currPref, user.value); + } + } + } + + run_test_in_child("test_large_pref.js"); + } + + // Check that each preference is set or not set, as appropriate. + for (let def of testValues) { + for (let user of testValues) { + if (!def.value && !user.value) { + continue; + } + let pref_name = prefName(def, user); + if (isParent || (def.name != "Large" && user.name != "Large")) { + Assert.equal(pb.getCharPref(pref_name), expectedPrefValue(def, user)); + } else { + // This is the child, and either the default or user value is + // large, so the preference should not be set. + let prefExists; + try { + let val = pb.getCharPref(pref_name); + prefExists = val.length > 128; + } catch (e) { + prefExists = false; + } + ok( + !prefExists, + "Pref " + pref_name + " should not be set in the child" + ); + } + } + } +} diff --git a/modules/libpref/test/unit_ipc/test_locked_prefs.js b/modules/libpref/test/unit_ipc/test_locked_prefs.js new file mode 100644 index 0000000000..64dd15dd0d --- /dev/null +++ b/modules/libpref/test/unit_ipc/test_locked_prefs.js @@ -0,0 +1,41 @@ +/* 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/. */ + +// Locked status should be communicated to children. + +const { Services } = ChromeUtils.import("resource://gre/modules/Services.jsm"); + +function isParentProcess() { + return Services.appinfo.processType == Ci.nsIXULRuntime.PROCESS_TYPE_DEFAULT; +} + +function run_test() { + const pb = Services.prefs; + + let bprefname = "Test.IPC.locked.bool"; + let iprefname = "Test.IPC.locked.int"; + let sprefname = "Test.IPC.locked.string"; + + let isParent = isParentProcess(); + if (isParent) { + pb.setBoolPref(bprefname, true); + pb.lockPref(bprefname); + + pb.setIntPref(iprefname, true); + pb.lockPref(iprefname); + + pb.setStringPref(sprefname, true); + pb.lockPref(sprefname); + pb.unlockPref(sprefname); + + run_test_in_child("test_locked_prefs.js"); + } + + ok(pb.prefIsLocked(bprefname), bprefname + " should be locked in the child"); + ok(pb.prefIsLocked(iprefname), iprefname + " should be locked in the child"); + ok( + !pb.prefIsLocked(sprefname), + sprefname + " should be unlocked in the child" + ); +} diff --git a/modules/libpref/test/unit_ipc/test_observed_prefs.js b/modules/libpref/test/unit_ipc/test_observed_prefs.js new file mode 100644 index 0000000000..6e451bbb74 --- /dev/null +++ b/modules/libpref/test/unit_ipc/test_observed_prefs.js @@ -0,0 +1,14 @@ +const { Services } = ChromeUtils.import("resource://gre/modules/Services.jsm"); + +function isParentProcess() { + return Services.appinfo.processType == Ci.nsIXULRuntime.PROCESS_TYPE_DEFAULT; +} + +function run_test() { + if (!isParentProcess()) { + const pb = Services.prefs; + Assert.equal(pb.getBoolPref("Test.IPC.bool.new"), true); + Assert.equal(pb.getIntPref("Test.IPC.int.new"), 23); + Assert.equal(pb.getCharPref("Test.IPC.char.new"), "hey"); + } +} diff --git a/modules/libpref/test/unit_ipc/test_sharedMap.js b/modules/libpref/test/unit_ipc/test_sharedMap.js new file mode 100644 index 0000000000..b51d987730 --- /dev/null +++ b/modules/libpref/test/unit_ipc/test_sharedMap.js @@ -0,0 +1,364 @@ +/* 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"; + +// This file tests the functionality of the preference service when using a +// shared memory snapshot. In this configuration, a snapshot of the initial +// state of the preferences database is made when we first spawn a child +// process, and changes after that point are stored as entries in a dynamic hash +// table, on top of the snapshot. + +const { Services } = ChromeUtils.import("resource://gre/modules/Services.jsm"); +const { ExtensionTestUtils } = ChromeUtils.import( + "resource://testing-common/ExtensionXPCShellUtils.jsm" +); + +ExtensionTestUtils.init(this); + +let contentPage; + +const { prefs } = Services; +const defaultPrefs = prefs.getDefaultBranch(""); + +const FRAME_SCRIPT_INIT = ` + const { Services } = ChromeUtils.import("resource://gre/modules/Services.jsm"); + var { prefs } = Services; + var defaultPrefs = prefs.getDefaultBranch(""); +`; + +function try_(fn) { + try { + return fn(); + } catch (e) { + return undefined; + } +} + +function getPref(pref) { + let flags = { + locked: try_(() => prefs.prefIsLocked(pref)), + hasUser: try_(() => prefs.prefHasUserValue(pref)), + }; + + switch (prefs.getPrefType(pref)) { + case prefs.PREF_INT: + return { + ...flags, + type: "Int", + user: try_(() => prefs.getIntPref(pref)), + default: try_(() => defaultPrefs.getIntPref(pref)), + }; + case prefs.PREF_BOOL: + return { + ...flags, + type: "Bool", + user: try_(() => prefs.getBoolPref(pref)), + default: try_(() => defaultPrefs.getBoolPref(pref)), + }; + case prefs.PREF_STRING: + return { + ...flags, + type: "String", + user: try_(() => prefs.getStringPref(pref)), + default: try_(() => defaultPrefs.getStringPref(pref)), + }; + } + return {}; +} + +function getPrefs(prefNames) { + let result = {}; + for (let pref of prefNames) { + result[pref] = getPref(pref); + } + result.childList = prefs.getChildList(""); + return result; +} + +function checkPref( + pref, + proc, + val, + type, + userVal, + defaultVal, + expectedFlags = {} +) { + info(`Check "${pref}" ${proc} value`); + + equal(val.type, type, `Expected type for "${pref}"`); + equal(val.user, userVal, `Expected user value for "${pref}"`); + + // We only send changes to the content process when they'll make a visible + // difference, so ignore content process default values when we have a defined + // user value. + if (proc !== "content" || val.user === undefined) { + equal(val.default, defaultVal, `Expected default value for "${pref}"`); + } + + for (let [flag, value] of Object.entries(expectedFlags)) { + equal(val[flag], value, `Expected ${flag} value for "${pref}"`); + } +} + +function getPrefList() { + return prefs.getChildList(""); +} + +const TESTS = { + "exists.thenDoesNot": { + beforeContent(PREF) { + prefs.setBoolPref(PREF, true); + + ok(getPrefList().includes(PREF), `Parent list includes "${PREF}"`); + }, + contentStartup(PREF, val, childList) { + ok(getPrefList().includes(PREF), `Parent list includes "${PREF}"`); + ok(childList.includes(PREF), `Child list includes "${PREF}"`); + + prefs.clearUserPref(PREF); + ok( + !getPrefList().includes(PREF), + `Parent list doesn't include "${PREF}"` + ); + }, + contentUpdate1(PREF, val, childList) { + ok( + !getPrefList().includes(PREF), + `Parent list doesn't include "${PREF}"` + ); + ok(!childList.includes(PREF), `Child list doesn't include "${PREF}"`); + + prefs.setCharPref(PREF, "foo"); + ok(getPrefList().includes(PREF), `Parent list includes "${PREF}"`); + checkPref(PREF, "parent", getPref(PREF), "String", "foo"); + }, + contentUpdate2(PREF, val, childList) { + ok(getPrefList().includes(PREF), `Parent list includes "${PREF}"`); + ok(childList.includes(PREF), `Child list includes "${PREF}"`); + + checkPref(PREF, "parent", getPref(PREF), "String", "foo"); + checkPref(PREF, "child", val, "String", "foo"); + }, + }, + "doesNotExists.thenDoes": { + contentStartup(PREF, val, childList) { + ok( + !getPrefList().includes(PREF), + `Parent list doesn't include "${PREF}"` + ); + ok(!childList.includes(PREF), `Child list doesn't include "${PREF}"`); + + prefs.setIntPref(PREF, 42); + ok(getPrefList().includes(PREF), `Parent list includes "${PREF}"`); + }, + contentUpdate1(PREF, val, childList) { + ok(getPrefList().includes(PREF), `Parent list includes "${PREF}"`); + ok(childList.includes(PREF), `Child list includes "${PREF}"`); + + checkPref(PREF, "parent", getPref(PREF), "Int", 42); + checkPref(PREF, "child", val, "Int", 42); + }, + }, +}; + +const PREFS = [ + { type: "Bool", values: [true, false, true] }, + { type: "Int", values: [24, 42, 73] }, + { type: "String", values: ["meh", "hem", "hrm"] }, +]; + +for (let { type, values } of PREFS) { + let set = `set${type}Pref`; + + function prefTest(opts) { + function check( + pref, + proc, + val, + { + expectedVal, + defaultVal = undefined, + expectedDefault = defaultVal, + expectedFlags = {}, + } + ) { + checkPref( + pref, + proc, + val, + type, + expectedVal, + expectedDefault, + expectedFlags + ); + } + + function updatePref( + PREF, + { userVal = undefined, defaultVal = undefined, flags = {} } + ) { + info(`Update "${PREF}"`); + if (userVal !== undefined) { + prefs[set](PREF, userVal); + } + if (defaultVal !== undefined) { + defaultPrefs[set](PREF, defaultVal); + } + if (flags.locked === true) { + prefs.lockPref(PREF); + } else if (flags.locked === false) { + prefs.unlockPref(PREF); + } + } + + return { + beforeContent(PREF) { + updatePref(PREF, opts.initial); + check(PREF, "parent", getPref(PREF), opts.initial); + }, + contentStartup(PREF, contentVal) { + check(PREF, "content", contentVal, opts.initial); + check(PREF, "parent", getPref(PREF), opts.initial); + + updatePref(PREF, opts.change1); + check(PREF, "parent", getPref(PREF), opts.change1); + }, + contentUpdate1(PREF, contentVal) { + check(PREF, "content", contentVal, opts.change1); + check(PREF, "parent", getPref(PREF), opts.change1); + + if (opts.change2) { + updatePref(PREF, opts.change2); + check(PREF, "parent", getPref(PREF), opts.change2); + } + }, + contentUpdate2(PREF, contentVal) { + if (opts.change2) { + check(PREF, "content", contentVal, opts.change2); + check(PREF, "parent", getPref(PREF), opts.change2); + } + }, + }; + } + + for (let i of [0, 1]) { + let userVal = values[i]; + let defaultVal = values[+!i]; + + TESTS[`type.${type}.${i}.default`] = prefTest({ + initial: { defaultVal, expectedVal: defaultVal }, + change1: { defaultVal: values[2], expectedVal: values[2] }, + }); + + TESTS[`type.${type}.${i}.user`] = prefTest({ + initial: { userVal, expectedVal: userVal }, + change1: { defaultVal: values[2], expectedVal: userVal }, + change2: { + userVal: values[2], + expectedDefault: values[2], + expectedVal: values[2], + }, + }); + + TESTS[`type.${type}.${i}.both`] = prefTest({ + initial: { userVal, defaultVal, expectedVal: userVal }, + change1: { defaultVal: values[2], expectedVal: userVal }, + change2: { + userVal: values[2], + expectedDefault: values[2], + expectedVal: values[2], + }, + }); + + TESTS[`type.${type}.${i}.both.thenLock`] = prefTest({ + initial: { userVal, defaultVal, expectedVal: userVal }, + change1: { + expectedDefault: defaultVal, + expectedVal: defaultVal, + flags: { locked: true }, + expectFlags: { locked: true }, + }, + }); + + TESTS[`type.${type}.${i}.both.thenUnlock`] = prefTest({ + initial: { + userVal, + defaultVal, + expectedVal: defaultVal, + flags: { locked: true }, + expectedFlags: { locked: true }, + }, + change1: { + expectedDefault: defaultVal, + expectedVal: userVal, + flags: { locked: false }, + expectFlags: { locked: false }, + }, + }); + + TESTS[`type.${type}.${i}.both.locked`] = prefTest({ + initial: { + userVal, + defaultVal, + expectedVal: defaultVal, + flags: { locked: true }, + expectedFlags: { locked: true }, + }, + change1: { + userVal: values[2], + expectedDefault: defaultVal, + expectedVal: defaultVal, + expectedFlags: { locked: true }, + }, + change2: { + defaultVal: values[2], + expectedDefault: defaultVal, + expectedVal: defaultVal, + expectedFlags: { locked: true }, + }, + }); + } +} + +add_task(async function test_sharedMap_prefs() { + let prefValues = {}; + + async function runChecks(op) { + for (let [pref, ops] of Object.entries(TESTS)) { + if (ops[op]) { + info(`Running ${op} for "${pref}"`); + await ops[op]( + pref, + prefValues[pref] || undefined, + prefValues.childList || undefined + ); + } + } + } + + await runChecks("beforeContent"); + + contentPage = await ExtensionTestUtils.loadContentPage("about:blank", { + remote: true, + }); + registerCleanupFunction(() => contentPage.close()); + + contentPage.addFrameScriptHelper(FRAME_SCRIPT_INIT); + contentPage.addFrameScriptHelper(try_); + contentPage.addFrameScriptHelper(getPref); + + let prefNames = Object.keys(TESTS); + prefValues = await contentPage.spawn(prefNames, getPrefs); + + await runChecks("contentStartup"); + + prefValues = await contentPage.spawn(prefNames, getPrefs); + + await runChecks("contentUpdate1"); + + prefValues = await contentPage.spawn(prefNames, getPrefs); + + await runChecks("contentUpdate2"); +}); diff --git a/modules/libpref/test/unit_ipc/test_sharedMap_static_prefs.js b/modules/libpref/test/unit_ipc/test_sharedMap_static_prefs.js new file mode 100644 index 0000000000..31a7d4d265 --- /dev/null +++ b/modules/libpref/test/unit_ipc/test_sharedMap_static_prefs.js @@ -0,0 +1,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/. */ +"use strict"; + +// Tests that static preferences in the content process +// correctly handle values which are different from their +// statically-defined defaults. +// +// Since we can't access static preference values from JS, this tests relies on +// assertions in debug builds to detect mismatches. The default and user +// values of two preferences are changed (respectively) before a content +// process is started. Once the content process is launched, the +// preference service asserts that the values stored in all static prefs +// match their current values as known to the preference service. If +// there's a mismatch, the shell will crash, and the test will fail. +// +// For sanity, we also check that the dynamically retrieved preference +// values in the content process match our expectations, though this is +// not strictly part of the test. + +const PREF1_NAME = "dom.webcomponents.shadowdom.report_usage"; +const PREF1_VALUE = false; + +const PREF2_NAME = "dom.mutation-events.cssom.disabled"; +const PREF2_VALUE = true; + +const { Services } = ChromeUtils.import("resource://gre/modules/Services.jsm"); +const { ExtensionTestUtils } = ChromeUtils.import( + "resource://testing-common/ExtensionXPCShellUtils.jsm" +); + +ExtensionTestUtils.init(this); + +const { prefs } = Services; +const defaultPrefs = prefs.getDefaultBranch(""); + +add_task(async function test_sharedMap_static_prefs() { + equal( + prefs.getBoolPref(PREF1_NAME), + PREF1_VALUE, + `Expected initial value for ${PREF1_NAME}` + ); + equal( + prefs.getBoolPref(PREF2_NAME), + PREF2_VALUE, + `Expected initial value for ${PREF2_NAME}` + ); + + defaultPrefs.setBoolPref(PREF1_NAME, !PREF1_VALUE); + prefs.setBoolPref(PREF2_NAME, !PREF2_VALUE); + + equal( + prefs.getBoolPref(PREF1_NAME), + !PREF1_VALUE, + `Expected updated value for ${PREF1_NAME}` + ); + equal( + prefs.getBoolPref(PREF2_NAME), + !PREF2_VALUE, + `Expected updated value for ${PREF2_NAME}` + ); + + let contentPage = await ExtensionTestUtils.loadContentPage("about:blank", { + remote: true, + }); + registerCleanupFunction(() => contentPage.close()); + + /* eslint-disable no-shadow */ + let values = await contentPage.spawn([PREF1_NAME, PREF2_NAME], prefs => { + const { Services } = ChromeUtils.import( + "resource://gre/modules/Services.jsm" + ); + return prefs.map(pref => Services.prefs.getBoolPref(pref)); + }); + /* eslint-enable no-shadow */ + + equal(values[0], !PREF1_VALUE, `Expected content value for ${PREF1_NAME}`); + equal(values[1], !PREF2_VALUE, `Expected content value for ${PREF2_NAME}`); +}); diff --git a/modules/libpref/test/unit_ipc/test_update_prefs.js b/modules/libpref/test/unit_ipc/test_update_prefs.js new file mode 100644 index 0000000000..741b690e00 --- /dev/null +++ b/modules/libpref/test/unit_ipc/test_update_prefs.js @@ -0,0 +1,36 @@ +const { Services } = ChromeUtils.import("resource://gre/modules/Services.jsm"); + +function isParentProcess() { + return Services.appinfo.processType == Ci.nsIXULRuntime.PROCESS_TYPE_DEFAULT; +} + +function run_test() { + if (isParentProcess()) { + do_load_child_test_harness(); + + var pb = Services.prefs; + + // these prefs are set after the child has been created. + pb.setBoolPref("Test.IPC.bool.new", true); + pb.setIntPref("Test.IPC.int.new", 23); + pb.setCharPref("Test.IPC.char.new", "hey"); + + run_test_in_child("test_observed_prefs.js", testPrefClear); + } +} + +function testPrefClear() { + var pb = Services.prefs; + pb.clearUserPref("Test.IPC.bool.new"); + + sendCommand( + 'var pb = Cc["@mozilla.org/preferences-service;1"].getService(Ci.nsIPrefBranch);\n' + + 'pb.prefHasUserValue("Test.IPC.bool.new");\n', + checkWasCleared + ); +} + +function checkWasCleared(existsStr) { + Assert.equal(existsStr, "false"); + do_test_finished(); +} diff --git a/modules/libpref/test/unit_ipc/test_user_default_prefs.js b/modules/libpref/test/unit_ipc/test_user_default_prefs.js new file mode 100644 index 0000000000..7821f34ece --- /dev/null +++ b/modules/libpref/test/unit_ipc/test_user_default_prefs.js @@ -0,0 +1,73 @@ +const { Services } = ChromeUtils.import("resource://gre/modules/Services.jsm"); +const pb = Services.prefs; + +// This pref is chosen somewhat arbitrarily --- we just need one +// that's guaranteed to have a default value. +const kPrefName = "intl.accept_languages"; // of type char, which we +// assume below +var initialValue = null; + +function check_child_pref_info_eq(continuation) { + sendCommand( + 'var pb = Components.classes["@mozilla.org/preferences-service;1"].getService(Components.interfaces.nsIPrefBranch);\n' + + // Returns concatenation "[value],[isUser]" + 'pb.getCharPref("' + + kPrefName + + '")+ "," +' + + 'pb.prefHasUserValue("' + + kPrefName + + '");', + function(info) { + let [value, isUser] = info.split(","); + Assert.equal(pb.getCharPref(kPrefName), value); + Assert.equal(pb.prefHasUserValue(kPrefName), isUser == "true"); + continuation(); + } + ); +} + +function run_test() { + // We finish in clean_up() + do_test_pending(); + + initialValue = pb.getCharPref(kPrefName); + + test_user_setting(); +} + +function test_user_setting() { + // We rely on setting this before the content process starts up. + // When it starts up, it should recognize this as a user pref, not + // a default pref. + pb.setCharPref(kPrefName, "i-imaginarylanguage"); + // NB: processing of the value-change notification in the child + // process triggered by the above set happens-before the remaining + // code here + check_child_pref_info_eq(function() { + Assert.equal(pb.prefHasUserValue(kPrefName), true); + + test_cleared_is_default(); + }); +} + +function test_cleared_is_default() { + pb.clearUserPref(kPrefName); + // NB: processing of the value-change notification in the child + // process triggered by the above set happens-before the remaining + // code here + check_child_pref_info_eq(function() { + Assert.equal(pb.prefHasUserValue(kPrefName), false); + + clean_up(); + }); +} + +function clean_up() { + pb.setCharPref(kPrefName, initialValue); + // NB: processing of the value-change notification in the child + // process triggered by the above set happens-before the remaining + // code here + check_child_pref_info_eq(function() { + do_test_finished(); + }); +} diff --git a/modules/libpref/test/unit_ipc/xpcshell.ini b/modules/libpref/test/unit_ipc/xpcshell.ini new file mode 100644 index 0000000000..e2a444f774 --- /dev/null +++ b/modules/libpref/test/unit_ipc/xpcshell.ini @@ -0,0 +1,14 @@ +[DEFAULT] +head = +skip-if = toolkit == 'android' + +[test_existing_prefs.js] +[test_initial_prefs.js] +[test_large_pref.js] +[test_locked_prefs.js] +[test_observed_prefs.js] +[test_update_prefs.js] +[test_sharedMap.js] +[test_sharedMap_static_prefs.js] +skip-if = !debug # Relies on debug assertions to catch failure cases. +[test_user_default_prefs.js] |