Why are imm shifts where imm >= width type eliminated entirely?

For example:

unsigned int x, y;

void foo()
{
y = x >> 129;
}

Where int is a 16bit type, the .ll is producing only ‘ret void’ at O3. At O0 the .ll looks fine but then llc gets rid of it an simply returns.

I’m just curious what the reasoning is for this? It isn’t trying to set y to anything at all.

Thanks.

Shifts amounts equal to or larger than the width of the promoted type being shifted are undefined behavior.

– Steve

For example:

unsigned int x, y;

void foo()
{
     y = x >> 129;
}

Where int is a 16bit type, the .ll is producing only 'ret void' at O3. At
O0 the .ll looks fine but then llc gets rid of it an simply returns.

I'm just curious what the reasoning is for this? It isn't trying to set y
to anything at all.

The optimization is performed here:
http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Analysis/InstructionSimplify.cpp?revision=233938&view=markup#l1278

What will happen is:
  %shr = lshr i16, %x, 129
  store i16 %shr, i16* @y

will get transformed into:
  store i16 undef, i16* @y

Then we will delete the store of undef using the following:
http://llvm.org/viewvc/llvm-project/llvm/trunk/lib/Transforms/InstCombine/InstCombineLoadStoreAlloca.cpp?revision=234601&view=markup#l978

Ok, this makes sense.

So, my follow up is then why, as in Mips, R600, etc… the bit value is checked in the tablegen. Seems that we should expect it to fit anyways if it still exists at this point?

I’m having a hard time trying to get shl to take a PatLeaf for Imm instead of an ImmLeaf.

Ok, this makes sense.

So, my follow up is then why, as in Mips, R600, etc... the bit value is
checked in the tablegen. Seems that we should expect it to fit anyways if
it still exists at this point?

These optimizations are not always run on IR that is fed to the backend.

As in O0, I see.

Thanks.

The DAG combiner also performs the undefined shift -> undef though, so it should still be OK

-Matt

The DAG combiner also performs the undefined shift -> undef though, so it
should still be OK

DAG combiner doesn't really run to convergence as far as I'm aware, so
you often get extremely difficult to test but necessary checks like
this.

Tim.

There can also be other “problems" like this one: http://reviews.llvm.org/D6946

  • Matthias

So when I use a PatLeaf in ‘shl’ as an immediate such as:

def immZExt16 : PatLeaf<(imm), [{return isInt<16>)(N->getZExtValue());}]>;

I get ‘could not infer all types’ for ‘shl’ with imm and an assert 'isConcrete() && “Type isn’t concrete yet”

Why does the type have to be concrete for shl? I’m obviously not getting this error for any other operations, such as add, sub, mul, div, divrem, etc… who all use the same super multiclass.

I’m trying to fit all 3 op alu instructions into two sub-multiclasses (commutative and non commutative, because LLVM makes the imm the rhs for commutative ops, you can’t just do one multiclass for both without getting warnings/errors). It would make sense that shl would be able to fit into this multiclass (which takes PatLeaf for the imm as above).

Thanks.

I have yet to see an example of how one would write a zero extended imm using ImmLeaf?

Thanks.