-
Notifications
You must be signed in to change notification settings - Fork 28
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
(Closes #1431) Initial changes to add the canonical loop trans abstract class #2190
base: master
Are you sure you want to change the base?
Conversation
Ok, I missed some cases I didn't think about. The loop is created from:
and transformed by PSyclone to:
This looks to be ok w.r.t canonical loop form, but is currently not handled correctly. |
This is something we've hit elsewhere. |
node.children[0].operator == BinaryOperation.Operator.MUL and | ||
(node.children[0].children[0].symbol == loop_var or | ||
node.children[0].children[1].symbol == loop_var)): | ||
return True |
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.
These tests still don't feel right. Too many very similar tests, and I am not even sure that they are complete (what about -a1\*var-a2
or +a1\*var+a2
, which from memory adds another UnaryOperation
node).
SymPy offers a polynomial class, which gives you access to the coefficients, and for the example above at least it will convert them all to a similar structure:
>>> sp.Poly(a1 * var - a2, var).all_coeffs()
[a1, -a2]
>>> sp.Poly(-a1 * var - a2, var).all_coeffs()
[-a1, -a2]
>>> sp.Poly(a2 - a1 * var,var).all_coeffs()
[-a1, a2]
etc. Unfortunately, it does still first simplify the expressions, so
>>> sp.Poly(a2 - a1 * var + 2*var,var).all_coeffs()
[2 - a1, a2]
Could we perhaps in a case like this rewrite the PSyIR with the equivalent expression (psyad is already doing this when expanding terms). Or you could additionally count the number of references and symbols in the original PSyIR, which should be less than or equal to 4? I checked, even in the SymPy internal representation the -a1
is a special node (multiplication of a1
by -1
, so that doesn't really help).
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.
I looked again and my interpretation of the OpenMP standard was also wrong, in that a1
and a2
simply need to be "loop invariant integer expressions", and not simply variables.
I think I should have already checked that any Reference
objects in these terms are loop invariant in validate
before reaching this function, so what actually needs to be done is:
- Check we have some structure that could be handled as one of the allowed structures.
- Check that the
a1
anda2
expressions (if present) are integer expressions.
I wonder if 2 would have been handled already during input/tree construction or if we can just ignore it.
I don't have a good idea how to check the structure conforms though, maybe the sp.Poly class you recommend will work straight out the box? But I'm not clear how to use this - could you provide a quick example?
I'm trying to work out what this actually disallows, and I think any operation involving all integer values/references, and only +-*
operations is allowed (since you could transform x*y*var_outer
into a1*var_outer
since a1=x*y
. Equally division (maybe any integer-safe) operations should be ok provided they are not performed on var_outer
. Does that make sense or have I missed something?
Not sure if I understand the exact problem - in the example eg1 this loop does not even reach your new code, since the loop type is
I somehow feel that I missed something ;) |
Yes, anything that uses |
So from I have added some code to output the
I think without the canonical loop validation check this loop will parallelise with OpenMP - and I think it should. I don't believe there is anything in this script that would mean this isn't attempted to be parallelised? The rough structure of this PSyclone (ignoring a few safety steps) is:
If you do The error is in my code, as I incorrectly detect the "read" of Edit: I think your response suggests this should be ok so I'll try that. |
The changes fix the known errors in the examples, so now the tests I had failing locally are also failing on github. |
Having some issues with the testing here, so I wanted to make this PR for potential discussion on why tests are failing if I can't work it out.
The canonical loop validation testing is not yet implemented either.