-
Bug
-
Resolution: Fixed
-
P4
-
6
-
b09
-
generic
-
generic
-
Verified
After the run of deadlock analysis tool JMTA through the AWT sources
(java.awt and subpackages), 2486 potential deadlock have been found,
with 290 unique lock combinations. Eventually, some of them (at least
those that may happen during the normal run of Swing application) will
need to be fixed.
Below the deadlocks corresponding to one lock combination are
presented. It is the class of deadlocks that take Component.this and
AWT TreeLock in the incorrect order (because this has narrower scope,
it must always be taken AFTER TreeLock) - the code paths on which
TreeLock is taken after Component.this are presented. They deadlock
with the code in Component.setFont, which takes lock in the order
TreeLock -> this.
First line in deadlock description shows four locking statements that
participate in a deadlock. Following them, code paths (one per
thread) are presented. Please find the attached test cases (named
DeadlockN.java, where N corresponds to the deadlock number), the
deadlocks can be reproduced using these test cases.
To reproduce:
1. Compile and run a test on any platform, jdk 1.6.0
2. Press Ctrl-\ (Unix) or Ctrl-Break(Windows) to get the stack dump
3. VM will report a deadlock. If not, wait a couple of seconds and
repeat step 2.
1. ======================================================
27:[synchronized(getTreeLock())(java.awt.Component:1516),
synchronized(this)(java.awt.Component:1517),
setColumns(java.awt.TextField:311),
synchronized(getTreeLock())(java.awt.Component:2430)]
Path 1:
synchronized(getTreeLock())(java.awt.Component:1516) -> synchronized(this)(java.awt.Component:1517)
Path 2:
[ setColumns(java.awt.TextField:311) -contains> invalidate()(java.awt.TextField:318), type: void
invalidate()(java.awt.TextField:318), type: void -calls> invalidate(java.awt.Component:0)
invalidate(java.awt.Component:0) -> synchronized(getTreeLock())(java.awt.Component:2430)]
--- alternative path ---
[ setColumns(java.awt.TextField:311) -contains> invalidate()(java.awt.TextField:318), type: void
invalidate()(java.awt.TextField:318), type: void -calls> invalidate(java.awt.Component:0)
invalidate(java.awt.Component:0) -implements> invalidate(java.awt.Container:0)
invalidate(java.awt.Container:0) -contains> super.invalidate()(java.awt.Container:1418), type: void
super.invalidate()(java.awt.Container:1418), type: void -calls> invalidate(java.awt.Component:0)
invalidate(java.awt.Component:0) -> synchronized(getTreeLock())(java.awt.Component:2430)]
3. ======================================================
27:[synchronized(getTreeLock())(java.awt.Component:1516),
synchronized(this)(java.awt.Component:1517),
add(java.awt.Component:6872),
synchronized(getTreeLock())(java.awt.MenuBar:236)]
Path 1:
synchronized(getTreeLock())(java.awt.Component:1516) -> synchronized(this)(java.awt.Component:1517)
Path 2:
[ add(java.awt.Component:6872) -contains> popup.parent.remove(popup)(java.awt.Component:6874), type: void
popup.parent.remove(popup)(java.awt.Component:6874), type: void -calls> remove(java.awt.MenuContainer:0)
remove(java.awt.MenuContainer:0) -implements> remove(java.awt.MenuBar:0)
remove(java.awt.MenuBar:0) -> synchronized(getTreeLock())(java.awt.MenuBar:236)]
--- alternative path ---
[ add(java.awt.Component:6872) -contains> popup.parent.remove(popup)(java.awt.Component:6874), type: void
popup.parent.remove(popup)(java.awt.Component:6874), type: void -calls> remove(java.awt.MenuContainer:0)
remove(java.awt.MenuContainer:0) -implements> remove(java.awt.MenuBar:0)
remove(java.awt.MenuBar:0) -> synchronized(getTreeLock())(java.awt.MenuBar:236)]
4. ======================================================
27:[synchronized(getTreeLock())(java.awt.Component:1516),
synchronized(this)(java.awt.Component:1517),
add(java.awt.Component:6872),
synchronized(getTreeLock())(java.awt.Frame:866)]
Path 1:
synchronized(getTreeLock())(java.awt.Component:1516) -> synchronized(this)(java.awt.Component:1517)
Path 2:
[ add(java.awt.Component:6872) -contains> popup.parent.remove(popup)(java.awt.Component:6874), type: void
popup.parent.remove(popup)(java.awt.Component:6874), type: void -calls> remove(java.awt.MenuContainer:0)
remove(java.awt.MenuContainer:0) -implements> remove(java.awt.Frame:0)
remove(java.awt.Frame:0) -> synchronized(getTreeLock())(java.awt.Frame:866)]
--- alternative path ---
[ add(java.awt.Component:6872) -contains> popup.parent.remove(popup)(java.awt.Component:6874), type: void
popup.parent.remove(popup)(java.awt.Component:6874), type: void -calls> remove(java.awt.MenuContainer:0)
remove(java.awt.MenuContainer:0) -implements> remove(java.awt.Frame:0)
remove(java.awt.Frame:0) -> synchronized(getTreeLock())(java.awt.Frame:866)]
5. ======================================================
27:[synchronized(getTreeLock())(java.awt.Component:1516),
synchronized(this)(java.awt.Component:1517),
add(java.awt.Component:6872),
synchronized(getTreeLock())(java.awt.PopupMenu:76)]
Path 1:
synchronized(getTreeLock())(java.awt.Component:1516) -> synchronized(this)(java.awt.Component:1517)
Path 2:
[ add(java.awt.Component:6872) -contains> popup.addNotify()(java.awt.Component:6884), type: void
popup.addNotify()(java.awt.Component:6884), type: void -calls> addNotify(java.awt.PopupMenu:0)
addNotify(java.awt.PopupMenu:0) -> synchronized(getTreeLock())(java.awt.PopupMenu:76)]
8. ======================================================
27:[synchronized(getTreeLock())(java.awt.Component:1516),
synchronized(this)(java.awt.Component:1517),
remove(java.awt.Component:6895),
synchronized(getTreeLock())(java.awt.Menu:168)]
Path 1:
synchronized(getTreeLock())(java.awt.Component:1516) -> synchronized(this)(java.awt.Component:1517)
Path 2:
[ remove(java.awt.Component:6895) -contains> pmenu.removeNotify()(java.awt.Component:6901), type: void
pmenu.removeNotify()(java.awt.Component:6901), type: void -calls> removeNotify(java.awt.Menu:0)
removeNotify(java.awt.Menu:0) -> synchronized(getTreeLock())(java.awt.Menu:168)]
###@###.### 2005-2-21 10:14:32 GMT
(java.awt and subpackages), 2486 potential deadlock have been found,
with 290 unique lock combinations. Eventually, some of them (at least
those that may happen during the normal run of Swing application) will
need to be fixed.
Below the deadlocks corresponding to one lock combination are
presented. It is the class of deadlocks that take Component.this and
AWT TreeLock in the incorrect order (because this has narrower scope,
it must always be taken AFTER TreeLock) - the code paths on which
TreeLock is taken after Component.this are presented. They deadlock
with the code in Component.setFont, which takes lock in the order
TreeLock -> this.
First line in deadlock description shows four locking statements that
participate in a deadlock. Following them, code paths (one per
thread) are presented. Please find the attached test cases (named
DeadlockN.java, where N corresponds to the deadlock number), the
deadlocks can be reproduced using these test cases.
To reproduce:
1. Compile and run a test on any platform, jdk 1.6.0
2. Press Ctrl-\ (Unix) or Ctrl-Break(Windows) to get the stack dump
3. VM will report a deadlock. If not, wait a couple of seconds and
repeat step 2.
1. ======================================================
27:[synchronized(getTreeLock())(java.awt.Component:1516),
synchronized(this)(java.awt.Component:1517),
setColumns(java.awt.TextField:311),
synchronized(getTreeLock())(java.awt.Component:2430)]
Path 1:
synchronized(getTreeLock())(java.awt.Component:1516) -> synchronized(this)(java.awt.Component:1517)
Path 2:
[ setColumns(java.awt.TextField:311) -contains> invalidate()(java.awt.TextField:318), type: void
invalidate()(java.awt.TextField:318), type: void -calls> invalidate(java.awt.Component:0)
invalidate(java.awt.Component:0) -> synchronized(getTreeLock())(java.awt.Component:2430)]
--- alternative path ---
[ setColumns(java.awt.TextField:311) -contains> invalidate()(java.awt.TextField:318), type: void
invalidate()(java.awt.TextField:318), type: void -calls> invalidate(java.awt.Component:0)
invalidate(java.awt.Component:0) -implements> invalidate(java.awt.Container:0)
invalidate(java.awt.Container:0) -contains> super.invalidate()(java.awt.Container:1418), type: void
super.invalidate()(java.awt.Container:1418), type: void -calls> invalidate(java.awt.Component:0)
invalidate(java.awt.Component:0) -> synchronized(getTreeLock())(java.awt.Component:2430)]
3. ======================================================
27:[synchronized(getTreeLock())(java.awt.Component:1516),
synchronized(this)(java.awt.Component:1517),
add(java.awt.Component:6872),
synchronized(getTreeLock())(java.awt.MenuBar:236)]
Path 1:
synchronized(getTreeLock())(java.awt.Component:1516) -> synchronized(this)(java.awt.Component:1517)
Path 2:
[ add(java.awt.Component:6872) -contains> popup.parent.remove(popup)(java.awt.Component:6874), type: void
popup.parent.remove(popup)(java.awt.Component:6874), type: void -calls> remove(java.awt.MenuContainer:0)
remove(java.awt.MenuContainer:0) -implements> remove(java.awt.MenuBar:0)
remove(java.awt.MenuBar:0) -> synchronized(getTreeLock())(java.awt.MenuBar:236)]
--- alternative path ---
[ add(java.awt.Component:6872) -contains> popup.parent.remove(popup)(java.awt.Component:6874), type: void
popup.parent.remove(popup)(java.awt.Component:6874), type: void -calls> remove(java.awt.MenuContainer:0)
remove(java.awt.MenuContainer:0) -implements> remove(java.awt.MenuBar:0)
remove(java.awt.MenuBar:0) -> synchronized(getTreeLock())(java.awt.MenuBar:236)]
4. ======================================================
27:[synchronized(getTreeLock())(java.awt.Component:1516),
synchronized(this)(java.awt.Component:1517),
add(java.awt.Component:6872),
synchronized(getTreeLock())(java.awt.Frame:866)]
Path 1:
synchronized(getTreeLock())(java.awt.Component:1516) -> synchronized(this)(java.awt.Component:1517)
Path 2:
[ add(java.awt.Component:6872) -contains> popup.parent.remove(popup)(java.awt.Component:6874), type: void
popup.parent.remove(popup)(java.awt.Component:6874), type: void -calls> remove(java.awt.MenuContainer:0)
remove(java.awt.MenuContainer:0) -implements> remove(java.awt.Frame:0)
remove(java.awt.Frame:0) -> synchronized(getTreeLock())(java.awt.Frame:866)]
--- alternative path ---
[ add(java.awt.Component:6872) -contains> popup.parent.remove(popup)(java.awt.Component:6874), type: void
popup.parent.remove(popup)(java.awt.Component:6874), type: void -calls> remove(java.awt.MenuContainer:0)
remove(java.awt.MenuContainer:0) -implements> remove(java.awt.Frame:0)
remove(java.awt.Frame:0) -> synchronized(getTreeLock())(java.awt.Frame:866)]
5. ======================================================
27:[synchronized(getTreeLock())(java.awt.Component:1516),
synchronized(this)(java.awt.Component:1517),
add(java.awt.Component:6872),
synchronized(getTreeLock())(java.awt.PopupMenu:76)]
Path 1:
synchronized(getTreeLock())(java.awt.Component:1516) -> synchronized(this)(java.awt.Component:1517)
Path 2:
[ add(java.awt.Component:6872) -contains> popup.addNotify()(java.awt.Component:6884), type: void
popup.addNotify()(java.awt.Component:6884), type: void -calls> addNotify(java.awt.PopupMenu:0)
addNotify(java.awt.PopupMenu:0) -> synchronized(getTreeLock())(java.awt.PopupMenu:76)]
8. ======================================================
27:[synchronized(getTreeLock())(java.awt.Component:1516),
synchronized(this)(java.awt.Component:1517),
remove(java.awt.Component:6895),
synchronized(getTreeLock())(java.awt.Menu:168)]
Path 1:
synchronized(getTreeLock())(java.awt.Component:1516) -> synchronized(this)(java.awt.Component:1517)
Path 2:
[ remove(java.awt.Component:6895) -contains> pmenu.removeNotify()(java.awt.Component:6901), type: void
pmenu.removeNotify()(java.awt.Component:6901), type: void -calls> removeNotify(java.awt.Menu:0)
removeNotify(java.awt.Menu:0) -> synchronized(getTreeLock())(java.awt.Menu:168)]
###@###.### 2005-2-21 10:14:32 GMT