-
Notifications
You must be signed in to change notification settings - Fork 366
[AIG] Refactor Longest Path Analysis with hierarchical path support #8630
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
Conversation
0c57de8
to
a4b1174
Compare
eee46e9
to
a29bea2
Compare
This patch refactors the Longest Path Analysis in the AIG dialect with several enhancements: - Refactor DataflowPath to use a clean variant-based API for different endpoint types - Reorganize the API with purpose-specific methods replacing complex tuple returns - Add support for hierarchical path elaboration with prependPaths methods - Introduce a unified getAllPaths convenience method to collect all timing paths - Simplify the PrintLongestPathAnalysis pass to use the new API The refactoring enables more comprehensive timing path analysis across module boundaries with proper hierarchical instance information while providing a cleaner, more maintainable API.
a29bea2
to
9fc57cb
Compare
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
LGTM
// Return input-to-internal timing paths for the given module. | ||
// These are open paths from module input ports to internal sequential | ||
// elements (registers/flip-flops). | ||
LogicalResult getOpenPathsFromInputPortsToInternal( | ||
StringAttr moduleName, SmallVectorImpl<DataflowPath> &results) const; | ||
|
||
// Return internal-to-output timing paths for the given module. | ||
// These are open paths from internal sequential elements to module output | ||
// ports. | ||
LogicalResult getOpenPathsFromInternalToOutputPorts( | ||
StringAttr moduleName, SmallVectorImpl<DataflowPath> &results) const; | ||
|
||
// Get all timing paths in the given module including both closed and open | ||
// paths. This is a convenience method that combines results from | ||
// getClosedPaths, getOpenPathsFromInputPortsToInternal, and | ||
// getOpenPathsFromInternalToOutputPorts. If elaboratedPaths is true, paths | ||
// include full hierarchical instance information. | ||
LogicalResult getAllPaths(StringAttr moduleName, | ||
SmallVectorImpl<DataflowPath> &results, | ||
bool elaboratePaths = false) const; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Nice split! Convenient to have results
be the same type everywhere.
// FanOut can be either an internal circuit object or a module output port | ||
// This flexibility allows representing both closed paths | ||
// (register-to-register) and open paths (register-to-output) in a unified way | ||
using FanOutType = std::variant<Object, std::pair<size_t, size_t>>; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Probably not really useful, but maybe a using Port = std::pair<size_t, size_t>
could help give the int pair discernible meaning?
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Good point! I created OutputPort alias as input port is represented as blockarg.
using Info = llvm::DenseMapInfo< | ||
std::tuple<circt::igraph::InstancePath, mlir::Value, size_t>>; |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Clever 😏
if (elaboratePaths) | ||
return impl->getClosedPaths<true>(moduleName, results); | ||
return impl->getClosedPaths<false>(moduleName, results); |
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Did you pull the elaborate
boolean out into a template argument to get two optimized hot loops in getClosedPaths
for the two cases? That's pretty neat 👍
There was a problem hiding this comment.
Choose a reason for hiding this comment
The reason will be displayed to describe this comment to others. Learn more.
Yep 👍
…lvm#8630) This patch refactors the Longest Path Analysis in the AIG dialect with several enhancements: - Refactor DataflowPath to use a clean variant-based API for different endpoint types - Reorganize the API with purpose-specific methods replacing complex tuple returns - Add support for hierarchical path elaboration with prependPaths methods - Introduce a unified getAllPaths convenience method to collect all timing paths - Simplify the PrintLongestPathAnalysis pass to use the new API The refactoring enables more comprehensive timing path analysis across module boundaries with proper hierarchical instance information while providing a cleaner, more maintainable API.
This patch refactors the Longest Path Analysis in the AIG dialect with several enhancements:
The refactoring enables more comprehensive timing path analysis across module boundaries with proper hierarchical instance information while providing a cleaner, more maintainable API.