[cfe-commits] r39311 - in /cfe/cfe/trunk: AST/ASTContext.cpp AST/Type.cpp include/clang/AST/ASTContext.h include/clang/AST/Type.h
sabre at cs.uiuc.edu
sabre at cs.uiuc.edu
Wed Jul 11 09:42:53 PDT 2007
Author: sabre
Date: Wed Jul 11 11:42:53 2007
New Revision: 39311
URL: http://llvm.org/viewvc/llvm-project?rev=39311&view=rev
Log:
Eliminate "obviously braindead" canonicalization of function types, using
a foldingset instead. This reduces the number of slow type lookups from
32K to 10K, which speeds up parsing of carbon.h from 11s to 3.5s.
Modified:
cfe/cfe/trunk/AST/ASTContext.cpp
cfe/cfe/trunk/AST/Type.cpp
cfe/cfe/trunk/include/clang/AST/ASTContext.h
cfe/cfe/trunk/include/clang/AST/Type.h
Modified: cfe/cfe/trunk/AST/ASTContext.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/cfe/trunk/AST/ASTContext.cpp?rev=39311&r1=39310&r2=39311&view=diff
==============================================================================
--- cfe/cfe/trunk/AST/ASTContext.cpp (original)
+++ cfe/cfe/trunk/AST/ASTContext.cpp Wed Jul 11 11:42:53 2007
@@ -203,27 +203,16 @@
/// list. isVariadic indicates whether the argument list includes '...'.
TypeRef ASTContext::getFunctionType(TypeRef ResultTy, TypeRef *ArgArray,
unsigned NumArgs, bool isVariadic) {
- // FIXME: This is obviously braindead!
// Unique functions, to guarantee there is only one function of a particular
// structure.
- ++NumSlowLookups;
- for (unsigned i = 0, e = Types.size(); i != e; ++i) {
- if (FunctionTypeProto *FTy = dyn_cast<FunctionTypeProto>(Types[i]))
- if (FTy->getResultType() == ResultTy &&
- FTy->getNumArgs() == NumArgs &&
- FTy->isVariadic() == isVariadic) {
- bool Match = true;
- for (unsigned arg = 0; arg != NumArgs; ++arg) {
- if (FTy->getArgType(arg) != ArgArray[arg]) {
- Match = false;
- break;
- }
- }
- if (Match)
- return Types[i];
- }
- }
-
+ FoldingSetNodeID ID;
+ FunctionTypeProto::Profile(ID, ResultTy, ArgArray, NumArgs, isVariadic);
+
+ void *InsertPos = 0;
+ if (FunctionTypeProto *FTP =
+ FunctionTypeProtos.FindNodeOrInsertPos(ID, InsertPos))
+ return FTP;
+
// Determine whether the type being created is already canonical or not.
bool isCanonical = ResultTy->isCanonical();
for (unsigned i = 0; i != NumArgs && isCanonical; ++i)
@@ -241,6 +230,11 @@
Canonical = getFunctionType(ResultTy.getCanonicalType(),
&CanonicalArgs[0], NumArgs,
isVariadic).getTypePtr();
+
+ // Get the new insert position for the node we care about.
+ FunctionTypeProto *NewIP =
+ FunctionTypeProtos.FindNodeOrInsertPos(ID, InsertPos);
+ assert(NewIP == 0 && "Shouldn't be in the map!");
}
// FunctionTypeProto objects are not allocated with new because they have a
@@ -252,6 +246,7 @@
Canonical);
Types.push_back(FTP);
+ FunctionTypeProtos.InsertNode(FTP, InsertPos);
return FTP;
}
Modified: cfe/cfe/trunk/AST/Type.cpp
URL: http://llvm.org/viewvc/llvm-project/cfe/cfe/trunk/AST/Type.cpp?rev=39311&r1=39310&r2=39311&view=diff
==============================================================================
--- cfe/cfe/trunk/AST/Type.cpp (original)
+++ cfe/cfe/trunk/AST/Type.cpp Wed Jul 11 11:42:53 2007
@@ -75,6 +75,15 @@
}
}
+void FunctionTypeProto::Profile(FoldingSetNodeID &ID, TypeRef Result,
+ TypeRef* ArgTys,
+ unsigned NumArgs, bool isVariadic) {
+ ID.AddPointer(Result.getAsOpaquePtr());
+ for (unsigned i = 0; i != NumArgs; ++i)
+ ID.AddPointer(ArgTys[i].getAsOpaquePtr());
+ ID.AddInteger(isVariadic);
+}
+
bool RecordType::classof(const Type *T) {
if (const TaggedType *TT = dyn_cast<TaggedType>(T))
return isa<RecordDecl>(TT->getDecl());
Modified: cfe/cfe/trunk/include/clang/AST/ASTContext.h
URL: http://llvm.org/viewvc/llvm-project/cfe/cfe/trunk/include/clang/AST/ASTContext.h?rev=39311&r1=39310&r2=39311&view=diff
==============================================================================
--- cfe/cfe/trunk/include/clang/AST/ASTContext.h (original)
+++ cfe/cfe/trunk/include/clang/AST/ASTContext.h Wed Jul 11 11:42:53 2007
@@ -25,9 +25,9 @@
/// ASTContext - This class holds long-lived AST nodes (such as types and
/// decls) that can be referred to throughout the semantic analysis of a file.
class ASTContext {
- // FIXME: This is a stupid data structure.
std::vector<Type*> Types;
unsigned NumSlowLookups;
+ FoldingSet<FunctionTypeProto> FunctionTypeProtos;
public:
Preprocessor &PP;
TargetInfo &Target;
Modified: cfe/cfe/trunk/include/clang/AST/Type.h
URL: http://llvm.org/viewvc/llvm-project/cfe/cfe/trunk/include/clang/AST/Type.h?rev=39311&r1=39310&r2=39311&view=diff
==============================================================================
--- cfe/cfe/trunk/include/clang/AST/Type.h (original)
+++ cfe/cfe/trunk/include/clang/AST/Type.h Wed Jul 11 11:42:53 2007
@@ -15,9 +15,7 @@
#define LLVM_CLANG_AST_TYPE_H
#include "llvm/Support/Casting.h"
-#include "llvm/Support/DataTypes.h"
-#include <cassert>
-#include <string>
+#include "llvm/ADT/FoldingSet.h"
namespace llvm {
namespace clang {
@@ -325,7 +323,7 @@
/// FunctionTypeProto - Represents a prototype with argument type info, e.g.
/// 'int foo(int)' or 'int foo(void)'. 'void' is represented as having no
/// arguments, not as having a single void argument.
-class FunctionTypeProto : public FunctionType {
+class FunctionTypeProto : public FunctionType, public FoldingSetNode {
FunctionTypeProto(TypeRef Result, TypeRef *ArgArray, unsigned numArgs,
bool isVariadic, Type *Canonical)
: FunctionType(FunctionProto, Result, isVariadic, Canonical),
@@ -357,6 +355,12 @@
return T->getTypeClass() == FunctionProto;
}
static bool classof(const FunctionTypeProto *) { return true; }
+
+ void Profile(FoldingSetNodeID &ID) {
+ Profile(ID, getResultType(), ArgInfo, NumArgs, isVariadic());
+ }
+ static void Profile(FoldingSetNodeID &ID, TypeRef Result, TypeRef* ArgTys,
+ unsigned NumArgs, bool isVariadic);
};
More information about the cfe-commits
mailing list