Repository: go
Issue: cmd/compile: PGO opportunities umbrella issue
Labels: NeedsInvestigation,umbrella,compiler/runtime

This issue is to track the list of PGO optimization opportunities we're considering. As we begin work on any of these, it should be broken into its own issue. We'll edit and add to this list over time.

- [x] [Inlining](https://github.com/golang/go/issues/55022)
- [x] Indirect call devirtualization: If the profile shows that a particular closure or method is by far the most common target of an indirect call, specialize the caller to check that that's the target and make a direct call if it is (possibly even inlining the target). Done modulo some follow-up work:
    - [ ] #64675
    - [ ] #64676
- [ ] Dynamic escapes on cold paths: If the profile shows that the only reason for an escape is on a cold path and the hot path does not escape an allocation, we could optimistically stack-allocate and dynamically move the allocation to the heap on the cold path.
- [ ] Stenciling: Stencil hot generic functions, possibly based on type information from the profile.
- [ ] Local basic block ordering: ordering blocks within a function to cluster hot blocks and potentially improve branch prediction (though the win of the latter on modern CPUs is small).
- [ ] Register allocation: register allocation currently uses heuristics to determine a hot path and move spills off that hot path. PGO can tell it the true hot path.
- [ ] Loop unrolling: Loop unrolling, like inlining, is a balance with binary size/i-cache footprint (also like inlining, its primary benefit on modern CPUs is enabling follow-on optimizations). We can use PGO to focus loop unrolling on hot loops, which will both have minimal impact on binary size and on compile time spent analyzing whether unrolling is worthwhile. (See #51302)
- [ ] Loop unswitching: In hot functions, loop unswitching is more likely to be worth the code size increase.
- [ ] Architecture feature check unswitching and/or function multiversioning: For architecture feature checks in hot functions, lift those feature checks, perhaps to the function level. (This is closely related to loop unswitching, but isn’t necessarily in a loop, and we know a priori that it’s safe to lift the condition.)
- [ ] Select between branches and conditional MOVs: When a condition is predictable, branches are more efficient, and when a conditional is unpredictable, conditional MOVs are more efficient. Use a profile to select between these. (Predictability is hard to get from a CPU profile, so this may require an LBR profile; however, an LBR profile doesn't capture conditional MOVs, so this may be just be impractical.)
- [ ] Function ordering: Clustering functions at a whole-binary level for better locality.
- [ ] Global block ordering: A step beyond function ordering. The basic form of this is hot/cold splitting, but it can be more aggressive than that.
- [ ] Map/slice pre-sizing: Pre-size maps and slices based on allocation site. (This requires more than a CPU profile.)
- [ ] Stack pre-sizing by site: Allocate initial stacks based on profiled stack sizes. (This requires more than a CPU profile. We already have simple runtime heuristics for this and it may be possible to do better at runtime, without a profile.)
- [ ] Lifetime allocation: Co-locate allocations with similar lifetimes by allocation site. (This also requires more than a CPU profile. This may be possible to do at runtime, but sophisticated techniques are also expensive.)
- [ ] Loop alignment: Aligning small loops can have a large performance impact, but also increases binary size. With PGO, we could do this only for hot loops. (E.g., section 3.4.1.4 of the [Intel Optimization Reference Manual](file:///home/austin/Downloads/248966-046A-software-optimization-manual.pdf))

(This list was originally based on an [old comment](https://github.com/golang/go/issues/55022#issuecomment-1245605666) of mine, and this issue is partly to surface and track this list better.)

Any basic block-level optimizations likely depend on profile discriminators (#59612).