@@ -63,6 +63,7 @@ and admin_instr' =
6363 | Invoke of func_inst
6464 | Trapping of string
6565 | Returning of value stack
66+ | ReturningInvoke of value stack * func_inst
6667 | Breaking of int32 * value stack
6768 | Throwing of Tag. t * value stack
6869 | Rethrowing of int32 * (admin_instr -> admin_instr )
@@ -214,6 +215,21 @@ let rec step (c : config) : config =
214215 else
215216 vs, [Invoke func @@ e.at]
216217
218+ | ReturnCall x , vs ->
219+ (match (step {c with code = (vs, [Plain (Call x) @@ e.at])}).code with
220+ | vs' , [{it = Invoke a; at}] -> vs', [ReturningInvoke (vs', a) @@ at]
221+ | _ -> assert false
222+ )
223+
224+ | ReturnCallIndirect (x , y ), vs ->
225+ (match
226+ (step {c with code = (vs, [Plain (CallIndirect (x, y)) @@ e.at])}).code
227+ with
228+ | vs' , [{it = Invoke a; at}] -> vs', [ReturningInvoke (vs', a) @@ at]
229+ | vs' , [{it = Trapping s; at}] -> vs', [Trapping s @@ at]
230+ | _ -> assert false
231+ )
232+
217233 | Throw x , vs ->
218234 let t = tag frame.inst x in
219235 let FuncType (ts, _) = Tag. type_of t in
@@ -629,7 +645,8 @@ let rec step (c : config) : config =
629645 | Trapping msg , vs ->
630646 assert false
631647
632- | Returning vs' , vs ->
648+ | Returning _, vs
649+ | ReturningInvoke _ , vs ->
633650 Crash. error e.at " undefined frame"
634651
635652 | Breaking (k , vs' ), vs ->
@@ -653,6 +670,9 @@ let rec step (c : config) : config =
653670 | Label (n , es0 , (vs' , {it = Returning vs0 ; at} :: es' )), vs ->
654671 vs, [Returning vs0 @@ at]
655672
673+ | Label (n , es0 , (vs' , {it = ReturningInvoke (vs0 , f ); at} :: es' )), vs ->
674+ vs, [ReturningInvoke (vs0, f) @@ at]
675+
656676 | Label (n , es0 , (vs' , {it = Breaking (0l , vs0 ); at} :: es' )), vs ->
657677 take n vs0 e.at @ vs, List. map plain es0
658678
@@ -684,6 +704,10 @@ let rec step (c : config) : config =
684704 | Frame (n , frame' , (vs' , {it = Returning vs0 ; at} :: es' )), vs ->
685705 take n vs0 e.at @ vs, []
686706
707+ | Frame (n , frame' , (vs' , {it = ReturningInvoke (vs0 , f ); at} :: es' )), vs ->
708+ let FuncType (ins, out) = Func. type_of f in
709+ take (Lib.List32. length ins) vs0 e.at @ vs, [Invoke f @@ at]
710+
687711 | Frame (n , frame' , (vs' , {it = Throwing (a , vs0 ); at} :: es' )), vs ->
688712 vs, [Throwing (a, vs0) @@ at]
689713
@@ -694,7 +718,7 @@ let rec step (c : config) : config =
694718 | Catch (n , cts , ca , (vs' , [] )), vs ->
695719 vs' @ vs, []
696720
697- | Catch (n , cts , ca , (vs' , ({it = Trapping _ | Breaking _ | Returning _ | Delegating _ ; at} as e ) :: es' )), vs ->
721+ | Catch (n , cts , ca , (vs' , ({it = Trapping _ | Breaking _ | Returning _ | ReturningInvoke _ | Delegating _ ; at} as e ) :: es' )), vs ->
698722 vs, [e]
699723
700724 | Catch (n , cts , ca , (vs' , {it = Rethrowing (k , cont ); at} :: es' )), vs ->
@@ -719,7 +743,7 @@ let rec step (c : config) : config =
719743 | Caught (n , a , vs0 , (vs' , [] )), vs ->
720744 vs' @ vs, []
721745
722- | Caught (n , a , vs0 , (vs' , ({it = Trapping _ | Breaking _ | Returning _ | Throwing _ | Delegating _ ; at} as e ) :: es' )), vs ->
746+ | Caught (n , a , vs0 , (vs' , ({it = Trapping _ | Breaking _ | Returning _ | ReturningInvoke _ | Throwing _ | Delegating _ ; at} as e ) :: es' )), vs ->
723747 vs, [e]
724748
725749 | Caught (n , a , vs0 , (vs' , {it = Rethrowing (0l , cont ); at} :: es' )), vs ->
@@ -735,7 +759,7 @@ let rec step (c : config) : config =
735759 | Delegate (l , (vs' , [] )), vs ->
736760 vs' @ vs, []
737761
738- | Delegate (l , (vs' , ({it = Trapping _ | Breaking _ | Returning _ | Rethrowing _ | Delegating _ ; at} as e ) :: es' )), vs ->
762+ | Delegate (l , (vs' , ({it = Trapping _ | Breaking _ | Returning _ | ReturningInvoke _ | Rethrowing _ | Delegating _ ; at} as e ) :: es' )), vs ->
739763 vs, [e]
740764
741765 | Delegate (l , (vs' , {it = Throwing (a , vs0 ); at} :: es' )), vs ->
0 commit comments