6592751: EmbeddedFrame disposal is fragile and breaks clean AppContext termination
Summary: AppContext.dispose() should be ready to get exceptions during disposal of toplevels. Also now we mark windows peers as destroyed when native object has been destroyed.
Reviewed-by: art
--- a/jdk/src/share/classes/sun/awt/AppContext.java Thu Mar 13 16:19:32 2008 +0300
+++ b/jdk/src/share/classes/sun/awt/AppContext.java Thu Mar 13 16:27:20 2008 +0300
@@ -1,5 +1,5 @@
/*
- * Copyright 1998-2007 Sun Microsystems, Inc. All Rights Reserved.
+ * Copyright 1998-2008 Sun Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@@ -40,6 +40,8 @@
import java.util.Map;
import java.util.Set;
import java.util.HashSet;
+import java.util.logging.Level;
+import java.util.logging.Logger;
import java.beans.PropertyChangeSupport;
import java.beans.PropertyChangeListener;
@@ -126,6 +128,7 @@
* @author Fred Ecks
*/
public final class AppContext {
+ private static final Logger log = Logger.getLogger("sun.awt.AppContext");
/* Since the contents of an AppContext are unique to each Java
* session, this class should never be serialized. */
@@ -385,7 +388,13 @@
public void run() {
Window[] windowsToDispose = Window.getOwnerlessWindows();
for (Window w : windowsToDispose) {
- w.dispose();
+ try {
+ w.dispose();
+ } catch (Throwable t) {
+ if (log.isLoggable(Level.FINER)) {
+ log.log(Level.FINER, "exception occured while disposing app context", t);
+ }
+ }
}
AccessController.doPrivileged(new PrivilegedAction() {
public Object run() {
--- a/jdk/src/windows/classes/sun/awt/windows/WObjectPeer.java Thu Mar 13 16:19:32 2008 +0300
+++ b/jdk/src/windows/classes/sun/awt/windows/WObjectPeer.java Thu Mar 13 16:27:20 2008 +0300
@@ -1,5 +1,5 @@
/*
- * Copyright 1996-2007 Sun Microsystems, Inc. All Rights Reserved.
+ * Copyright 1996-2008 Sun Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@@ -30,8 +30,12 @@
initIDs();
}
- long pData; // The Windows handle for the native widget.
- Object target; // The associated AWT object.
+ // The Windows handle for the native widget.
+ long pData;
+ // if the native peer has been destroyed
+ boolean destroyed = false;
+ // The associated AWT object.
+ Object target;
private volatile boolean disposed;
--- a/jdk/src/windows/native/sun/windows/awt.h Thu Mar 13 16:19:32 2008 +0300
+++ b/jdk/src/windows/native/sun/windows/awt.h Thu Mar 13 16:27:20 2008 +0300
@@ -1,5 +1,5 @@
/*
- * Copyright 1996-2006 Sun Microsystems, Inc. All Rights Reserved.
+ * Copyright 1996-2008 Sun Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@@ -47,7 +47,7 @@
JNI_CHECK_NULL_GOTO(peer, "peer", where); \
pData = JNI_GET_PDATA(peer); \
if (pData == NULL) { \
- JNU_ThrowNullPointerException(env, "null pData"); \
+ THROW_NULL_PDATA_IF_NOT_DESTROYED(peer); \
goto where; \
} \
}
@@ -63,7 +63,7 @@
JNI_CHECK_NULL_RETURN(peer, "peer"); \
pData = JNI_GET_PDATA(peer); \
if (pData == NULL) { \
- JNU_ThrowNullPointerException(env, "null pData"); \
+ THROW_NULL_PDATA_IF_NOT_DESTROYED(peer); \
return; \
} \
}
@@ -96,7 +96,7 @@
JNI_CHECK_NULL_RETURN_NULL(peer, "peer"); \
pData = JNI_GET_PDATA(peer); \
if (pData == NULL) { \
- JNU_ThrowNullPointerException(env, "null pData"); \
+ THROW_NULL_PDATA_IF_NOT_DESTROYED(peer); \
return 0; \
} \
}
@@ -105,16 +105,27 @@
JNI_CHECK_NULL_RETURN_VAL(peer, "peer", val); \
pData = JNI_GET_PDATA(peer); \
if (pData == NULL) { \
- JNU_ThrowNullPointerException(env, "null pData"); \
+ THROW_NULL_PDATA_IF_NOT_DESTROYED(peer); \
return val; \
} \
}
+#define THROW_NULL_PDATA_IF_NOT_DESTROYED(peer) { \
+ jboolean destroyed = JNI_GET_DESTROYED(peer); \
+ if (destroyed != JNI_TRUE) { \
+ JNU_ThrowNullPointerException(env, "null pData"); \
+ } \
+}
+
#define JNI_GET_PDATA(peer) (PDATA) env->GetLongField(peer, AwtObject::pDataID)
+#define JNI_GET_DESTROYED(peer) env->GetBooleanField(peer, AwtObject::destroyedID)
#define JNI_SET_PDATA(peer, data) env->SetLongField(peer, \
- AwtObject::pDataID, \
- (jlong)data)
+ AwtObject::pDataID, \
+ (jlong)data)
+#define JNI_SET_DESTROYED(peer) env->SetBooleanField(peer, \
+ AwtObject::destroyedID, \
+ JNI_TRUE)
/* /NEW JNI */
/*
--- a/jdk/src/windows/native/sun/windows/awt_Component.cpp Thu Mar 13 16:19:32 2008 +0300
+++ b/jdk/src/windows/native/sun/windows/awt_Component.cpp Thu Mar 13 16:27:20 2008 +0300
@@ -5403,6 +5403,7 @@
if (m_peerObject) {
env->SetLongField(m_peerObject, AwtComponent::hwndID, 0);
JNI_SET_PDATA(m_peerObject, static_cast<PDATA>(NULL));
+ JNI_SET_DESTROYED(m_peerObject);
env->DeleteGlobalRef(m_peerObject);
m_peerObject = NULL;
}
--- a/jdk/src/windows/native/sun/windows/awt_Object.cpp Thu Mar 13 16:19:32 2008 +0300
+++ b/jdk/src/windows/native/sun/windows/awt_Object.cpp Thu Mar 13 16:27:20 2008 +0300
@@ -1,5 +1,5 @@
/*
- * Copyright 1996-2006 Sun Microsystems, Inc. All Rights Reserved.
+ * Copyright 1996-2008 Sun Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@@ -39,6 +39,7 @@
*/
jfieldID AwtObject::pDataID;
+jfieldID AwtObject::destroyedID;
jfieldID AwtObject::targetID;
jclass AwtObject::wObjectPeerClass;
jmethodID AwtObject::getPeerForTargetMID;
@@ -223,6 +224,7 @@
AwtObject::wObjectPeerClass = (jclass)env->NewGlobalRef(cls);
AwtObject::pDataID = env->GetFieldID(cls, "pData", "J");
+ AwtObject::destroyedID = env->GetFieldID(cls, "destroyed", "Z");
AwtObject::targetID = env->GetFieldID(cls, "target",
"Ljava/lang/Object;");
@@ -233,6 +235,7 @@
AwtObject::createErrorID = env->GetFieldID(cls, "createError", "Ljava/lang/Error;");
DASSERT(AwtObject::pDataID != NULL);
+ DASSERT(AwtObject::destroyedID != NULL);
DASSERT(AwtObject::targetID != NULL);
DASSERT(AwtObject::getPeerForTargetMID != NULL);
DASSERT(AwtObject::createErrorID != NULL);
--- a/jdk/src/windows/native/sun/windows/awt_Object.h Thu Mar 13 16:19:32 2008 +0300
+++ b/jdk/src/windows/native/sun/windows/awt_Object.h Thu Mar 13 16:27:20 2008 +0300
@@ -1,5 +1,5 @@
/*
- * Copyright 1996-2006 Sun Microsystems, Inc. All Rights Reserved.
+ * Copyright 1996-2008 Sun Microsystems, Inc. All Rights Reserved.
* DO NOT ALTER OR REMOVE COPYRIGHT NOTICES OR THIS FILE HEADER.
*
* This code is free software; you can redistribute it and/or modify it
@@ -51,6 +51,7 @@
/* sun.awt.windows.WObjectPeer field and method ids */
static jfieldID pDataID;
+ static jfieldID destroyedID;
static jfieldID targetID;
static jmethodID getPeerForTargetMID;