Fix inline decision reporting + noinline propagation (#87115)
authorEgor Bogatov <egorbo@gmail.com>
Thu, 8 Jun 2023 09:27:53 +0000 (11:27 +0200)
committerGitHub <noreply@github.com>
Thu, 8 Jun 2023 09:27:53 +0000 (11:27 +0200)
src/coreclr/jit/importercalls.cpp
src/coreclr/jit/inline.def
src/coreclr/jit/inlinepolicy.cpp

index 4afb8c5..86d91fa 100644 (file)
@@ -6280,12 +6280,6 @@ void Compiler::impMarkInlineCandidate(GenTree*               callNode,
 {
     if (!opts.OptEnabled(CLFLG_INLINING))
     {
-        /* XXX Mon 8/18/2008
-         * This assert is misleading.  The caller does not ensure that we have CLFLG_INLINING set before
-         * calling impMarkInlineCandidate.  However, if this assert trips it means that we're an inlinee and
-         * CLFLG_MINOPT is set.  That doesn't make a lot of sense.  If you hit this assert, work back and
-         * figure out why we did not set MAXOPT for this compile.
-         */
         assert(!compIsForInlining());
         return;
     }
@@ -6301,12 +6295,11 @@ void Compiler::impMarkInlineCandidate(GenTree*               callNode,
         assert(call->GetInlineCandidatesCount() > 0);
         for (uint8_t candidateId = 0; candidateId < call->GetInlineCandidatesCount(); candidateId++)
         {
-            InlineResult inlineResult(this, call, nullptr, "impMarkInlineCandidate", true);
+            InlineResult inlineResult(this, call, nullptr, "impMarkInlineCandidate for GDV");
 
             // Do the actual evaluation
             impMarkInlineCandidateHelper(call, candidateId, exactContextHnd, exactContextNeedsRuntimeLookup, callInfo,
                                          ilOffset, &inlineResult);
-
             // Ignore non-inlineable candidates
             // TODO: Consider keeping them to just devirtualize without inlining, at least for interface
             // calls on NativeAOT, but that requires more changes elsewhere too.
@@ -6316,12 +6309,19 @@ void Compiler::impMarkInlineCandidate(GenTree*               callNode,
                 candidateId--;
             }
         }
+
+        // None of the candidates made it, make sure the call is no longer marked as "has inline info"
+        if (call->GetInlineCandidatesCount() == 0)
+        {
+            assert(!call->IsInlineCandidate());
+            assert(!call->IsGuardedDevirtualizationCandidate());
+        }
     }
     else
     {
         const uint8_t candidatesCount = call->GetInlineCandidatesCount();
         assert(candidatesCount <= 1);
-        InlineResult inlineResult(this, call, nullptr, "impMarkInlineCandidate", true);
+        InlineResult inlineResult(this, call, nullptr, "impMarkInlineCandidate");
         impMarkInlineCandidateHelper(call, 0, exactContextHnd, exactContextNeedsRuntimeLookup, callInfo, ilOffset,
                                      &inlineResult);
     }
index b918fb6..9371e65 100644 (file)
@@ -28,7 +28,6 @@ INLINE_OBSERVATION(UNUSED_INITIAL,            bool,   "unused initial observatio
 INLINE_OBSERVATION(BAD_ARGUMENT_NUMBER,       bool,   "invalid argument number",              FATAL,       CALLEE)
 INLINE_OBSERVATION(BAD_LOCAL_NUMBER,          bool,   "invalid local number",                 FATAL,       CALLEE)
 INLINE_OBSERVATION(COMPILATION_ERROR,         bool,   "compilation error",                    FATAL,       CALLEE)
-INLINE_OBSERVATION(EXCEEDS_THRESHOLD,         bool,   "exceeds profit threshold",             FATAL,       CALLEE)
 INLINE_OBSERVATION(HAS_EH,                    bool,   "has exception handling",               FATAL,       CALLEE)
 INLINE_OBSERVATION(HAS_ENDFILTER,             bool,   "has endfilter",                        FATAL,       CALLEE)
 INLINE_OBSERVATION(HAS_ENDFINALLY,            bool,   "has endfinally",                       FATAL,       CALLEE)
@@ -132,7 +131,6 @@ INLINE_OBSERVATION(CANT_EMBED_VARARGS_COOKIE, bool,   "can't embed varargs cooki
 INLINE_OBSERVATION(CANT_CLASS_INIT,           bool,   "can't class init",                     FATAL,       CALLSITE)
 INLINE_OBSERVATION(COMPILATION_ERROR,         bool,   "compilation error",                    FATAL,       CALLSITE)
 INLINE_OBSERVATION(COMPILATION_FAILURE,       bool,   "failed to compile",                    FATAL,       CALLSITE)
-INLINE_OBSERVATION(EXCEEDS_THRESHOLD,         bool,   "exceeds profit threshold",             FATAL,       CALLSITE)
 INLINE_OBSERVATION(EXPLICIT_TAIL_PREFIX,      bool,   "explicit tail prefix",                 FATAL,       CALLSITE)
 INLINE_OBSERVATION(GENERIC_DICTIONARY_LOOKUP, bool,   "runtime dictionary lookup",            FATAL,       CALLSITE)
 INLINE_OBSERVATION(HAS_CALL_VIA_LDVIRTFTN,    bool,   "call via ldvirtftn",                   FATAL,       CALLSITE)
index 75088eb..7339419 100644 (file)
@@ -2335,7 +2335,12 @@ bool DiscretionaryPolicy::PropagateNeverToRuntime() const
     //
     switch (m_Observation)
     {
+        // Not-profitable depends on call-site:
         case InlineObservation::CALLEE_NOT_PROFITABLE_INLINE:
+            return false;
+
+        // If we mark no-returns as noinline we won't be able to recognize them
+        // as no-returns in future inlines.
         case InlineObservation::CALLEE_DOES_NOT_RETURN:
             return false;