This is an archive of the discontinued LLVM Phabricator instance.

Transforms: add ConvergenceControlHeuristic pass
Needs ReviewPublic

Authored by nhaehnle on Aug 9 2020, 7:45 AM.

Details

Summary

This pass turns uncontrolled convergent operations into controlled ones
by adding appropriate "convergencectrl" bundles and inserting
convergence control intrinsics.

When this pass is used immediately after generating LLVM IR, it will in
many cases establish convergence control that enforces the semantics
that a programmer would likely expect based on the high-level language
source. However, there are exceptions.

This pass is not intended to be used by default. Frontends that care
about semantics of convergent operations should really emit convergence
control information directly, but this pass can serve as a convenient
stop-gap.

Change-Id: I1c72b53567cb4e8b9b82f31f9c8525f2622cd242

Diff Detail

Event Timeline

nhaehnle created this revision.Aug 9 2020, 7:45 AM
Herald added a project: Restricted Project. · View Herald TranscriptAug 9 2020, 7:45 AM
nhaehnle requested review of this revision.Aug 9 2020, 7:45 AM
arsenm added inline comments.Aug 9 2020, 8:30 AM
llvm/lib/Transforms/Utils/ConvergenceControlHeuristic.cpp
76–77

Don't need intermediate changed variable

116

Why do you need to recreate it? Can't you just directly add the bundle / mutate the instructon? That would also make invoke support free?

126

Can you also add a test with an asm call

nhaehnle updated this revision to Diff 285712.Aug 14 2020, 11:37 AM
nhaehnle marked an inline comment as done.
  • add an inline assembly test
  • simplification suggest by a review comment
nhaehnle marked an inline comment as done.Aug 14 2020, 11:39 AM
nhaehnle added inline comments.
llvm/lib/Transforms/Utils/ConvergenceControlHeuristic.cpp
116

Is that possible? There isn't really any infrastructure for adding or removing operands on a User, and with the way that they're allocated it would seem to be a rather invasive change to allow that.

126

Can you also add a test with an asm call

Done.

simoll added a subscriber: simoll.Aug 18 2020, 6:11 AM
Anastasia added inline comments.
llvm/lib/Transforms/Utils/ConvergenceControlHeuristic.cpp
15

Can I clarify what do you mean by refer here?

I presume if you only have IR with uncontrolled convergent operation there wouldn't be any tokens to find? Although perhaps this could apply if one has been inserted for another uncontrolled operation previously?

17

Right now Clang decorates all function by convergent regardless whether or not they have convergent operations so it seems that if we are to generalize to the new behavior we could just append an entry intrinsic to the entry basic block everywhere?

18

I would quite like to get an example of HL code that needs an anchor. I am not very clear where it fits at the moment.

20

Ok, in the frontend we might have very limited information about the full CF structure while parsing.

Although we could also think of some combined approaches where frontend generates partial information and then the pass completes the rest...

nhaehnle marked 2 inline comments as done.Apr 13 2021, 7:58 AM

Hi @Anastasia, thank you for your comments. I replied inline, but a high-level point upfront is that in many ways, this patch only exists because HLL don't really have well-defined semantics for convergent operations yet. Most of us have a shared mental model of what they should be for most high-level constructs, but intuition breaks down for the trickier corner cases. I made some proposals in the Khronos Memory Model TSG for how useful semantics could be added to HLL, taking the corner cases into account, but on my end all of this is on hold while I'm on leave.

llvm/lib/Transforms/Utils/ConvergenceControlHeuristic.cpp
15

Yes, that's correct.

17

Yes.

18

It depends on the relevant definitions of the HL languages, which don't exist yet.

If you were to translate an algorithm from CUDA, you'd basically use an anchor wherever __activemask() is used.

An example of a piece of code that would leverage it is at https://github.com/nhaehnle/llvm-project/blob/controlflow-wip-v9-pre/llvm/docs/ConvergentOperations.rst#opportunistic-convergent-operations (the @reserveSpaceInBuffer example) -- it's not in a HLL, but again, that's because HLL don't really offer these controls yet as inherent language features.

20

If this is in response to the irreducible cycles, keep in mind that you can only really get those with goto in modern languages (or possibly after some transforms have already happened).

I don't know much about Clang in particular, but fong-term, for HLL that have well-defined expected semantics of convergent operations, I expect that it would always be preferable to emit the convergence control information as part of the frontend IR generation.

Hi @Anastasia, thank you for your comments. I replied inline, but a high-level point upfront is that in many ways, this patch only exists because HLL don't really have well-defined semantics for convergent operations yet. Most of us have a shared mental model of what they should be for most high-level constructs, but intuition breaks down for the trickier corner cases. I made some proposals in the Khronos Memory Model TSG for how useful semantics could be added to HLL, taking the corner cases into account, but on my end all of this is on hold while I'm on leave.

Great! I will try to find more details there.

llvm/lib/Transforms/Utils/ConvergenceControlHeuristic.cpp
18

I see, potentially some of the new extended subgroup functions in OpenCL could be using that intrinsics for example sub_group_ballot.
https://www.khronos.org/registry/OpenCL/specs/3.0-unified/html/OpenCL_Ext.html#_extended_subgroup_functions