Make use of the align parameter attribute for all pointer arguments

We previously supported the align attribute on all (pointer) parameters, but we
only used it for byval parameters. However, it is completely consistent at the
IR level to treat 'align n' on all pointer parameters as an alignment
assumption on the pointer, and now we wll. Specifically, this causes
computeKnownBits to use the align attribute on all pointer parameters, not just
byval parameters. I've also added an explicit parameter attribute test for this
to test/Bitcode/attributes.ll.

And I've updated the LangRef to document the align parameter attribute (as it
turns out, it was not documented at all previously, although the byval
documentation mentioned that it could be used).

There are (at least) two benefits to doing this:
 - It allows enhancing alignment based on the pointer alignment after inlining callees.
 - It allows simplification of pointer arithmetic.

git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@213670 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
Hal Finkel 2014-07-22 16:58:55 +00:00
parent 50f2f1434c
commit b3b2aac5be
4 changed files with 29 additions and 6 deletions

View File

@ -921,6 +921,13 @@ Currently, only the following parameter attributes are defined:
the first parameter. This is not a valid attribute for return
values.
``align <n>``
This indicates that the pointer value may be assumed by the optimizer to
have the specified alignment.
Note that this attribute has additional semantics when combined with the
``byval`` attribute.
.. _noalias:
``noalias``

View File

@ -308,13 +308,9 @@ void llvm::computeKnownBits(Value *V, APInt &KnownZero, APInt &KnownOne,
}
if (Argument *A = dyn_cast<Argument>(V)) {
unsigned Align = 0;
unsigned Align = A->getType()->isPointerTy() ? A->getParamAlignment() : 0;
if (A->hasByValOrInAllocaAttr()) {
// Get alignment information off byval/inalloca arguments if specified in
// the IR.
Align = A->getParamAlignment();
} else if (TD && A->hasStructRetAttr()) {
if (!Align && TD && A->hasStructRetAttr()) {
// An sret parameter has at least the ABI alignment of the return type.
Type *EltTy = cast<PointerType>(A->getType())->getElementType();
if (EltTy->isSized())

View File

@ -239,6 +239,11 @@ define dereferenceable(18446744073709551606) i8* @f40(i8* dereferenceable(184467
ret i8* %a
}
define void @f41(i8* align 32, double* align 64) {
; CHECK: define void @f41(i8* align 32, double* align 64) {
ret void
}
; CHECK: attributes #0 = { noreturn }
; CHECK: attributes #1 = { nounwind }
; CHECK: attributes #2 = { readnone }

View File

@ -0,0 +1,15 @@
; RUN: opt < %s -instcombine -S | FileCheck %s
target datalayout = "e-m:e-i64:64-f80:128-n8:16:32:64-S128"
target triple = "x86_64-unknown-linux-gnu"
; Function Attrs: nounwind uwtable
define i32 @foo1(i32* align 32 %a) #0 {
entry:
%0 = load i32* %a, align 4
ret i32 %0
; CHECK-LABEL: @foo1
; CHECK-DAG: load i32* %a, align 32
; CHECK: ret i32
}