зеркало из https://github.com/microsoft/clang.git
First stage of adding AltiVec support
git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@95335 91177308-0d34-0410-b5e6-96231b3b80d8
This commit is contained in:
Родитель
6202119003
Коммит
82287d19de
|
@ -502,7 +502,8 @@ public:
|
|||
|
||||
/// getVectorType - Return the unique reference to a vector type of
|
||||
/// the specified element type and size. VectorType must be a built-in type.
|
||||
QualType getVectorType(QualType VectorType, unsigned NumElts);
|
||||
QualType getVectorType(QualType VectorType, unsigned NumElts,
|
||||
bool AltiVec, bool IsPixel);
|
||||
|
||||
/// getExtVectorType - Return the unique reference to an extended vector type
|
||||
/// of the specified element type and size. VectorType must be a built-in
|
||||
|
|
|
@ -1594,7 +1594,8 @@ public:
|
|||
|
||||
/// VectorType - GCC generic vector type. This type is created using
|
||||
/// __attribute__((vector_size(n)), where "n" specifies the vector size in
|
||||
/// bytes. Since the constructor takes the number of vector elements, the
|
||||
/// bytes; or from an Altivec __vector or vector declaration.
|
||||
/// Since the constructor takes the number of vector elements, the
|
||||
/// client is responsible for converting the size into the number of elements.
|
||||
class VectorType : public Type, public llvm::FoldingSetNode {
|
||||
protected:
|
||||
|
@ -1604,13 +1605,21 @@ protected:
|
|||
/// NumElements - The number of elements in the vector.
|
||||
unsigned NumElements;
|
||||
|
||||
VectorType(QualType vecType, unsigned nElements, QualType canonType) :
|
||||
/// AltiVec - True if this is for an Altivec vector.
|
||||
bool AltiVec;
|
||||
|
||||
/// Pixel - True if this is for an Altivec vector pixel.
|
||||
bool Pixel;
|
||||
|
||||
VectorType(QualType vecType, unsigned nElements, QualType canonType,
|
||||
bool isAltiVec, bool isPixel) :
|
||||
Type(Vector, canonType, vecType->isDependentType()),
|
||||
ElementType(vecType), NumElements(nElements) {}
|
||||
ElementType(vecType), NumElements(nElements),
|
||||
AltiVec(isAltiVec), Pixel(isPixel) {}
|
||||
VectorType(TypeClass tc, QualType vecType, unsigned nElements,
|
||||
QualType canonType)
|
||||
QualType canonType, bool isAltiVec, bool isPixel)
|
||||
: Type(tc, canonType, vecType->isDependentType()), ElementType(vecType),
|
||||
NumElements(nElements) {}
|
||||
NumElements(nElements), AltiVec(isAltiVec), Pixel(isPixel) {}
|
||||
friend class ASTContext; // ASTContext creates these.
|
||||
public:
|
||||
|
||||
|
@ -1620,14 +1629,22 @@ public:
|
|||
bool isSugared() const { return false; }
|
||||
QualType desugar() const { return QualType(this, 0); }
|
||||
|
||||
bool isAltiVec() const { return AltiVec; }
|
||||
|
||||
bool isPixel() const { return Pixel; }
|
||||
|
||||
void Profile(llvm::FoldingSetNodeID &ID) {
|
||||
Profile(ID, getElementType(), getNumElements(), getTypeClass());
|
||||
Profile(ID, getElementType(), getNumElements(), getTypeClass(),
|
||||
AltiVec, Pixel);
|
||||
}
|
||||
static void Profile(llvm::FoldingSetNodeID &ID, QualType ElementType,
|
||||
unsigned NumElements, TypeClass TypeClass) {
|
||||
unsigned NumElements, TypeClass TypeClass,
|
||||
bool isAltiVec, bool isPixel) {
|
||||
ID.AddPointer(ElementType.getAsOpaquePtr());
|
||||
ID.AddInteger(NumElements);
|
||||
ID.AddInteger(TypeClass);
|
||||
ID.AddBoolean(isAltiVec);
|
||||
ID.AddBoolean(isPixel);
|
||||
}
|
||||
|
||||
virtual Linkage getLinkage() const;
|
||||
|
@ -1645,7 +1662,7 @@ public:
|
|||
/// points, colors, and textures (modeled after OpenGL Shading Language).
|
||||
class ExtVectorType : public VectorType {
|
||||
ExtVectorType(QualType vecType, unsigned nElements, QualType canonType) :
|
||||
VectorType(ExtVector, vecType, nElements, canonType) {}
|
||||
VectorType(ExtVector, vecType, nElements, canonType, false, false) {}
|
||||
friend class ASTContext; // ASTContext creates these.
|
||||
public:
|
||||
static int getPointAccessorIdx(char c) {
|
||||
|
|
|
@ -160,6 +160,14 @@ def err_typename_invalid_functionspec : Error<
|
|||
"type name does not allow function specifier to be specified">;
|
||||
def err_invalid_decl_spec_combination : Error<
|
||||
"cannot combine with previous '%0' declaration specifier">;
|
||||
def err_invalid_vector_decl_spec_combination : Error<
|
||||
"cannot combine with previous '%0' declaration specifier. \"__vector\" must be first">;
|
||||
def err_invalid_pixel_decl_spec_combination : Error<
|
||||
"\"__pixel\" must be preceded by \"__vector\". '%0' declaration specifier not allowed here">;
|
||||
def err_invalid_vector_double_decl_spec_combination : Error<
|
||||
"cannot use \"double\" with \"__vector\"">;
|
||||
def warn_vector_long_decl_spec_combination : Warning<
|
||||
"Use of \"long\" with \"__vector\" is deprecated">;
|
||||
def err_friend_invalid_in_context : Error<
|
||||
"'friend' used outside of class">;
|
||||
def err_unknown_typename : Error<
|
||||
|
|
|
@ -46,6 +46,7 @@ namespace clang {
|
|||
TST_decimal32, // _Decimal32
|
||||
TST_decimal64, // _Decimal64
|
||||
TST_decimal128, // _Decimal128
|
||||
TST_pixel, // AltiVec
|
||||
TST_enum,
|
||||
TST_union,
|
||||
TST_struct,
|
||||
|
|
|
@ -227,7 +227,7 @@ KEYWORD(__func__ , KEYALL)
|
|||
|
||||
// C++ 2.11p1: Keywords.
|
||||
KEYWORD(asm , KEYCXX|KEYGNU)
|
||||
KEYWORD(bool , BOOLSUPPORT)
|
||||
KEYWORD(bool , BOOLSUPPORT|KEYALTIVEC)
|
||||
KEYWORD(catch , KEYCXX)
|
||||
KEYWORD(class , KEYCXX)
|
||||
KEYWORD(const_cast , KEYCXX)
|
||||
|
@ -235,7 +235,7 @@ KEYWORD(delete , KEYCXX)
|
|||
KEYWORD(dynamic_cast , KEYCXX)
|
||||
KEYWORD(explicit , KEYCXX)
|
||||
KEYWORD(export , KEYCXX)
|
||||
KEYWORD(false , BOOLSUPPORT)
|
||||
KEYWORD(false , BOOLSUPPORT|KEYALTIVEC)
|
||||
KEYWORD(friend , KEYCXX)
|
||||
KEYWORD(mutable , KEYCXX)
|
||||
KEYWORD(namespace , KEYCXX)
|
||||
|
@ -249,7 +249,7 @@ KEYWORD(static_cast , KEYCXX)
|
|||
KEYWORD(template , KEYCXX)
|
||||
KEYWORD(this , KEYCXX)
|
||||
KEYWORD(throw , KEYCXX)
|
||||
KEYWORD(true , BOOLSUPPORT)
|
||||
KEYWORD(true , BOOLSUPPORT|KEYALTIVEC)
|
||||
KEYWORD(try , KEYCXX)
|
||||
KEYWORD(typename , KEYCXX)
|
||||
KEYWORD(typeid , KEYCXX)
|
||||
|
@ -340,6 +340,10 @@ KEYWORD(__ptr64 , KEYALL)
|
|||
KEYWORD(__w64 , KEYALL)
|
||||
KEYWORD(__forceinline , KEYALL)
|
||||
|
||||
// Altivec Extension.
|
||||
KEYWORD(__vector , KEYALTIVEC)
|
||||
KEYWORD(__pixel , KEYALTIVEC)
|
||||
|
||||
// Alternate spelling for various tokens. There are GCC extensions in all
|
||||
// languages, but should not be disabled in strict conformance mode.
|
||||
ALIAS("__attribute__", __attribute, KEYALL)
|
||||
|
|
|
@ -113,6 +113,7 @@ public:
|
|||
static const TST TST_decimal32 = clang::TST_decimal32;
|
||||
static const TST TST_decimal64 = clang::TST_decimal64;
|
||||
static const TST TST_decimal128 = clang::TST_decimal128;
|
||||
static const TST TST_pixel = clang::TST_pixel;
|
||||
static const TST TST_enum = clang::TST_enum;
|
||||
static const TST TST_union = clang::TST_union;
|
||||
static const TST TST_struct = clang::TST_struct;
|
||||
|
@ -153,6 +154,8 @@ private:
|
|||
/*TSC*/unsigned TypeSpecComplex : 2;
|
||||
/*TSS*/unsigned TypeSpecSign : 2;
|
||||
/*TST*/unsigned TypeSpecType : 5;
|
||||
bool TypeAltiVecVector : 1;
|
||||
bool TypeAltiVecPixel : 1;
|
||||
bool TypeSpecOwned : 1;
|
||||
|
||||
// type-qualifiers
|
||||
|
@ -193,7 +196,7 @@ private:
|
|||
SourceRange Range;
|
||||
|
||||
SourceLocation StorageClassSpecLoc, SCS_threadLoc;
|
||||
SourceLocation TSWLoc, TSCLoc, TSSLoc, TSTLoc;
|
||||
SourceLocation TSWLoc, TSCLoc, TSSLoc, TSTLoc, AltiVecLoc;
|
||||
SourceRange TypeofParensRange;
|
||||
SourceLocation TQ_constLoc, TQ_restrictLoc, TQ_volatileLoc;
|
||||
SourceLocation FS_inlineLoc, FS_virtualLoc, FS_explicitLoc;
|
||||
|
@ -213,6 +216,8 @@ public:
|
|||
TypeSpecComplex(TSC_unspecified),
|
||||
TypeSpecSign(TSS_unspecified),
|
||||
TypeSpecType(TST_unspecified),
|
||||
TypeAltiVecVector(false),
|
||||
TypeAltiVecPixel(false),
|
||||
TypeSpecOwned(false),
|
||||
TypeQualifiers(TSS_unspecified),
|
||||
FS_inline_specified(false),
|
||||
|
@ -250,6 +255,8 @@ public:
|
|||
TSC getTypeSpecComplex() const { return (TSC)TypeSpecComplex; }
|
||||
TSS getTypeSpecSign() const { return (TSS)TypeSpecSign; }
|
||||
TST getTypeSpecType() const { return (TST)TypeSpecType; }
|
||||
bool isTypeAltiVecVector() const { return TypeAltiVecVector; }
|
||||
bool isTypeAltiVecPixel() const { return TypeAltiVecPixel; }
|
||||
bool isTypeSpecOwned() const { return TypeSpecOwned; }
|
||||
void *getTypeRep() const { return TypeRep; }
|
||||
CXXScopeSpec &getTypeSpecScope() { return TypeScope; }
|
||||
|
@ -260,6 +267,7 @@ public:
|
|||
SourceLocation getTypeSpecComplexLoc() const { return TSCLoc; }
|
||||
SourceLocation getTypeSpecSignLoc() const { return TSSLoc; }
|
||||
SourceLocation getTypeSpecTypeLoc() const { return TSTLoc; }
|
||||
SourceLocation getAltiVecLoc() const { return AltiVecLoc; }
|
||||
|
||||
SourceRange getTypeofParensRange() const { return TypeofParensRange; }
|
||||
void setTypeofParensRange(SourceRange range) { TypeofParensRange = range; }
|
||||
|
@ -344,6 +352,10 @@ public:
|
|||
unsigned &DiagID);
|
||||
bool SetTypeSpecType(TST T, SourceLocation Loc, const char *&PrevSpec,
|
||||
unsigned &DiagID, void *Rep = 0, bool Owned = false);
|
||||
bool SetTypeAltiVecVector(bool isAltiVecVector, SourceLocation Loc,
|
||||
const char *&PrevSpec, unsigned &DiagID);
|
||||
bool SetTypeAltiVecPixel(bool isAltiVecPixel, SourceLocation Loc,
|
||||
const char *&PrevSpec, unsigned &DiagID);
|
||||
bool SetTypeSpecError();
|
||||
void UpdateTypeRep(void *Rep) { TypeRep = Rep; }
|
||||
|
||||
|
|
|
@ -81,6 +81,11 @@ class Parser {
|
|||
/// Ident_super - IdentifierInfo for "super", to support fast
|
||||
/// comparison.
|
||||
IdentifierInfo *Ident_super;
|
||||
/// Ident_vector and Ident_pixel - cached IdentifierInfo's for
|
||||
/// "vector" and "pixel" fast comparison. Only present if
|
||||
/// AltiVec enabled.
|
||||
IdentifierInfo *Ident_vector;
|
||||
IdentifierInfo *Ident_pixel;
|
||||
|
||||
llvm::OwningPtr<PragmaHandler> PackHandler;
|
||||
llvm::OwningPtr<PragmaHandler> UnusedHandler;
|
||||
|
@ -320,6 +325,81 @@ private:
|
|||
/// annotated.
|
||||
bool TryAnnotateCXXScopeToken(bool EnteringContext = false);
|
||||
|
||||
/// TryAltiVecToken - Check for context-sensitive AltiVec identifier tokens,
|
||||
/// replacing them with the non-context-sensitive keywords. This returns
|
||||
/// true if the token was replaced.
|
||||
bool TryAltiVecToken(DeclSpec &DS, SourceLocation Loc,
|
||||
const char *&PrevSpec, unsigned &DiagID, bool &isInvalid) {
|
||||
if (getLang().AltiVec) {
|
||||
if (Tok.getIdentifierInfo() == Ident_vector) {
|
||||
const Token nextToken = NextToken();
|
||||
switch (nextToken.getKind()) {
|
||||
case tok::kw_short:
|
||||
case tok::kw_long:
|
||||
case tok::kw_signed:
|
||||
case tok::kw_unsigned:
|
||||
case tok::kw_void:
|
||||
case tok::kw_char:
|
||||
case tok::kw_int:
|
||||
case tok::kw_float:
|
||||
case tok::kw_double:
|
||||
case tok::kw_bool:
|
||||
case tok::kw___pixel:
|
||||
isInvalid = DS.SetTypeAltiVecVector(true, Loc, PrevSpec, DiagID);
|
||||
return true;
|
||||
case tok::identifier:
|
||||
if (nextToken.getIdentifierInfo() == Ident_pixel) {
|
||||
isInvalid = DS.SetTypeAltiVecVector(true, Loc, PrevSpec, DiagID);
|
||||
return true;
|
||||
}
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
} else if ((Tok.getIdentifierInfo() == Ident_pixel) &&
|
||||
DS.isTypeAltiVecVector()) {
|
||||
isInvalid = DS.SetTypeAltiVecPixel(true, Loc, PrevSpec, DiagID);
|
||||
return true;
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
/// TryAltiVecVectorToken - Check for context-sensitive AltiVec vector
|
||||
/// identifier token, replacing it with the non-context-sensitive __vector.
|
||||
/// This returns true if the token was replaced.
|
||||
bool TryAltiVecVectorToken() {
|
||||
if (getLang().AltiVec) {
|
||||
if (Tok.getIdentifierInfo() == Ident_vector) {
|
||||
const Token nextToken = NextToken();
|
||||
switch (nextToken.getKind()) {
|
||||
case tok::kw_short:
|
||||
case tok::kw_long:
|
||||
case tok::kw_signed:
|
||||
case tok::kw_unsigned:
|
||||
case tok::kw_void:
|
||||
case tok::kw_char:
|
||||
case tok::kw_int:
|
||||
case tok::kw_float:
|
||||
case tok::kw_double:
|
||||
case tok::kw_bool:
|
||||
case tok::kw___pixel:
|
||||
Tok.setKind(tok::kw___vector);
|
||||
return true;
|
||||
case tok::identifier:
|
||||
if (nextToken.getIdentifierInfo() == Ident_pixel) {
|
||||
Tok.setKind(tok::kw___vector);
|
||||
return true;
|
||||
}
|
||||
break;
|
||||
default:
|
||||
break;
|
||||
}
|
||||
}
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
/// TentativeParsingAction - An object that is used as a kind of "tentative
|
||||
/// parsing transaction". It gets instantiated to mark the token position and
|
||||
/// after the token consumption is done, Commit() or Revert() is called to
|
||||
|
|
|
@ -1610,7 +1610,8 @@ QualType ASTContext::getIncompleteArrayType(QualType EltTy,
|
|||
|
||||
/// getVectorType - Return the unique reference to a vector type of
|
||||
/// the specified element type and size. VectorType must be a built-in type.
|
||||
QualType ASTContext::getVectorType(QualType vecType, unsigned NumElts) {
|
||||
QualType ASTContext::getVectorType(QualType vecType, unsigned NumElts,
|
||||
bool IsAltiVec, bool IsPixel) {
|
||||
BuiltinType *baseType;
|
||||
|
||||
baseType = dyn_cast<BuiltinType>(getCanonicalType(vecType).getTypePtr());
|
||||
|
@ -1618,7 +1619,8 @@ QualType ASTContext::getVectorType(QualType vecType, unsigned NumElts) {
|
|||
|
||||
// Check if we've already instantiated a vector of this type.
|
||||
llvm::FoldingSetNodeID ID;
|
||||
VectorType::Profile(ID, vecType, NumElts, Type::Vector);
|
||||
VectorType::Profile(ID, vecType, NumElts, Type::Vector,
|
||||
IsAltiVec, IsPixel);
|
||||
void *InsertPos = 0;
|
||||
if (VectorType *VTP = VectorTypes.FindNodeOrInsertPos(ID, InsertPos))
|
||||
return QualType(VTP, 0);
|
||||
|
@ -1626,15 +1628,16 @@ QualType ASTContext::getVectorType(QualType vecType, unsigned NumElts) {
|
|||
// If the element type isn't canonical, this won't be a canonical type either,
|
||||
// so fill in the canonical type field.
|
||||
QualType Canonical;
|
||||
if (!vecType.isCanonical()) {
|
||||
Canonical = getVectorType(getCanonicalType(vecType), NumElts);
|
||||
if (!vecType.isCanonical() || IsAltiVec || IsPixel) {
|
||||
Canonical = getVectorType(getCanonicalType(vecType),
|
||||
NumElts, false, false);
|
||||
|
||||
// Get the new insert position for the node we care about.
|
||||
VectorType *NewIP = VectorTypes.FindNodeOrInsertPos(ID, InsertPos);
|
||||
assert(NewIP == 0 && "Shouldn't be in the map!"); NewIP = NewIP;
|
||||
}
|
||||
VectorType *New = new (*this, TypeAlignment)
|
||||
VectorType(vecType, NumElts, Canonical);
|
||||
VectorType(vecType, NumElts, Canonical, IsAltiVec, IsPixel);
|
||||
VectorTypes.InsertNode(New, InsertPos);
|
||||
Types.push_back(New);
|
||||
return QualType(New, 0);
|
||||
|
@ -1650,7 +1653,7 @@ QualType ASTContext::getExtVectorType(QualType vecType, unsigned NumElts) {
|
|||
|
||||
// Check if we've already instantiated a vector of this type.
|
||||
llvm::FoldingSetNodeID ID;
|
||||
VectorType::Profile(ID, vecType, NumElts, Type::ExtVector);
|
||||
VectorType::Profile(ID, vecType, NumElts, Type::ExtVector, false, false);
|
||||
void *InsertPos = 0;
|
||||
if (VectorType *VTP = VectorTypes.FindNodeOrInsertPos(ID, InsertPos))
|
||||
return QualType(VTP, 0);
|
||||
|
@ -4636,7 +4639,7 @@ QualType ASTContext::getCorrespondingUnsignedType(QualType T) {
|
|||
// Turn <4 x signed int> -> <4 x unsigned int>
|
||||
if (const VectorType *VTy = T->getAs<VectorType>())
|
||||
return getVectorType(getCorrespondingUnsignedType(VTy->getElementType()),
|
||||
VTy->getNumElements());
|
||||
VTy->getNumElements(), VTy->isAltiVec(), VTy->isPixel());
|
||||
|
||||
// For enums, we return the unsigned version of the base type.
|
||||
if (const EnumType *ETy = T->getAs<EnumType>())
|
||||
|
@ -4793,7 +4796,8 @@ static QualType DecodeTypeFromStr(const char *&Str, ASTContext &Context,
|
|||
Str = End;
|
||||
|
||||
QualType ElementType = DecodeTypeFromStr(Str, Context, Error, false);
|
||||
Type = Context.getVectorType(ElementType, NumElements);
|
||||
// FIXME: Don't know what to do about AltiVec.
|
||||
Type = Context.getVectorType(ElementType, NumElements, false, false);
|
||||
break;
|
||||
}
|
||||
case 'X': {
|
||||
|
|
|
@ -225,15 +225,24 @@ void TypePrinter::PrintDependentSizedExtVector(
|
|||
}
|
||||
|
||||
void TypePrinter::PrintVector(const VectorType *T, std::string &S) {
|
||||
// FIXME: We prefer to print the size directly here, but have no way
|
||||
// to get the size of the type.
|
||||
Print(T->getElementType(), S);
|
||||
std::string V = "__attribute__((__vector_size__(";
|
||||
V += llvm::utostr_32(T->getNumElements()); // convert back to bytes.
|
||||
std::string ET;
|
||||
Print(T->getElementType(), ET);
|
||||
V += " * sizeof(" + ET + ")))) ";
|
||||
S = V + S;
|
||||
if (T->isAltiVec()) {
|
||||
if (T->isPixel())
|
||||
S = "__vector __pixel " + S;
|
||||
else {
|
||||
Print(T->getElementType(), S);
|
||||
S = "__vector " + S;
|
||||
}
|
||||
} else {
|
||||
// FIXME: We prefer to print the size directly here, but have no way
|
||||
// to get the size of the type.
|
||||
Print(T->getElementType(), S);
|
||||
std::string V = "__attribute__((__vector_size__(";
|
||||
V += llvm::utostr_32(T->getNumElements()); // convert back to bytes.
|
||||
std::string ET;
|
||||
Print(T->getElementType(), ET);
|
||||
V += " * sizeof(" + ET + ")))) ";
|
||||
S = V + S;
|
||||
}
|
||||
}
|
||||
|
||||
void TypePrinter::PrintExtVector(const ExtVectorType *T, std::string &S) {
|
||||
|
|
|
@ -68,7 +68,8 @@ namespace {
|
|||
KEYCXX0X = 8,
|
||||
KEYGNU = 16,
|
||||
KEYMS = 32,
|
||||
BOOLSUPPORT = 64
|
||||
BOOLSUPPORT = 64,
|
||||
KEYALTIVEC = 128
|
||||
};
|
||||
}
|
||||
|
||||
|
@ -91,6 +92,7 @@ static void AddKeyword(const char *Keyword, unsigned KWLen,
|
|||
else if (LangOpts.GNUMode && (Flags & KEYGNU)) AddResult = 1;
|
||||
else if (LangOpts.Microsoft && (Flags & KEYMS)) AddResult = 1;
|
||||
else if (LangOpts.Bool && (Flags & BOOLSUPPORT)) AddResult = 2;
|
||||
else if (LangOpts.AltiVec && (Flags & KEYALTIVEC)) AddResult = 2;
|
||||
|
||||
// Don't add this keyword if disabled in this language.
|
||||
if (AddResult == 0) return;
|
||||
|
|
|
@ -1880,18 +1880,20 @@ QualType PCHReader::ReadTypeRecord(uint64_t Offset) {
|
|||
}
|
||||
|
||||
case pch::TYPE_VECTOR: {
|
||||
if (Record.size() != 2) {
|
||||
if (Record.size() != 4) {
|
||||
Error("incorrect encoding of vector type in PCH file");
|
||||
return QualType();
|
||||
}
|
||||
|
||||
QualType ElementType = GetType(Record[0]);
|
||||
unsigned NumElements = Record[1];
|
||||
return Context->getVectorType(ElementType, NumElements);
|
||||
bool AltiVec = Record[2];
|
||||
bool Pixel = Record[3];
|
||||
return Context->getVectorType(ElementType, NumElements, AltiVec, Pixel);
|
||||
}
|
||||
|
||||
case pch::TYPE_EXT_VECTOR: {
|
||||
if (Record.size() != 2) {
|
||||
if (Record.size() != 4) {
|
||||
Error("incorrect encoding of extended vector type in PCH file");
|
||||
return QualType();
|
||||
}
|
||||
|
|
|
@ -128,6 +128,8 @@ void PCHTypeWriter::VisitVariableArrayType(const VariableArrayType *T) {
|
|||
void PCHTypeWriter::VisitVectorType(const VectorType *T) {
|
||||
Writer.AddTypeRef(T->getElementType(), Record);
|
||||
Record.push_back(T->getNumElements());
|
||||
Record.push_back(T->isAltiVec());
|
||||
Record.push_back(T->isPixel());
|
||||
Code = pch::TYPE_VECTOR;
|
||||
}
|
||||
|
||||
|
|
|
@ -192,6 +192,7 @@ const char *DeclSpec::getSpecifierName(DeclSpec::TST T) {
|
|||
case DeclSpec::TST_decimal32: return "_Decimal32";
|
||||
case DeclSpec::TST_decimal64: return "_Decimal64";
|
||||
case DeclSpec::TST_decimal128: return "_Decimal128";
|
||||
case DeclSpec::TST_pixel: return "__pixel";
|
||||
case DeclSpec::TST_enum: return "enum";
|
||||
case DeclSpec::TST_class: return "class";
|
||||
case DeclSpec::TST_union: return "union";
|
||||
|
@ -253,6 +254,11 @@ bool DeclSpec::SetTypeSpecWidth(TSW W, SourceLocation Loc,
|
|||
return BadSpecifier(W, (TSW)TypeSpecWidth, PrevSpec, DiagID);
|
||||
TypeSpecWidth = W;
|
||||
TSWLoc = Loc;
|
||||
if (TypeAltiVecVector && ((TypeSpecWidth == TSW_long) || (TypeSpecWidth == TSW_longlong))) {
|
||||
PrevSpec = DeclSpec::getSpecifierName((TST) TypeSpecType);
|
||||
DiagID = diag::warn_vector_long_decl_spec_combination;
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
|
@ -289,6 +295,38 @@ bool DeclSpec::SetTypeSpecType(TST T, SourceLocation Loc,
|
|||
TypeRep = Rep;
|
||||
TSTLoc = Loc;
|
||||
TypeSpecOwned = Owned;
|
||||
if (TypeAltiVecVector && (TypeSpecType == TST_double)) {
|
||||
PrevSpec = DeclSpec::getSpecifierName((TST) TypeSpecType);
|
||||
DiagID = diag::err_invalid_vector_double_decl_spec_combination;
|
||||
return true;
|
||||
}
|
||||
return false;
|
||||
}
|
||||
|
||||
bool DeclSpec::SetTypeAltiVecVector(bool isAltiVecVector, SourceLocation Loc,
|
||||
const char *&PrevSpec, unsigned &DiagID) {
|
||||
if (TypeSpecType != TST_unspecified) {
|
||||
PrevSpec = DeclSpec::getSpecifierName((TST) TypeSpecType);
|
||||
DiagID = diag::err_invalid_vector_decl_spec_combination;
|
||||
return true;
|
||||
}
|
||||
TypeAltiVecVector = isAltiVecVector;
|
||||
AltiVecLoc = Loc;
|
||||
return false;
|
||||
}
|
||||
|
||||
bool DeclSpec::SetTypeAltiVecPixel(bool isAltiVecPixel, SourceLocation Loc,
|
||||
const char *&PrevSpec, unsigned &DiagID) {
|
||||
if (!TypeAltiVecVector || (TypeSpecType != TST_unspecified)) {
|
||||
PrevSpec = DeclSpec::getSpecifierName((TST) TypeSpecType);
|
||||
DiagID = diag::err_invalid_pixel_decl_spec_combination;
|
||||
return true;
|
||||
}
|
||||
TypeSpecType = TST_int;
|
||||
TypeSpecSign = TSS_unsigned;
|
||||
TypeSpecWidth = TSW_short;
|
||||
TypeAltiVecPixel = isAltiVecPixel;
|
||||
TSTLoc = Loc;
|
||||
return false;
|
||||
}
|
||||
|
||||
|
|
|
@ -1029,6 +1029,10 @@ void Parser::ParseDeclarationSpecifiers(DeclSpec &DS,
|
|||
if (DS.hasTypeSpecifier())
|
||||
goto DoneWithDeclSpec;
|
||||
|
||||
// Check for need to substitute AltiVec keyword tokens.
|
||||
if (TryAltiVecToken(DS, Loc, PrevSpec, DiagID, isInvalid))
|
||||
break;
|
||||
|
||||
// It has to be available as a typedef too!
|
||||
TypeTy *TypeRep = Actions.getTypeName(*Tok.getIdentifierInfo(),
|
||||
Tok.getLocation(), CurScope);
|
||||
|
@ -1270,6 +1274,12 @@ void Parser::ParseDeclarationSpecifiers(DeclSpec &DS,
|
|||
isInvalid = DS.SetTypeSpecType(DeclSpec::TST_decimal128, Loc, PrevSpec,
|
||||
DiagID);
|
||||
break;
|
||||
case tok::kw___vector:
|
||||
isInvalid = DS.SetTypeAltiVecVector(true, Loc, PrevSpec, DiagID);
|
||||
break;
|
||||
case tok::kw___pixel:
|
||||
isInvalid = DS.SetTypeAltiVecPixel(true, Loc, PrevSpec, DiagID);
|
||||
break;
|
||||
|
||||
// class-specifier:
|
||||
case tok::kw_class:
|
||||
|
@ -1395,6 +1405,7 @@ void Parser::ParseDeclarationSpecifiers(DeclSpec &DS,
|
|||
/// [OBJC] class-name objc-protocol-refs[opt] [TODO]
|
||||
/// [OBJC] typedef-name objc-protocol-refs[opt] [TODO]
|
||||
/// [C++0x] 'decltype' ( expression )
|
||||
/// [AltiVec] '__vector'
|
||||
bool Parser::ParseOptionalTypeSpecifier(DeclSpec &DS, bool& isInvalid,
|
||||
const char *&PrevSpec,
|
||||
unsigned &DiagID,
|
||||
|
@ -1404,6 +1415,10 @@ bool Parser::ParseOptionalTypeSpecifier(DeclSpec &DS, bool& isInvalid,
|
|||
|
||||
switch (Tok.getKind()) {
|
||||
case tok::identifier: // foo::bar
|
||||
// Check for need to substitute AltiVec keyword tokens.
|
||||
if (TryAltiVecToken(DS, Loc, PrevSpec, DiagID, isInvalid))
|
||||
break;
|
||||
// Fall through.
|
||||
case tok::kw_typename: // typename foo::bar
|
||||
// Annotate typenames and C++ scope specifiers. If we get one, just
|
||||
// recurse to handle whatever we get.
|
||||
|
@ -1520,7 +1535,13 @@ bool Parser::ParseOptionalTypeSpecifier(DeclSpec &DS, bool& isInvalid,
|
|||
isInvalid = DS.SetTypeSpecType(DeclSpec::TST_decimal128, Loc, PrevSpec,
|
||||
DiagID);
|
||||
break;
|
||||
|
||||
case tok::kw___vector:
|
||||
isInvalid = DS.SetTypeAltiVecVector(true, Loc, PrevSpec, DiagID);
|
||||
break;
|
||||
case tok::kw___pixel:
|
||||
isInvalid = DS.SetTypeAltiVecPixel(true, Loc, PrevSpec, DiagID);
|
||||
break;
|
||||
|
||||
// class-specifier:
|
||||
case tok::kw_class:
|
||||
case tok::kw_struct:
|
||||
|
@ -1987,6 +2008,9 @@ bool Parser::isTypeSpecifierQualifier() {
|
|||
default: return false;
|
||||
|
||||
case tok::identifier: // foo::bar
|
||||
if (TryAltiVecVectorToken())
|
||||
return true;
|
||||
// Fall through.
|
||||
case tok::kw_typename: // typename T::type
|
||||
// Annotate typenames and C++ scope specifiers. If we get one, just
|
||||
// recurse to handle whatever we get.
|
||||
|
@ -2032,6 +2056,7 @@ bool Parser::isTypeSpecifierQualifier() {
|
|||
case tok::kw__Decimal32:
|
||||
case tok::kw__Decimal64:
|
||||
case tok::kw__Decimal128:
|
||||
case tok::kw___vector:
|
||||
|
||||
// struct-or-union-specifier (C99) or class-specifier (C++)
|
||||
case tok::kw_class:
|
||||
|
@ -2072,7 +2097,9 @@ bool Parser::isDeclarationSpecifier() {
|
|||
// Unfortunate hack to support "Class.factoryMethod" notation.
|
||||
if (getLang().ObjC1 && NextToken().is(tok::period))
|
||||
return false;
|
||||
// Fall through
|
||||
if (TryAltiVecVectorToken())
|
||||
return true;
|
||||
// Fall through.
|
||||
|
||||
case tok::kw_typename: // typename T::type
|
||||
// Annotate typenames and C++ scope specifiers. If we get one, just
|
||||
|
@ -2123,6 +2150,7 @@ bool Parser::isDeclarationSpecifier() {
|
|||
case tok::kw__Decimal32:
|
||||
case tok::kw__Decimal64:
|
||||
case tok::kw__Decimal128:
|
||||
case tok::kw___vector:
|
||||
|
||||
// struct-or-union-specifier (C99) or class-specifier (C++)
|
||||
case tok::kw_class:
|
||||
|
@ -2768,7 +2796,8 @@ void Parser::ParseFunctionDeclarator(SourceLocation LParenLoc, Declarator &D,
|
|||
|
||||
// Alternatively, this parameter list may be an identifier list form for a
|
||||
// K&R-style function: void foo(a,b,c)
|
||||
if (!getLang().CPlusPlus && Tok.is(tok::identifier)) {
|
||||
if (!getLang().CPlusPlus && Tok.is(tok::identifier)
|
||||
&& !TryAltiVecVectorToken()) {
|
||||
if (!TryAnnotateTypeOrScopeToken()) {
|
||||
// K&R identifier lists can't have typedefs as identifiers, per
|
||||
// C99 6.7.5.3p11.
|
||||
|
|
|
@ -780,6 +780,7 @@ Parser::OwningExprResult Parser::ParseCastExpression(bool isUnaryExpression,
|
|||
case tok::kw_void:
|
||||
case tok::kw_typename:
|
||||
case tok::kw_typeof:
|
||||
case tok::kw___vector:
|
||||
case tok::annot_typename: {
|
||||
if (!getLang().CPlusPlus) {
|
||||
Diag(Tok, diag::err_expected_expression);
|
||||
|
|
|
@ -672,6 +672,11 @@ Parser::TPResult Parser::TryParseDeclarator(bool mayBeAbstract,
|
|||
Parser::TPResult Parser::isCXXDeclarationSpecifier() {
|
||||
switch (Tok.getKind()) {
|
||||
case tok::identifier: // foo::bar
|
||||
// Check for need to substitute AltiVec __vector keyword
|
||||
// for "vector" identifier.
|
||||
if (TryAltiVecVectorToken())
|
||||
return TPResult::True();
|
||||
// Fall through.
|
||||
case tok::kw_typename: // typename T::type
|
||||
// Annotate typenames and C++ scope specifiers. If we get one, just
|
||||
// recurse to handle whatever we get.
|
||||
|
@ -750,6 +755,10 @@ Parser::TPResult Parser::isCXXDeclarationSpecifier() {
|
|||
case tok::kw___ptr64:
|
||||
case tok::kw___forceinline:
|
||||
return TPResult::True();
|
||||
|
||||
// AltiVec
|
||||
case tok::kw___vector:
|
||||
return TPResult::True();
|
||||
|
||||
case tok::annot_cxxscope: // foo::bar or ::foo::bar, but already parsed
|
||||
// We've already annotated a scope; try to annotate a type.
|
||||
|
|
|
@ -346,6 +346,11 @@ void Parser::Initialize() {
|
|||
}
|
||||
|
||||
Ident_super = &PP.getIdentifierTable().get("super");
|
||||
|
||||
if (getLang().AltiVec) {
|
||||
Ident_vector = &PP.getIdentifierTable().get("vector");
|
||||
Ident_pixel = &PP.getIdentifierTable().get("pixel");
|
||||
}
|
||||
}
|
||||
|
||||
/// ParseTopLevelDecl - Parse one top-level declaration, return whatever the
|
||||
|
|
|
@ -343,6 +343,11 @@ static QualType ConvertDeclSpecToType(Declarator &TheDeclarator, Sema &TheSema){
|
|||
if (TheSema.getLangOptions().Freestanding)
|
||||
TheSema.Diag(DS.getTypeSpecComplexLoc(), diag::ext_freestanding_complex);
|
||||
Result = Context.getComplexType(Result);
|
||||
} else if (DS.isTypeAltiVecVector()) {
|
||||
unsigned typeSize = static_cast<unsigned>(Context.getTypeSize(Result));
|
||||
assert(typeSize > 0 && "type size for vector must be greater than 0 bits");
|
||||
Result = Context.getVectorType(Result, 128/typeSize, true,
|
||||
DS.isTypeAltiVecPixel());
|
||||
}
|
||||
|
||||
assert(DS.getTypeSpecComplex() != DeclSpec::TSC_imaginary &&
|
||||
|
@ -1753,7 +1758,7 @@ static void HandleVectorSizeAttr(QualType& CurType, const AttributeList &Attr, S
|
|||
|
||||
// Success! Instantiate the vector type, the number of elements is > 0, and
|
||||
// not required to be a power of 2, unlike GCC.
|
||||
CurType = S.Context.getVectorType(CurType, vectorSize/typeSize);
|
||||
CurType = S.Context.getVectorType(CurType, vectorSize/typeSize, false, false);
|
||||
}
|
||||
|
||||
void Sema::ProcessTypeAttributeList(QualType &Result, const AttributeList *AL,
|
||||
|
|
|
@ -428,7 +428,8 @@ public:
|
|||
///
|
||||
/// By default, performs semantic analysis when building the vector type.
|
||||
/// Subclasses may override this routine to provide different behavior.
|
||||
QualType RebuildVectorType(QualType ElementType, unsigned NumElements);
|
||||
QualType RebuildVectorType(QualType ElementType, unsigned NumElements,
|
||||
bool IsAltiVec, bool IsPixel);
|
||||
|
||||
/// \brief Build a new extended vector type given the element type and
|
||||
/// number of elements.
|
||||
|
@ -2472,7 +2473,8 @@ QualType TreeTransform<Derived>::TransformVectorType(TypeLocBuilder &TLB,
|
|||
QualType Result = TL.getType();
|
||||
if (getDerived().AlwaysRebuild() ||
|
||||
ElementType != T->getElementType()) {
|
||||
Result = getDerived().RebuildVectorType(ElementType, T->getNumElements());
|
||||
Result = getDerived().RebuildVectorType(ElementType, T->getNumElements(),
|
||||
T->isAltiVec(), T->isPixel());
|
||||
if (Result.isNull())
|
||||
return QualType();
|
||||
}
|
||||
|
@ -5421,9 +5423,11 @@ TreeTransform<Derived>::RebuildDependentSizedArrayType(QualType ElementType,
|
|||
|
||||
template<typename Derived>
|
||||
QualType TreeTransform<Derived>::RebuildVectorType(QualType ElementType,
|
||||
unsigned NumElements) {
|
||||
unsigned NumElements,
|
||||
bool IsAltiVec, bool IsPixel) {
|
||||
// FIXME: semantic checking!
|
||||
return SemaRef.Context.getVectorType(ElementType, NumElements);
|
||||
return SemaRef.Context.getVectorType(ElementType, NumElements,
|
||||
IsAltiVec, IsPixel);
|
||||
}
|
||||
|
||||
template<typename Derived>
|
||||
|
|
|
@ -0,0 +1,91 @@
|
|||
// RUN: %clang_cc1 -faltivec -fsyntax-only -verify %s
|
||||
|
||||
__vector char vv_c;
|
||||
__vector signed char vv_sc;
|
||||
__vector unsigned char vv_uc;
|
||||
__vector short vv_s;
|
||||
__vector signed short vv_ss;
|
||||
__vector unsigned short vv_us;
|
||||
__vector short int vv_si;
|
||||
__vector signed short int vv_ssi;
|
||||
__vector unsigned short int vv_usi;
|
||||
__vector int vv_i;
|
||||
__vector signed int vv_sint;
|
||||
__vector unsigned int vv_ui;
|
||||
__vector float vv_f;
|
||||
__vector bool vv_b;
|
||||
__vector __pixel vv_p;
|
||||
__vector pixel vv__p;
|
||||
__vector int vf__r();
|
||||
void vf__a(__vector int a);
|
||||
void vf__a2(int b, __vector int a);
|
||||
|
||||
vector char v_c;
|
||||
vector signed char v_sc;
|
||||
vector unsigned char v_uc;
|
||||
vector short v_s;
|
||||
vector signed short v_ss;
|
||||
vector unsigned short v_us;
|
||||
vector short int v_si;
|
||||
vector signed short int v_ssi;
|
||||
vector unsigned short int v_usi;
|
||||
vector int v_i;
|
||||
vector signed int v_sint;
|
||||
vector unsigned int v_ui;
|
||||
vector float v_f;
|
||||
vector bool v_b;
|
||||
vector __pixel v_p;
|
||||
vector pixel v__p;
|
||||
vector int f__r();
|
||||
void f_a(vector int a);
|
||||
void f_a2(int b, vector int a);
|
||||
|
||||
// These should have warnings.
|
||||
__vector long vv_l; // expected-warning {{Use of "long" with "__vector" is deprecated}}
|
||||
__vector signed long vv_sl; // expected-warning {{Use of "long" with "__vector" is deprecated}}
|
||||
__vector unsigned long vv_ul; // expected-warning {{Use of "long" with "__vector" is deprecated}}
|
||||
__vector long int vv_li; // expected-warning {{Use of "long" with "__vector" is deprecated}}
|
||||
__vector signed long int vv_sli; // expected-warning {{Use of "long" with "__vector" is deprecated}}
|
||||
__vector unsigned long int vv_uli; // expected-warning {{Use of "long" with "__vector" is deprecated}}
|
||||
vector long v_l; // expected-warning {{Use of "long" with "__vector" is deprecated}}
|
||||
vector signed long v_sl; // expected-warning {{Use of "long" with "__vector" is deprecated}}
|
||||
vector unsigned long v_ul; // expected-warning {{Use of "long" with "__vector" is deprecated}}
|
||||
vector long int v_li; // expected-warning {{Use of "long" with "__vector" is deprecated}}
|
||||
vector signed long int v_sli; // expected-warning {{Use of "long" with "__vector" is deprecated}}
|
||||
vector unsigned long int v_uli; // expected-warning {{Use of "long" with "__vector" is deprecated}}
|
||||
__vector long double vv_ld; // expected-warning {{Use of "long" with "__vector" is deprecated}} expected-error {{cannot use "double" with "__vector"}}
|
||||
vector long double v_ld; // expected-warning {{Use of "long" with "__vector" is deprecated}} expected-error {{cannot use "double" with "__vector"}}
|
||||
|
||||
// These should have errors.
|
||||
__vector double vv_d; // expected-error {{cannot use "double" with "__vector"}}
|
||||
__vector double vv_d; // expected-error {{cannot use "double" with "__vector"}}
|
||||
vector double v_d; // expected-error {{cannot use "double" with "__vector"}}
|
||||
vector double v_d; // expected-error {{cannot use "double" with "__vector"}}
|
||||
__vector long double vv_ld; // expected-warning {{Use of "long" with "__vector" is deprecated}} expected-error {{cannot use "double" with "__vector"}}
|
||||
vector long double v_ld; // expected-warning {{Use of "long" with "__vector" is deprecated}} expected-error {{cannot use "double" with "__vector"}}
|
||||
|
||||
void f() {
|
||||
__vector unsigned int v = {0,0,0,0};
|
||||
__vector int v__cast = (__vector int)v;
|
||||
__vector int v_cast = (vector int)v;
|
||||
__vector char vb_cast = (vector char)v;
|
||||
|
||||
// Check some casting between gcc and altivec vectors.
|
||||
#define gccvector __attribute__((vector_size(16)))
|
||||
gccvector unsigned int gccv = {0,0,0,0};
|
||||
gccvector unsigned int gccv1 = gccv;
|
||||
gccvector int gccv2 = (gccvector int)gccv;
|
||||
gccvector unsigned int gccv3 = v;
|
||||
__vector unsigned int av = gccv;
|
||||
__vector int avi = (__vector int)gccv;
|
||||
gccvector unsigned int gv = v;
|
||||
gccvector int gvi = (gccvector int)v;
|
||||
__attribute__((vector_size(8))) unsigned int gv8;
|
||||
gv8 = gccv; // expected-error {{incompatible type assigning '__attribute__((__vector_size__(4 * sizeof(unsigned int)))) unsigned int', expected '__attribute__((__vector_size__(2 * sizeof(unsigned int)))) unsigned int'}}
|
||||
av = gv8; // expected-error {{incompatible type assigning '__attribute__((__vector_size__(2 * sizeof(unsigned int)))) unsigned int', expected '__vector unsigned int'}}
|
||||
|
||||
v = gccv;
|
||||
__vector unsigned int tv = gccv;
|
||||
gccv = v;
|
||||
gccvector unsigned int tgv = v;
|
||||
}
|
|
@ -0,0 +1,108 @@
|
|||
// RUN: %clang_cc1 -faltivec -fsyntax-only -verify %s
|
||||
|
||||
// This is the same as the C version:
|
||||
|
||||
__vector char vv_c;
|
||||
__vector signed char vv_sc;
|
||||
__vector unsigned char vv_uc;
|
||||
__vector short vv_s;
|
||||
__vector signed short vv_ss;
|
||||
__vector unsigned short vv_us;
|
||||
__vector short int vv_si;
|
||||
__vector signed short int vv_ssi;
|
||||
__vector unsigned short int vv_usi;
|
||||
__vector int vv_i;
|
||||
__vector signed int vv_sint;
|
||||
__vector unsigned int vv_ui;
|
||||
__vector float vv_f;
|
||||
__vector bool vv_b;
|
||||
__vector __pixel vv_p;
|
||||
__vector pixel vv__p;
|
||||
__vector int vf__r();
|
||||
void vf__a(__vector int a);
|
||||
void vf__a2(int b, __vector int a);
|
||||
|
||||
vector char v_c;
|
||||
vector signed char v_sc;
|
||||
vector unsigned char v_uc;
|
||||
vector short v_s;
|
||||
vector signed short v_ss;
|
||||
vector unsigned short v_us;
|
||||
vector short int v_si;
|
||||
vector signed short int v_ssi;
|
||||
vector unsigned short int v_usi;
|
||||
vector int v_i;
|
||||
vector signed int v_sint;
|
||||
vector unsigned int v_ui;
|
||||
vector float v_f;
|
||||
vector bool v_b;
|
||||
vector __pixel v_p;
|
||||
vector pixel v__p;
|
||||
vector int f__r();
|
||||
void f_a(vector int a);
|
||||
void f_a2(int b, vector int a);
|
||||
|
||||
// These should have warnings.
|
||||
__vector long vv_l; // expected-warning {{Use of "long" with "__vector" is deprecated}}
|
||||
__vector signed long vv_sl; // expected-warning {{Use of "long" with "__vector" is deprecated}}
|
||||
__vector unsigned long vv_ul; // expected-warning {{Use of "long" with "__vector" is deprecated}}
|
||||
__vector long int vv_li; // expected-warning {{Use of "long" with "__vector" is deprecated}}
|
||||
__vector signed long int vv_sli; // expected-warning {{Use of "long" with "__vector" is deprecated}}
|
||||
__vector unsigned long int vv_uli; // expected-warning {{Use of "long" with "__vector" is deprecated}}
|
||||
vector long v_l; // expected-warning {{Use of "long" with "__vector" is deprecated}}
|
||||
vector signed long v_sl; // expected-warning {{Use of "long" with "__vector" is deprecated}}
|
||||
vector unsigned long v_ul; // expected-warning {{Use of "long" with "__vector" is deprecated}}
|
||||
vector long int v_li; // expected-warning {{Use of "long" with "__vector" is deprecated}}
|
||||
vector signed long int v_sli; // expected-warning {{Use of "long" with "__vector" is deprecated}}
|
||||
vector unsigned long int v_uli; // expected-warning {{Use of "long" with "__vector" is deprecated}}
|
||||
__vector long double vv_ld; // expected-warning {{Use of "long" with "__vector" is deprecated}} expected-error {{cannot use "double" with "__vector"}}
|
||||
vector long double v_ld; // expected-warning {{Use of "long" with "__vector" is deprecated}} expected-error {{cannot use "double" with "__vector"}}
|
||||
|
||||
// These should have errors.
|
||||
__vector double vv_d1; // expected-error {{cannot use "double" with "__vector"}}
|
||||
vector double v_d2; // expected-error {{cannot use "double" with "__vector"}}
|
||||
__vector long double vv_ld3; // expected-warning {{Use of "long" with "__vector" is deprecated}} expected-error {{cannot use "double" with "__vector"}}
|
||||
vector long double v_ld4; // expected-warning {{Use of "long" with "__vector" is deprecated}} expected-error {{cannot use "double" with "__vector"}}
|
||||
|
||||
void f() {
|
||||
__vector unsigned int v = {0,0,0,0};
|
||||
__vector int v__cast = (__vector int)v;
|
||||
__vector int v_cast = (vector int)v;
|
||||
__vector char vb_cast = (vector char)v;
|
||||
|
||||
// Check some casting between gcc and altivec vectors.
|
||||
#define gccvector __attribute__((vector_size(16)))
|
||||
gccvector unsigned int gccv = {0,0,0,0};
|
||||
gccvector unsigned int gccv1 = gccv;
|
||||
gccvector int gccv2 = (gccvector int)gccv;
|
||||
gccvector unsigned int gccv3 = v;
|
||||
__vector unsigned int av = gccv;
|
||||
__vector int avi = (__vector int)gccv;
|
||||
gccvector unsigned int gv = v;
|
||||
gccvector int gvi = (gccvector int)v;
|
||||
__attribute__((vector_size(8))) unsigned int gv8;
|
||||
gv8 = gccv; // expected-error {{incompatible type assigning '__attribute__((__vector_size__(4 * sizeof(unsigned int)))) unsigned int', expected '__attribute__((__vector_size__(2 * sizeof(unsigned int)))) unsigned int'}}
|
||||
av = gv8; // expected-error {{incompatible type assigning '__attribute__((__vector_size__(2 * sizeof(unsigned int)))) unsigned int', expected '__vector unsigned int'}}
|
||||
|
||||
v = gccv;
|
||||
__vector unsigned int tv = gccv;
|
||||
gccv = v;
|
||||
gccvector unsigned int tgv = v;
|
||||
}
|
||||
|
||||
// Now for the C++ version:
|
||||
|
||||
class vc__v {
|
||||
__vector int v;
|
||||
__vector int f__r();
|
||||
void f__a(__vector int a);
|
||||
void f__a2(int b, __vector int a);
|
||||
};
|
||||
|
||||
class c_v {
|
||||
vector int v;
|
||||
vector int f__r();
|
||||
void f__a(vector int a);
|
||||
void f__a2(int b, vector int a);
|
||||
};
|
||||
|
Загрузка…
Ссылка в новой задаче