Skip to content
New issue

Have a question about this project? Sign up for a free GitHub account to open an issue and contact its maintainers and the community.

By clicking “Sign up for GitHub”, you agree to our terms of service and privacy statement. We’ll occasionally send you account related emails.

Already on GitHub? Sign in to your account

cmd/compile: escape analysis for backing arrays #42165

Open
snadrus opened this issue Oct 23, 2020 · 2 comments
Open

cmd/compile: escape analysis for backing arrays #42165

snadrus opened this issue Oct 23, 2020 · 2 comments
Milestone

Comments

@snadrus
Copy link

@snadrus snadrus commented Oct 23, 2020

Go's automatic memory management doesn't rely entirely on garbage collection. Escape analysis provides a faster solution where possible.
Lets apply escape analysis to backing arrays (the arrays behind slices).

Example

In the next example, if append grows the array, it could put the old array directly back into the free lists:

func filter(haystack []X, predicate func(X) bool) []X {
  var result []X
  for _, v := range haystack {
    if predicate(v) {
      result = append(result, v)               // result may grow many times. 
  }
  return result
}

An alternate append-grow that returns the heap memory to a thread-local free list could be proven safe.

The compiler can verify that no references to intermediate slice values survive later iterations, so there are zero references at the function end to previous backing arrays. If an intermediate was used in a function call, this would follow the regular escape analysis logic.

Collision with GC

To avoid Garbage Collection competition, these non-escaping slices could be removed from stack maps. Their capturing func would need an implicit defer-type behavior to add them to GC when returned.

 defer func(){ retValGC = retValNoEscape }()      // added by compiler. Shouldn't affect line numbers, etc.

This also enables panic() scenarios to not leak. This is perhaps too literal as all that would happen would be a stack map reference.

Result

Garbage Collection would be reduced and Go programs would use considerably less memory-over-time (derivative). No language changes would be necessary, and the Go1 promise is kept. Potentially the same work will be completed with less total CPU.

Maps' private slices should be able to benefit from this too as they only grow when a single thread is writing and no other activity is taking-place. I doubt escape analysis can determine this, so it may need to be hard-coded.

Future

Future advances in Escape Analysis would help more cases of Go's automatic memory management to have a minimal footprint in all but the most especially-complex cases where Garbage Collection is the most reasonable solution.

@gopherbot gopherbot added this to the Proposal milestone Oct 23, 2020
@gopherbot gopherbot added the Proposal label Oct 23, 2020
@ianlancetaylor
Copy link
Contributor

@ianlancetaylor ianlancetaylor commented Oct 23, 2020

There is no user-visible change suggested here, so no need to use the proposal process. I will change to a suggestion for the compiler.

@ianlancetaylor ianlancetaylor changed the title Proposal: Escape analysis for backing arrays cmd/compile: escape analysis for backing arrays Oct 23, 2020
@ianlancetaylor ianlancetaylor modified the milestones: Proposal, Backlog Oct 23, 2020
@mdempsky
Copy link
Member

@mdempsky mdempsky commented Nov 1, 2020

I think this requires flow-sensitive analysis, which escape analysis isn't currently setup for. This might be more feasible once escape analysis moves to SSA.

It also requires the runtime to prove a "free" operation that the compiler could emit calls to for allocations that are known to no longer be in use.

Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Projects
None yet
Linked pull requests

Successfully merging a pull request may close this issue.

None yet
4 participants
You can’t perform that action at this time.