[gjs/wip/ptomato/785657: 6/6] closure: Don't access objects when destroying context
- From: Philip Chimento <pchimento src gnome org>
- To: commits-list gnome org
- Cc:
- Subject: [gjs/wip/ptomato/785657: 6/6] closure: Don't access objects when destroying context
- Date: Wed, 23 Aug 2017 00:00:54 +0000 (UTC)
commit 28c3fec5913cbb06d90a5746da834e946c1f6346
Author: Philip Chimento <philip endlessm com>
Date: Tue Aug 22 16:55:00 2017 -0700
closure: Don't access objects when destroying context
When the JSContext is being destroyed, it's not a good idea to access
objects, since at this point they are all being destroyed as well. Check
in the closure invalidation and finalize notifiers that the context is
not being destroyed before cutting the ties to JS objects.
Also, make sure to call ExposeToActiveJS on the JS object in order to
prevent it from being dropped out of a garbage collection.
gi/closure.cpp | 20 ++++++++++++++++----
1 files changed, 16 insertions(+), 4 deletions(-)
---
diff --git a/gi/closure.cpp b/gi/closure.cpp
index 2528b13..1cd5e3c 100644
--- a/gi/closure.cpp
+++ b/gi/closure.cpp
@@ -28,6 +28,7 @@
#include <util/log.h>
#include "closure.h"
+#include "gjs/context.h"
#include "gjs/jsapi-util-root.h"
#include "gjs/jsapi-wrapper.h"
#include "gjs/mem.h"
@@ -166,10 +167,17 @@ closure_set_invalid(gpointer data,
{
Closure *self = &((GjsClosure*) closure)->priv;
- gjs_debug_closure("Invalidating signal closure %p which calls object %p",
- closure, self->obj.get());
+ GjsContext *gcx = gjs_context_get_current();
+ if (_gjs_context_destroying(gcx)) {
+ gjs_debug_closure("Invalidating signal closure %p which calls a dead "
+ "object", closure);
+ } else {
+ gjs_debug_closure("Invalidating signal closure %p which calls object "
+ "%p", closure, self->obj.get());
+ JS::ExposeObjectToActiveJS(self->obj);
+ self->obj.reset();
+ }
- self->obj.reset();
self->context = nullptr;
GJS_DEC_COUNTER(closure);
@@ -181,7 +189,11 @@ closure_finalize(gpointer data,
{
Closure *self = &((GjsClosure*) closure)->priv;
- self->~Closure();
+ /* All objects are already destroyed in the last GC when the context is
+ * destroyed. */
+ GjsContext *gcx = gjs_context_get_current();
+ if (!_gjs_context_destroying(gcx))
+ self->~Closure();
}
void
[
Date Prev][
Date Next] [
Thread Prev][
Thread Next]
[
Thread Index]
[
Date Index]
[
Author Index]