Skip to content

Swift Optimizer: add EscapeInfo, a new utility for escape analysis #42242

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

Merged
merged 5 commits into from
Apr 21, 2022

Conversation

eeckstein
Copy link
Contributor

This PR is the first step of replacing the old EscapeAnalysis with a new utility, implemented in Swift (instead of C++) and with a much simple design.
While the old EscapeAnalysis builds a connection graph, the new EscapeInfo just performs a simple def-use and use-def walk in the SIL.
The EscapeInfo does not need to analyze the whole function (like the EscapeAnalysis does), but just the relevant value which is inspected. Therefore EscapeInfo is not an Analysis which caches its result across optimization passes - it’s not needed.

To do inter-procedural escape analysis, the new compute-effects pass derives escape information for function arguments and adds those effects in the function. Those effects can then be used by EscapeInfo to get escape-information of called functions.

The EscapeInfo utility is tested with the help of the dump-escape-info and dump-addr-escape-info passes, which dump escape information for the SIL in the corresponding test files.

All the utilities and passes in this PR only compute escape information, but don't use it, yet. So, regarding the generated code it's still a NFC. The second step for completely replacing EscapeAnalysis with the new EscapeInfo is here: #39438

@eeckstein eeckstein requested a review from atrick April 7, 2022 08:32
@eeckstein eeckstein force-pushed the escapeinfo branch 3 times, most recently from 3e87303 to ce2ea6b Compare April 7, 2022 09:45
@eeckstein
Copy link
Contributor Author

@swift-ci test

3 similar comments
@eeckstein
Copy link
Contributor Author

@swift-ci test

@eeckstein
Copy link
Contributor Author

@swift-ci test

@eeckstein
Copy link
Contributor Author

@swift-ci test

@eeckstein
Copy link
Contributor Author

@swift-ci test

@eeckstein
Copy link
Contributor Author

@swift-ci test

@eeckstein
Copy link
Contributor Author

@swift-ci test linux

@eeckstein
Copy link
Contributor Author

@swift-ci smoke test

Copy link
Contributor

@atrick atrick left a comment

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

A couple of minor comments on the first 2 commits

Comment on lines 305 to 310
if k.isClassField {
neededBits = totalBits
totalBits += numBits
} else {
totalBits += numBits
if !k.isValueField { neededBits = totalBits }
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

It looks like the isClassField check should have been removed since the code already checks !isValueField.

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

isValueField is not !isClassField because .anything is not neither a class field nor a value field.
I'll add a comment.

Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

isValueField is not !isClassField because .anything is not neither a class field nor a value field.

ok, sure, but isn't isClassField a subset of !isValueField?

Comment on lines 103 to 104
/// Types for which this property is not known, e.g. generic types, it is
/// assumed that the type has not a Builtin.RawPointer.
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

I wasn't sure how to read this and suspected a typo. It could be more clear

HasRawPointer is true only for types that are known to contain Builtin.RawPointer.
It is not assumed true for generic or resilient types.

* rename `matchesAllValueFields` -> `topMatchesAnyValueField`
* add `hasSingleClassIndirection` and `hasClassProjection`
* add `popLastClassAndValuesFromTail`
…RawPointer

This is needed for the new escape analysis
It’s a replacement for the old `EscapeAnalysis`, implemented in Swift (instead of C++) and with a much simple design and implementation.
While the old EscapeAnalysis builds a connection graph, the new EscapeInfo just performs a simple def-use and use-def walk in the SIL.
The EscapeInfo does not need to analyze the whole function (like the EscapeAnalysis does), but just the relevant value which is inspected. Therefore EscapeInfo is not an `Analysis` which caches its result across optimization passes - it’s not needed.
And add test files which uses the passes for verification of EscapeInfo
The ComputeEffects pass derives escape information for function arguments and adds those effects in the function.
This needs a lot of changes in check-lines in the tests, because the effects are printed in SIL
@eeckstein
Copy link
Contributor Author

@swift-ci smoke test

@eeckstein eeckstein merged commit c05e064 into swiftlang:main Apr 21, 2022
@eeckstein eeckstein deleted the escapeinfo branch April 21, 2022 09:09
Comment on lines +956 to +961
case is DestructureStructInst, is DestructureTupleInst:
val = inst.operands[0].value
// TODO: only push the specific result index.
// But currently there is no O(0) method to get the result index
// from a result value.
p = p.popAllValueFields().push(.anyValueFields)
Copy link
Contributor

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

@eeckstein this really needs to be fixed because our goal is to migrate to destructures as much as possible for ownership forwarding. There shouldn't be any hidden downstream performance effects of one vs. the other. destructure vs. extract should be equivalent for all analysis that doesn't care about ownership! The result index is embedded in the result value. That won't work?

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

You are right. Somehow I didn't realize that. I'll change it

Copy link
Contributor Author

Choose a reason for hiding this comment

The reason will be displayed to describe this comment to others. Learn more.

done in #42571

@compnerd
Copy link
Member

This seems to have caused a regression on Windows: https://ci-external.swift.org/job/oss-swift-windows-toolchain-x86_64-vs2019/547/console

@compnerd
Copy link
Member

CC: @shahmishal the CI didnt trigger here

compnerd added a commit to compnerd/apple-swift that referenced this pull request Apr 22, 2022
This reverts commit c05e064, reversing
changes made to c1534d5.

This caused a regression on Windows.
shahmishal added a commit that referenced this pull request Apr 22, 2022
Revert "Merge pull request #42242 from eeckstein/escapeinfo"
@atrick
Copy link
Contributor

atrick commented May 9, 2022

I'm using the following design document to review the escape analysis design that was introduced in this PR:
https://gist.github.com/atrick/562c0b69b44230dd7b04e0898514d806

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

Successfully merging this pull request may close these issues.

3 participants