[cfe-commits] r52876 - in /cfe/trunk: include/clang/Parse/DeclSpec.h lib/Sema/Sema.h lib/Sema/SemaDeclAttr.cpp test/Sema/attr-mode.c
Chris Lattner
sabre at nondot.org
Sat Jun 28 17:16:32 PDT 2008
Author: lattner
Date: Sat Jun 28 19:16:31 2008
New Revision: 52876
URL: http://llvm.org/viewvc/llvm-project?rev=52876&view=rev
Log:
Make ProcessDeclAttributes walk the declarator structure pulling
decl attributes out of the various places they can hide. This makes
us correctly reject things like this:
t.c:2:22: error: mode attribute only supported for integer and floating-point types
int **__attribute((mode(HI)))* i32;
^
because you can't make a pointer be HImode.
Modified:
cfe/trunk/include/clang/Parse/DeclSpec.h
cfe/trunk/lib/Sema/Sema.h
cfe/trunk/lib/Sema/SemaDeclAttr.cpp
cfe/trunk/test/Sema/attr-mode.c
Modified: cfe/trunk/include/clang/Parse/DeclSpec.h
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/include/clang/Parse/DeclSpec.h?rev=52876&r1=52875&r2=52876&view=diff
==============================================================================
--- cfe/trunk/include/clang/Parse/DeclSpec.h (original)
+++ cfe/trunk/include/clang/Parse/DeclSpec.h Sat Jun 28 19:16:31 2008
@@ -457,6 +457,19 @@
};
+ /// getAttrs - If there are attributes applied to this declaratorchunk, return
+ /// them.
+ const AttributeList *getAttrs() const {
+ switch (Kind) {
+ default: assert(0 && "Unknown declarator kind!");
+ case Pointer: return Ptr.AttrList;
+ case Reference: return Ref.AttrList;
+ case Array: return 0;
+ case Function: return 0;
+ }
+ }
+
+
/// getPointer - Return a DeclaratorChunk for a pointer.
///
static DeclaratorChunk getPointer(unsigned TypeQuals, SourceLocation Loc,
Modified: cfe/trunk/lib/Sema/Sema.h
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/Sema.h?rev=52876&r1=52875&r2=52876&view=diff
==============================================================================
--- cfe/trunk/lib/Sema/Sema.h (original)
+++ cfe/trunk/lib/Sema/Sema.h Sat Jun 28 19:16:31 2008
@@ -301,7 +301,7 @@
ScopedDecl *ImplicitlyDefineFunction(SourceLocation Loc, IdentifierInfo &II,
Scope *S);
// Decl attributes - this routine is the top level dispatcher.
- void ProcessDeclAttributes(Decl *D, Declarator &PD);
+ void ProcessDeclAttributes(Decl *D, const Declarator &PD);
void ProcessDeclAttributeList(Decl *D, const AttributeList *AttrList);
void ProcessDeclAttribute(Decl *D, const AttributeList &Attr);
Modified: cfe/trunk/lib/Sema/SemaDeclAttr.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/lib/Sema/SemaDeclAttr.cpp?rev=52876&r1=52875&r2=52876&view=diff
==============================================================================
--- cfe/trunk/lib/Sema/SemaDeclAttr.cpp (original)
+++ cfe/trunk/lib/Sema/SemaDeclAttr.cpp Sat Jun 28 19:16:31 2008
@@ -16,9 +16,12 @@
#include "clang/Basic/TargetInfo.h"
using namespace clang;
+//===----------------------------------------------------------------------===//
+// Helper functions
+//===----------------------------------------------------------------------===//
+
static const FunctionTypeProto *getFunctionProto(Decl *d) {
QualType Ty;
-
if (ValueDecl *decl = dyn_cast<ValueDecl>(d))
Ty = decl->getType();
else if (FieldDecl *decl = dyn_cast<FieldDecl>(d))
@@ -54,27 +57,44 @@
ClsName == &Ctx.Idents.get("NSMutableString");
}
-void Sema::ProcessDeclAttributes(Decl *D, Declarator &PD) {
- const AttributeList *DeclSpecAttrs = PD.getDeclSpec().getAttributes();
- const AttributeList *DeclaratorAttrs = PD.getAttributes();
-
- if (DeclSpecAttrs == 0 && DeclaratorAttrs == 0) return;
-
- ProcessDeclAttributeList(D, DeclSpecAttrs);
-
- // If there are any type attributes that were in the declarator, apply them to
- // its top level type.
- if (ValueDecl *VD = dyn_cast<ValueDecl>(D)) {
- QualType DT = VD->getType();
- ProcessTypeAttributes(DT, DeclaratorAttrs);
- VD->setType(DT);
- } else if (TypedefDecl *TD = dyn_cast<TypedefDecl>(D)) {
- QualType DT = TD->getUnderlyingType();
- ProcessTypeAttributes(DT, DeclaratorAttrs);
- TD->setUnderlyingType(DT);
+//===----------------------------------------------------------------------===//
+// Top Level Sema Entry Points
+//===----------------------------------------------------------------------===//
+
+/// ProcessDeclAttributes - Given a declarator (PD) with attributes indicated in
+/// it, apply them to D. This is a bit tricky because PD can have attributes
+/// specified in many different places, and we need to find and apply them all.
+void Sema::ProcessDeclAttributes(Decl *D, const Declarator &PD) {
+ // Apply decl attributes from the DeclSpec if present.
+ if (const AttributeList *Attrs = PD.getDeclSpec().getAttributes())
+ ProcessDeclAttributeList(D, Attrs);
+
+ // Walk the declarator structure, applying decl attributes that were in a type
+ // position to the decl itself. This handles cases like:
+ // int *__attr__(x)** D;
+ // when X is a decl attribute.
+ for (unsigned i = 0, e = PD.getNumTypeObjects(); i != e; ++i)
+ if (const AttributeList *Attrs = PD.getTypeObject(i).getAttrs())
+ ProcessDeclAttributeList(D, Attrs);
+
+ // Finally, apply any attributes on the decl itself.
+ if (const AttributeList *Attrs = PD.getAttributes()) {
+ ProcessDeclAttributeList(D, Attrs);
+
+ // If there are any type attributes that were in the declarator, apply them to
+ // its top-level type.
+ // FIXME: we shouldn't allow type attributes here. :(
+ if (ValueDecl *VD = dyn_cast<ValueDecl>(D)) {
+ QualType DT = VD->getType();
+ ProcessTypeAttributes(DT, Attrs);
+ VD->setType(DT);
+ } else if (TypedefDecl *TD = dyn_cast<TypedefDecl>(D)) {
+ QualType DT = TD->getUnderlyingType();
+ ProcessTypeAttributes(DT, Attrs);
+ TD->setUnderlyingType(DT);
+ }
+ // FIXME: field decl?
}
-
- ProcessDeclAttributeList(D, DeclaratorAttrs);
}
/// ProcessDeclAttributeList - Apply all the decl attributes in the specified
@@ -126,6 +146,10 @@
}
}
+//===----------------------------------------------------------------------===//
+// Attribute Implementations
+//===----------------------------------------------------------------------===//
+
void Sema::HandleExtVectorTypeAttribute(Decl *d, const AttributeList &Attr) {
TypedefDecl *tDecl = dyn_cast<TypedefDecl>(d);
if (tDecl == 0) {
Modified: cfe/trunk/test/Sema/attr-mode.c
URL: http://llvm.org/viewvc/llvm-project/cfe/trunk/test/Sema/attr-mode.c?rev=52876&r1=52875&r2=52876&view=diff
==============================================================================
--- cfe/trunk/test/Sema/attr-mode.c (original)
+++ cfe/trunk/test/Sema/attr-mode.c Sat Jun 28 19:16:31 2008
@@ -13,3 +13,5 @@
typedef int invalid_3 __attribute((mode(II))); // expected-error{{unknown machine mode}}
typedef struct {int i,j,k;} invalid_4 __attribute((mode(SI))); // expected-error{{mode attribute only supported for integer and floating-point types}}
typedef float invalid_5 __attribute((mode(SI))); // expected-error{{type of machine mode does not match type of base type}}
+
+int **__attribute((mode(QI)))* i32; // expected-error{{mode attribute}}
More information about the cfe-commits
mailing list