Skip to content

Commit d23411a

Browse files
committed
error for bitfields. tests for bitfield errors. minor pr suggestion change
1 parent 03ed417 commit d23411a

File tree

5 files changed

+64
-5
lines changed

5 files changed

+64
-5
lines changed

clang/include/clang/Sema/SemaHLSL.h

Lines changed: 2 additions & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -141,7 +141,8 @@ class SemaHLSL : public SemaBase {
141141
bool diagnoseInputIDType(QualType T, const ParsedAttr &AL);
142142

143143
bool CanPerformScalarCast(QualType SrcTy, QualType DestTy);
144-
bool CanPerformAggregateCast(Expr *Src, QualType DestType);
144+
bool ContainsBitField(QualType BaseTy);
145+
bool CanPerformElementwiseCast(Expr *Src, QualType DestType);
145146
ExprResult ActOnOutParamExpr(ParmVarDecl *Param, Expr *Arg);
146147

147148
QualType getInoutParameterType(QualType Ty);

clang/lib/CodeGen/CGExpr.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -6417,7 +6417,7 @@ void CodeGenFunction::FlattenAccessAndType(
64176417
llvm::Value *Idx = llvm::ConstantInt::get(IdxTy, I);
64186418
// gep on vector fields is not recommended so combine gep with
64196419
// extract/insert
6420-
AccessList.push_back({GEP, Idx});
6420+
AccessList.emplace_back(GEP, Idx);
64216421
FlatTypes.push_back(VT->getElementType());
64226422
}
64236423
} else {

clang/lib/Sema/SemaCast.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -2776,7 +2776,7 @@ void CastOperation::CheckCXXCStyleCast(bool FunctionalStyle,
27762776
// vector cast, vector truncation, or special hlsl splat cases
27772777
QualType SrcTy = SrcExpr.get()->getType();
27782778
if (Self.getLangOpts().HLSL &&
2779-
Self.HLSL().CanPerformAggregateCast(SrcExpr.get(), DestType)) {
2779+
Self.HLSL().CanPerformElementwiseCast(SrcExpr.get(), DestType)) {
27802780
if (SrcTy->isConstantArrayType())
27812781
SrcExpr = Self.ImpCastExprToType(
27822782
SrcExpr.get(), Self.Context.getArrayParameterType(SrcTy),

clang/lib/Sema/SemaHLSL.cpp

Lines changed: 39 additions & 2 deletions
Original file line numberDiff line numberDiff line change
@@ -2476,9 +2476,43 @@ bool SemaHLSL::CanPerformScalarCast(QualType SrcTy, QualType DestTy) {
24762476
llvm_unreachable("Unhandled scalar cast");
24772477
}
24782478

2479-
// Can we perform an HLSL Flattened cast?
2479+
// Detect if a type contains a bitfield. Will be removed when
2480+
// bitfield support is added to HLSLElementwiseCast
2481+
bool SemaHLSL::ContainsBitField(QualType BaseTy) {
2482+
llvm::SmallVector<QualType, 16> WorkList;
2483+
WorkList.push_back(BaseTy);
2484+
while (!WorkList.empty()) {
2485+
QualType T = WorkList.pop_back_val();
2486+
T = T.getCanonicalType().getUnqualifiedType();
2487+
// only check aggregate types
2488+
if (const auto *AT = dyn_cast<ConstantArrayType>(T)) {
2489+
WorkList.push_back(AT->getElementType());
2490+
continue;
2491+
}
2492+
if (const auto *RT = dyn_cast<RecordType>(T)) {
2493+
const RecordDecl *RD = RT->getDecl();
2494+
if (RD->isUnion())
2495+
continue;
2496+
2497+
const CXXRecordDecl *CXXD = dyn_cast<CXXRecordDecl>(RD);
2498+
2499+
if (CXXD && CXXD->isStandardLayout())
2500+
RD = CXXD->getStandardLayoutBaseWithFields();
2501+
2502+
for (const auto *FD : RD->fields()) {
2503+
if (FD->isBitField())
2504+
return true;
2505+
WorkList.push_back(FD->getType());
2506+
}
2507+
continue;
2508+
}
2509+
}
2510+
return false;
2511+
}
2512+
2513+
// Can we perform an HLSL Elementwise cast?
24802514
// TODO: update this code when matrices are added; see issue #88060
2481-
bool SemaHLSL::CanPerformAggregateCast(Expr *Src, QualType DestTy) {
2515+
bool SemaHLSL::CanPerformElementwiseCast(Expr *Src, QualType DestTy) {
24822516

24832517
// Don't handle casts where LHS and RHS are any combination of scalar/vector
24842518
// There must be an aggregate somewhere
@@ -2490,6 +2524,9 @@ bool SemaHLSL::CanPerformAggregateCast(Expr *Src, QualType DestTy) {
24902524
(DestTy->isScalarType() || DestTy->isVectorType()))
24912525
return false;
24922526

2527+
if (ContainsBitField(DestTy) || ContainsBitField(SrcTy))
2528+
return false;
2529+
24932530
llvm::SmallVector<QualType> DestTypes;
24942531
BuildFlattenedTypeList(DestTy, DestTypes);
24952532
llvm::SmallVector<QualType> SrcTypes;

clang/test/SemaHLSL/Language/ElementwiseCast-errors.hlsl

Lines changed: 21 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -6,3 +6,24 @@ export void cantCast() {
66
B = (int[4])A;
77
// expected-error@-1 {{C-style cast from 'int *' to 'int[4]' is not allowed}}
88
}
9+
10+
struct S {
11+
// expected-note@-1 {{candidate constructor (the implicit copy constructor) not viable: no known conversion from 'int2' (aka 'vector<int, 2>') to 'const S' for 1st argument}}
12+
// expected-note@-2 {{candidate constructor (the implicit move constructor) not viable: no known conversion from 'int2' (aka 'vector<int, 2>') to 'S' for 1st argument}}
13+
// expected-note@-3 {{candidate constructor (the implicit default constructor) not viable: requires 0 arguments, but 1 was provided}}
14+
int A : 8;
15+
int B;
16+
};
17+
18+
// casting types which contain bitfields is not yet supported.
19+
export void cantCast2() {
20+
S s = {1,2};
21+
int2 C = (int2)s;
22+
// expected-error@-1 {{cannot convert 'S' to 'int2' (aka 'vector<int, 2>') without a conversion operator}}
23+
}
24+
25+
export void cantCast3() {
26+
int2 C = {1,2};
27+
S s = (S)C;
28+
// expected-error@-1 {{no matching conversion for C-style cast from 'int2' (aka 'vector<int, 2>') to 'S'}}
29+
}

0 commit comments

Comments
 (0)