when fileDelete fired ,DirWatcher it calls tail.removeCursor(c)
1,(sucess)get lock of tail --> synchronized public void removeCursor
2,get lock of rmCursors--->synchronized (rmCursors)
if at this time , TailThread has some rmCursors to handle
1,(sucess)get lock of rmCursors
2,foreach rmCursors call c.flush()
in c.flush(), it put event in SynchronousQueue,block until
another thread(PumperThread) to poll it
1,(success)poll from SynchronousQueue,
2,try get lock of tail to updateEventProcessingStats,but it can beacuse
DirWather get it!so the PumperThread block here.
Because the PumperThread blocked , the SynchronousQueue didn't release it's capacity,then the TailThread 2 step blocked ,and the TailThread didn't release the lock of rmCursors ,and the DirWather 2 step blocked .
it's a block chain.