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

Fix loop unrolling bugs related to issue4739 #4783

Merged
merged 3 commits into from
Jul 7, 2024

Conversation

ChrisDodd
Copy link
Contributor

  • fix FindUninitialized in simplifyDefUse.cpp to correctly get live state for for loop bodies, so as to not dead-code eliminate things unused after the loop exit
  • fix midend/def_use.cpp ComputeDefUse to visit assignments right then left to get correct info for assignments that read the old value of the lhs
  • fix loopUnrolling.cpp UnrollLoops to not unroll loops where the index is modified in the loop body in addition to the loop increment.
  • more logging in ComputeDefUse to see help debugging

@ChrisDodd ChrisDodd requested review from asl, grg, fruffy and jafingerhut July 4, 2024 07:03
@fruffy fruffy added the core Topics concerning the core segments of the compiler (frontend, midend, parser) label Jul 4, 2024
Copy link
Contributor

@jafingerhut jafingerhut left a comment

Choose a reason for hiding this comment

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

I have reviewed the new test P4 program and its samples_outputs files, and agree that they appear to be functionally equivalent to the input P4 program, whereas before these changes to p4c they were erroneous.

As usual, I have not attempted any careful review of the C++ implementation code of p4c, as for most of it I have little or not familiarity with how it works.

@fruffy
Copy link
Collaborator

fruffy commented Jul 4, 2024

The P4Testgen failures might happen because the loops are not unrolled. Are they meant to be unrolled here by a pass?

@jafingerhut
Copy link
Contributor

Chris can answer authoritatively, but I suspect this new test program is one that theoretically could be unrolled by a sophisticated-enough unroller, but the current unroller is not able to do so.

@fruffy
Copy link
Collaborator

fruffy commented Jul 4, 2024

Chris can answer authoritatively, but I suspect this new test program is one that theoretically could be unrolled by a sophisticated-enough unroller, but the current unroller is not able to do so.

I guess the question is whether we need to implement loops support in P4Testgen or rely on some compiler pass to unroll this.

@jafingerhut
Copy link
Contributor

Chris can answer authoritatively, but I suspect this new test program is one that theoretically could be unrolled by a sophisticated-enough unroller, but the current unroller is not able to do so.

I guess the question is whether we need to implement loops support in P4Testgen or rely on some compiler pass to unroll this.

It seems reasonable to me to take a position that P4testgen only generates tests for P4 programs where the loops have been completely unrolled for it, by p4c.

@ChrisDodd
Copy link
Contributor Author

ChrisDodd commented Jul 4, 2024

Chris can answer authoritatively, but I suspect this new test program is one that theoretically could be unrolled by a sophisticated-enough unroller, but the current unroller is not able to do so.

Yes -- this program has modifications of the loop variable in the body of the loop, not just in the loop updates. In theory, this could be unrolled, but that would require more extensive analysis of the loop. Dealing with modifications of the index var in the loop body that are inside ifs or after a potential continue is very hard. This specific case doesn't have that, but I thought the incremental benefit of dealing with just this case (an unconditional mod of the index that might as well be in the update) was not worth it.

return nullptr;
}

static bool find_def(const IR::IndexedVector<IR::StatOrDecl> &stmts, const IR::Node *def,
Copy link
Contributor

Choose a reason for hiding this comment

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

Looks like it could be simplified by returning a->to<IR::AssignmentStatement>(), also the function itself could be renamed according to the code style.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

The reason the signature is the way it is (returning bool, with the actual node returned by pointer) was to make it easy to write the looped call at lines 199-202 -- when the return value is false, we don't want to overwrite the pointer that might have been returned by a previous call. That in turn lets to two loops (199-202 and 209-212) look the same except the second one is ignoring the returned pointers as it is just making sure things are consistent.

It feels like there should be a way of turning the loops inside out and making this a method of ComputeDefUse and much cleaner overall, but I haven't figured out what that would be. I'll think on it some more.

Copy link
Contributor Author

Choose a reason for hiding this comment

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

I ended up rewriting this to be simpler and not need these extra functions -- now all the tests for correct and matching def/use are in the evalLoop that needs to be called to evaluate each iteration. This avoids the separate check for that, and actually allows unrolling more cases (where the increment is in the loop body instead of in the loop increment)

ChrisDodd added 2 commits July 7, 2024 00:45
- fix FindUninitialized in simplifyDefUse.cpp to correctly get live
  state for for loop bodies, so as to not dead-code eliminate things
  unused after the loop exit
- fix midend/def_use.cpp ComputeDefUse to visit assignments right then left
  to get correct info for assignments that read the old value of the lhs
- fix loopUnrolling.cpp UnrollLoops to not unroll loops where the index
  is modified in the loop body in addition to the loop increment.
- more logging in ComputeDefUse to see help debugging

Signed-off-by: Chris Dodd <[email protected]>
- just need to look at def-use chains for the index var, so actually
  will unroll a few more cases.

Signed-off-by: Chris Dodd <[email protected]>
@ChrisDodd ChrisDodd added this pull request to the merge queue Jul 7, 2024
Merged via the queue into p4lang:main with commit 5fda7d2 Jul 7, 2024
17 checks passed
@ChrisDodd ChrisDodd deleted the cdodd-loops branch July 7, 2024 03:33
Sign up for free to join this conversation on GitHub. Already have an account? Sign in to comment
Labels
core Topics concerning the core segments of the compiler (frontend, midend, parser)
Projects
None yet
Development

Successfully merging this pull request may close these issues.

4 participants