tor-browser

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

test_origin.js (9097B)


      1 var ssm = Services.scriptSecurityManager;
      2 function makeURI(uri) {
      3  return Services.io.newURI(uri);
      4 }
      5 
      6 function checkThrows(f) {
      7  var threw = false;
      8  try {
      9    f();
     10  } catch (e) {
     11    threw = true;
     12  }
     13  Assert.ok(threw);
     14 }
     15 
     16 function checkCrossOrigin(a, b) {
     17  Assert.ok(!a.equals(b));
     18  Assert.ok(!a.equalsConsideringDomain(b));
     19  Assert.ok(!a.subsumes(b));
     20  Assert.ok(!a.subsumesConsideringDomain(b));
     21  Assert.ok(!b.subsumes(a));
     22  Assert.ok(!b.subsumesConsideringDomain(a));
     23 }
     24 
     25 function checkOriginAttributes(prin, attrs, suffix) {
     26  attrs = attrs || {};
     27  Assert.equal(prin.originSuffix, suffix || "");
     28  Assert.equal(ChromeUtils.originAttributesToSuffix(attrs), suffix || "");
     29  Assert.ok(
     30    ChromeUtils.originAttributesMatchPattern(prin.originAttributes, attrs)
     31  );
     32  if (!prin.isNullPrincipal && !prin.origin.startsWith("[")) {
     33    Assert.ok(ssm.createContentPrincipalFromOrigin(prin.origin).equals(prin));
     34  } else {
     35    checkThrows(() => ssm.createContentPrincipalFromOrigin(prin.origin));
     36  }
     37 }
     38 
     39 function checkSandboxOriginAttributes(arr, attrs, options) {
     40  options = options || {};
     41  var sandbox = Cu.Sandbox(arr, options);
     42  checkOriginAttributes(
     43    Cu.getObjectPrincipal(sandbox),
     44    attrs,
     45    ChromeUtils.originAttributesToSuffix(attrs)
     46  );
     47 }
     48 
     49 // utility function useful for debugging
     50 // eslint-disable-next-line no-unused-vars
     51 function printAttrs(name, attrs) {
     52  info(
     53    name +
     54      " {\n" +
     55      "\tuserContextId: " +
     56      attrs.userContextId +
     57      ",\n" +
     58      "\tprivateBrowsingId: '" +
     59      attrs.privateBrowsingId +
     60      "',\n" +
     61      "\tfirstPartyDomain: '" +
     62      attrs.firstPartyDomain +
     63      "'\n}"
     64  );
     65 }
     66 
     67 function checkValues(attrs, values) {
     68  values = values || {};
     69  // printAttrs("attrs", attrs);
     70  // printAttrs("values", values);
     71  Assert.equal(attrs.userContextId, values.userContextId || 0);
     72  Assert.equal(attrs.privateBrowsingId, values.privateBrowsingId || "");
     73  Assert.equal(attrs.firstPartyDomain, values.firstPartyDomain || "");
     74 }
     75 
     76 function run_test() {
     77  // Attributeless origins.
     78  Assert.equal(ssm.getSystemPrincipal().origin, "[System Principal]");
     79  checkOriginAttributes(ssm.getSystemPrincipal());
     80  var exampleOrg = ssm.createContentPrincipal(
     81    makeURI("http://example.org"),
     82    {}
     83  );
     84  Assert.equal(exampleOrg.origin, "http://example.org");
     85  checkOriginAttributes(exampleOrg);
     86  var exampleCom = ssm.createContentPrincipal(
     87    makeURI("https://www.example.com:123"),
     88    {}
     89  );
     90  Assert.equal(exampleCom.origin, "https://www.example.com:123");
     91  checkOriginAttributes(exampleCom);
     92  var nullPrin = Cu.getObjectPrincipal(new Cu.Sandbox(null));
     93  Assert.ok(
     94    /^moz-nullprincipal:\{([0-9]|[a-z]|\-){36}\}$/.test(nullPrin.origin)
     95  );
     96  checkOriginAttributes(nullPrin);
     97  var ipv6Prin = ssm.createContentPrincipal(
     98    makeURI("https://[2001:db8::ff00:42:8329]:123"),
     99    {}
    100  );
    101  Assert.equal(ipv6Prin.origin, "https://[2001:db8::ff00:42:8329]:123");
    102  checkOriginAttributes(ipv6Prin);
    103  var ipv6NPPrin = ssm.createContentPrincipal(
    104    makeURI("https://[2001:db8::ff00:42:8329]"),
    105    {}
    106  );
    107  Assert.equal(ipv6NPPrin.origin, "https://[2001:db8::ff00:42:8329]");
    108  checkOriginAttributes(ipv6NPPrin);
    109  var ep = Cu.getObjectPrincipal(
    110    Cu.Sandbox([exampleCom, nullPrin, exampleOrg])
    111  );
    112  checkOriginAttributes(ep);
    113  checkCrossOrigin(exampleCom, exampleOrg);
    114  checkCrossOrigin(exampleOrg, nullPrin);
    115 
    116  // nsEP origins should be in lexical order.
    117  Assert.equal(
    118    ep.origin,
    119    `[Expanded Principal [${exampleCom.origin}, ${nullPrin.origin}, ${exampleOrg.origin}]]`
    120  );
    121 
    122  // Make sure createContentPrincipal does what the rest of gecko does.
    123  Assert.ok(
    124    exampleOrg.equals(
    125      Cu.getObjectPrincipal(new Cu.Sandbox("http://example.org"))
    126    )
    127  );
    128 
    129  //
    130  // Test origin attributes.
    131  //
    132 
    133  // First party Uri
    134  var exampleOrg_firstPartyDomain = ssm.createContentPrincipal(
    135    makeURI("http://example.org"),
    136    { firstPartyDomain: "example.org" }
    137  );
    138  checkOriginAttributes(
    139    exampleOrg_firstPartyDomain,
    140    { firstPartyDomain: "example.org" },
    141    "^firstPartyDomain=example.org"
    142  );
    143  Assert.equal(
    144    exampleOrg_firstPartyDomain.origin,
    145    "http://example.org^firstPartyDomain=example.org"
    146  );
    147 
    148  // Just userContext.
    149  var exampleOrg_userContext = ssm.createContentPrincipal(
    150    makeURI("http://example.org"),
    151    { userContextId: 42 }
    152  );
    153  checkOriginAttributes(
    154    exampleOrg_userContext,
    155    { userContextId: 42 },
    156    "^userContextId=42"
    157  );
    158  Assert.equal(
    159    exampleOrg_userContext.origin,
    160    "http://example.org^userContextId=42"
    161  );
    162 
    163  checkSandboxOriginAttributes(null, {});
    164  checkSandboxOriginAttributes("http://example.org", {});
    165  checkSandboxOriginAttributes(
    166    "http://example.org",
    167    {},
    168    { originAttributes: {} }
    169  );
    170  checkSandboxOriginAttributes(["http://example.org"], {});
    171  checkSandboxOriginAttributes(
    172    ["http://example.org"],
    173    {},
    174    { originAttributes: {} }
    175  );
    176 
    177  // Check that all of the above are cross-origin.
    178  checkCrossOrigin(exampleOrg_firstPartyDomain, exampleOrg);
    179  checkCrossOrigin(exampleOrg_userContext, exampleOrg);
    180 
    181  // Check Principal kinds.
    182  function checkKind(prin, kind) {
    183    Assert.equal(prin.isNullPrincipal, kind == "nullPrincipal");
    184    Assert.equal(prin.isContentPrincipal, kind == "contentPrincipal");
    185    Assert.equal(prin.isExpandedPrincipal, kind == "expandedPrincipal");
    186    Assert.equal(prin.isSystemPrincipal, kind == "systemPrincipal");
    187  }
    188  checkKind(ssm.createNullPrincipal({}), "nullPrincipal");
    189  checkKind(
    190    ssm.createContentPrincipal(makeURI("http://www.example.com"), {}),
    191    "contentPrincipal"
    192  );
    193  checkKind(
    194    Cu.getObjectPrincipal(
    195      Cu.Sandbox([
    196        ssm.createContentPrincipal(makeURI("http://www.example.com"), {}),
    197      ])
    198    ),
    199    "expandedPrincipal"
    200  );
    201  checkKind(ssm.getSystemPrincipal(), "systemPrincipal");
    202 
    203  //
    204  // Test Origin Attribute Manipulation
    205  //
    206 
    207  // check that we can create an empty origin attributes dict with default
    208  // members and values.
    209  var emptyAttrs = ChromeUtils.fillNonDefaultOriginAttributes({});
    210  checkValues(emptyAttrs);
    211 
    212  var uri = "http://example.org";
    213  var tests = [
    214    ["", {}],
    215    ["^userContextId=3", { userContextId: 3 }],
    216    ["^firstPartyDomain=example.org", { firstPartyDomain: "example.org" }],
    217  ];
    218 
    219  // check that we can create an origin attributes from an origin properly
    220  tests.forEach(t => {
    221    let attrs = ChromeUtils.createOriginAttributesFromOrigin(uri + t[0]);
    222    checkValues(attrs, t[1]);
    223    Assert.equal(ChromeUtils.originAttributesToSuffix(attrs), t[0]);
    224  });
    225 
    226  // check that we can create an origin attributes from a dict properly
    227  tests.forEach(t => {
    228    let attrs = ChromeUtils.fillNonDefaultOriginAttributes(t[1]);
    229    checkValues(attrs, t[1]);
    230    Assert.equal(ChromeUtils.originAttributesToSuffix(attrs), t[0]);
    231  });
    232 
    233  // each row in the dflt_tests array has these values:
    234  // [0] - the suffix used to create an origin attribute from
    235  // [1] - the expected result of creating an origin attributes from [0]
    236  // [2] - the expected result after setting userContextId to the default
    237  // [3] - the expected result of creating a suffix from [2]
    238  var dflt_tests = [
    239    ["", {}, {}, ""],
    240    ["^userContextId=3", { userContextId: 3 }, {}, ""],
    241  ];
    242 
    243  // check that we can set the userContextId to default properly
    244  dflt_tests.forEach(t => {
    245    let orig = ChromeUtils.createOriginAttributesFromOrigin(uri + t[0]);
    246    checkValues(orig, t[1]);
    247    let mod = orig;
    248    mod.userContextId = 0;
    249    checkValues(mod, t[2]);
    250    Assert.equal(ChromeUtils.originAttributesToSuffix(mod), t[3]);
    251  });
    252 
    253  // each row in the dflt2_tests array has these values:
    254  // [0] - the suffix used to create an origin attribute from
    255  // [1] - the expected result of creating an origin attributes from [0]
    256  // [2] - the expected result after setting firstPartyUri to the default
    257  // [3] - the expected result of creating a suffix from [2]
    258  var dflt2_tests = [
    259    ["", {}, {}, ""],
    260    ["^firstPartyDomain=foo.com", { firstPartyDomain: "foo.com" }, {}, ""],
    261  ];
    262 
    263  // check that we can set the userContextId to default properly
    264  dflt2_tests.forEach(t => {
    265    let orig = ChromeUtils.createOriginAttributesFromOrigin(uri + t[0]);
    266    checkValues(orig, t[1]);
    267    let mod = orig;
    268    mod.firstPartyDomain = "";
    269    checkValues(mod, t[2]);
    270    Assert.equal(ChromeUtils.originAttributesToSuffix(mod), t[3]);
    271  });
    272 
    273  var fileURI = makeURI("file:///foo/bar").QueryInterface(Ci.nsIFileURL);
    274  var fileTests = [
    275    [true, fileURI.spec],
    276    [false, "file://UNIVERSAL_FILE_URI_ORIGIN"],
    277  ];
    278  fileTests.forEach(t => {
    279    Services.prefs.setBoolPref("security.fileuri.strict_origin_policy", t[0]);
    280    var filePrin = ssm.createContentPrincipal(fileURI, {});
    281    Assert.equal(filePrin.origin, t[1]);
    282  });
    283  Services.prefs.clearUserPref("security.fileuri.strict_origin_policy");
    284 
    285  var aboutBlankURI = makeURI("about:blank");
    286  var aboutBlankPrin = ssm.createContentPrincipal(aboutBlankURI, {});
    287  Assert.ok(
    288    /^moz-nullprincipal:\{([0-9]|[a-z]|\-){36}\}$/.test(aboutBlankPrin.origin)
    289  );
    290 }