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

Legacy code removal in pass manager #11448

Merged
merged 15 commits into from
Jan 10, 2024

Conversation

nkanazawa1989
Copy link
Contributor

@nkanazawa1989 nkanazawa1989 commented Dec 21, 2023

Summary

This PR is a followup of #10127 in which several methods and classes were deprecated. This PR removes deprecated code, and introduces new pattern to build pass pipeline.

Details and comments

The main goal of this PR is to remove following pattern to a build pass pipeline.

pm = PassManager()
pm.append([my_pass1, my_pass2, my_pass3], condition=callable1, do_while=callable2)

This pattern implicitly calls a factory function to create flow controller instances and wrap the passes my_pass* with them, by digesting the controller namespace defined in FlowController class attributes. This also internally tracks the group of passes appended together along with the specified controller names, with the extra overhead of memory footprint., i.e. PassManager._pass_sets.

With this PR, this append pattern is almost eliminated. Users now need to explicitly instantiate the controller class instead of using the syntactic sugar above. This drastically simplifies the factory logic, and the user can also precisely manage the building of nested controllers.

In addition to this, following classes and methods are also removed.

  • .append method of flow controller subclasses 937567a
  • RunningPassManager which is a subclass of FlowControllerLinear e02f6f5
  • Fenced objects a6c4916
  • max_iteration argument in append and replace 3b1161e

@nkanazawa1989 nkanazawa1989 added Changelog: API Change Include in the "Changed" section of the changelog mod: transpiler Issues and PRs related to Transpiler labels Dec 21, 2023
@nkanazawa1989 nkanazawa1989 added this to the 1.0.0 milestone Dec 21, 2023
@nkanazawa1989 nkanazawa1989 requested review from nonhermitian and a team as code owners December 21, 2023 08:40
@qiskit-bot
Copy link
Collaborator

One or more of the the following people are requested to review this:

@nkanazawa1989 nkanazawa1989 force-pushed the upgrade/pass_manager_cleanup branch from 778428e to 7cf2358 Compare December 21, 2023 08:49
@coveralls
Copy link

coveralls commented Dec 21, 2023

Pull Request Test Coverage Report for Build 7417016020

Warning: This coverage report may be inaccurate.

We've detected an issue with your CI configuration that might affect the accuracy of this pull request's coverage report.
To ensure accuracy in future PRs, please see these guidelines.
A quick fix for this PR: rebase it; your next report should be accurate.

  • 0 of 0 changed or added relevant lines in 0 files are covered.
  • No unchanged relevant lines lost coverage.
  • Overall coverage increased (+0.08%) to 87.608%

Totals Coverage Status
Change from base Build 7282035075: 0.08%
Covered Lines: 59315
Relevant Lines: 67705

💛 - Coveralls

Copy link
Member

@jakelishman jakelishman left a comment

Choose a reason for hiding this comment

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

For the most part this looks sensible to me, though it's rather hard to verify that the preset passmanagers have stayed logically the same; it perhaps would have been easier to do the simple one-to-one replacements in this PR, and have a follow-up that does the refactoring of the logic, so the two can be checked separately. I tried to check them, but I'm not certain I'd have spotted a potential mistake.

Other than that, mostly just the additional question about transpiler.PassManager.passes - I'm not certain that keeping around the list format is a good idea, especially if it's in principal only for the visualisation. Exposing a tasks() method that returns a copy of the raw underlying list seems fine, though (maybe even on BasePassManager).

raise KeyError("Flow controller not found: %s" % name)
del cls.registered_controllers[name]
cls.hierarchy.remove(name)
FlowController = BaseController
Copy link
Member

Choose a reason for hiding this comment

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

Do we need to keep this name around now, or can we just rely on BaseController?

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Not necessary. The alias is removed in 6e6d90e. I was just worried about deprecation of import path.

Comment on lines 450 to 459
def _write_passes_recursive(tasks: BaseController | GenericPass | Sequence):
"""Write passmanager passes list for visualization.

Conventionally, conditional flow controllers were initialized through .append() method
with keyword arguments.

pm = PassManager()
pm.append([PassA, PassB])
pm.append([PassC, PassD], condition=callable)
pm.append([PassE])
Copy link
Member

Choose a reason for hiding this comment

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

If this function is purely for visualisation, it should be in the pass_manager_visualization module, most likely. We should probably deprecate and remove PassManager.passes in favour of the flat PassManager.tasks, which I think already exists?

We shouldn't attempt to keep the recursive list structure around into the future; we already know that it's insufficient to represent even existing flow controllers, let alone future ones in the new structure.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

Yeah this makes perfect sense. Actually drawer doesn't need to rely on this pass representation. This method and representation are removed in e3a991b. I also need to update #11449 to add deprecation for the method.

@nkanazawa1989
Copy link
Contributor Author

I reverted the commit for builtin passmanagers in 98c2ccf and added minimum change to them just to avoid deprecated code in 2f48717. In the followup PR #11494 builtin pass managers are refactored to eliminate use of the append pattern. This PR must be merged first, then I'll rebase the followup PR.

Copy link
Member

@jakelishman jakelishman left a comment

Choose a reason for hiding this comment

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

Thanks Naoki for making the modifications to this - it was 100x easier to check the changes to the preset pass managers, and it's clear that the vast majority of cases have 1:1 replacements that are strictly more powerful now.

)
)

Note that you can manage the pecking order of controllers when you want to nest them,
Copy link
Member

Choose a reason for hiding this comment

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

pecking order

I love this description!

Comment on lines 616 to -606


class DoXTimesController(FlowController):
"""A control-flow plugin for running a set of passes an X amount of times."""

def __init__(self, passes, options, do_x_times, **_):
super().__init__(options)
self.passes = passes
self.do_x_times = do_x_times

# pylint: disable=missing-function-docstring
def iter_tasks(self, metadata):
for _ in range(self.do_x_times(metadata.property_set)):
for pass_ in self.passes:
metadata = yield pass_


Copy link
Member

Choose a reason for hiding this comment

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

This is removed because it's tested as part of qiskit.passmanager elsewhere, I assume?

@jakelishman jakelishman added this pull request to the merge queue Jan 10, 2024
@jakelishman jakelishman added the Changelog: Removal Include in the Removed section of the changelog label Jan 10, 2024
Merged via the queue into Qiskit:main with commit b8d21ae Jan 10, 2024
13 checks passed
ShellyGarion pushed a commit to ShellyGarion/qiskit-terra that referenced this pull request Jan 18, 2024
* Remove flow controller subclass .append

* Update builtin pass managers to avoid append pattern

* Remove running pass manager

* Remove PropertySet and Fenced objects from transpile

* Remove _pass_sets and let PassManager generate pass list on the fly

This is necessary because kwargs is going to be removed from append method.
Current pass list is generated based on the kwargs.

* Remove kwargs from PassManager.append and .replace

This also removes FlowController factory class

* Remove max_iteration keyword from append and replace

* Reno

* minor: fix test and docs

* Remove qiskit.passmanager.flow_controllers.FlowController

* Remove .passes method from PassManager and StagedPassManager

* Update reference image of pass manager drawer test

* minor: fix drawer label generation

* Revert "Update builtin pass managers to avoid append pattern"

This reverts commit 4bcfcd6.

* Minimum update of builtin pass managers
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
Changelog: API Change Include in the "Changed" section of the changelog Changelog: Removal Include in the Removed section of the changelog mod: transpiler Issues and PRs related to Transpiler
Projects
None yet
Development

Successfully merging this pull request may close these issues.

4 participants