Skip to content

Commit 701addf

Browse files
hubert-reinterpretcasttstellar
authored andcommitted
[clang][Sema] Fix PR47676: Handle dependent AltiVec C-style cast
Fix premature decision in the presence of type-dependent expression operands on whether AltiVec vector initializations from single expressions are "splat" operations. Verify that the instantiation is able to determine the correct cast semantics for both the scalar type and the vector type case. Note that, because the change only affects the single-expression case (and the target type is an AltiVec-style vector type), the replacement of a parenthesized list with a parenthesized expression does not change the semantics of the program in a program-observable manner. Reviewed By: aaron.ballman Differential Revision: https://reviews.llvm.org/D88526 (cherry picked from commit 35ecc7f)
1 parent 5ad2592 commit 701addf

File tree

2 files changed

+39
-1
lines changed

2 files changed

+39
-1
lines changed

clang/lib/Sema/SemaExpr.cpp

Lines changed: 1 addition & 1 deletion
Original file line numberDiff line numberDiff line change
@@ -7401,7 +7401,7 @@ Sema::ActOnCastExpr(Scope *S, SourceLocation LParenLoc,
74017401
}
74027402
if (PE || PLE->getNumExprs() == 1) {
74037403
Expr *E = (PE ? PE->getSubExpr() : PLE->getExpr(0));
7404-
if (!E->getType()->isVectorType())
7404+
if (!E->isTypeDependent() && !E->getType()->isVectorType())
74057405
isVectorLiteral = true;
74067406
}
74077407
else

clang/test/SemaTemplate/pr47676.cpp

Lines changed: 38 additions & 0 deletions
Original file line numberDiff line numberDiff line change
@@ -0,0 +1,38 @@
1+
// RUN: %clang_cc1 -triple=powerpc64le-unknown-linux-gnu \
2+
// RUN: -target-feature +altivec -fsyntax-only -ast-dump \
3+
// RUN: -xc++ < %s 2>&1 \
4+
// RUN: | FileCheck %s
5+
6+
// Ensures that casts to AltiVec type with a dependent expression operand does
7+
// not hit the assertion failure reported in PR47676. Further checks that casts
8+
// to AltiVec type with a dependent expression operand is, on instantiation,
9+
// able to correctly differentiate between a splat case and a bitcast case.
10+
template <typename T> void f(T *tp) {
11+
extern void g(int, ...);
12+
g(0, (__vector int)(*tp));
13+
g(0, (__vector int)*tp);
14+
}
15+
16+
void g(void) {
17+
f<__vector float>(nullptr);
18+
// CHECK: | |-FunctionDecl {{.*}} f 'void (__vector float *)'
19+
20+
// CHECK: | | `-CStyleCastExpr {{.*}} '__vector int' <NoOp>
21+
// CHECK-NEXT: | | `-ImplicitCastExpr {{.*}} '__vector int' <BitCast>
22+
// CHECK-NEXT: | | `-ImplicitCastExpr {{.*}}'__vector float' <LValueToRValue>
23+
24+
// CHECK: | `-CStyleCastExpr {{.*}} '__vector int' <NoOp>
25+
// CHECK-NEXT: | `-ImplicitCastExpr {{.*}} '__vector int' <BitCast>
26+
// CHECK-NEXT: | `-ImplicitCastExpr {{.*}}'__vector float' <LValueToRValue>
27+
28+
f<double>(nullptr);
29+
// CHECK: | `-FunctionDecl {{.*}} f 'void (double *)'
30+
31+
// CHECK: | | `-CStyleCastExpr {{.*}} '__vector int' <VectorSplat>
32+
// CHECK-NEXT: | | `-ImplicitCastExpr {{.*}} 'int' <FloatingToIntegral>
33+
// CHECK-NEXT: | | `-ImplicitCastExpr {{.*}}'double' <LValueToRValue>
34+
35+
// CHECK: | `-CStyleCastExpr {{.*}} '__vector int' <VectorSplat>
36+
// CHECK-NEXT: | `-ImplicitCastExpr {{.*}} 'int' <FloatingToIntegral>
37+
// CHECK-NEXT: | `-ImplicitCastExpr {{.*}}:'double' <LValueToRValue>
38+
}

0 commit comments

Comments
 (0)