[SeparateConstOffsetFromGEP] Fix: sext(a) + sext(b) -> sext(a + b) matches add and...
authorDrew Wock <ajwock@gmail.com>
Wed, 15 Jan 2020 17:51:42 +0000 (12:51 -0500)
committerKevin P. Neal <kevin.neal@sas.com>
Fri, 17 Jan 2020 17:22:52 +0000 (12:22 -0500)
commit0bcfafc5e71d4f636d456317a3a2e6fd903d4755
tree4d9c790fb791c403bdb8cd714ab140ab6d7410aa
parentf343544b813891387add8ef01406d36b82ed0a7e
[SeparateConstOffsetFromGEP] Fix: sext(a) + sext(b) -> sext(a + b) matches add and sub instructions with one another

During the SeparateConstOffsetFromGEP pass, signed extensions are distributed
to the values that feed into them and then later recombined. The recombination
stage is somewhat problematic- it doesn't differ add and sub instructions
from another when matching the sext(a) +/- sext(b) -> sext(a +/- b) pattern
in some instances.

An example- the IR contains:
%unextendedA
%unextendedB
%subuAuB = unextendedA - unextendedB
%extA = extend A
%extB = extend B
%addeAeB = extA + extB

The problematic optimization will transform that into:

%unextendedA
%unextendedB
%subuAuB = unextendedA - unextendedB
%extA = extend A
%extB = extend B
%addeAeB = extend subuAuB ; Obviously not semantically equivalent to the IR input.

This patch fixes that.

Patch by Drew Wock <drew.wock@sas.com>
Differential Revision: https://reviews.llvm.org/D65967
llvm/lib/Transforms/Scalar/SeparateConstOffsetFromGEP.cpp
llvm/test/Transforms/SeparateConstOffsetFromGEP/test-add-sub-separation.ll [new file with mode: 0644]