tor-browser

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

testLookup.cpp (3140B)


      1 /* -*- Mode: C++; tab-width: 8; indent-tabs-mode: nil; c-basic-offset: 2 -*-
      2 * vim: set ts=8 sts=2 et sw=2 tw=80:
      3 */
      4 /* This Source Code Form is subject to the terms of the Mozilla Public
      5 * License, v. 2.0. If a copy of the MPL was not distributed with this
      6 * file, You can obtain one at http://mozilla.org/MPL/2.0/. */
      7 
      8 #include "js/PropertyAndElement.h"  // JS_DefineProperty, JS_DefinePropertyById, JS_GetProperty
      9 #include "jsapi-tests/tests.h"
     10 #include "vm/JSFunction.h"  // for js::IsInternalFunctionObject
     11 
     12 #include "vm/JSObject-inl.h"
     13 
     14 BEGIN_TEST(testLookup_bug522590) {
     15  // Define a function that makes method-bearing objects.
     16  JS::RootedValue x(cx);
     17  EXEC("function mkobj() { return {f: function () {return 2;}} }");
     18 
     19  // Calling mkobj() multiple times must create multiple functions in ES5.
     20  EVAL("mkobj().f !== mkobj().f", &x);
     21  CHECK(x.isTrue());
     22 
     23  // Now make x.f a method.
     24  EVAL("mkobj()", &x);
     25  JS::RootedObject xobj(cx, x.toObjectOrNull());
     26 
     27  // This lookup must not return an internal function object.
     28  JS::RootedValue r(cx);
     29  CHECK(JS_GetProperty(cx, xobj, "f", &r));
     30  CHECK(r.isObject());
     31  JSObject* funobj = &r.toObject();
     32  CHECK(funobj->is<JSFunction>());
     33  CHECK(!js::IsInternalFunctionObject(*funobj));
     34 
     35  return true;
     36 }
     37 END_TEST(testLookup_bug522590)
     38 
     39 static const JSClass DocumentAllClass = {
     40    "DocumentAll",
     41    JSCLASS_EMULATES_UNDEFINED,
     42 };
     43 
     44 bool document_resolve(JSContext* cx, JS::HandleObject obj, JS::HandleId id,
     45                      bool* resolvedp) {
     46  // If id is "all", resolve document.all=true.
     47  JS::RootedValue v(cx);
     48  if (!JS_IdToValue(cx, id, &v)) {
     49    return false;
     50  }
     51 
     52  if (v.isString()) {
     53    JSString* str = v.toString();
     54    JSLinearString* linearStr = JS_EnsureLinearString(cx, str);
     55    if (!linearStr) {
     56      return false;
     57    }
     58    if (JS_LinearStringEqualsLiteral(linearStr, "all")) {
     59      JS::Rooted<JSObject*> docAll(cx, JS_NewObject(cx, &DocumentAllClass));
     60      if (!docAll) {
     61        return false;
     62      }
     63 
     64      JS::Rooted<JS::Value> allValue(cx, JS::ObjectValue(*docAll));
     65      if (!JS_DefinePropertyById(cx, obj, id, allValue, JSPROP_RESOLVING)) {
     66        return false;
     67      }
     68 
     69      *resolvedp = true;
     70      return true;
     71    }
     72  }
     73 
     74  *resolvedp = false;
     75  return true;
     76 }
     77 
     78 static const JSClassOps document_classOps = {
     79    nullptr,           // addProperty
     80    nullptr,           // delProperty
     81    nullptr,           // enumerate
     82    nullptr,           // newEnumerate
     83    document_resolve,  // resolve
     84    nullptr,           // mayResolve
     85    nullptr,           // finalize
     86    nullptr,           // call
     87    nullptr,           // construct
     88    nullptr,           // trace
     89 };
     90 
     91 static const JSClass document_class = {
     92    "document",
     93    0,
     94    &document_classOps,
     95 };
     96 
     97 BEGIN_TEST(testLookup_bug570195) {
     98  JS::RootedObject obj(cx, JS_NewObject(cx, &document_class));
     99  CHECK(obj);
    100  CHECK(JS_DefineProperty(cx, global, "document", obj, 0));
    101  JS::RootedValue v(cx);
    102  EVAL("document.all ? true : false", &v);
    103  CHECK(v.isFalse());
    104  EVAL("document.hasOwnProperty('all')", &v);
    105  CHECK(v.isTrue());
    106  return true;
    107 }
    108 END_TEST(testLookup_bug570195)