Add an explicit API entry to notify V8 that one or more
authorkasperl@chromium.org <kasperl@chromium.org@ce2b1a6d-e550-0410-aec6-3dcde31c8c00>
Fri, 26 Feb 2010 11:51:33 +0000 (11:51 +0000)
committerkasperl@chromium.org <kasperl@chromium.org@ce2b1a6d-e550-0410-aec6-3dcde31c8c00>
Fri, 26 Feb 2010 11:51:33 +0000 (11:51 +0000)
contexts have been disposed.
Review URL: http://codereview.chromium.org/661173

git-svn-id: http://v8.googlecode.com/svn/branches/bleeding_edge@3971 ce2b1a6d-e550-0410-aec6-3dcde31c8c00

include/v8.h
src/api.cc
src/heap.cc
src/heap.h

index 13f8191..e8b19ec 100644 (file)
@@ -2473,6 +2473,13 @@ class V8EXPORT V8 {
    */
   static void LowMemoryNotification();
 
+  /**
+   * Optional notification that one or more context have been
+   * disposed. V8 may choose to collect garbage to get rid of any
+   * external memory associated with the disposed contexts.
+   */
+  static void ContextDisposedNotification();
+
  private:
   V8();
 
index dbb3d8b..05a87a6 100644 (file)
@@ -2821,6 +2821,12 @@ void v8::V8::LowMemoryNotification() {
 }
 
 
+void v8::V8::ContextDisposedNotification() {
+  if (!i::V8::IsRunning()) return;
+  i::Heap::CollectAllGarbageIfContextDisposed(true);
+}
+
+
 const char* v8::V8::GetVersion() {
   static v8::internal::EmbeddedVector<char, 128> buffer;
   v8::internal::Version::GetString(buffer);
@@ -2857,7 +2863,7 @@ Persistent<Context> v8::Context::New(
     // decide when should make a full GC.
 #else
     // Give the heap a chance to cleanup if we've disposed contexts.
-    i::Heap::CollectAllGarbageIfContextDisposed();
+    i::Heap::CollectAllGarbageIfContextDisposed(false);
 #endif
     v8::Handle<ObjectTemplate> proxy_template = global_template;
     i::Handle<i::FunctionTemplateInfo> proxy_constructor;
index 15e1b97..1282fbe 100644 (file)
@@ -371,12 +371,20 @@ void Heap::CollectAllGarbage(bool force_compaction) {
 }
 
 
-void Heap::CollectAllGarbageIfContextDisposed() {
+void Heap::CollectAllGarbageIfContextDisposed(bool notified) {
+  // If the request has ever been the result of an explicit
+  // notification, we ignore non-notified requests. This is a
+  // temporary solution to let the two ways of achieving GC at
+  // context disposal time co-exist.
+  static bool ever_notified = false;
+  if (notified) ever_notified = true;
+  if (ever_notified && !notified) return;
+
   // If the garbage collector interface is exposed through the global
   // gc() function, we avoid being clever about forcing GCs when
   // contexts are disposed and leave it to the embedder to make
   // informed decisions about when to force a collection.
-  if (!FLAG_expose_gc && context_disposed_pending_) {
+  if (!FLAG_expose_gc && (notified || context_disposed_pending_)) {
     HistogramTimerScope scope(&Counters::gc_context);
     CollectAllGarbage(false);
   }
index 5b27926..93ddedd 100644 (file)
@@ -634,7 +634,7 @@ class Heap : public AllStatic {
 
   // Performs a full garbage collection if a context has been disposed
   // since the last time the check was performed.
-  static void CollectAllGarbageIfContextDisposed();
+  static void CollectAllGarbageIfContextDisposed(bool notified);
 
   // Notify the heap that a context has been disposed.
   static void NotifyContextDisposed();