Open ceedubs opened 5 months ago
it seems like it should have to reraise the failure
The correct protocol for interruption is to clean resources and rethrow, never swallow a ThreadKilled. However, when I did the latest change to some of the relevant code (to not log ThreadKilled) I decided to not change the current behaviour for now, to avoid muddying the waters until we understand what's going on
To be clear to those less familiar with the context, I think that @SystemFw is referring to changes that he made in the @unison/httpserver
library, not to the Unison language itself.
@SystemFw in cases like that, where it is at the top level of a forked thread, I don't know if there is really a better option. fork
only accepts {IO}
, not Exception
, and anything that bubbles up to the top of the fork is ultimately going to be ignored or just logged.
I don't know if there is really a better option. fork only accepts {IO}, not Exception, and anything that bubbles up to the top of the fork is ultimately going to be ignored or just logged.
that's true, but if you see in the whole chain of calls from Tcp server and up there are quite a few places that call catchAll
before getting to the top of the thread.
Also, just repeating what I said on Slack wrt worst case scenario: in the current Unison model on the Haskell runtime there is no way to guarantee the release of something, if you’re unlucky enough. The primitive is :
catchAll : '{IO, Exception} a ->{IO} Either Failure a
and so if you have
res = catchAll do something
!finalizer
and you are unlucky enough, something will terminate naturally, but then interruption will hit in between res
and !finalizer
, and finalization won’t run. You cannot prevent this in any way in Unison only, it simply lacks the relevant primitive from Haskell (mask
), whilst inheriting its super granular interruption semantics.
The situation is also complicated by what the scheme runtime does, and basically I have held back from designing proper semantics because my preliminary analysis is that supporting it on both the Haskell and the Scheme runtime is nigh impossible
I just noticed that when I did a
ctrl-c
on arun
, the main thread stopped but a child thread continued to run. After trying a few variations, it seems like this happens ifcatchAll
(or something similar based ontryEval
) catches the thread killed exception. On the one hand, there's an argument for letting a thread catch the thread kill to clean up resources. But in the case of the thread being killed, it seems like it should have to reraise the failure or be shut down after a grace period or something.Here is an example: