@@ -330,7 +330,9 @@ type IncrementalOptimizationEnv =
330330 // Recursively bound vars. If an sub-expression that is a candidate for method splitting
331331 // contains any of these variables then don't split it, for fear of mucking up tailcalls.
332332 // See FSharp 1.0 bug 2892
333- dontSplitVars: ValMap < unit >
333+ dontSplitVars: ValMap < unit >
334+ // Disable method splitting in loops
335+ inLoop: bool
334336 /// The Val for the function binding being generated, if any.
335337 functionVal: ( Val * Tast .ValReprInfo ) option
336338 typarInfos: ( Typar * TypeValueInfo ) list
@@ -343,6 +345,7 @@ type IncrementalOptimizationEnv =
343345 typarInfos = []
344346 functionVal = None
345347 dontSplitVars = ValMap.Empty
348+ inLoop = false
346349 localExternalVals = LayeredMap.Empty
347350 globalModuleInfos = LayeredMap.Empty }
348351
@@ -1825,8 +1828,8 @@ and OptimizeExprOp cenv env (op,tyargs,args,m) =
18251828 MightMakeCriticalTailcall = false
18261829 Info = UnknownValue }
18271830 (* Handle these as special cases since mutables are allowed inside their bodies *)
1828- | TOp.While ( spWhile, marker),_,[ Expr.Lambda(_,_,_,[_], e1,_,_); Expr.Lambda(_,_,_,[_], e2,_,_)] -> OptimizeWhileLoop cenv env ( spWhile, marker, e1, e2, m)
1829- | TOp.For( spStart, dir),_,[ Expr.Lambda(_,_,_,[_], e1,_,_); Expr.Lambda(_,_,_,[_], e2,_,_); Expr.Lambda(_,_,_,[ v], e3,_,_)] -> OptimizeFastIntegerForLoop cenv env ( spStart, v, e1, dir, e2, e3, m)
1831+ | TOp.While ( spWhile, marker),_,[ Expr.Lambda(_,_,_,[_], e1,_,_); Expr.Lambda(_,_,_,[_], e2,_,_)] -> OptimizeWhileLoop cenv { env with inLoop = true } ( spWhile, marker, e1, e2, m)
1832+ | TOp.For( spStart, dir),_,[ Expr.Lambda(_,_,_,[_], e1,_,_); Expr.Lambda(_,_,_,[_], e2,_,_); Expr.Lambda(_,_,_,[ v], e3,_,_)] -> OptimizeFastIntegerForLoop cenv { env with inLoop = true } ( spStart, v, e1, dir, e2, e3, m)
18301833 | TOp.TryFinally( spTry, spFinally),[ resty],[ Expr.Lambda(_,_,_,[_], e1,_,_); Expr.Lambda(_,_,_,[_], e2,_,_)] -> OptimizeTryFinally cenv env ( spTry, spFinally, e1, e2, m, resty)
18311834 | TOp.TryCatch( spTry, spWith),[ resty],[ Expr.Lambda(_,_,_,[_], e1,_,_); Expr.Lambda(_,_,_,[ vf], ef,_,_); Expr.Lambda(_,_,_,[ vh], eh,_,_)] -> OptimizeTryCatch cenv env ( e1, vf, ef, vh, eh, m, resty, spTry, spWith)
18321835 | TOp.TraitCall( traitInfo),[], args -> OptimizeTraitCall cenv env ( traitInfo, args, m)
@@ -2770,6 +2773,7 @@ and ComputeSplitToMethodCondition flag threshold cenv env (e,einfo) =
27702773 // REVIEW: This should only apply to methods that actually make self-tailcalls (tested further below).
27712774 // Old comment "don't mess with taking guaranteed tailcalls if used with --no-tailcalls!"
27722775 cenv.emitTailcalls &&
2776+ not env.inLoop &&
27732777 einfo.FunctionSize >= threshold &&
27742778
27752779 // We can only split an expression out as a method if certain conditions are met.
0 commit comments