aboutsummaryrefslogtreecommitdiff
diff options
context:
space:
mode:
-rw-r--r--include/clang/Parse/Action.h7
-rw-r--r--lib/Parse/Parser.cpp1
-rw-r--r--lib/Sema/Sema.h1
-rw-r--r--lib/Sema/SemaDecl.cpp16
-rw-r--r--test/Sema/function.c4
-rw-r--r--test/Sema/redefinition.c5
6 files changed, 30 insertions, 4 deletions
diff --git a/include/clang/Parse/Action.h b/include/clang/Parse/Action.h
index 5d87b17221..0f0d88acc8 100644
--- a/include/clang/Parse/Action.h
+++ b/include/clang/Parse/Action.h
@@ -223,6 +223,13 @@ public:
return Group;
}
+ /// @brief Indicates that all K&R-style parameter declarations have
+ /// been parsed prior to a function definition.
+ /// @param S The function prototype scope.
+ /// @param D The function declarator.
+ virtual void ActOnFinishKNRParamDeclarations(Scope *S, Declarator &D) {
+ }
+
/// ActOnStartOfFunctionDef - This is called at the start of a function
/// definition, instead of calling ActOnDeclarator. The Declarator includes
/// information about formal arguments that are part of this function.
diff --git a/lib/Parse/Parser.cpp b/lib/Parse/Parser.cpp
index 6ae3bf038f..7e1cef950f 100644
--- a/lib/Parse/Parser.cpp
+++ b/lib/Parse/Parser.cpp
@@ -674,6 +674,7 @@ void Parser::ParseKNRParamDeclarations(Declarator &D) {
}
// The actions module must verify that all arguments were declared.
+ Actions.ActOnFinishKNRParamDeclarations(CurScope, D);
}
diff --git a/lib/Sema/Sema.h b/lib/Sema/Sema.h
index 128ba8813a..40cfe8f193 100644
--- a/lib/Sema/Sema.h
+++ b/lib/Sema/Sema.h
@@ -311,6 +311,7 @@ public:
void ActOnUninitializedDecl(DeclTy *dcl);
virtual DeclTy *FinalizeDeclaratorGroup(Scope *S, DeclTy *Group);
+ virtual void ActOnFinishKNRParamDeclarations(Scope *S, Declarator &D);
virtual DeclTy *ActOnStartOfFunctionDef(Scope *S, Declarator &D);
virtual DeclTy *ActOnStartOfFunctionDef(Scope *S, DeclTy *D);
virtual void ObjCActOnStartOfMethodDef(Scope *S, DeclTy *D);
diff --git a/lib/Sema/SemaDecl.cpp b/lib/Sema/SemaDecl.cpp
index 276f2e24e8..e766ca06a5 100644
--- a/lib/Sema/SemaDecl.cpp
+++ b/lib/Sema/SemaDecl.cpp
@@ -2633,8 +2633,7 @@ Sema::ActOnParamDeclarator(Scope *S, Declarator &D) {
}
-Sema::DeclTy *Sema::ActOnStartOfFunctionDef(Scope *FnBodyScope, Declarator &D) {
- assert(getCurFunctionDecl() == 0 && "Function parsing confused");
+void Sema::ActOnFinishKNRParamDeclarations(Scope *S, Declarator &D) {
assert(D.getTypeObject(0).Kind == DeclaratorChunk::Function &&
"Not a function declarator!");
DeclaratorChunk::FunctionTypeInfo &FTI = D.getTypeObject(0).Fun;
@@ -2654,10 +2653,19 @@ Sema::DeclTy *Sema::ActOnStartOfFunctionDef(Scope *FnBodyScope, Declarator &D) {
PrevSpec);
Declarator ParamD(DS, Declarator::KNRTypeListContext);
ParamD.SetIdentifier(FTI.ArgInfo[i].Ident, FTI.ArgInfo[i].IdentLoc);
- FTI.ArgInfo[i].Param = ActOnParamDeclarator(FnBodyScope, ParamD);
+ FTI.ArgInfo[i].Param = ActOnParamDeclarator(S, ParamD);
}
}
- } else {
+ }
+}
+
+Sema::DeclTy *Sema::ActOnStartOfFunctionDef(Scope *FnBodyScope, Declarator &D) {
+ assert(getCurFunctionDecl() == 0 && "Function parsing confused");
+ assert(D.getTypeObject(0).Kind == DeclaratorChunk::Function &&
+ "Not a function declarator!");
+ DeclaratorChunk::FunctionTypeInfo &FTI = D.getTypeObject(0).Fun;
+
+ if (FTI.hasPrototype) {
// FIXME: Diagnose arguments without names in C.
}
diff --git a/test/Sema/function.c b/test/Sema/function.c
index de970a09b3..677f6a3f0e 100644
--- a/test/Sema/function.c
+++ b/test/Sema/function.c
@@ -39,3 +39,7 @@ void t13() {
int t14() {
return; // expected-warning {{non-void function 't14' should return a value}}
}
+
+// <rdar://problem/6097326>
+y(y) { return y; } // expected-warning{{parameter 'y' was not declared, defaulting to type 'int'}} \
+ // expected-warning{{type specifier missing, defaults to 'int'}}
diff --git a/test/Sema/redefinition.c b/test/Sema/redefinition.c
index 5e79070623..97e0473148 100644
--- a/test/Sema/redefinition.c
+++ b/test/Sema/redefinition.c
@@ -3,3 +3,8 @@ int f(int a) { } // expected-note {{previous definition is here}}
int f(int);
int f(int a) { } // expected-error {{redefinition of 'f'}}
+// <rdar://problem/6097326>
+int foo(x) {
+ return 0;
+}
+int x = 1;