2014-09-07 22:58:14 +00:00
// RUN: %clang_cc1 -fsyntax-only -verify %s
int test1 ( int * a ) {
a = __builtin_assume_aligned ( a , 32 , 0ull ) ;
return a [ 0 ] ;
}
int test2 ( int * a ) {
a = __builtin_assume_aligned ( a , 32 , 0 ) ;
return a [ 0 ] ;
}
int test3 ( int * a ) {
a = __builtin_assume_aligned ( a , 32 ) ;
return a [ 0 ] ;
}
int test4 ( int * a ) {
a = __builtin_assume_aligned ( a , - 32 ) ; // expected-error {{requested alignment is not a power of 2}}
2014-09-08 00:09:15 +00:00
// FIXME: The line below produces {{requested alignment is not a power of 2}}
// on i386-freebsd, but not on x86_64-linux (for example).
// a = __builtin_assume_aligned(a, 1ULL << 63);
2014-09-07 22:58:14 +00:00
return a [ 0 ] ;
}
int test5 ( int * a , unsigned * b ) {
a = __builtin_assume_aligned ( a , 32 , b ) ; // expected-warning {{incompatible pointer to integer conversion passing 'unsigned int *' to parameter of type}}
return a [ 0 ] ;
}
int test6 ( int * a ) {
a = __builtin_assume_aligned ( a , 32 , 0 , 0 ) ; // expected-error {{too many arguments to function call, expected at most 3, have 4}}
return a [ 0 ] ;
}
int test7 ( int * a ) {
a = __builtin_assume_aligned ( a , 31 ) ; // expected-error {{requested alignment is not a power of 2}}
return a [ 0 ] ;
}
int test8 ( int * a , int j ) {
a = __builtin_assume_aligned ( a , j ) ; // expected-error {{must be a constant integer}}
return a [ 0 ] ;
}
2014-09-26 05:04:30 +00:00
void test_void_assume_aligned ( void ) __attribute__ ( ( assume_aligned ( 32 ) ) ) ; // expected-warning {{'assume_aligned' attribute only applies to return values that are pointers}}
int test_int_assume_aligned ( void ) __attribute__ ( ( assume_aligned ( 16 ) ) ) ; // expected-warning {{'assume_aligned' attribute only applies to return values that are pointers}}
void * test_ptr_assume_aligned ( void ) __attribute__ ( ( assume_aligned ( 64 ) ) ) ; // no-warning
2021-10-06 11:20:44 -07:00
void * test_ptr_assume_aligned ( void ) __attribute__ ( ( assume_aligned ( 8589934592 ) ) ) ; // expected-warning {{requested alignment must be 4294967296 bytes or smaller; maximum alignment assumed}}
2014-09-26 05:04:30 +00:00
2017-11-26 20:01:12 +00:00
int j __attribute__ ( ( assume_aligned ( 8 ) ) ) ; // expected-warning {{'assume_aligned' attribute only applies to Objective-C methods and functions}}
2014-09-26 05:04:30 +00:00
void * test_no_fn_proto ( ) __attribute__ ( ( assume_aligned ( 32 ) ) ) ; // no-warning
void * test_with_fn_proto ( void ) __attribute__ ( ( assume_aligned ( 128 ) ) ) ; // no-warning
void * test_no_fn_proto ( ) __attribute__ ( ( assume_aligned ( 31 ) ) ) ; // expected-error {{requested alignment is not a power of 2}}
void * test_no_fn_proto ( ) __attribute__ ( ( assume_aligned ( 32 , 73 ) ) ) ; // no-warning
void * test_no_fn_proto ( ) __attribute__ ( ( assume_aligned ) ) ; // expected-error {{'assume_aligned' attribute takes at least 1 argument}}
void * test_no_fn_proto ( ) __attribute__ ( ( assume_aligned ( ) ) ) ; // expected-error {{'assume_aligned' attribute takes at least 1 argument}}
void * test_no_fn_proto ( ) __attribute__ ( ( assume_aligned ( 32 , 45 , 37 ) ) ) ; // expected-error {{'assume_aligned' attribute takes no more than 2 arguments}}
2019-10-11 14:59:44 +00:00
int pr43638 ( int * a ) {
2021-10-06 11:20:44 -07:00
a = __builtin_assume_aligned ( a , 8589934592 ) ; // expected-warning {{requested alignment must be 4294967296 bytes or smaller; maximum alignment assumed}}
The maximal representable alignment in LLVM IR is 1GiB, not 512MiB
In LLVM IR, `AlignmentBitfieldElementT` is 5-bit wide
But that means that the maximal alignment exponent is `(1<<5)-2`,
which is `30`, not `29`. And indeed, alignment of `1073741824`
roundtrips IR serialization-deserialization.
While this doesn't seem all that important, this doubles
the maximal supported alignment from 512MiB to 1GiB,
and there's actually one noticeable use-case for that;
On X86, the huge pages can have sizes of 2MiB and 1GiB (!).
So while this doesn't add support for truly huge alignments,
which i think we can easily-ish do if wanted, i think this adds
zero-cost support for a not-trivially-dismissable case.
I don't believe we need any upgrade infrastructure,
and since we don't explicitly record the IR version,
we don't need to bump one either.
As @craig.topper speculates in D108661#2963519,
this might be an artificial limit imposed by the original implementation
of the `getAlignment()` functions.
Differential Revision: https://reviews.llvm.org/D108661
2021-08-26 11:51:28 +03:00
return a [ 0 ] ;
2019-10-11 14:59:44 +00:00
}