[LLVMdev] A small pass to constant fold branch conditions in destination blocks
Duncan Sands
baldrick at free.fr
Mon Feb 7 05:57:17 PST 2011
Hi Jeff, sorry my example was misleading.
> Then I misunderstood it's purpose. I see now that constant propagation could
> remove branches because you know a value is true. I was looking at the problem
> through my 'register allocator' lens. Here is a more expressive example of what
> you are doing.
>
> define i1 @t1(i1 %c) {
> br i1 %c, label %t, label %f
> t:
> br i1 %c, label %t2, label %f2
> t2:
> code...
> ret something
> f2:
> code...
> ret something
>
> f:
> br i1 %c, label %t3, label %f3
> t3:
> code...
> ret something
> f3:
> code...
> ret something
> }
>
> Would be changed into:
> define i1 @t1(i1 %c) {
> br i1 %c, label %t2, label %f3
> t2:
> code...
> ret something
> f3:
> code...
> ret something
> }
Yes that's exactly what it would do, and this happens a lot in practice. The
reason that it fires a lot in Ada code for example if that the code is full of
compiler generated checks (eg: every array access is checked) and the checks
often end up being repeated (eg: because you access the same array element
twice). Now all the later checks are eliminated if they are implied by the
earlier checks.
Ciao, Duncan.
>
> Jeff Kunkel
> On Mon, Feb 7, 2011 at 8:37 AM, Duncan Sands <baldrick at free.fr
> <mailto:baldrick at free.fr>> wrote:
>
> Hi Jeff,
>
>
> Are you sure this is really advantageous? '%c' is only one variable, but
> when
> you add the constant propagation, '%c' and false/true are two different
> variables. Thus
>
>
> the example was explanatory, not typical. In fact I didn't ever see returns
> being split like this in practice. What I do see typically is branches
> being eliminated. For example, consider the effect on bzip2: 36 branches are
> completely removed, 1 is changed from conditional to unconditional, various
> bits of dead code are eliminated (not a lot, 4 stores and a few computations).
> I chose this example randomly, but it's typical of what I see elsewhere.
>
> Ciao, Duncan.
>
>
>
> define i1 @t1(i1 %c) {
> br i1 %c, label %t, label %f
> t:
> ret i1 %c
> f:
> ret i1 %c
> }
> should be
> br i1 R0, label %t, label %f
> t:
> ret R0
> f:
> ret R0
>
> However, with your pass
> define i1 @t1(i1 %c) {
> br i1 %c, label %t, label %f
> t:
> ret i1 true
> f:
> ret i1 false
> }
> will be
> define i1 @t1(i1 %c) {
> br i1 R0, label %t, label %f
> t:
> R1 = true
> ret i1 R1
> f:
> R1 = false
> ret i1 R1
> }
>
> I am thinking X86 where '%c' would be allocated a register and the
> false/true
> statement would be allocated a different register which would be EAX/AX
> on the
> x86 machine.
>
> Honestly, I believe this pattern could be conditional constant propagation
> / conditional re-materialization in the spiller. LLVM uses the spiller to
> propagate constants. This pass would be useful to identify some conditional
> re-materializations. You should look into hacking the spiller and see if
> this
> can be added to it.
>
> - My 2 cents,
> Jeff Kunkel
>
> On Mon, Feb 7, 2011 at 7:50 AM, Duncan Sands <baldrick at free.fr
> <mailto:baldrick at free.fr>
> <mailto:baldrick at free.fr <mailto:baldrick at free.fr>>> wrote:
>
> Hi all, I wrote a little pass (attached) which does the following:
> if it sees a
> conditional branch instruction then it replaces all occurrences of
> the condition
> in the true block with "true" and in the false block with "false".
> Well, OK, it
> is a bit more sophisticated (and a bit more careful!) than that but
> you get the
> idea. It will turn this
> define i1 @t1(i1 %c) {
> br i1 %c, label %t, label %f
> t:
> ret i1 %c
> f:
> ret i1 %c
> }
> into this
> define i1 @t1(i1 %c) {
> br i1 %c, label %t, label %f
> t:
> ret i1 true
> f:
> ret i1 false
> }
> for example. Curiously enough LLVM doesn't seem to have a pass that
> does this.
> I took a look at the effect on the testsuite by scheduling a run of
> this pass
> just after each run of -correlated-propagation. In spite of being
> so simple
> (not to say simplistic) it has an enormous positive impact on Ada
> code and a
> substantial positive impact throughout the LLVM test-suite (I didn't
> check that
> programs still work after running the pass, so it could be that it
> has such a
> big effect because it is wrong!).
>
> So... should this kind of logic be incorporated into LLVM? Perhaps
> as part of
> an existing pass like -correlated-propagation?
>
> It would be easy to make the pass a bit more powerful. For example
> if the
> condition was "X == 0" then it could also replace X with 0
> everywhere in the
> true block.
>
> Ciao, Duncan.
>
> PS: This was inspired by PR9004.
>
> _______________________________________________
> LLVM Developers mailing list
> LLVMdev at cs.uiuc.edu <mailto:LLVMdev at cs.uiuc.edu>
> <mailto:LLVMdev at cs.uiuc.edu <mailto:LLVMdev at cs.uiuc.edu>>
> http://llvm.cs.uiuc.edu
>
> http://lists.cs.uiuc.edu/mailman/listinfo/llvmdev
>
>
>
>
More information about the llvm-dev
mailing list