Looks like a tough one. First of all, the problem with synchronizing in
onDestroy is also a deadlock issue: since onDestroy is called from an
HttpSessionBindingListener, the Servlet container may have a lock on the
session itself when onDestroy is called. I don't think it's mandated by
the Servlet spec, but I don't think it's forbidden either.
Unfortunately, this means that a deadlock can occur if code in another
thread synchronizes on the page flow instance first (as in an action
method invocation), then calls a method on HttpSession that synchronizes
on the session object. Again, I don't think this is mandated by the
spec, but it happens.
Nothing strikes me off the bat, but I actually don't understand the
deadlock sequence below (I don't disagree -- just don't have enough info
to see it). What grabs the lock on
BeanContextServicesSupport.globalHierarchyLock? What prevents deadlock
in general between locking on
BeanContextServicesSupport.globalHierarchyLock and BarControlBean?
Also, how is the same JPF being *created* by two separate threads?
Rich
Eddie O'Neil wrote:
Rich/Daryl--
Hey, I've run into a thread deadlock problem in the interaction
between Controls and Page Flow that happens in the following
circumstance:
thread1: acquire lock on FooPageFlow (during FlowController.execute)
thread2: acquire lock on
BeanContextServicesSupport.globalHierarchyLock (JDK class)
thread1: acquire lock on BarControlBean (ControlBean.ensureControl())
thread2: wait for lock on BarControlBean (BeanContextSupport.remove())
thread1: wait for lock on
BeanContextServicesSupport.globalHierarchyLock (JDK class)
So, the problem is that the same JPF is being both created and
destroyed by two different threads. It appears that the "destroy"
phase of the JPF lifecycle is entirely unsynchronized and can freely
acquire Control locks without having serialized access to the Page
Flow itself.
My thought is to add a synchronization point in
JavaControlUtils.uninitJavaControls that locks on the
PageFlowManagedObject as this would serialize access to the Page Flow.
But, I seem to recall some threading issues with locking on a JPF
during the "destroy" part of the lifecycle and don't want to resurrect
those.
Any suggestions about how best to make this fix?
Eddie