forked from OSchip/llvm-project
Fix array->pointer decay. This unbreaks test/CodeGen/array.c
llvm-svn: 41202
This commit is contained in:
parent
9717080968
commit
76ba849ed3
|
@ -586,7 +586,7 @@ RValue CodeGenFunction::EmitExpr(const Expr *E) {
|
|||
E->getType(),
|
||||
cast<SizeOfAlignOfTypeExpr>(E)->isSizeOf());
|
||||
case Expr::ImplicitCastExprClass:
|
||||
return EmitCastExpr(cast<ImplicitCastExpr>(E)->getSubExpr(), E->getType());
|
||||
return EmitImplicitCastExpr(cast<ImplicitCastExpr>(E));
|
||||
case Expr::CastExprClass:
|
||||
return EmitCastExpr(cast<CastExpr>(E)->getSubExpr(), E->getType());
|
||||
case Expr::CallExprClass:
|
||||
|
@ -660,6 +660,31 @@ RValue CodeGenFunction::EmitCastExpr(const Expr *Op, QualType DestTy) {
|
|||
return EmitConversion(Src, Op->getType(), DestTy);
|
||||
}
|
||||
|
||||
/// EmitImplicitCastExpr - Implicit casts are the same as normal casts, but also
|
||||
/// handle things like function to pointer-to-function decay, and array to
|
||||
/// pointer decay.
|
||||
RValue CodeGenFunction::EmitImplicitCastExpr(const ImplicitCastExpr *E) {
|
||||
const Expr *Op = E->getSubExpr();
|
||||
QualType OpTy = Op->getType().getCanonicalType();
|
||||
|
||||
// If this is due to array->pointer conversion, emit the array expression as
|
||||
// an l-value.
|
||||
if (isa<ArrayType>(OpTy)) {
|
||||
// FIXME: For now we assume that all source arrays map to LLVM arrays. This
|
||||
// will not true when we add support for VLAs.
|
||||
llvm::Value *V = EmitLValue(Op).getAddress(); // Bitfields can't be arrays.
|
||||
|
||||
assert(isa<llvm::PointerType>(V->getType()) &&
|
||||
isa<llvm::ArrayType>(cast<llvm::PointerType>(V->getType())
|
||||
->getElementType()) &&
|
||||
"Doesn't support VLAs yet!");
|
||||
llvm::Constant *Idx0 = llvm::ConstantInt::get(llvm::Type::Int32Ty, 0);
|
||||
return RValue::get(Builder.CreateGEP(V, Idx0, Idx0, "arraydecay"));
|
||||
}
|
||||
|
||||
return EmitCastExpr(Op, E->getType());
|
||||
}
|
||||
|
||||
RValue CodeGenFunction::EmitCallExpr(const CallExpr *E) {
|
||||
if (const ImplicitCastExpr *IcExpr =
|
||||
dyn_cast<const ImplicitCastExpr>(E->getCallee()))
|
||||
|
|
|
@ -50,6 +50,7 @@ namespace clang {
|
|||
class CharacterLiteral;
|
||||
class TypesCompatibleExpr;
|
||||
|
||||
class ImplicitCastExpr;
|
||||
class CastExpr;
|
||||
class CallExpr;
|
||||
class UnaryOperator;
|
||||
|
@ -350,6 +351,7 @@ public:
|
|||
RValue EmitCharacterLiteral(const CharacterLiteral *E);
|
||||
RValue EmitTypesCompatibleExpr(const TypesCompatibleExpr *E);
|
||||
|
||||
RValue EmitImplicitCastExpr(const ImplicitCastExpr *Op);
|
||||
RValue EmitCastExpr(const Expr *Op, QualType DestTy);
|
||||
RValue EmitCallExpr(const CallExpr *E);
|
||||
RValue EmitBuiltinExpr(unsigned builtinID, const CallExpr *E);
|
||||
|
|
|
@ -0,0 +1,6 @@
|
|||
// RUN: clang -emit-llvm %s
|
||||
|
||||
int f() {
|
||||
int a[2];
|
||||
a[0] = 0;
|
||||
}
|
Loading…
Reference in New Issue