I investigated the PostOrderFunctionAttrsPass and the removal of the convergent attribute in particular, and there is something that seems odd to me.
Why the removal of the attribute from the CallSite happen in a later pass (InstCombine)
and doesn’t occur in PostOrderFunctionAttrsPass, where the convergent attribute is actually being removed from the function.
Small example : https://godbolt.org/z/zEPx1zWdc
The function ‘non_convergent_function’ marked with convergent attribute but isn’t actually a convergent function - so PostOrderFunctionAttrsPass can remove the convergent attribute and will do it but it won’t remove the attribute from the CallSite.
It seems that we lose opportunities to optimize code this way , for example the convergent attribute can block some optimizations(SimplifyCFG, LoopUnswitch, LoopUnroll and more).
If we run PostOrderFunctionAttrsPass and then InstCombine then the attribute is removed from the CallSite as well but we lost the opportunity to optimize code until we will remove the convergent attribute from the CallSite in the next run of PostOrderFunctionAttrsPass .
So, I guess my question is what the logic behind this ? why not remove the CallSite attribute right after the removal of the function attribute ?