src/Pure/ML-Systems/smlnj.ML
changeset 26084 a7475459c740
parent 25732 308315ee2b6d
child 26220 d34b68c21f9a
equal deleted inserted replaced
26083:abb3f8dd66dc 26084:a7475459c740
   137 
   137 
   138 (** interrupts **)
   138 (** interrupts **)
   139 
   139 
   140 exception Interrupt;
   140 exception Interrupt;
   141 
   141 
   142 fun ignore_interrupt f x =
   142 local
   143   let
   143 
   144     val old_handler = Signals.setHandler (Signals.sigINT, Signals.IGNORE);
   144 fun change_signal new_handler f x =
   145     val result = Exn.capture f x;
   145   let
       
   146     val old_handler = Signals.setHandler (Signals.sigINT, new_handler);
       
   147     val result = Exn.capture (f old_handler) x;
   146     val _ = Signals.setHandler (Signals.sigINT, old_handler);
   148     val _ = Signals.setHandler (Signals.sigINT, old_handler);
   147   in Exn.release result end;
   149   in Exn.release result end;
   148 
   150 
   149 fun raise_interrupt f x =
   151 in
   150   let
   152 
   151     val interrupted = ref false;
   153 fun interruptible (f: 'a -> 'b) x =
   152     val result = ref (Exn.Result ());
   154   let
       
   155     val result = ref (Exn.Exn Interrupt: 'b Exn.result);
   153     val old_handler = Signals.inqHandler Signals.sigINT;
   156     val old_handler = Signals.inqHandler Signals.sigINT;
   154   in
   157   in
   155     SMLofNJ.Cont.callcc (fn cont =>
   158     SMLofNJ.Cont.callcc (fn cont =>
   156       (Signals.setHandler (Signals.sigINT, Signals.HANDLER (fn _ => (interrupted := true; cont)));
   159       (Signals.setHandler (Signals.sigINT, Signals.HANDLER (fn _ => cont));
   157       result := Exn.capture f x));
   160         result := Exn.capture f x));
   158     Signals.setHandler (Signals.sigINT, old_handler);
   161     Signals.setHandler (Signals.sigINT, old_handler);
   159     if ! interrupted then raise Interrupt else Exn.release (! result)
   162     Exn.release (! result)
   160   end;
   163   end;
       
   164 
       
   165 fun uninterruptible f =
       
   166   change_signal Signals.IGNORE
       
   167     (fn old_handler => f (fn g => change_signal old_handler (fn _ => g)));
       
   168 
       
   169 end;
   161 
   170 
   162 
   171 
   163 (* basis library fixes *)
   172 (* basis library fixes *)
   164 
   173 
   165 structure TextIO =
   174 structure TextIO =