Improve jiterpreter heuristic branch handling (#80275)
authorKatelyn Gadd <kg@luminance.org>
Fri, 6 Jan 2023 22:19:05 +0000 (14:19 -0800)
committerGitHub <noreply@github.com>
Fri, 6 Jan 2023 22:19:05 +0000 (14:19 -0800)
* Improve jiterpreter heuristic and bailout conditions
* Handle backwards branches in the jiterpreter heuristic

src/mono/mono/mini/interp/jiterpreter.c
src/mono/wasm/runtime/jiterpreter.ts

index 16ae18d..6c6e948 100644 (file)
@@ -687,14 +687,21 @@ jiterp_should_abort_trace (InterpInst *ins, gboolean *inside_branch_block)
 
                case MINT_BR:
                case MINT_BR_S:
-                       if (*inside_branch_block)
-                               return TRACE_CONTINUE;
+               case MINT_LEAVE:
+               case MINT_LEAVE_S:
+                       // Detect backwards branches
+                       if (ins->info.target_bb->il_offset <= ins->il_offset) {
+                               if (*inside_branch_block)
+                                       return TRACE_CONTINUE;
+                               else
+                                       return TRACE_ABORT;
+                       }
 
-                       return TRACE_ABORT;
+                       *inside_branch_block = TRUE;
+                       return TRACE_CONTINUE;
 
+               case MINT_MONO_RETHROW:
                case MINT_THROW:
-               case MINT_LEAVE:
-               case MINT_LEAVE_S:
                        if (*inside_branch_block)
                                return TRACE_CONTINUE;
 
@@ -708,7 +715,6 @@ jiterp_should_abort_trace (InterpInst *ins, gboolean *inside_branch_block)
                case MINT_CALL_HANDLER_S:
                case MINT_ENDFINALLY:
                case MINT_RETHROW:
-               case MINT_MONO_RETHROW:
                case MINT_PROF_EXIT:
                case MINT_PROF_EXIT_VOID:
                case MINT_SAFEPOINT:
index da9e650..5cf810d 100644 (file)
@@ -1175,6 +1175,9 @@ function generate_wasm_body (
                 }
                 break;
 
+            // Unlike regular rethrow which will only appear in catch blocks,
+            //  MONO_RETHROW appears to show up in other places, so it's worth conditional bailout
+            case MintOpcode.MINT_MONO_RETHROW:
             case MintOpcode.MINT_THROW:
                 // As above, only abort if this throw happens unconditionally.
                 // Otherwise, it may be in a branch that is unlikely to execute