diff options
author | Eli Friedman <eli.friedman@gmail.com> | 2009-11-16 21:33:53 +0000 |
---|---|---|
committer | Eli Friedman <eli.friedman@gmail.com> | 2009-11-16 21:33:53 +0000 |
commit | c08bdea63d4d9a23aba62f2fd81ca1e9ca48c2a3 (patch) | |
tree | a40568b9ef7d2ce6277d5752fef49c16163d7b36 | |
parent | bf44533846973fda837b822508a6f51fd1a51695 (diff) | |
download | bcm5719-llvm-c08bdea63d4d9a23aba62f2fd81ca1e9ca48c2a3.tar.gz bcm5719-llvm-c08bdea63d4d9a23aba62f2fd81ca1e9ca48c2a3.zip |
Clean up scalar cast kind handling; make cast kind handling explicitly handle
more cases. No intended visible change.
llvm-svn: 88968
-rw-r--r-- | clang/lib/CodeGen/CGExprScalar.cpp | 97 |
1 files changed, 61 insertions, 36 deletions
diff --git a/clang/lib/CodeGen/CGExprScalar.cpp b/clang/lib/CodeGen/CGExprScalar.cpp index f81aae97aa1..5d5cd739a6b 100644 --- a/clang/lib/CodeGen/CGExprScalar.cpp +++ b/clang/lib/CodeGen/CGExprScalar.cpp @@ -765,49 +765,20 @@ Value *ScalarExprEmitter::EmitCastExpr(const CastExpr *CE) { switch (Kind) { default: - // FIXME: Assert here. - // assert(0 && "Unhandled cast kind!"); + //return CGF.ErrorUnsupported(E, "type of cast"); break; + case CastExpr::CK_Unknown: - // FIXME: We should really assert here - Unknown casts should never get - // as far as to codegen. + //assert(0 && "Unknown cast kind!"); break; + case CastExpr::CK_BitCast: { Value *Src = Visit(const_cast<Expr*>(E)); return Builder.CreateBitCast(Src, ConvertType(DestTy)); } - case CastExpr::CK_ArrayToPointerDecay: { - assert(E->getType()->isArrayType() && - "Array to pointer decay must have array source type!"); - - Value *V = EmitLValue(E).getAddress(); // Bitfields can't be arrays. - - // Note that VLA pointers are always decayed, so we don't need to do - // anything here. - if (!E->getType()->isVariableArrayType()) { - assert(isa<llvm::PointerType>(V->getType()) && "Expected pointer"); - assert(isa<llvm::ArrayType>(cast<llvm::PointerType>(V->getType()) - ->getElementType()) && - "Expected pointer to array"); - V = Builder.CreateStructGEP(V, 0, "arraydecay"); - } + case CastExpr::CK_NoOp: + return Visit(const_cast<Expr*>(E)); - // The resultant pointer type can be implicitly casted to other pointer - // types as well (e.g. void*) and can be implicitly converted to integer. - const llvm::Type *DestLTy = ConvertType(DestTy); - if (V->getType() != DestLTy) { - if (isa<llvm::PointerType>(DestLTy)) - V = Builder.CreateBitCast(V, DestLTy, "ptrconv"); - else { - assert(isa<llvm::IntegerType>(DestLTy) && "Unknown array decay"); - V = Builder.CreatePtrToInt(V, DestLTy, "ptrconv"); - } - } - return V; - } - case CastExpr::CK_NullToMemberPointer: - return CGF.CGM.EmitNullConstant(DestTy); - case CastExpr::CK_DerivedToBase: { const RecordType *DerivedClassTy = E->getType()->getAs<PointerType>()->getPointeeType()->getAs<RecordType>(); @@ -833,6 +804,33 @@ Value *ScalarExprEmitter::EmitCastExpr(const CastExpr *CE) { return CGF.GetAddressCXXOfBaseClass(Src, DerivedClassDecl, BaseClassDecl, NullCheckValue); } + case CastExpr::CK_ToUnion: { + assert(0 && "Should be unreachable!"); + break; + } + case CastExpr::CK_ArrayToPointerDecay: { + assert(E->getType()->isArrayType() && + "Array to pointer decay must have array source type!"); + + Value *V = EmitLValue(E).getAddress(); // Bitfields can't be arrays. + + // Note that VLA pointers are always decayed, so we don't need to do + // anything here. + if (!E->getType()->isVariableArrayType()) { + assert(isa<llvm::PointerType>(V->getType()) && "Expected pointer"); + assert(isa<llvm::ArrayType>(cast<llvm::PointerType>(V->getType()) + ->getElementType()) && + "Expected pointer to array"); + V = Builder.CreateStructGEP(V, 0, "arraydecay"); + } + + return V; + } + case CastExpr::CK_FunctionToPointerDecay: + return EmitLValue(E).getAddress(); + + case CastExpr::CK_NullToMemberPointer: + return CGF.CGM.EmitNullConstant(DestTy); case CastExpr::CK_IntegralToPointer: { Value *Src = Visit(const_cast<Expr*>(E)); @@ -853,12 +851,39 @@ Value *ScalarExprEmitter::EmitCastExpr(const CastExpr *CE) { return Builder.CreatePtrToInt(Src, ConvertType(DestTy)); } + case CastExpr::CK_ToVoid: { + CGF.EmitAnyExpr(E, 0, false, true); + return 0; + } + case CastExpr::CK_Dynamic: { Value *V = Visit(const_cast<Expr*>(E)); const CXXDynamicCastExpr *DCE = cast<CXXDynamicCastExpr>(CE); return CGF.EmitDynamicCast(V, DCE); } - + + case CastExpr::CK_VectorSplat: { + const llvm::Type *DstTy = ConvertType(DestTy); + Value *Elt = Visit(const_cast<Expr*>(E)); + + // Insert the element in element zero of an undef vector + llvm::Value *UnV = llvm::UndefValue::get(DstTy); + llvm::Value *Idx = + llvm::ConstantInt::get(llvm::Type::getInt32Ty(VMContext), 0); + UnV = Builder.CreateInsertElement(UnV, Elt, Idx, "tmp"); + + // Splat the element across to all elements + llvm::SmallVector<llvm::Constant*, 16> Args; + unsigned NumElements = cast<llvm::VectorType>(DstTy)->getNumElements(); + for (unsigned i = 0; i < NumElements; i++) + Args.push_back(llvm::ConstantInt::get( + llvm::Type::getInt32Ty(VMContext), 0)); + + llvm::Constant *Mask = llvm::ConstantVector::get(&Args[0], NumElements); + llvm::Value *Yay = Builder.CreateShuffleVector(UnV, UnV, Mask, "splat"); + return Yay; + } + } // Handle cases where the source is an non-complex type. |