Ejemplo n.º 1
0
static void
TraceArray(JSTracer* trc, void* data)
{
  ArrayT* array = static_cast<ArrayT *>(data);
  for (unsigned i = 0; i < array->Length(); ++i)
    JS_CallHeapObjectTracer(trc, &array->ElementAt(i), "array-element");
}
Ejemplo n.º 2
0
static void
RunTest(JSRuntime* rt, JSContext* cx)
{
  JS_GC(rt);

  /*
   * Create an array with space for half the final number of elements to test
   * that moving Heap<T> elements works correctly.
   */
  const int elements = 100;
  ArrayT* array = new ArrayT(elements / 2);
  ASSERT_TRUE(array != nullptr);
  JS_AddExtraGCRootsTracer(rt, TraceArray, array);

  /*
   * Create the array and fill it with new JS objects. With GGC these will be
   * allocated in the nursery.
   */
  RootedValue value(cx);
  const char* property = "foo";
  JS::shadow::Runtime* srt = reinterpret_cast<JS::shadow::Runtime*>(rt);
  for (int i = 0; i < elements; ++i) {
    RootedObject obj(cx, JS_NewObject(cx, nullptr, JS::NullPtr(), JS::NullPtr()));
#ifdef JSGC_GENERATIONAL
    ASSERT_TRUE(js::gc::IsInsideNursery(srt, obj));
#else
    ASSERT_FALSE(js::gc::IsInsideNursery(srt, obj));
#endif
    value = Int32Value(i);
    ASSERT_TRUE(JS_SetProperty(cx, obj, property, value));
    array->AppendElement(obj);
  }

  /*
   * If postbarriers are not working, we will crash here when we try to mark
   * objects that have been moved to the tenured heap.
   */
  JS_GC(rt);

  /*
   * Sanity check that our array contains what we expect.
   */
  for (int i = 0; i < elements; ++i) {
    RootedObject obj(cx, array->ElementAt(i));
    ASSERT_FALSE(js::gc::IsInsideNursery(srt, obj));
    ASSERT_TRUE(JS_GetProperty(cx, obj, property, &value));
    ASSERT_TRUE(value.isInt32());
    ASSERT_EQ(i, value.toInt32());
  }

  JS_RemoveExtraGCRootsTracer(rt, TraceArray, array);
}