Patricia Shanahan wrote:
I have questions about the TaskManager remove(Task) method. Trying to end work by any means other than run to completion is always a bit tricky.

In the event of a remove call for an active Task, TaskManager issues an interrupt unless the call is in the task's thread. It also removes the Task from its bookkeeping.

In the current implementation, removal from the ArrayList immediately stops the removed task from blocking later tasks that need to runAfter it. That can let a dependent task start running before the removed task notices the interrupt. That could be bad if, for example, they share data that is being protected through the runAfter system.

Perhaps a hashmap might be used to store tasks that are pending removal, so they can be left on the queue until the removed task has been interrupted?


It will get worse in any performance improved TaskManager. One of the performance issues is a tendency to use only one thread, regardless of the number of runnable tasks or the constructor parameters, if there are a lot of runAfter dependencies. I plan to fix that so that the number of threads will be in accordance with the constructor parameters.

The other issue is that a task that ignores the interrupt can keep possession of its thread, indefinitely, despite a remove call. Since we only create a bounded number of threads, that could effectively kill the TaskManager. To what extent are TaskManager instances shared by tasks whose run methods don't have the same trust characteristics?

Currently TaskManager is only used internally, so the trust should be the same between tasks, although I like the idea of a singleton TaskManager and did mention it earlier, that doesn't suit the current implementation. We could put an AccessController permission check in TaskManager before a task is placed into the queue?


Patricia


Reply via email to