-
Notifications
You must be signed in to change notification settings - Fork 69
New issue
Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.
By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.
Already on GitHub? Sign in to your account
Improve the semantics of asynchronous exceptions (new simpler version) #802
Improve the semantics of asynchronous exceptions (new simpler version) #802
Conversation
8704f8a
to
c478bbb
Compare
One hitch: there isn't a 32-bit x86 implementation provided for native code, and I don't really want to write one. I'm going to see again if we can stop building the 32-bit compiler. |
I'm afraid that this change would break at least a few packages, for instance:
|
98bb22d
to
893a9c4
Compare
This will be a breaking change, but I think any fix to this problem is going to suffer from the same. We decided on a simple model where users are expected to use This PR has now been updated with a 32-bit x86 implementation in |
@stedolan could you please review this, thanks. |
An earlier version of this patch (IIRC) made |
This was to make sure that async exns only appear at |
@stedolan and I discussed this. I'm going to change this PR so that |
def3b17
to
a80743b
Compare
I am basically happy with this patch, but I'm concerned with the size of the diff to the runtime. (Especially as I'm about to try to merge 4.14 into this branch!). I've made a patch that simplifies some of the mechanisms here with a view to making a smaller change, which should also aid in upstreaming this. The patch is at stedolan/flambda-backend/tree/async-exns-only-break, let me know what you think of it. Commit message copied below:
|
) * Simplify the implementation of new asynchronous exception semantics - Use a flag in Caml_state to indicate whether an async exception is being raised, removing the need for two versions of caml_start_program - Use the same flag mechanism to distinguish async exceptions on both bytecode and native code - Check that only Break may be raised from async callbacks at the point of *raising*, rather than at the point of running the callback - No longer propagate Stack_overflow from async callbacks to the main program - Simplify raising logic by removing prepare_for_raise, as there is no longer a need to carefully avoid caml_raise recursion (Now, caml_raise may trigger callbacks, which may trigger caml_raise_async, which can trigger no further work) - Revert a change to setsigmask behaviour in interp.c - caml_raise_out_of_memory_fatal renamed to caml_fatal_out_of_memory, and is always a fatal error on both bytecode and native * review * comments
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
For files owned by me
25188da695 flambda-backend: Missed comment from PR802 (ocaml-flambda#887) 9469765e42 flambda-backend: Improve the semantics of asynchronous exceptions (new simpler version) (ocaml-flambda#802) d9e4dd0c40 flambda-backend: Fix `make runtest` on NixOS (ocaml-flambda#874) 4bbde7a0f0 flambda-backend: Simpler symbols (ocaml-flambda#753) ef37262ef1 flambda-backend: Add opaqueness to Obj.magic under Flambda 2 (ocaml-flambda#862) a9616e98b1 flambda-backend: Add build system hooks for ocaml-jst (ocaml-flambda#869) 045ef67fdb flambda-backend: Allow the compiler to build with stock Dune (ocaml-flambda#868) 3cac5be480 flambda-backend: Simplify Makefile logic for natdynlinkops (ocaml-flambda#866) c5b12bf362 flambda-backend: Remove unnecessary install lines (ocaml-flambda#860) ff12bbe344 flambda-backend: Fix unused variable warning in st_stubs.c (ocaml-flambda#861) c84976c1a2 flambda-backend: Static check for noalloc: attributes (ocaml-flambda#825) ca56052e19 flambda-backend: Build system refactoring for ocaml-jst (ocaml-flambda#857) 39eb7f9b12 flambda-backend: Remove integer comparison involving nonconstant polymorphic variants (ocaml-flambda#854) c102688f57 flambda-backend: Fix soundness bug by using currying information from typing (ocaml-flambda#850) 6a96b6142d flambda-backend: Add a primitive to enable/disable the tick thread (ocaml-flambda#852) f64370bad9 flambda-backend: Make Obj.dup use a new primitive, %obj_dup (ocaml-flambda#843) 9b78eb2192 flambda-backend: Add test for ocaml-flambda#820 (include functor soundness bug) (ocaml-flambda#841) 8f24346583 flambda-backend: Add `-dtimings-precision` flag (ocaml-flambda#833) 65c2f22d33 flambda-backend: Add test for ocaml-flambda#829 (ocaml-flambda#831) 7b27a49334 flambda-backend: Follow-up PR#829 (comballoc fixes for locals) (ocaml-flambda#830) ad7ec10060 flambda-backend: Use a custom condition variable implementation (ocaml-flambda#787) 3ee650c14d flambda-backend: Fix soundness bug in include functor (ocaml-flambda#820) 2f573789f3 flambda-backend: Static check noalloc (ocaml-flambda#778) aaad625f4d flambda-backend: Emit begin/end region only when stack allocation is enabled (ocaml-flambda#812) 17c7173251 flambda-backend: Fix .cmt for included signatures (ocaml-flambda#803) e11966990e flambda-backend: Increase delays in tests/lib-threads/beat.ml (ocaml-flambda#800) ccc356dd43 flambda-backend: Prevent dynamic loading of the same .cmxs twice in private mode, etc. (ocaml-flambda#784) 14eb57247e flambda-backend: Make local extension point equivalent to local_ expression (ocaml-flambda#790) 487d11baee flambda-backend: Fix tast_iterator and tast_mapper for include functor. (ocaml-flambda#795) a50a818fa0 flambda-backend: Reduce closure allocation in List (ocaml-flambda#792) 96c9c60d5f flambda-backend: Merge ocaml-jst a775b88500 flambda-backend: Fix ocaml/otherlibs/unix 32-bit build (ocaml-flambda#767) f7c2679d77 flambda-backend: Create object files internally to avoid invoking GAS (ocaml-flambda#757) c7a46bb939 flambda-backend: Bugfix for Cmmgen.expr_size with locals (ocaml-flambda#756) b337cb6015 flambda-backend: Fix build_upstream for PR749 (ocaml-flambda#750) 8e7e81c0ab flambda-backend: Differentiate is_int primitive between generic and variant-only versions (ocaml-flambda#749) git-subtree-dir: ocaml git-subtree-split: 25188da6951ae276e561923457fcfeb95b7ef392
Supercedes #765. This works in bytecode as well as native now.
New rules of the game:
Sys.Break
orStack_overflow
may be raised from signal handlers, finalisers or memprof callbacks. (Stack_overflow
is not supposed to be raised by user code.) This helps prevent exfiltration of data from these callbacks by means of asynchronous exceptions; and avoids decisions in the runtime about how to "join" more descriptive exceptions in the case where a second asynchronous exception arises during processing of another.Exceptions will no longer be raised at allocation points; this is reflected in
Mach.operation_can_raise
. This now matches the semantics expected by Flambda 2.Note that this is a breaking change: as noted in
sys.mli
, you will likely want to useSys.with_async_exns
after usingSys.catch_break
, or else Ctrl+C interrupts will cause exceptions to be sent to the toplevel uncaught exception handler.I still need to add some more test cases, although the one I've added plus the existing testsuite seem to cover the majority of cases.
For some reason it seemed that the existing bytecode interpreter use of
sigsetjmp
(for implementing exceptions) was incorrect; these calls weren't being told to save the signal mask, but thesiglongjmp
calls were instructing restoration of such mask. This had to be fixed for this PR to work correctly; the signal masks should be restored across these jumps.@stedolan is on the hook to review this in due course. We plan to initiate some discussion upstream too.