Fix array->pointer decay. This unbreaks test/CodeGen/array.c

llvm-svn: 41202
This commit is contained in:
Chris Lattner 2007-08-20 22:37:10 +00:00
parent 9717080968
commit 76ba849ed3
3 changed files with 34 additions and 1 deletions

View File

@ -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()))

View File

@ -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);

View File

@ -0,0 +1,6 @@
// RUN: clang -emit-llvm %s
int f() {
int a[2];
a[0] = 0;
}