Version 3.19.7
Added support for //# sourceURL similar to deprecated //@ sourceURL one. (issue 2702)
Made sure IfBuilder::Return clears the current block. (Chromium issue 243868)
Fixed two CPU profiler tests on ARM and MIPS simulators (issue 2628)
Fixed idle incremental GC for large objects. (Chromium issue 241815)
Disabled --optimize-constructed-arrays due to crashes (Chromium issue 244461)
Performance and stability improvements on all platforms.
git-svn-id: http://v8.googlecode.com/svn/trunk@14900 ce2b1a6d-e550-0410-aec6-3dcde31c8c00
diff --git a/test/cctest/cctest.status b/test/cctest/cctest.status
index b0451e9..84a1a70 100644
--- a/test/cctest/cctest.status
+++ b/test/cctest/cctest.status
@@ -70,15 +70,6 @@
test-serialize/DeserializeFromSecondSerialization: SKIP
##############################################################################
-[ $arch == arm || $arch == mipsel ]
-
-# BUG(2628): Signal may come when pc is close to frame enter/exit code and on
-# simulator the stack frame is not set up when it is expected to be for the pc
-# value.
-test-cpu-profiler/CollectCpuProfile: PASS || FAIL
-test-cpu-profiler/SampleWhenFrameIsNotSetup: PASS || FAIL
-
-##############################################################################
[ $arch == android_arm || $arch == android_ia32 ]
# Tests crash as there is no /tmp directory in Android.
diff --git a/test/cctest/test-api.cc b/test/cctest/test-api.cc
index e52dde3..9eecf94 100644
--- a/test/cctest/test-api.cc
+++ b/test/cctest/test-api.cc
@@ -32,11 +32,6 @@
#include <unistd.h> // getpid
#endif // WIN32
-// TODO(dcarney): remove
-#define V8_ALLOW_ACCESS_TO_RAW_HANDLE_CONSTRUCTOR
-#define V8_ALLOW_ACCESS_TO_PERSISTENT_IMPLICIT
-#define V8_ALLOW_ACCESS_TO_PERSISTENT_ARROW
-
#include "v8.h"
#include "api.h"
@@ -1034,6 +1029,7 @@
// variable return values
static bool fast_return_value_bool = false;
static bool fast_return_value_void_is_null = false;
+static bool fast_return_value_object_is_empty = false;
template<>
void FastReturnValueCallback<int32_t>(
@@ -1077,7 +1073,9 @@
template<>
void FastReturnValueCallback<Object>(
const v8::FunctionCallbackInfo<v8::Value>& info) {
- info.GetReturnValue().Set(Object::New());
+ v8::Handle<v8::Object> object;
+ if (!fast_return_value_object_is_empty) object = Object::New();
+ info.GetReturnValue().Set(object);
}
template<typename T>
@@ -1124,8 +1122,13 @@
CHECK(value->IsUndefined());
}
}
+ // check handles
+ fast_return_value_object_is_empty = false;
value = TestFastReturnValues<Object>();
CHECK(value->IsObject());
+ fast_return_value_object_is_empty = true;
+ value = TestFastReturnValues<Object>();
+ CHECK(value->IsUndefined());
}
@@ -2782,71 +2785,75 @@
v8::Persistent<String> global;
{
v8::HandleScope scope(isolate);
- Local<String> str = v8_str("str");
- global = v8::Persistent<String>::New(isolate, str);
+ global.Reset(isolate, v8_str("str"));
}
- CHECK_EQ(global->Length(), 3);
- global.Dispose(isolate);
-
{
v8::HandleScope scope(isolate);
- Local<String> str = v8_str("str");
- global = v8::Persistent<String>::New(isolate, str);
+ CHECK_EQ(v8::Local<String>::New(isolate, global)->Length(), 3);
}
- CHECK_EQ(global->Length(), 3);
- global.Dispose(isolate);
+ global.Dispose();
+ global.Clear();
+ {
+ v8::HandleScope scope(isolate);
+ global.Reset(isolate, v8_str("str"));
+ }
+ {
+ v8::HandleScope scope(isolate);
+ CHECK_EQ(v8::Local<String>::New(isolate, global)->Length(), 3);
+ }
+ global.Dispose();
}
THREADED_TEST(ResettingGlobalHandle) {
v8::Isolate* isolate = v8::Isolate::GetCurrent();
- v8::internal::GlobalHandles* global_handles = NULL;
- int initial_handle_count = 0;
v8::Persistent<String> global;
{
v8::HandleScope scope(isolate);
- Local<String> str = v8_str("str");
- global_handles =
- reinterpret_cast<v8::internal::Isolate*>(isolate)->global_handles();
- initial_handle_count = global_handles->NumberOfGlobalHandles();
- global = v8::Persistent<String>::New(isolate, str);
+ global.Reset(isolate, v8_str("str"));
}
- CHECK_EQ(global->Length(), 3);
- CHECK_EQ(global_handles->NumberOfGlobalHandles(), initial_handle_count + 1);
+ v8::internal::GlobalHandles* global_handles =
+ reinterpret_cast<v8::internal::Isolate*>(isolate)->global_handles();
+ int initial_handle_count = global_handles->NumberOfGlobalHandles();
{
v8::HandleScope scope(isolate);
- Local<String> str = v8_str("longer");
- global.Reset(isolate, str);
+ CHECK_EQ(v8::Local<String>::New(isolate, global)->Length(), 3);
}
- CHECK_EQ(global->Length(), 6);
- CHECK_EQ(global_handles->NumberOfGlobalHandles(), initial_handle_count + 1);
- global.Dispose(isolate);
+ {
+ v8::HandleScope scope(isolate);
+ global.Reset(isolate, v8_str("longer"));
+ }
CHECK_EQ(global_handles->NumberOfGlobalHandles(), initial_handle_count);
+ {
+ v8::HandleScope scope(isolate);
+ CHECK_EQ(v8::Local<String>::New(isolate, global)->Length(), 6);
+ }
+ global.Dispose(isolate);
+ CHECK_EQ(global_handles->NumberOfGlobalHandles(), initial_handle_count - 1);
}
THREADED_TEST(ResettingGlobalHandleToEmpty) {
v8::Isolate* isolate = v8::Isolate::GetCurrent();
- v8::internal::GlobalHandles* global_handles = NULL;
- int initial_handle_count = 0;
v8::Persistent<String> global;
{
v8::HandleScope scope(isolate);
- Local<String> str = v8_str("str");
- global_handles =
- reinterpret_cast<v8::internal::Isolate*>(isolate)->global_handles();
- initial_handle_count = global_handles->NumberOfGlobalHandles();
- global = v8::Persistent<String>::New(isolate, str);
+ global.Reset(isolate, v8_str("str"));
}
- CHECK_EQ(global->Length(), 3);
- CHECK_EQ(global_handles->NumberOfGlobalHandles(), initial_handle_count + 1);
+ v8::internal::GlobalHandles* global_handles =
+ reinterpret_cast<v8::internal::Isolate*>(isolate)->global_handles();
+ int initial_handle_count = global_handles->NumberOfGlobalHandles();
+ {
+ v8::HandleScope scope(isolate);
+ CHECK_EQ(v8::Local<String>::New(isolate, global)->Length(), 3);
+ }
{
v8::HandleScope scope(isolate);
Local<String> empty;
global.Reset(isolate, empty);
}
CHECK(global.IsEmpty());
- CHECK_EQ(global_handles->NumberOfGlobalHandles(), initial_handle_count);
+ CHECK_EQ(global_handles->NumberOfGlobalHandles(), initial_handle_count - 1);
}
@@ -2861,7 +2868,7 @@
global_handles =
reinterpret_cast<v8::internal::Isolate*>(isolate)->global_handles();
initial_handle_count = global_handles->NumberOfGlobalHandles();
- global = v8::Persistent<String>::New(isolate, str);
+ global.Reset(isolate, str);
}
CHECK_EQ(global_handles->NumberOfGlobalHandles(), initial_handle_count + 1);
String* str = global.ClearAndLeak();
@@ -2897,7 +2904,7 @@
static void WeakPointerCallback(v8::Isolate* isolate,
- Persistent<Object>* handle,
+ Persistent<Value>* handle,
WeakCallCounter* counter) {
CHECK_EQ(1234, counter->id());
counter->increment();
@@ -2905,128 +2912,47 @@
}
-THREADED_TEST(OldApiObjectGroups) {
- LocalContext env;
- v8::Isolate* iso = env->GetIsolate();
- HandleScope scope(iso);
-
- Persistent<Object> g1s1;
- Persistent<Object> g1s2;
- Persistent<Object> g1c1;
- Persistent<Object> g2s1;
- Persistent<Object> g2s2;
- Persistent<Object> g2c1;
-
- WeakCallCounter counter(1234);
-
- {
- HandleScope scope(iso);
- g1s1 = Persistent<Object>::New(iso, Object::New());
- g1s2 = Persistent<Object>::New(iso, Object::New());
- g1c1 = Persistent<Object>::New(iso, Object::New());
- g1s1.MakeWeak(iso, &counter, &WeakPointerCallback);
- g1s2.MakeWeak(iso, &counter, &WeakPointerCallback);
- g1c1.MakeWeak(iso, &counter, &WeakPointerCallback);
-
- g2s1 = Persistent<Object>::New(iso, Object::New());
- g2s2 = Persistent<Object>::New(iso, Object::New());
- g2c1 = Persistent<Object>::New(iso, Object::New());
- g2s1.MakeWeak(iso, &counter, &WeakPointerCallback);
- g2s2.MakeWeak(iso, &counter, &WeakPointerCallback);
- g2c1.MakeWeak(iso, &counter, &WeakPointerCallback);
- }
-
- Persistent<Object> root = Persistent<Object>::New(iso, g1s1); // make a root.
-
- // Connect group 1 and 2, make a cycle.
- CHECK(g1s2->Set(0, Handle<Object>(*g2s2)));
- CHECK(g2s1->Set(0, Handle<Object>(*g1s1)));
-
- {
- Persistent<Value> g1_objects[] = { g1s1, g1s2 };
- Persistent<Value> g1_children[] = { g1c1 };
- Persistent<Value> g2_objects[] = { g2s1, g2s2 };
- Persistent<Value> g2_children[] = { g2c1 };
- V8::AddObjectGroup(g1_objects, 2);
- V8::AddImplicitReferences(g1s1, g1_children, 1);
- V8::AddObjectGroup(g2_objects, 2);
- V8::AddImplicitReferences(g2s1, g2_children, 1);
- }
- // Do a single full GC, ensure incremental marking is stopped.
- HEAP->CollectAllGarbage(i::Heap::kAbortIncrementalMarkingMask);
-
- // All object should be alive.
- CHECK_EQ(0, counter.NumberOfWeakCalls());
-
- // Weaken the root.
- root.MakeWeak(iso, &counter, &WeakPointerCallback);
- // But make children strong roots---all the objects (except for children)
- // should be collectable now.
- g1c1.ClearWeak(iso);
- g2c1.ClearWeak(iso);
-
- // Groups are deleted, rebuild groups.
- {
- Persistent<Value> g1_objects[] = { g1s1, g1s2 };
- Persistent<Value> g1_children[] = { g1c1 };
- Persistent<Value> g2_objects[] = { g2s1, g2s2 };
- Persistent<Value> g2_children[] = { g2c1 };
- V8::AddObjectGroup(g1_objects, 2);
- V8::AddImplicitReferences(g1s1, g1_children, 1);
- V8::AddObjectGroup(g2_objects, 2);
- V8::AddImplicitReferences(g2s1, g2_children, 1);
- }
-
- HEAP->CollectAllGarbage(i::Heap::kAbortIncrementalMarkingMask);
-
- // All objects should be gone. 5 global handles in total.
- CHECK_EQ(5, counter.NumberOfWeakCalls());
-
- // And now make children weak again and collect them.
- g1c1.MakeWeak(iso, &counter, &WeakPointerCallback);
- g2c1.MakeWeak(iso, &counter, &WeakPointerCallback);
-
- HEAP->CollectAllGarbage(i::Heap::kAbortIncrementalMarkingMask);
- CHECK_EQ(7, counter.NumberOfWeakCalls());
-}
-
-
THREADED_TEST(ApiObjectGroups) {
LocalContext env;
v8::Isolate* iso = env->GetIsolate();
HandleScope scope(iso);
- Persistent<Object> g1s1;
- Persistent<Object> g1s2;
- Persistent<Object> g1c1;
- Persistent<Object> g2s1;
- Persistent<Object> g2s2;
- Persistent<Object> g2c1;
+ Persistent<Value> g1s1;
+ Persistent<Value> g1s2;
+ Persistent<Value> g1c1;
+ Persistent<Value> g2s1;
+ Persistent<Value> g2s2;
+ Persistent<Value> g2c1;
WeakCallCounter counter(1234);
{
HandleScope scope(iso);
- g1s1 = Persistent<Object>::New(iso, Object::New());
- g1s2 = Persistent<Object>::New(iso, Object::New());
- g1c1 = Persistent<Object>::New(iso, Object::New());
+ g1s1.Reset(iso, Object::New());
+ g1s2.Reset(iso, Object::New());
+ g1c1.Reset(iso, Object::New());
g1s1.MakeWeak(iso, &counter, &WeakPointerCallback);
g1s2.MakeWeak(iso, &counter, &WeakPointerCallback);
g1c1.MakeWeak(iso, &counter, &WeakPointerCallback);
- g2s1 = Persistent<Object>::New(iso, Object::New());
- g2s2 = Persistent<Object>::New(iso, Object::New());
- g2c1 = Persistent<Object>::New(iso, Object::New());
+ g2s1.Reset(iso, Object::New());
+ g2s2.Reset(iso, Object::New());
+ g2c1.Reset(iso, Object::New());
g2s1.MakeWeak(iso, &counter, &WeakPointerCallback);
g2s2.MakeWeak(iso, &counter, &WeakPointerCallback);
g2c1.MakeWeak(iso, &counter, &WeakPointerCallback);
}
- Persistent<Object> root = Persistent<Object>::New(iso, g1s1); // make a root.
+ Persistent<Value> root(iso, g1s1); // make a root.
// Connect group 1 and 2, make a cycle.
- CHECK(g1s2->Set(0, Local<Value>(*g2s2)));
- CHECK(g2s1->Set(0, Local<Value>(*g1s1)));
+ {
+ HandleScope scope(iso);
+ CHECK(Local<Object>::New(iso, g1s2.As<Object>())->
+ Set(0, Local<Value>(*g2s2)));
+ CHECK(Local<Object>::New(iso, g2s1.As<Object>())->
+ Set(0, Local<Value>(*g1s1)));
+ }
{
UniqueId id1(reinterpret_cast<intptr_t>(*g1s1));
@@ -3079,112 +3005,6 @@
}
-THREADED_TEST(OldApiObjectGroupsCycle) {
- LocalContext env;
- v8::Isolate* iso = env->GetIsolate();
- HandleScope scope(iso);
-
- WeakCallCounter counter(1234);
-
- Persistent<Object> g1s1;
- Persistent<Object> g1s2;
- Persistent<Object> g2s1;
- Persistent<Object> g2s2;
- Persistent<Object> g3s1;
- Persistent<Object> g3s2;
- Persistent<Object> g4s1;
- Persistent<Object> g4s2;
-
- {
- HandleScope scope(iso);
- g1s1 = Persistent<Object>::New(iso, Object::New());
- g1s2 = Persistent<Object>::New(iso, Object::New());
- g1s1.MakeWeak(iso, &counter, &WeakPointerCallback);
- g1s2.MakeWeak(iso, &counter, &WeakPointerCallback);
- CHECK(g1s1.IsWeak(iso));
- CHECK(g1s2.IsWeak(iso));
-
- g2s1 = Persistent<Object>::New(iso, Object::New());
- g2s2 = Persistent<Object>::New(iso, Object::New());
- g2s1.MakeWeak(iso, &counter, &WeakPointerCallback);
- g2s2.MakeWeak(iso, &counter, &WeakPointerCallback);
- CHECK(g2s1.IsWeak(iso));
- CHECK(g2s2.IsWeak(iso));
-
- g3s1 = Persistent<Object>::New(iso, Object::New());
- g3s2 = Persistent<Object>::New(iso, Object::New());
- g3s1.MakeWeak(iso, &counter, &WeakPointerCallback);
- g3s2.MakeWeak(iso, &counter, &WeakPointerCallback);
- CHECK(g3s1.IsWeak(iso));
- CHECK(g3s2.IsWeak(iso));
-
- g4s1 = Persistent<Object>::New(iso, Object::New());
- g4s2 = Persistent<Object>::New(iso, Object::New());
- g4s1.MakeWeak(iso, &counter, &WeakPointerCallback);
- g4s2.MakeWeak(iso, &counter, &WeakPointerCallback);
- CHECK(g4s1.IsWeak(iso));
- CHECK(g4s2.IsWeak(iso));
- }
-
- Persistent<Object> root = Persistent<Object>::New(iso, g1s1); // make a root.
-
- // Connect groups. We're building the following cycle:
- // G1: { g1s1, g2s1 }, g1s1 implicitly references g2s1, ditto for other
- // groups.
- {
- Persistent<Value> g1_objects[] = { g1s1, g1s2 };
- Persistent<Value> g1_children[] = { g2s1 };
- Persistent<Value> g2_objects[] = { g2s1, g2s2 };
- Persistent<Value> g2_children[] = { g3s1 };
- Persistent<Value> g3_objects[] = { g3s1, g3s2 };
- Persistent<Value> g3_children[] = { g4s1 };
- Persistent<Value> g4_objects[] = { g4s1, g4s2 };
- Persistent<Value> g4_children[] = { g1s1 };
- V8::AddObjectGroup(g1_objects, 2);
- V8::AddImplicitReferences(g1s1, g1_children, 1);
- V8::AddObjectGroup(g2_objects, 2);
- V8::AddImplicitReferences(g2s1, g2_children, 1);
- V8::AddObjectGroup(g3_objects, 2);
- V8::AddImplicitReferences(g3s1, g3_children, 1);
- V8::AddObjectGroup(iso, g4_objects, 2);
- V8::AddImplicitReferences(g4s1, g4_children, 1);
- }
- // Do a single full GC
- HEAP->CollectAllGarbage(i::Heap::kAbortIncrementalMarkingMask);
-
- // All object should be alive.
- CHECK_EQ(0, counter.NumberOfWeakCalls());
-
- // Weaken the root.
- root.MakeWeak(iso, &counter, &WeakPointerCallback);
-
- // Groups are deleted, rebuild groups.
- {
- Persistent<Value> g1_objects[] = { g1s1, g1s2 };
- Persistent<Value> g1_children[] = { g2s1 };
- Persistent<Value> g2_objects[] = { g2s1, g2s2 };
- Persistent<Value> g2_children[] = { g3s1 };
- Persistent<Value> g3_objects[] = { g3s1, g3s2 };
- Persistent<Value> g3_children[] = { g4s1 };
- Persistent<Value> g4_objects[] = { g4s1, g4s2 };
- Persistent<Value> g4_children[] = { g1s1 };
- V8::AddObjectGroup(g1_objects, 2);
- V8::AddImplicitReferences(g1s1, g1_children, 1);
- V8::AddObjectGroup(g2_objects, 2);
- V8::AddImplicitReferences(g2s1, g2_children, 1);
- V8::AddObjectGroup(g3_objects, 2);
- V8::AddImplicitReferences(g3s1, g3_children, 1);
- V8::AddObjectGroup(g4_objects, 2);
- V8::AddImplicitReferences(g4s1, g4_children, 1);
- }
-
- HEAP->CollectAllGarbage(i::Heap::kAbortIncrementalMarkingMask);
-
- // All objects should be gone. 9 global handles in total.
- CHECK_EQ(9, counter.NumberOfWeakCalls());
-}
-
-
THREADED_TEST(ApiObjectGroupsCycle) {
LocalContext env;
v8::Isolate* iso = env->GetIsolate();
@@ -3192,47 +3012,47 @@
WeakCallCounter counter(1234);
- Persistent<Object> g1s1;
- Persistent<Object> g1s2;
- Persistent<Object> g2s1;
- Persistent<Object> g2s2;
- Persistent<Object> g3s1;
- Persistent<Object> g3s2;
- Persistent<Object> g4s1;
- Persistent<Object> g4s2;
+ Persistent<Value> g1s1;
+ Persistent<Value> g1s2;
+ Persistent<Value> g2s1;
+ Persistent<Value> g2s2;
+ Persistent<Value> g3s1;
+ Persistent<Value> g3s2;
+ Persistent<Value> g4s1;
+ Persistent<Value> g4s2;
{
HandleScope scope(iso);
- g1s1 = Persistent<Object>::New(iso, Object::New());
- g1s2 = Persistent<Object>::New(iso, Object::New());
+ g1s1.Reset(iso, Object::New());
+ g1s2.Reset(iso, Object::New());
g1s1.MakeWeak(iso, &counter, &WeakPointerCallback);
g1s2.MakeWeak(iso, &counter, &WeakPointerCallback);
CHECK(g1s1.IsWeak(iso));
CHECK(g1s2.IsWeak(iso));
- g2s1 = Persistent<Object>::New(iso, Object::New());
- g2s2 = Persistent<Object>::New(iso, Object::New());
+ g2s1.Reset(iso, Object::New());
+ g2s2.Reset(iso, Object::New());
g2s1.MakeWeak(iso, &counter, &WeakPointerCallback);
g2s2.MakeWeak(iso, &counter, &WeakPointerCallback);
CHECK(g2s1.IsWeak(iso));
CHECK(g2s2.IsWeak(iso));
- g3s1 = Persistent<Object>::New(iso, Object::New());
- g3s2 = Persistent<Object>::New(iso, Object::New());
+ g3s1.Reset(iso, Object::New());
+ g3s2.Reset(iso, Object::New());
g3s1.MakeWeak(iso, &counter, &WeakPointerCallback);
g3s2.MakeWeak(iso, &counter, &WeakPointerCallback);
CHECK(g3s1.IsWeak(iso));
CHECK(g3s2.IsWeak(iso));
- g4s1 = Persistent<Object>::New(iso, Object::New());
- g4s2 = Persistent<Object>::New(iso, Object::New());
+ g4s1.Reset(iso, Object::New());
+ g4s2.Reset(iso, Object::New());
g4s1.MakeWeak(iso, &counter, &WeakPointerCallback);
g4s2.MakeWeak(iso, &counter, &WeakPointerCallback);
CHECK(g4s1.IsWeak(iso));
CHECK(g4s2.IsWeak(iso));
}
- Persistent<Object> root = Persistent<Object>::New(iso, g1s1); // make a root.
+ Persistent<Value> root(iso, g1s1); // make a root.
// Connect groups. We're building the following cycle:
// G1: { g1s1, g2s1 }, g1s1 implicitly references g2s1, ditto for other
@@ -3295,103 +3115,6 @@
// TODO(mstarzinger): This should be a THREADED_TEST but causes failures
// on the buildbots, so was made non-threaded for the time being.
-TEST(OldApiObjectGroupsCycleForScavenger) {
- i::FLAG_stress_compaction = false;
- i::FLAG_gc_global = false;
- LocalContext env;
- v8::Isolate* iso = env->GetIsolate();
- HandleScope scope(iso);
-
- WeakCallCounter counter(1234);
-
- Persistent<Object> g1s1;
- Persistent<Object> g1s2;
- Persistent<Object> g2s1;
- Persistent<Object> g2s2;
- Persistent<Object> g3s1;
- Persistent<Object> g3s2;
-
- {
- HandleScope scope(iso);
- g1s1 = Persistent<Object>::New(iso, Object::New());
- g1s2 = Persistent<Object>::New(iso, Object::New());
- g1s1.MakeWeak(iso, &counter, &WeakPointerCallback);
- g1s2.MakeWeak(iso, &counter, &WeakPointerCallback);
-
- g2s1 = Persistent<Object>::New(iso, Object::New());
- g2s2 = Persistent<Object>::New(iso, Object::New());
- g2s1.MakeWeak(iso, &counter, &WeakPointerCallback);
- g2s2.MakeWeak(iso, &counter, &WeakPointerCallback);
-
- g3s1 = Persistent<Object>::New(iso, Object::New());
- g3s2 = Persistent<Object>::New(iso, Object::New());
- g3s1.MakeWeak(iso, &counter, &WeakPointerCallback);
- g3s2.MakeWeak(iso, &counter, &WeakPointerCallback);
- }
-
- // Make a root.
- Persistent<Object> root = Persistent<Object>::New(iso, g1s1);
- root.MarkPartiallyDependent(iso);
-
- // Connect groups. We're building the following cycle:
- // G1: { g1s1, g2s1 }, g1s1 implicitly references g2s1, ditto for other
- // groups.
- {
- g1s1.MarkPartiallyDependent(iso);
- g1s2.MarkPartiallyDependent(iso);
- g2s1.MarkPartiallyDependent(iso);
- g2s2.MarkPartiallyDependent(iso);
- g3s1.MarkPartiallyDependent(iso);
- g3s2.MarkPartiallyDependent(iso);
- Persistent<Value> g1_objects[] = { g1s1, g1s2 };
- Persistent<Value> g2_objects[] = { g2s1, g2s2 };
- Persistent<Value> g3_objects[] = { g3s1, g3s2 };
- V8::AddObjectGroup(g1_objects, 2);
- g1s1->Set(v8_str("x"), Handle<Object>(*g2s1));
- V8::AddObjectGroup(g2_objects, 2);
- g2s1->Set(v8_str("x"), Handle<Object>(*g3s1));
- V8::AddObjectGroup(g3_objects, 2);
- g3s1->Set(v8_str("x"), Handle<Object>(*g1s1));
- }
-
- HEAP->CollectGarbage(i::NEW_SPACE);
-
- // All objects should be alive.
- CHECK_EQ(0, counter.NumberOfWeakCalls());
-
- // Weaken the root.
- root.MakeWeak(iso, &counter, &WeakPointerCallback);
- root.MarkPartiallyDependent(iso);
-
- v8::Isolate* isolate = v8::Isolate::GetCurrent();
- // Groups are deleted, rebuild groups.
- {
- g1s1.MarkPartiallyDependent(isolate);
- g1s2.MarkPartiallyDependent(isolate);
- g2s1.MarkPartiallyDependent(isolate);
- g2s2.MarkPartiallyDependent(isolate);
- g3s1.MarkPartiallyDependent(isolate);
- g3s2.MarkPartiallyDependent(isolate);
- Persistent<Value> g1_objects[] = { g1s1, g1s2 };
- Persistent<Value> g2_objects[] = { g2s1, g2s2 };
- Persistent<Value> g3_objects[] = { g3s1, g3s2 };
- V8::AddObjectGroup(g1_objects, 2);
- g1s1->Set(v8_str("x"), Handle<Object>(*g2s1));
- V8::AddObjectGroup(g2_objects, 2);
- g2s1->Set(v8_str("x"), Handle<Object>(*g3s1));
- V8::AddObjectGroup(g3_objects, 2);
- g3s1->Set(v8_str("x"), Handle<Object>(*g1s1));
- }
-
- HEAP->CollectGarbage(i::NEW_SPACE);
-
- // All objects should be gone. 7 global handles in total.
- CHECK_EQ(7, counter.NumberOfWeakCalls());
-}
-
-
-// TODO(mstarzinger): This should be a THREADED_TEST but causes failures
-// on the buildbots, so was made non-threaded for the time being.
TEST(ApiObjectGroupsCycleForScavenger) {
i::FLAG_stress_compaction = false;
i::FLAG_gc_global = false;
@@ -3401,39 +3124,40 @@
WeakCallCounter counter(1234);
- Persistent<Object> g1s1;
- Persistent<Object> g1s2;
- Persistent<Object> g2s1;
- Persistent<Object> g2s2;
- Persistent<Object> g3s1;
- Persistent<Object> g3s2;
+ Persistent<Value> g1s1;
+ Persistent<Value> g1s2;
+ Persistent<Value> g2s1;
+ Persistent<Value> g2s2;
+ Persistent<Value> g3s1;
+ Persistent<Value> g3s2;
{
HandleScope scope(iso);
- g1s1 = Persistent<Object>::New(iso, Object::New());
- g1s2 = Persistent<Object>::New(iso, Object::New());
+ g1s1.Reset(iso, Object::New());
+ g1s2.Reset(iso, Object::New());
g1s1.MakeWeak(iso, &counter, &WeakPointerCallback);
g1s2.MakeWeak(iso, &counter, &WeakPointerCallback);
- g2s1 = Persistent<Object>::New(iso, Object::New());
- g2s2 = Persistent<Object>::New(iso, Object::New());
+ g2s1.Reset(iso, Object::New());
+ g2s2.Reset(iso, Object::New());
g2s1.MakeWeak(iso, &counter, &WeakPointerCallback);
g2s2.MakeWeak(iso, &counter, &WeakPointerCallback);
- g3s1 = Persistent<Object>::New(iso, Object::New());
- g3s2 = Persistent<Object>::New(iso, Object::New());
+ g3s1.Reset(iso, Object::New());
+ g3s2.Reset(iso, Object::New());
g3s1.MakeWeak(iso, &counter, &WeakPointerCallback);
g3s2.MakeWeak(iso, &counter, &WeakPointerCallback);
}
// Make a root.
- Persistent<Object> root = Persistent<Object>::New(iso, g1s1);
+ Persistent<Value> root(iso, g1s1);
root.MarkPartiallyDependent(iso);
// Connect groups. We're building the following cycle:
// G1: { g1s1, g2s1 }, g1s1 implicitly references g2s1, ditto for other
// groups.
{
+ HandleScope handle_scope(iso);
g1s1.MarkPartiallyDependent(iso);
g1s2.MarkPartiallyDependent(iso);
g2s1.MarkPartiallyDependent(iso);
@@ -3442,13 +3166,16 @@
g3s2.MarkPartiallyDependent(iso);
iso->SetObjectGroupId(g1s1, UniqueId(1));
iso->SetObjectGroupId(g1s2, UniqueId(1));
- g1s1->Set(v8_str("x"), Local<Value>(*g2s1));
+ Local<Object>::New(iso, g1s1.As<Object>())->Set(v8_str("x"),
+ Local<Value>(*g2s1));
iso->SetObjectGroupId(g2s1, UniqueId(2));
iso->SetObjectGroupId(g2s2, UniqueId(2));
- g2s1->Set(v8_str("x"), Local<Value>(*g3s1));
+ Local<Object>::New(iso, g2s1.As<Object>())->Set(v8_str("x"),
+ Local<Value>(*g3s1));
iso->SetObjectGroupId(g3s1, UniqueId(3));
iso->SetObjectGroupId(g3s2, UniqueId(3));
- g3s1->Set(v8_str("x"), Local<Value>(*g1s1));
+ Local<Object>::New(iso, g3s1.As<Object>())->Set(v8_str("x"),
+ Local<Value>(*g1s1));
}
v8::internal::Heap* heap = reinterpret_cast<v8::internal::Isolate*>(
@@ -3465,6 +3192,7 @@
v8::Isolate* isolate = v8::Isolate::GetCurrent();
// Groups are deleted, rebuild groups.
{
+ HandleScope handle_scope(iso);
g1s1.MarkPartiallyDependent(isolate);
g1s2.MarkPartiallyDependent(isolate);
g2s1.MarkPartiallyDependent(isolate);
@@ -3473,13 +3201,16 @@
g3s2.MarkPartiallyDependent(isolate);
iso->SetObjectGroupId(g1s1, UniqueId(1));
iso->SetObjectGroupId(g1s2, UniqueId(1));
- g1s1->Set(v8_str("x"), Local<Value>(*g2s1));
+ Local<Object>::New(iso, g1s1.As<Object>())->Set(v8_str("x"),
+ Local<Value>(*g2s1));
iso->SetObjectGroupId(g2s1, UniqueId(2));
iso->SetObjectGroupId(g2s2, UniqueId(2));
- g2s1->Set(v8_str("x"), Local<Value>(*g3s1));
+ Local<Object>::New(iso, g2s1.As<Object>())->Set(v8_str("x"),
+ Local<Value>(*g3s1));
iso->SetObjectGroupId(g3s1, UniqueId(3));
iso->SetObjectGroupId(g3s2, UniqueId(3));
- g3s1->Set(v8_str("x"), Local<Value>(*g1s1));
+ Local<Object>::New(iso, g3s1.As<Object>())->Set(v8_str("x"),
+ Local<Value>(*g1s1));
}
heap->CollectGarbage(i::NEW_SPACE);
@@ -4618,8 +4349,7 @@
CHECK(!v8::False()->StrictEquals(v8::Undefined()));
v8::Handle<v8::Object> obj = v8::Object::New();
- v8::Persistent<v8::Object> alias =
- v8::Persistent<v8::Object>::New(isolate, obj);
+ v8::Persistent<v8::Object> alias(isolate, obj);
CHECK(alias->StrictEquals(obj));
alias.Dispose(isolate);
}
@@ -4919,7 +4649,7 @@
CHECK_EQ(info.Data(), v8_str("donut"));
CHECK_EQ(name, v8_str("x"));
CHECK(xValue.IsEmpty());
- xValue = v8::Persistent<Value>::New(info.GetIsolate(), value);
+ xValue.Reset(info.GetIsolate(), value);
}
@@ -4935,7 +4665,7 @@
script->Run();
CHECK_EQ(v8_num(4), Handle<Value>(*xValue));
xValue.Dispose(context->GetIsolate());
- xValue = v8::Persistent<Value>();
+ xValue.Clear();
}
}
@@ -4952,7 +4682,7 @@
script->Run();
CHECK_EQ(v8_num(4), Handle<Value>(*xValue));
xValue.Dispose(context->GetIsolate());
- xValue = v8::Persistent<Value>();
+ xValue.Clear();
}
}
@@ -5815,15 +5545,14 @@
static inline void PersistentHandles(v8::Isolate* isolate) {
USE(PersistentHandles);
Local<String> str = v8_str("foo");
- v8::Persistent<String> p_str = v8::Persistent<String>::New(isolate, str);
- USE(p_str);
+ v8::Persistent<String> p_str(isolate, str);
+ p_str.Dispose();
Local<Script> scr = Script::Compile(v8_str(""));
- v8::Persistent<Script> p_scr = v8::Persistent<Script>::New(isolate, scr);
- USE(p_scr);
+ v8::Persistent<Script> p_scr(isolate, scr);
+ p_scr.Dispose();
Local<ObjectTemplate> templ = ObjectTemplate::New();
- v8::Persistent<ObjectTemplate> p_templ =
- v8::Persistent<ObjectTemplate>::New(isolate, templ);
- USE(p_templ);
+ v8::Persistent<ObjectTemplate> p_templ(isolate, templ);
+ p_templ.Dispose();
}
@@ -6327,10 +6056,7 @@
explicit Whammy(v8::Isolate* isolate) : cursor_(0), isolate_(isolate) { }
~Whammy() { script_.Dispose(isolate_); }
v8::Handle<Script> getScript() {
- if (script_.IsEmpty()) {
- script_ = v8::Persistent<Script>::New(isolate_,
- v8_compile("({}).blammo"));
- }
+ if (script_.IsEmpty()) script_.Reset(isolate_, v8_compile("({}).blammo"));
return Local<Script>(*script_);
}
@@ -6354,11 +6080,9 @@
Whammy* whammy =
static_cast<Whammy*>(v8::Handle<v8::External>::Cast(info.Data())->Value());
- v8::Persistent<v8::Object> prev = whammy->objects_[whammy->cursor_];
+ v8::Persistent<v8::Object>& prev = whammy->objects_[whammy->cursor_];
v8::Handle<v8::Object> obj = v8::Object::New();
- v8::Persistent<v8::Object> global =
- v8::Persistent<v8::Object>::New(info.GetIsolate(), obj);
if (!prev.IsEmpty()) {
prev->Set(v8_str("next"), obj);
prev.MakeWeak<Value, Snorkel>(info.GetIsolate(),
@@ -6366,7 +6090,7 @@
&HandleWeakReference);
whammy->objects_[whammy->cursor_].Clear();
}
- whammy->objects_[whammy->cursor_] = global;
+ whammy->objects_[whammy->cursor_].Reset(info.GetIsolate(), obj);
whammy->cursor_ = (whammy->cursor_ + 1) % Whammy::kObjectCount;
return whammy->getScript()->Run();
}
@@ -6419,8 +6143,8 @@
{
v8::HandleScope handle_scope(iso);
- object_a = v8::Persistent<v8::Object>::New(iso, v8::Object::New());
- object_b = v8::Persistent<v8::Object>::New(iso, v8::Object::New());
+ object_a.Reset(iso, v8::Object::New());
+ object_b.Reset(iso, v8::Object::New());
}
bool object_a_disposed = false;
@@ -6484,7 +6208,7 @@
v8::Persistent<v8::Object> object;
{
v8::HandleScope handle_scope(isolate);
- object = v8::Persistent<v8::Object>::New(isolate, v8::Object::New());
+ object.Reset(isolate, v8::Object::New());
}
bool disposed = false;
object.MakeWeak(isolate, &disposed, gc_forcing_callback[inner_gc]);
@@ -6513,7 +6237,7 @@
v8::Persistent<v8::Object> object;
{
v8::HandleScope handle_scope(isolate);
- object = v8::Persistent<v8::Object>::New(isolate, v8::Object::New());
+ object.Reset(isolate, v8::Object::New());
object->Set(v8_str("x"), v8::Integer::New(1));
v8::Local<String> y_str = v8_str("y");
object->Set(y_str, y_str);
@@ -12056,7 +11780,7 @@
v8::HandleScope scope(args.GetIsolate());
v8::Handle<Value> value = CompileRun(code);
CHECK(value.IsEmpty());
- return v8_str("foo");
+ return scope.Close(v8_str("foo"));
}
}
@@ -12224,7 +11948,7 @@
v8::Persistent<v8::Value>* handle,
void*) {
v8::HandleScope scope(isolate);
- bad_handle = v8::Persistent<v8::Object>::New(isolate, some_object);
+ bad_handle.Reset(isolate, some_object);
handle->Dispose(isolate);
}
@@ -12236,9 +11960,9 @@
v8::Persistent<v8::Object> handle1, handle2;
{
v8::HandleScope scope(isolate);
- some_object = v8::Persistent<v8::Object>::New(isolate, v8::Object::New());
- handle1 = v8::Persistent<v8::Object>::New(isolate, v8::Object::New());
- handle2 = v8::Persistent<v8::Object>::New(isolate, v8::Object::New());
+ some_object.Reset(isolate, v8::Object::New());
+ handle1.Reset(isolate, v8::Object::New());
+ handle2.Reset(isolate, v8::Object::New());
}
// Note: order is implementation dependent alas: currently
// global handle nodes are processed by PostGarbageCollectionProcessing
@@ -12270,11 +11994,11 @@
v8::Persistent<v8::Object> handle1, handle2;
{
v8::HandleScope scope(isolate);
- handle1 = v8::Persistent<v8::Object>::New(isolate, v8::Object::New());
- handle2 = v8::Persistent<v8::Object>::New(isolate, v8::Object::New());
+ handle1.Reset(isolate, v8::Object::New());
+ handle2.Reset(isolate, v8::Object::New());
}
handle1.MakeWeak<v8::Value, void>(isolate, NULL, DisposeAndForceGcCallback);
- to_be_disposed = handle2;
+ to_be_disposed.Reset(isolate, handle2);
HEAP->CollectAllGarbage(i::Heap::kNoGCFlags);
}
@@ -12300,9 +12024,9 @@
v8::Persistent<v8::Object> handle1, handle2, handle3;
{
v8::HandleScope scope(isolate);
- handle3 = v8::Persistent<v8::Object>::New(isolate, v8::Object::New());
- handle2 = v8::Persistent<v8::Object>::New(isolate, v8::Object::New());
- handle1 = v8::Persistent<v8::Object>::New(isolate, v8::Object::New());
+ handle3.Reset(isolate, v8::Object::New());
+ handle2.Reset(isolate, v8::Object::New());
+ handle1.Reset(isolate, v8::Object::New());
}
handle2.MakeWeak<v8::Value, void>(isolate, NULL, DisposingCallback);
handle3.MakeWeak<v8::Value, void>(isolate, NULL, HandleCreatingCallback);
@@ -12761,8 +12485,7 @@
v8::HandleScope inner(isolate);
v8::Handle<v8::ObjectTemplate> local = v8::ObjectTemplate::New();
local->SetInternalFieldCount(1);
- templ =
- v8::Persistent<v8::ObjectTemplate>::New(isolate, inner.Close(local));
+ templ.Reset(isolate, inner.Close(local));
}
v8::Handle<v8::Object> result = templ->NewInstance();
CHECK_EQ(1, result->InternalFieldCount());
@@ -16017,8 +15740,13 @@
"}\n"
"foo();\n"
"}\n"
- "eval('(' + outer +')()//@ sourceURL=eval_url');";
- CHECK(CompileRun(source)->IsUndefined());
+ "eval('(' + outer +')()%s');";
+
+ i::ScopedVector<char> code(1024);
+ i::OS::SNPrintF(code, source, "//# sourceURL=eval_url");
+ CHECK(CompileRun(code.start())->IsUndefined());
+ i::OS::SNPrintF(code, source, "//@ sourceURL=eval_url");
+ CHECK(CompileRun(code.start())->IsUndefined());
}
@@ -16058,9 +15786,13 @@
"}\n"
"foo();\n"
"}\n"
- "outer()\n"
- "//@ sourceURL=source_url";
- CHECK(CompileRunWithOrigin(source, "url", 0, 1)->IsUndefined());
+ "outer()\n%s";
+
+ i::ScopedVector<char> code(1024);
+ i::OS::SNPrintF(code, source, "//# sourceURL=source_url");
+ CHECK(CompileRunWithOrigin(code.start(), "url", 0, 1)->IsUndefined());
+ i::OS::SNPrintF(code, source, "//@ sourceURL=source_url");
+ CHECK(CompileRunWithOrigin(code.start(), "url", 0, 1)->IsUndefined());
}
@@ -16100,9 +15832,13 @@
"}\n"
"foo();\n"
"}\n"
- "outer()\n"
- "//@ sourceURL=source_url";
- CHECK(CompileRunWithOrigin(source, "url", 0, 0)->IsUndefined());
+ "outer()\n%s";
+
+ i::ScopedVector<char> code(1024);
+ i::OS::SNPrintF(code, source, "//# sourceURL=source_url");
+ CHECK(CompileRunWithOrigin(code.start(), "url", 0, 0)->IsUndefined());
+ i::OS::SNPrintF(code, source, "//@ sourceURL=source_url");
+ CHECK(CompileRunWithOrigin(code.start(), "url", 0, 0)->IsUndefined());
}
static void CreateGarbageInOldSpace() {
@@ -17782,23 +17518,32 @@
class Visitor42 : public v8::PersistentHandleVisitor {
public:
- explicit Visitor42(v8::Persistent<v8::Object> object)
+ explicit Visitor42(v8::Persistent<v8::Object>* object)
: counter_(0), object_(object) { }
+#ifdef V8_USE_OLD_STYLE_PERSISTENT_HANDLE_VISITORS
virtual void VisitPersistentHandle(Persistent<Value> value,
uint16_t class_id) {
- if (class_id == 42) {
- CHECK(value->IsObject());
- v8::Persistent<v8::Object> visited =
- v8::Persistent<v8::Object>::Cast(value);
- CHECK_EQ(42, visited.WrapperClassId(v8::Isolate::GetCurrent()));
- CHECK_EQ(Handle<Value>(*object_), Handle<Value>(*visited));
- ++counter_;
- }
+ VisitPersistentHandle(&value, class_id);
+ }
+#endif
+
+ virtual void VisitPersistentHandle(Persistent<Value>* value,
+ uint16_t class_id) {
+ if (class_id != 42) return;
+ CHECK_EQ(42, value->WrapperClassId());
+ v8::Isolate* isolate = v8::Isolate::GetCurrent();
+ v8::HandleScope handle_scope(isolate);
+ v8::Handle<v8::Value> handle = v8::Local<v8::Value>::New(isolate, *value);
+ v8::Handle<v8::Value> object =
+ v8::Local<v8::Object>::New(isolate, *object_);
+ CHECK(handle->IsObject());
+ CHECK_EQ(Handle<Object>::Cast(handle), object);
+ ++counter_;
}
int counter_;
- v8::Persistent<v8::Object> object_;
+ v8::Persistent<v8::Object>* object_;
};
@@ -17806,13 +17551,12 @@
LocalContext context;
v8::Isolate* isolate = context->GetIsolate();
v8::HandleScope scope(isolate);
- v8::Persistent<v8::Object> object =
- v8::Persistent<v8::Object>::New(isolate, v8::Object::New());
+ v8::Persistent<v8::Object> object(isolate, v8::Object::New());
CHECK_EQ(0, object.WrapperClassId(isolate));
object.SetWrapperClassId(isolate, 42);
CHECK_EQ(42, object.WrapperClassId(isolate));
- Visitor42 visitor(object);
+ Visitor42 visitor(&object);
v8::V8::VisitHandlesWithClassIds(&visitor);
CHECK_EQ(1, visitor.counter_);
@@ -17824,8 +17568,7 @@
LocalContext context;
v8::Isolate* isolate = context->GetIsolate();
v8::HandleScope scope(isolate);
- v8::Persistent<v8::Object> object =
- v8::Persistent<v8::Object>::New(isolate, v8::Object::New());
+ v8::Persistent<v8::Object> object(isolate, v8::Object::New());
CHECK_EQ(0, object.WrapperClassId(isolate));
object.SetWrapperClassId(isolate, 65535);
CHECK_EQ(65535, object.WrapperClassId(isolate));
@@ -17837,21 +17580,19 @@
LocalContext context;
v8::Isolate* isolate = context->GetIsolate();
v8::HandleScope scope(isolate);
- v8::Persistent<v8::Object> object1 =
- v8::Persistent<v8::Object>::New(isolate, v8::Object::New());
+ v8::Persistent<v8::Object> object1(isolate, v8::Object::New());
CHECK_EQ(0, object1.WrapperClassId(isolate));
object1.SetWrapperClassId(isolate, 42);
CHECK_EQ(42, object1.WrapperClassId(isolate));
HEAP->CollectAllGarbage(i::Heap::kNoGCFlags);
- v8::Persistent<v8::Object> object2 =
- v8::Persistent<v8::Object>::New(isolate, v8::Object::New());
+ v8::Persistent<v8::Object> object2(isolate, v8::Object::New());
CHECK_EQ(0, object2.WrapperClassId(isolate));
object2.SetWrapperClassId(isolate, 42);
CHECK_EQ(42, object2.WrapperClassId(isolate));
- Visitor42 visitor(object2);
+ Visitor42 visitor(&object2);
v8::V8::VisitHandlesForPartialDependence(isolate, &visitor);
CHECK_EQ(1, visitor.counter_);
diff --git a/test/cctest/test-heap.cc b/test/cctest/test-heap.cc
index 1122fa9..1f1b357 100644
--- a/test/cctest/test-heap.cc
+++ b/test/cctest/test-heap.cc
@@ -3107,3 +3107,19 @@
isolate->handle_scope_implementer()->Iterate(&visitor);
deferred.Detach();
}
+
+
+TEST(IncrementalMarkingStepMakesBigProgressWithLargeObjects) {
+ CcTest::InitializeVM();
+ v8::HandleScope scope(CcTest::isolate());
+ CompileRun("function f(n) {"
+ " var a = new Array(n);"
+ " for (var i = 0; i < n; i += 100) a[i] = i;"
+ "};"
+ "f(10 * 1024 * 1024);");
+ IncrementalMarking* marking = HEAP->incremental_marking();
+ if (marking->IsStopped()) marking->Start();
+ // This big step should be sufficient to mark the whole array.
+ marking->Step(100 * MB, IncrementalMarking::NO_GC_VIA_STACK_GUARD);
+ ASSERT(marking->IsComplete());
+}
diff --git a/test/mjsunit/allocation-site-info.js b/test/mjsunit/allocation-site-info.js
index 4560531..d718993 100644
--- a/test/mjsunit/allocation-site-info.js
+++ b/test/mjsunit/allocation-site-info.js
@@ -37,7 +37,7 @@
// support_smi_only_arrays = %HasFastSmiElements(new Array(1,2,3,4,5,6,7,8));
support_smi_only_arrays = true;
-optimize_constructed_arrays = true;
+optimize_constructed_arrays = false;
if (support_smi_only_arrays) {
print("Tests include smi-only arrays.");
diff --git a/test/mjsunit/debug-compile-event.js b/test/mjsunit/debug-compile-event.js
index 94dddfa..89a71dd 100644
--- a/test/mjsunit/debug-compile-event.js
+++ b/test/mjsunit/debug-compile-event.js
@@ -80,7 +80,7 @@
var msg = eval('(' + json + ')');
assertTrue('context' in msg.body.script);
- // Check that we pick script name from //@ sourceURL, iff present
+ // Check that we pick script name from //# sourceURL, iff present
assertEquals(current_source.indexOf('sourceURL') >= 0 ?
'myscript.js' : undefined,
event_data.script().name());
@@ -103,7 +103,7 @@
source_count += 2; // Using eval causes additional compilation event.
compileSource('JSON.parse(\'{"a":1,"b":2}\')');
// Using JSON.parse does not causes additional compilation events.
-compileSource('x=1; //@ sourceURL=myscript.js');
+compileSource('x=1; //# sourceURL=myscript.js');
// Make sure that the debug event listener was invoked.
assertFalse(exception, "exception in listener")
diff --git a/test/mjsunit/debug-set-script-source.js b/test/mjsunit/debug-set-script-source.js
index 34ae848..10ab43c 100644
--- a/test/mjsunit/debug-set-script-source.js
+++ b/test/mjsunit/debug-set-script-source.js
@@ -36,10 +36,10 @@
function listener(event, exec_state, event_data, data) {
if (event == Debug.DebugEvent.BeforeCompile) {
event_data.script().setSource(event_data.script().source() +
- " //@ sourceURL=proper_location_" + (++script_number));
+ " //# sourceURL=proper_location_" + (++script_number));
} else if (event == Debug.DebugEvent.AfterCompile) {
try {
- event_data.script().setSource("a=1 //@ sourceURL=wrong_location");
+ event_data.script().setSource("a=1 //# sourceURL=wrong_location");
} catch(e) {
exception = e;
}
diff --git a/test/mjsunit/debug-setbreakpoint.js b/test/mjsunit/debug-setbreakpoint.js
index 90dfcd1..8531c4e 100644
--- a/test/mjsunit/debug-setbreakpoint.js
+++ b/test/mjsunit/debug-setbreakpoint.js
@@ -146,7 +146,7 @@
};
eval('function h(){}');
-eval('function sourceUrlFunc() { a = 2; }\n//@ sourceURL=sourceUrlScript');
+eval('function sourceUrlFunc() { a = 2; }\n//# sourceURL=sourceUrlScript');
o = {a:function(){},b:function(){}}
diff --git a/test/mjsunit/harmony/object-observe.js b/test/mjsunit/harmony/object-observe.js
index 47b5d8c..4c75e63 100644
--- a/test/mjsunit/harmony/object-observe.js
+++ b/test/mjsunit/harmony/object-observe.js
@@ -1175,11 +1175,13 @@
]);
// Pop
-reset()
-var array = {0: 1, 1: 2, length: 2};
+reset();
+var array = [1, 2];
Object.observe(array, observer.callback);
-Array.prototype.pop.call(array);
-Array.prototype.pop.call(array);
+Array.observe(array, observer2.callback);
+array.pop();
+array.pop();
+array.pop();
Object.deliverChangeRecords(observer.callback);
observer.assertCallbackRecords([
{ object: array, name: '1', type: 'deleted', oldValue: 2 },
@@ -1187,13 +1189,20 @@
{ object: array, name: '0', type: 'deleted', oldValue: 1 },
{ object: array, name: 'length', type: 'updated', oldValue: 1 },
]);
+Object.deliverChangeRecords(observer2.callback);
+observer2.assertCallbackRecords([
+ { object: array, type: 'splice', index: 1, removed: [2], addedCount: 0 },
+ { object: array, type: 'splice', index: 0, removed: [1], addedCount: 0 }
+]);
// Shift
-reset()
-var array = {0: 1, 1: 2, length: 2};
+reset();
+var array = [1, 2];
Object.observe(array, observer.callback);
-Array.prototype.shift.call(array);
-Array.prototype.shift.call(array);
+Array.observe(array, observer2.callback);
+array.shift();
+array.shift();
+array.shift();
Object.deliverChangeRecords(observer.callback);
observer.assertCallbackRecords([
{ object: array, name: '0', type: 'updated', oldValue: 1 },
@@ -1202,32 +1211,71 @@
{ object: array, name: '0', type: 'deleted', oldValue: 2 },
{ object: array, name: 'length', type: 'updated', oldValue: 1 },
]);
+Object.deliverChangeRecords(observer2.callback);
+observer2.assertCallbackRecords([
+ { object: array, type: 'splice', index: 0, removed: [1], addedCount: 0 },
+ { object: array, type: 'splice', index: 0, removed: [2], addedCount: 0 }
+]);
// Unshift
-reset()
-var array = {0: 1, 1: 2, length: 2};
+reset();
+var array = [1, 2];
Object.observe(array, observer.callback);
-Array.prototype.unshift.call(array, 3, 4);
+Array.observe(array, observer2.callback);
+array.unshift(3, 4);
+array.unshift(5);
Object.deliverChangeRecords(observer.callback);
observer.assertCallbackRecords([
{ object: array, name: '3', type: 'new' },
+ { object: array, name: 'length', type: 'updated', oldValue: 2 },
{ object: array, name: '2', type: 'new' },
{ object: array, name: '0', type: 'updated', oldValue: 1 },
{ object: array, name: '1', type: 'updated', oldValue: 2 },
- { object: array, name: 'length', type: 'updated', oldValue: 2 },
+ { object: array, name: '4', type: 'new' },
+ { object: array, name: 'length', type: 'updated', oldValue: 4 },
+ { object: array, name: '3', type: 'updated', oldValue: 2 },
+ { object: array, name: '2', type: 'updated', oldValue: 1 },
+ { object: array, name: '1', type: 'updated', oldValue: 4 },
+ { object: array, name: '0', type: 'updated', oldValue: 3 },
+]);
+Object.deliverChangeRecords(observer2.callback);
+observer2.assertCallbackRecords([
+ { object: array, type: 'splice', index: 0, removed: [], addedCount: 2 },
+ { object: array, type: 'splice', index: 0, removed: [], addedCount: 1 }
]);
// Splice
-reset()
-var array = {0: 1, 1: 2, 2: 3, length: 3};
+reset();
+var array = [1, 2, 3];
Object.observe(array, observer.callback);
-Array.prototype.splice.call(array, 1, 1, 4, 5);
+Array.observe(array, observer2.callback);
+array.splice(1, 0, 4, 5); // 1 4 5 2 3
+array.splice(0, 2); // 5 2 3
+array.splice(1, 2, 6, 7); // 5 6 7
+array.splice(2, 0);
Object.deliverChangeRecords(observer.callback);
observer.assertCallbackRecords([
+ { object: array, name: '4', type: 'new' },
+ { object: array, name: 'length', type: 'updated', oldValue: 3 },
{ object: array, name: '3', type: 'new' },
{ object: array, name: '1', type: 'updated', oldValue: 2 },
{ object: array, name: '2', type: 'updated', oldValue: 3 },
- { object: array, name: 'length', type: 'updated', oldValue: 3 },
+
+ { object: array, name: '0', type: 'updated', oldValue: 1 },
+ { object: array, name: '1', type: 'updated', oldValue: 4 },
+ { object: array, name: '2', type: 'updated', oldValue: 5 },
+ { object: array, name: '4', type: 'deleted', oldValue: 3 },
+ { object: array, name: '3', type: 'deleted', oldValue: 2 },
+ { object: array, name: 'length', type: 'updated', oldValue: 5 },
+
+ { object: array, name: '1', type: 'updated', oldValue: 2 },
+ { object: array, name: '2', type: 'updated', oldValue: 3 },
+]);
+Object.deliverChangeRecords(observer2.callback);
+observer2.assertCallbackRecords([
+ { object: array, type: 'splice', index: 1, removed: [], addedCount: 2 },
+ { object: array, type: 'splice', index: 0, removed: [1, 4], addedCount: 0 },
+ { object: array, type: 'splice', index: 1, removed: [2, 3], addedCount: 2 },
]);
// Exercise StoreIC_ArrayLength
diff --git a/test/mjsunit/regress/regress-1853.js b/test/mjsunit/regress/regress-1853.js
index f80bade..cfafe82 100644
--- a/test/mjsunit/regress/regress-1853.js
+++ b/test/mjsunit/regress/regress-1853.js
@@ -102,13 +102,13 @@
' assertFalse(test_break_1); \n' +
' assertTrue(test_break_1); \n' +
'} \n' +
- '//@ sourceURL=testScriptOne');
+ '//# sourceURL=testScriptOne');
eval('function test2() { \n' +
' assertFalse(test_break_2); \n' +
' assertTrue(test_break_2); \n' +
'} \n' +
- '//@ sourceURL=testScriptTwo');
+ '//# sourceURL=testScriptTwo');
test1();
test2();
diff --git a/test/mjsunit/regress/regress-convert-hole.js b/test/mjsunit/regress/regress-convert-hole.js
index 1424221..1e9c3f3 100644
--- a/test/mjsunit/regress/regress-convert-hole.js
+++ b/test/mjsunit/regress/regress-convert-hole.js
@@ -27,7 +27,7 @@
// Flags: --allow-natives-syntax
-function f(test, test2, a, i) {
+function f_store(test, test2, a, i) {
var o = [0.5,1,,3];
var d;
if (test) {
@@ -42,11 +42,68 @@
return d;
}
-var a = [0, 0, 0, {}];
-f(true, false, a, 0);
-f(true, true, a, 0);
-f(false, false, a, 1);
-f(false, true, a, 1);
-%OptimizeFunctionOnNextCall(f);
-f(false, false, a, 2);
-assertEquals(undefined, a[2]);
+var a1 = [0, 0, 0, {}];
+f_store(true, false, a1, 0);
+f_store(true, true, a1, 0);
+f_store(false, false, a1, 1);
+f_store(false, true, a1, 1);
+%OptimizeFunctionOnNextCall(f_store);
+f_store(false, false, a1, 2);
+assertEquals(undefined, a1[2]);
+
+function test_arg(expected) {
+ return function(v) {
+ assertEquals(expected, v);
+ }
+}
+
+function f_call(f, test, test2, i) {
+ var o = [0.5,1,,3];
+ var d;
+ if (test) {
+ d = 1.5;
+ } else {
+ d = o[i];
+ }
+ if (test2) {
+ d += 1;
+ }
+ f(d);
+ return d;
+}
+
+f_call(test_arg(1.5), true, false, 0);
+f_call(test_arg(2.5), true, true, 0);
+f_call(test_arg(1), false, false, 1);
+f_call(test_arg(2), false, true, 1);
+%OptimizeFunctionOnNextCall(f_call);
+f_call(test_arg(undefined), false, false, 2);
+
+
+function f_external(test, test2, test3, a, i) {
+ var o = [0.5,1,,3];
+ var d;
+ if (test) {
+ d = 1.5;
+ } else {
+ d = o[i];
+ }
+ if (test2) {
+ d += 1;
+ }
+ if (test3) {
+ d = d|0;
+ }
+ a[d] = 1;
+ assertEquals(1, a[d]);
+ return d;
+}
+
+var a2 = new Int32Array(10);
+f_external(true, false, true, a2, 0);
+f_external(true, true, true, a2, 0);
+f_external(false, false, true, a2, 1);
+f_external(false, true, true, a2, 1);
+%OptimizeFunctionOnNextCall(f_external);
+f_external(false, false, false, a2, 2);
+assertEquals(1, a2[undefined]);
diff --git a/test/mjsunit/stack-traces.js b/test/mjsunit/stack-traces.js
index b5d58fa..4a37ee6 100644
--- a/test/mjsunit/stack-traces.js
+++ b/test/mjsunit/stack-traces.js
@@ -64,13 +64,13 @@
}
function testEvalWithSourceURL() {
- eval("function Doo() { FAIL; }; Doo();\n//@ sourceURL=res://name");
+ eval("function Doo() { FAIL; }; Doo();\n//# sourceURL=res://name");
}
function testNestedEvalWithSourceURL() {
var x = "FAIL";
var innerEval = 'function Inner() { eval(x); }\n//@ sourceURL=res://inner-eval';
- eval("function Outer() { eval(innerEval); Inner(); }; Outer();\n//@ sourceURL=res://outer-eval");
+ eval("function Outer() { eval(innerEval); Inner(); }; Outer();\n//# sourceURL=res://outer-eval");
}
function testValue() {