From 94e00733bc7124a59a6651e459a1cae6752236d4 Mon Sep 17 00:00:00 2001 From: BlackMinou Date: Fri, 8 Apr 2016 20:22:21 -0400 Subject: [PATCH] Interpreter: using catch to modify abort behaviour Signed-off-by: BlackMinou --- src/interpreter/naive_interpreter.nit | 24 ++++++++++++++++++++++-- 1 file changed, 22 insertions(+), 2 deletions(-) diff --git a/src/interpreter/naive_interpreter.nit b/src/interpreter/naive_interpreter.nit index 9236d99..c70dc83 100644 --- a/src/interpreter/naive_interpreter.nit +++ b/src/interpreter/naive_interpreter.nit @@ -121,6 +121,13 @@ class NaiveInterpreter # Set this mark to skip the evaluation until a labeled statement catch it with `is_escape` var escapemark: nullable EscapeMark = null + # Is an abort being executed ? + # Set this mark to return to the last `catch` bloc or effectively aborting if there isn't any + var catch_mark = new EscapeMark + + # The count of `catch` blocs that have been encountered and can catch an abort + var catch_count = 0 + # Is a return or a break or a continue executed? # Use this function to know if you must skip the evaluation of statements fun is_escaping: Bool do return returnmark != null or escapemark != null @@ -1709,8 +1716,14 @@ end redef class AAbortExpr redef fun stmt(v) do - fatal(v, "Aborted") - exit(1) + # Abort as asked if there is no `catch` bloc + if v.catch_count <= 0 then + fatal(v, "Aborted") + exit(1) + else + # Abort mode, skipping everything until a `catch` bloc is reached + v.escapemark = v.catch_mark + end end end @@ -1754,8 +1767,15 @@ end redef class ADoExpr redef fun stmt(v) do + # If this bloc has a catch, register it in the counter + if self.n_catch != null then v.catch_count += 1 v.stmt(self.n_block) v.is_escape(self.break_mark) # Clear the break (if any) + if self.n_catch != null then + v.catch_count -= 1 + # Are we in abort mode? then this catch is executing + if v.is_escape(v.catch_mark) then v.stmt(self.n_catch) + end end end -- 1.7.9.5