r339167 - [Sema] Fix for crash on conditional operation with address_space pointer
Leonard Chan via cfe-commits
cfe-commits at lists.llvm.org
Tue Aug 7 12:43:54 PDT 2018
Author: leonardchan
Date: Tue Aug 7 12:43:53 2018
New Revision: 339167
URL: http://llvm.org/viewvc/llvm-project?rev=339167&view=rev
Log:
[Sema] Fix for crash on conditional operation with address_space pointer
Compiling the following causes clang to crash
```
char *cmp(__attribute__((address_space(1))) char *x, __attribute__((address_space(2))) char *y) {
return x < y ? x : y;
}
```
with the message: "wrong cast for pointers in different address
spaces(must be an address space cast)!"
This is because during IR emission, the source and dest type for a
bitcast should not have differing address spaces.
This fix prints an error since the code shouldn't compile in the first place.
Differential Revision: https://reviews.llvm.org/D50278
Modified:
cfe/trunk/lib/Sema/SemaExpr.cpp
cfe/trunk/test/Sema/address_spaces.c
cfe/trunk/test/Sema/conditional-expr.c
Modified: cfe/trunk/lib/Sema/SemaExpr.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaExpr.cpp?rev=339167&r1=339166&r2=339167&view=diff
==============================================================================
--- cfe/trunk/lib/Sema/SemaExpr.cpp (original)
+++ cfe/trunk/lib/Sema/SemaExpr.cpp Tue Aug 7 12:43:53 2018
@@ -6460,20 +6460,18 @@ static QualType checkConditionalPointerC
LangAS ResultAddrSpace = LangAS::Default;
LangAS LAddrSpace = lhQual.getAddressSpace();
LangAS RAddrSpace = rhQual.getAddressSpace();
- if (S.getLangOpts().OpenCL) {
- // OpenCL v1.1 s6.5 - Conversion between pointers to distinct address
- // spaces is disallowed.
- if (lhQual.isAddressSpaceSupersetOf(rhQual))
- ResultAddrSpace = LAddrSpace;
- else if (rhQual.isAddressSpaceSupersetOf(lhQual))
- ResultAddrSpace = RAddrSpace;
- else {
- S.Diag(Loc,
- diag::err_typecheck_op_on_nonoverlapping_address_space_pointers)
- << LHSTy << RHSTy << 2 << LHS.get()->getSourceRange()
- << RHS.get()->getSourceRange();
- return QualType();
- }
+
+ // OpenCL v1.1 s6.5 - Conversion between pointers to distinct address
+ // spaces is disallowed.
+ if (lhQual.isAddressSpaceSupersetOf(rhQual))
+ ResultAddrSpace = LAddrSpace;
+ else if (rhQual.isAddressSpaceSupersetOf(lhQual))
+ ResultAddrSpace = RAddrSpace;
+ else {
+ S.Diag(Loc, diag::err_typecheck_op_on_nonoverlapping_address_space_pointers)
+ << LHSTy << RHSTy << 2 << LHS.get()->getSourceRange()
+ << RHS.get()->getSourceRange();
+ return QualType();
}
unsigned MergedCVRQual = lhQual.getCVRQualifiers() | rhQual.getCVRQualifiers();
@@ -6491,16 +6489,12 @@ static QualType checkConditionalPointerC
// Thus for conditional operator we merge CVR and address space unqualified
// pointees and if there is a composite type we return a pointer to it with
// merged qualifiers.
- if (S.getLangOpts().OpenCL) {
- LHSCastKind = LAddrSpace == ResultAddrSpace
- ? CK_BitCast
- : CK_AddressSpaceConversion;
- RHSCastKind = RAddrSpace == ResultAddrSpace
- ? CK_BitCast
- : CK_AddressSpaceConversion;
- lhQual.removeAddressSpace();
- rhQual.removeAddressSpace();
- }
+ LHSCastKind =
+ LAddrSpace == ResultAddrSpace ? CK_BitCast : CK_AddressSpaceConversion;
+ RHSCastKind =
+ RAddrSpace == ResultAddrSpace ? CK_BitCast : CK_AddressSpaceConversion;
+ lhQual.removeAddressSpace();
+ rhQual.removeAddressSpace();
lhptee = S.Context.getQualifiedType(lhptee.getUnqualifiedType(), lhQual);
rhptee = S.Context.getQualifiedType(rhptee.getUnqualifiedType(), rhQual);
@@ -6516,6 +6510,7 @@ static QualType checkConditionalPointerC
S.Context.getAddrSpaceQualType(S.Context.VoidTy, ResultAddrSpace));
LHS = S.ImpCastExprToType(LHS.get(), incompatTy, LHSCastKind);
RHS = S.ImpCastExprToType(RHS.get(), incompatTy, RHSCastKind);
+
// FIXME: For OpenCL the warning emission and cast to void* leaves a room
// for casts between types with incompatible address space qualifiers.
// For the following code the compiler produces casts between global and
@@ -6526,6 +6521,7 @@ static QualType checkConditionalPointerC
S.Diag(Loc, diag::ext_typecheck_cond_incompatible_pointers)
<< LHSTy << RHSTy << LHS.get()->getSourceRange()
<< RHS.get()->getSourceRange();
+
return incompatTy;
}
Modified: cfe/trunk/test/Sema/address_spaces.c
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/Sema/address_spaces.c?rev=339167&r1=339166&r2=339167&view=diff
==============================================================================
--- cfe/trunk/test/Sema/address_spaces.c (original)
+++ cfe/trunk/test/Sema/address_spaces.c Tue Aug 7 12:43:53 2018
@@ -71,5 +71,5 @@ __attribute__((address_space("12"))) int
// Clang extension doesn't forbid operations on pointers to different address spaces.
char* cmp(_AS1 char *x, _AS2 char *y) {
- return x < y ? x : y; // expected-warning {{pointer type mismatch ('__attribute__((address_space(1))) char *' and '__attribute__((address_space(2))) char *')}}
+ return x < y ? x : y; // expected-error{{conditional operator with the second and third operands of type ('__attribute__((address_space(1))) char *' and '__attribute__((address_space(2))) char *') which are pointers to non-overlapping address spaces}}
}
Modified: cfe/trunk/test/Sema/conditional-expr.c
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/Sema/conditional-expr.c?rev=339167&r1=339166&r2=339167&view=diff
==============================================================================
--- cfe/trunk/test/Sema/conditional-expr.c (original)
+++ cfe/trunk/test/Sema/conditional-expr.c Tue Aug 7 12:43:53 2018
@@ -73,10 +73,10 @@ void foo() {
int __attribute__((address_space(2))) *adr2;
int __attribute__((address_space(3))) *adr3;
- test0 ? adr2 : adr3; // expected-warning {{pointer type mismatch}} expected-warning {{expression result unused}}
+ test0 ? adr2 : adr3; // expected-error{{conditional operator with the second and third operands of type ('__attribute__((address_space(2))) int *' and '__attribute__((address_space(3))) int *') which are pointers to non-overlapping address spaces}}
// Make sure address-space mask ends up in the result type
- (test0 ? (test0 ? adr2 : adr2) : nonconst_int); // expected-warning {{pointer type mismatch}} expected-warning {{expression result unused}}
+ (test0 ? (test0 ? adr2 : adr2) : nonconst_int); // expected-error{{conditional operator with the second and third operands of type ('__attribute__((address_space(2))) int *' and 'int *') which are pointers to non-overlapping address spaces}}
}
int Postgresql() {
More information about the cfe-commits
mailing list