Merged in mainline Clang on August 29, 2011.

llvm-svn: 138733
diff --git a/safecode/tools/clang/include/clang/ARCMigrate/FileRemapper.h b/safecode/tools/clang/include/clang/ARCMigrate/FileRemapper.h
index 8a4e132..181e130 100644
--- a/safecode/tools/clang/include/clang/ARCMigrate/FileRemapper.h
+++ b/safecode/tools/clang/include/clang/ARCMigrate/FileRemapper.h
@@ -65,7 +65,7 @@
   const FileEntry *getOriginalFile(StringRef filePath);
   void resetTarget(Target &targ);
 
-  bool report(const std::string &err, Diagnostic &Diag);
+  bool report(const Twine &err, Diagnostic &Diag);
 
   std::string getRemapInfoFile(StringRef outputDir);
 };
diff --git a/safecode/tools/clang/include/clang/AST/DeclBase.h b/safecode/tools/clang/include/clang/AST/DeclBase.h
index 042c50f..8dc15de 100644
--- a/safecode/tools/clang/include/clang/AST/DeclBase.h
+++ b/safecode/tools/clang/include/clang/AST/DeclBase.h
@@ -1322,6 +1322,12 @@
     ExternalVisibleStorage = ES;
   }
 
+  /// \brief Determine whether the given declaration is stored in the list of
+  /// declarations lexically within this context.
+  bool isDeclInLexicalTraversal(const Decl *D) const {
+    return D && (D->NextDeclInContext || D == FirstDecl || D == LastDecl);
+  }
+  
   static bool classof(const Decl *D);
   static bool classof(const DeclContext *D) { return true; }
 #define DECL(NAME, BASE)
diff --git a/safecode/tools/clang/include/clang/AST/DeclObjC.h b/safecode/tools/clang/include/clang/AST/DeclObjC.h
index 6f03443..e639606 100644
--- a/safecode/tools/clang/include/clang/AST/DeclObjC.h
+++ b/safecode/tools/clang/include/clang/AST/DeclObjC.h
@@ -918,29 +918,23 @@
     ObjCInterfaceDecl *getInterface() const { return ID; }
   };
 private:
-  ObjCClassRef *ForwardDecls;
-  unsigned NumDecls;
+  ObjCClassRef *ForwardDecl;
 
   ObjCClassDecl(DeclContext *DC, SourceLocation L,
-                ObjCInterfaceDecl *const *Elts, const SourceLocation *Locs,                
-                unsigned nElts, ASTContext &C);
+                ObjCInterfaceDecl *const Elt, const SourceLocation Loc,                
+                ASTContext &C);
 public:
   static ObjCClassDecl *Create(ASTContext &C, DeclContext *DC, SourceLocation L,
-                               ObjCInterfaceDecl *const *Elts = 0,
-                               const SourceLocation *Locs = 0,
-                               unsigned nElts = 0);
+                               ObjCInterfaceDecl *const Elt = 0,
+                               const SourceLocation Locs = SourceLocation());
+    
+  ObjCInterfaceDecl *getForwardInterfaceDecl() { return ForwardDecl->getInterface(); }
+  ObjCClassRef *getForwardDecl() { return ForwardDecl; }
+  void setClass(ASTContext &C, ObjCInterfaceDecl*const Cls,
+                const SourceLocation Locs);
   
   virtual SourceRange getSourceRange() const;
 
-  typedef const ObjCClassRef* iterator;
-  iterator begin() const { return ForwardDecls; }
-  iterator end() const { return ForwardDecls + NumDecls; }
-  unsigned size() const { return NumDecls; }
-
-  /// setClassList - Set the list of forward classes.
-  void setClassList(ASTContext &C, ObjCInterfaceDecl*const*List,
-                    const SourceLocation *Locs, unsigned Num);
-
   static bool classof(const Decl *D) { return classofKind(D->getKind()); }
   static bool classof(const ObjCClassDecl *D) { return true; }
   static bool classofKind(Kind K) { return K == ObjCClass; }
diff --git a/safecode/tools/clang/include/clang/Basic/Builtins.def b/safecode/tools/clang/include/clang/Basic/Builtins.def
index d12a04d..50cf872 100644
--- a/safecode/tools/clang/include/clang/Basic/Builtins.def
+++ b/safecode/tools/clang/include/clang/Basic/Builtins.def
@@ -389,7 +389,7 @@
 BUILTIN(__builtin_classify_type, "i.", "nct")
 BUILTIN(__builtin___CFStringMakeConstantString, "FC*cC*", "nc")
 BUILTIN(__builtin___NSStringMakeConstantString, "FC*cC*", "nc")
-BUILTIN(__builtin_va_start, "vA.", "n")
+BUILTIN(__builtin_va_start, "vA.", "nt")
 BUILTIN(__builtin_va_end, "vA", "n")
 BUILTIN(__builtin_va_copy, "vAA", "n")
 BUILTIN(__builtin_stdarg_start, "vA.", "n")
diff --git a/safecode/tools/clang/include/clang/Basic/DiagnosticCommonKinds.td b/safecode/tools/clang/include/clang/Basic/DiagnosticCommonKinds.td
index 4b5de36..62d8525 100644
--- a/safecode/tools/clang/include/clang/Basic/DiagnosticCommonKinds.td
+++ b/safecode/tools/clang/include/clang/Basic/DiagnosticCommonKinds.td
@@ -59,7 +59,8 @@
   "cannot define a function with non-namespace scope in a friend declaration">;
 def err_deleted_non_function : Error<
   "only functions can have deleted definitions">;
-
+def warn_module_not_found : Warning<"module '%0' not found">, DefaultFatal;
+  
 // Sema && Lex
 def ext_longlong : Extension<
   "'long long' is an extension when C99 mode is not enabled">,
diff --git a/safecode/tools/clang/include/clang/Basic/DiagnosticGroups.td b/safecode/tools/clang/include/clang/Basic/DiagnosticGroups.td
index add2ac3..a552542 100644
--- a/safecode/tools/clang/include/clang/Basic/DiagnosticGroups.td
+++ b/safecode/tools/clang/include/clang/Basic/DiagnosticGroups.td
@@ -235,11 +235,12 @@
                         DiagCategory<"Unused Entity Issue">;
 
 // Format settings.
+def FormatInvalidSpecifier : DiagGroup<"format-invalid-specifier">;
 def FormatSecurity : DiagGroup<"format-security">;
 def FormatY2K : DiagGroup<"format-y2k">;
 def Format : DiagGroup<"format",
                        [FormatExtraArgs, FormatZeroLength, NonNull,
-                        FormatSecurity, FormatY2K]>,
+                        FormatSecurity, FormatY2K, FormatInvalidSpecifier]>,
              DiagCategory<"Format String Issue">;
 def FormatNonLiteral : DiagGroup<"format-nonliteral", [FormatSecurity]>;
 def Format2 : DiagGroup<"format=2",
diff --git a/safecode/tools/clang/include/clang/Basic/DiagnosticParseKinds.td b/safecode/tools/clang/include/clang/Basic/DiagnosticParseKinds.td
index 27b4f85..9a6e754 100644
--- a/safecode/tools/clang/include/clang/Basic/DiagnosticParseKinds.td
+++ b/safecode/tools/clang/include/clang/Basic/DiagnosticParseKinds.td
@@ -569,5 +569,11 @@
 def err_seh___finally_block : Error<
   "%0 only allowed in __finally block">;
 
+// Modules
+def err_module_expected_ident : Error<
+  "expected a module name after '__import__'">;
+def err_module_expected_semi : Error<
+  "expected a semicolon name after module name">;
+  
 } // end of Parse Issue category.
 } // end of Parser diagnostics
diff --git a/safecode/tools/clang/include/clang/Basic/DiagnosticSemaKinds.td b/safecode/tools/clang/include/clang/Basic/DiagnosticSemaKinds.td
index 3d8fbd3..7bf2dc4 100644
--- a/safecode/tools/clang/include/clang/Basic/DiagnosticSemaKinds.td
+++ b/safecode/tools/clang/include/clang/Basic/DiagnosticSemaKinds.td
@@ -573,6 +573,9 @@
 def warn_objc_missing_super_dealloc : Warning<
   "method possibly missing a [super dealloc] call">,
   InGroup<ObjCMissingSuperCalls>;
+def warn_objc_missing_super_finalize : Warning<
+  "method possibly missing a [super finalize] call">,
+  InGroup<ObjCMissingSuperCalls>;
 def warn_undeclared_selector : Warning<
   "undeclared selector %0">, InGroup<UndeclaredSelector>, DefaultIgnore;
 def warn_implicit_atomic_property : Warning<
@@ -2851,7 +2854,8 @@
   "existing ivar %1 for strong property %0 may not be "
   "%select{|__unsafe_unretained||__weak}2">;
 def err_arc_assign_property_ownership : Error<
-  "existing ivar %1 for unsafe_unretained property %0 must be __unsafe_unretained">;
+  "existing ivar %1 for property %0 with %select{unsafe_unretained| assign}2 "
+  "attribute must be __unsafe_unretained">;
 def err_arc_inconsistent_property_ownership : Error<
   "%select{strong|weak|unsafe_unretained}1 property %0 may not also be "
   "declared %select{|__unsafe_unretained|__strong|__weak|__autoreleasing}2">;
@@ -3371,10 +3375,11 @@
 
 def warn_setter_getter_impl_required : Warning<
   "property %0 requires method %1 to be defined - "
-  "use @synthesize, @dynamic or provide a method implementation">;
+  "use @synthesize, @dynamic or provide a method implementation "
+  "in this class implementation">;
 def warn_setter_getter_impl_required_in_category : Warning<
   "property %0 requires method %1 to be defined - "
-  "use @dynamic or provide a method implementation in category">;
+  "use @dynamic or provide a method implementation in this category">;
 def note_property_impl_required : Note<
   "implementation is here">;
 def note_parameter_named_here : Note<
@@ -4231,7 +4236,7 @@
 def warn_printf_data_arg_not_used : Warning<
   "data argument not used by format string">, InGroup<FormatExtraArgs>;
 def warn_format_invalid_conversion : Warning<
-  "invalid conversion specifier '%0'">, InGroup<Format>;
+  "invalid conversion specifier '%0'">, InGroup<FormatInvalidSpecifier>;
 def warn_printf_incomplete_specifier : Warning<
   "incomplete format specifier">, InGroup<Format>;
 def warn_missing_format_string : Warning<
diff --git a/safecode/tools/clang/include/clang/Basic/IdentifierTable.h b/safecode/tools/clang/include/clang/Basic/IdentifierTable.h
index 017af5c..bd0b539 100644
--- a/safecode/tools/clang/include/clang/Basic/IdentifierTable.h
+++ b/safecode/tools/clang/include/clang/Basic/IdentifierTable.h
@@ -487,6 +487,7 @@
   // selector with the given name.
   OMF_autorelease,
   OMF_dealloc,
+  OMF_finalize,
   OMF_release,
   OMF_retain,
   OMF_retainCount,
diff --git a/safecode/tools/clang/include/clang/Basic/TokenKinds.def b/safecode/tools/clang/include/clang/Basic/TokenKinds.def
index e0b22b7..ccc2e61 100644
--- a/safecode/tools/clang/include/clang/Basic/TokenKinds.def
+++ b/safecode/tools/clang/include/clang/Basic/TokenKinds.def
@@ -397,6 +397,7 @@
 
 // Apple Extension.
 KEYWORD(__private_extern__          , KEYALL)
+KEYWORD(__import__                  , KEYALL)
 
 // Microsoft Extension.
 KEYWORD(__declspec                  , KEYALL)
diff --git a/safecode/tools/clang/include/clang/Driver/CC1Options.td b/safecode/tools/clang/include/clang/Driver/CC1Options.td
index 8ba8c4f..9535add 100644
--- a/safecode/tools/clang/include/clang/Driver/CC1Options.td
+++ b/safecode/tools/clang/include/clang/Driver/CC1Options.td
@@ -404,9 +404,6 @@
 def arcmt_migrate_emit_arc_errors : Flag<"-arcmt-migrate-emit-errors">,
   HelpText<"Emit ARC errors even if the migrator can fix them">;
 
-def import_module : Separate<"-import-module">,
-  HelpText<"Import a module definition file">;
-
 def working_directory : JoinedOrSeparate<"-working-directory">,
   HelpText<"Resolve file paths relative to the specified directory">;
 def working_directory_EQ : Joined<"-working-directory=">,
diff --git a/safecode/tools/clang/include/clang/Driver/Driver.h b/safecode/tools/clang/include/clang/Driver/Driver.h
index e979146..bcb75b3 100644
--- a/safecode/tools/clang/include/clang/Driver/Driver.h
+++ b/safecode/tools/clang/include/clang/Driver/Driver.h
@@ -373,11 +373,11 @@
                                  const char *BaseInput,
                                  bool AtTopLevel) const;
 
-  /// GetTemporaryPath - Return the pathname of a temporary file to
-  /// use as part of compilation; the file will have the given suffix.
+  /// GetTemporaryPath - Return the pathname of a temporary file to use 
+  /// as part of compilation; the file will have the given prefix and suffix.
   ///
   /// GCC goes to extra lengths here to be a bit more robust.
-  std::string GetTemporaryPath(const char *Suffix) const;
+  std::string GetTemporaryPath(StringRef Prefix, const char *Suffix) const;
 
   /// GetHostInfo - Construct a new host info object for the given
   /// host triple.
diff --git a/safecode/tools/clang/include/clang/Frontend/ASTUnit.h b/safecode/tools/clang/include/clang/Frontend/ASTUnit.h
index 190ab85..731ce38 100644
--- a/safecode/tools/clang/include/clang/Frontend/ASTUnit.h
+++ b/safecode/tools/clang/include/clang/Frontend/ASTUnit.h
@@ -18,6 +18,7 @@
 #include "clang/Serialization/ASTBitCodes.h"
 #include "clang/Sema/Sema.h"
 #include "clang/Sema/CodeCompleteConsumer.h"
+#include "clang/Lex/ModuleLoader.h"
 #include "clang/Lex/PreprocessingRecord.h"
 #include "clang/Basic/SourceManager.h"
 #include "clang/Basic/FileManager.h"
@@ -66,7 +67,7 @@
   
 /// \brief Utility class for loading a ASTContext from an AST file.
 ///
-class ASTUnit {
+class ASTUnit : public ModuleLoader {
 public:
   typedef std::map<FileID, std::vector<PreprocessedEntity *> > 
     PreprocessedEntitiesByFileMap;
@@ -696,6 +697,13 @@
   ///
   /// \returns True if an error occurred, false otherwise.
   bool serialize(raw_ostream &OS);
+  
+  virtual ModuleKey loadModule(SourceLocation ImportLoc, 
+                               IdentifierInfo &ModuleName,
+                               SourceLocation ModuleNameLoc) {
+    // ASTUnit doesn't know how to load modules (not that this matters).
+    return 0;
+  }
 };
 
 } // namespace clang
diff --git a/safecode/tools/clang/include/clang/Frontend/CompilerInstance.h b/safecode/tools/clang/include/clang/Frontend/CompilerInstance.h
index 3f97f1a..88f8976 100644
--- a/safecode/tools/clang/include/clang/Frontend/CompilerInstance.h
+++ b/safecode/tools/clang/include/clang/Frontend/CompilerInstance.h
@@ -11,6 +11,7 @@
 #define LLVM_CLANG_FRONTEND_COMPILERINSTANCE_H_
 
 #include "clang/Frontend/CompilerInvocation.h"
+#include "clang/Lex/ModuleLoader.h"
 #include "llvm/ADT/IntrusiveRefCntPtr.h"
 #include "llvm/ADT/StringRef.h"
 #include "llvm/ADT/OwningPtr.h"
@@ -56,7 +57,7 @@
 /// in to the compiler instance for everything. When possible, utility functions
 /// come in two forms; a short form that reuses the CompilerInstance objects,
 /// and a long form that takes explicit instances of any required objects.
-class CompilerInstance {
+class CompilerInstance : public ModuleLoader {
   /// The options used in this compiler instance.
   llvm::IntrusiveRefCntPtr<CompilerInvocation> Invocation;
 
@@ -498,20 +499,6 @@
   /// and replace any existing one with it.
   void createPreprocessor();
 
-  /// Create a Preprocessor object.
-  ///
-  /// Note that this also creates a new HeaderSearch object which will be owned
-  /// by the resulting Preprocessor.
-  ///
-  /// \return The new object on success, or null on failure.
-  static Preprocessor *createPreprocessor(Diagnostic &, const LangOptions &,
-                                          const PreprocessorOptions &,
-                                          const HeaderSearchOptions &,
-                                          const DependencyOutputOptions &,
-                                          const TargetInfo &,
-                                          const FrontendOptions &,
-                                          SourceManager &, FileManager &);
-
   /// Create the AST context.
   void createASTContext();
 
@@ -626,6 +613,10 @@
                                       const FrontendOptions &Opts);
 
   /// }
+  
+  virtual ModuleKey loadModule(SourceLocation ImportLoc, 
+                               IdentifierInfo &ModuleName,
+                               SourceLocation ModuleNameLoc);
 };
 
 } // end namespace clang
diff --git a/safecode/tools/clang/include/clang/Frontend/FrontendOptions.h b/safecode/tools/clang/include/clang/Frontend/FrontendOptions.h
index ec75b59..4876ceb 100644
--- a/safecode/tools/clang/include/clang/Frontend/FrontendOptions.h
+++ b/safecode/tools/clang/include/clang/Frontend/FrontendOptions.h
@@ -119,9 +119,6 @@
   /// \brief The list of AST files to merge.
   std::vector<std::string> ASTMergeFiles;
 
-  /// \brief The list of modules to import.
-  std::vector<std::string> Modules;
-
   /// \brief A list of arguments to forward to LLVM's option processing; this
   /// should only be used for debugging and experimental features.
   std::vector<std::string> LLVMArgs;
diff --git a/safecode/tools/clang/include/clang/Lex/ModuleLoader.h b/safecode/tools/clang/include/clang/Lex/ModuleLoader.h
new file mode 100644
index 0000000..72ec0e3
--- /dev/null
+++ b/safecode/tools/clang/include/clang/Lex/ModuleLoader.h
@@ -0,0 +1,55 @@
+//===--- ModuleLoader.h - Module Loader Interface ---------------*- C++ -*-===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+//
+//  This file defines the ModuleLoader interface, which is responsible for 
+//  loading named modules.
+//
+//===----------------------------------------------------------------------===//
+#ifndef LLVM_CLANG_LEX_MODULE_LOADER_H
+#define LLVM_CLANG_LEX_MODULE_LOADER_H
+
+#include "clang/Basic/SourceLocation.h"
+
+namespace clang {
+
+class IdentifierInfo;
+  
+/// \brief An opaque key that is used to describe the module and can be 
+/// interpreted by the module loader itself.
+typedef void *ModuleKey;
+  
+/// \brief Abstract interface for a module loader.
+///
+/// This abstract interface describes a module loader, which is responsible
+/// for resolving a module name (e.g., "std") to an actual module file, and
+/// then loading that module.
+class ModuleLoader {
+public:
+  virtual ~ModuleLoader();
+  
+  /// \brief Attempt to load the given module.
+  ///
+  /// This routine attempts to load the module described by the given 
+  /// parameters.
+  ///
+  /// \param ImportLoc The location of the 'import' keyword.
+  /// \param ModuleName The name of the module to be loaded.
+  /// \param ModuleNameLoc The location of the module name.
+  ///
+  /// \returns If successful, a non-NULL module key describing this module.
+  /// Otherwise, returns NULL to indicate that the module could not be
+  /// loaded.
+  virtual ModuleKey loadModule(SourceLocation ImportLoc, 
+                               IdentifierInfo &ModuleName,
+                               SourceLocation ModuleNameLoc) = 0;
+};
+  
+}
+
+#endif
diff --git a/safecode/tools/clang/include/clang/Lex/Preprocessor.h b/safecode/tools/clang/include/clang/Lex/Preprocessor.h
index a956454..b14c7e8 100644
--- a/safecode/tools/clang/include/clang/Lex/Preprocessor.h
+++ b/safecode/tools/clang/include/clang/Lex/Preprocessor.h
@@ -49,6 +49,7 @@
 class CodeCompletionHandler;
 class DirectoryLookup;
 class PreprocessingRecord;
+class ModuleLoader;
   
 /// Preprocessor - This object engages in a tight little dance with the lexer to
 /// efficiently preprocess tokens.  Lexers know only about tokens within a
@@ -63,10 +64,12 @@
   SourceManager     &SourceMgr;
   ScratchBuffer     *ScratchBuf;
   HeaderSearch      &HeaderInfo;
+  ModuleLoader      &TheModuleLoader;
 
   /// \brief External source of macros.
   ExternalPreprocessorSource *ExternalSource;
 
+  
   /// PTH - An optional PTHManager object used for getting tokens from
   ///  a token cache rather than lexing the original source file.
   llvm::OwningPtr<PTHManager> PTH;
@@ -115,6 +118,9 @@
   /// \brief Whether we have already loaded macros from the external source.
   mutable bool ReadMacrosFromExternalSource : 1;
 
+  /// \brief Tracks the depth of Lex() Calls.
+  unsigned LexDepth;
+  
   /// Identifiers - This is mapping/lookup information for all identifiers in
   /// the program, including program keywords.
   mutable IdentifierTable Identifiers;
@@ -294,6 +300,7 @@
   Preprocessor(Diagnostic &diags, const LangOptions &opts,
                const TargetInfo &target,
                SourceManager &SM, HeaderSearch &Headers,
+               ModuleLoader &TheModuleLoader,
                IdentifierInfoLookup *IILookup = 0,
                bool OwnsHeaderSearch = false);
 
@@ -325,6 +332,9 @@
     return ExternalSource;
   }
 
+  /// \brief Retrieve the module loader associated with this preprocessor.
+  ModuleLoader &getModuleLoader() const { return TheModuleLoader; }
+  
   /// SetCommentRetentionState - Control whether or not the preprocessor retains
   /// comments in output.
   void SetCommentRetentionState(bool KeepComments, bool KeepMacroComments) {
@@ -524,6 +534,7 @@
   /// Lex - To lex a token from the preprocessor, just pull a token from the
   /// current lexer or macro object.
   void Lex(Token &Result) {
+    ++LexDepth;
     if (CurLexer)
       CurLexer->Lex(Result);
     else if (CurPTHLexer)
@@ -532,6 +543,11 @@
       CurTokenLexer->Lex(Result);
     else
       CachingLex(Result);
+    --LexDepth;
+    
+    // If we have the __import__ keyword, handle the module import now.
+    if (Result.getKind() == tok::kw___import__ && LexDepth == 0)
+      HandleModuleImport(Result);
   }
 
   /// LexNonComment - Lex a token.  If it's a comment, keep lexing until we get
@@ -1008,6 +1024,9 @@
   /// the macro should not be expanded return true, otherwise return false.
   bool HandleMacroExpandedIdentifier(Token &Tok, MacroInfo *MI);
 
+  /// \brief Handle a module import directive.
+  void HandleModuleImport(Token &Import);
+  
   /// \brief Cache macro expanded tokens for TokenLexers.
   //
   /// Works like a stack; a TokenLexer adds the macro expanded tokens that is
diff --git a/safecode/tools/clang/include/clang/Parse/Parser.h b/safecode/tools/clang/include/clang/Parse/Parser.h
index 1215e2d..f74a1e4 100644
--- a/safecode/tools/clang/include/clang/Parse/Parser.h
+++ b/safecode/tools/clang/include/clang/Parse/Parser.h
@@ -1060,8 +1060,8 @@
   ExprResult ParseAsmStringLiteral();
 
   // Objective-C External Declarations
-  Decl *ParseObjCAtDirectives();
-  Decl *ParseObjCAtClassDeclaration(SourceLocation atLoc);
+  Parser::DeclGroupPtrTy ParseObjCAtDirectives();
+  Parser::DeclGroupPtrTy ParseObjCAtClassDeclaration(SourceLocation atLoc);
   Decl *ParseObjCAtInterfaceDeclaration(SourceLocation atLoc,
                                         ParsedAttributes &prefixAttrs);
   void ParseObjCClassInstanceVariables(Decl *interfaceDecl,
@@ -1916,6 +1916,10 @@
                                         SourceLocation &DeclEnd);
 
   //===--------------------------------------------------------------------===//
+  // Modules
+  DeclGroupPtrTy ParseModuleImport();
+  
+  //===--------------------------------------------------------------------===//
   // GNU G++: Type Traits [Type-Traits.html in the GCC manual]
   ExprResult ParseUnaryTypeTrait();
   ExprResult ParseBinaryTypeTrait();
diff --git a/safecode/tools/clang/include/clang/Sema/Sema.h b/safecode/tools/clang/include/clang/Sema/Sema.h
index adf2702..f6d5edc 100644
--- a/safecode/tools/clang/include/clang/Sema/Sema.h
+++ b/safecode/tools/clang/include/clang/Sema/Sema.h
@@ -493,6 +493,9 @@
   /// A flag that is set when parsing a -dealloc method and no [super dealloc]
   /// call was found yet.
   bool ObjCShouldCallSuperDealloc;
+  /// A flag that is set when parsing a -finalize method and no [super finalize]
+  /// call was found yet.
+  bool ObjCShouldCallSuperFinalize;
 
   /// \brief The set of declarations that have been referenced within
   /// a potentially evaluated expression.
@@ -1073,6 +1076,17 @@
                               SourceLocation AsmLoc,
                               SourceLocation RParenLoc);
 
+  /// \brief The parser has processed a module import declaration.
+  ///
+  /// \param ImportLoc The location of the '__import__' keyword.
+  ///
+  /// \param ModuleName The name of the module.
+  ///
+  /// \param ModuleNameLoc The location of the module name.
+  DeclResult ActOnModuleImport(SourceLocation ImportLoc,
+                               IdentifierInfo &ModuleName,
+                               SourceLocation ModuleNameLoc);
+  
   /// Scope actions.
   void ActOnPopScope(SourceLocation Loc, Scope *S);
   void ActOnTranslationUnitScope(Scope *S);
@@ -4999,7 +5013,7 @@
                                          IdentifierInfo *CatName,
                                          SourceLocation CatLoc);
 
-  Decl *ActOnForwardClassDeclaration(SourceLocation Loc,
+  DeclGroupPtrTy ActOnForwardClassDeclaration(SourceLocation Loc,
                                      IdentifierInfo **IdentList,
                                      SourceLocation *IdentLocs,
                                      unsigned NumElts);
diff --git a/safecode/tools/clang/include/clang/StaticAnalyzer/Core/BugReporter/BugReporter.h b/safecode/tools/clang/include/clang/StaticAnalyzer/Core/BugReporter/BugReporter.h
index 1c1b985..61b06bb 100644
--- a/safecode/tools/clang/include/clang/StaticAnalyzer/Core/BugReporter/BugReporter.h
+++ b/safecode/tools/clang/include/clang/StaticAnalyzer/Core/BugReporter/BugReporter.h
@@ -42,7 +42,6 @@
 class BugReporter;
 class BugReporterContext;
 class ExprEngine;
-class ProgramState;
 class BugType;
 
 //===----------------------------------------------------------------------===//
diff --git a/safecode/tools/clang/include/clang/StaticAnalyzer/Core/BugReporter/BugType.h b/safecode/tools/clang/include/clang/StaticAnalyzer/Core/BugReporter/BugType.h
index 62b531b..78067cd 100644
--- a/safecode/tools/clang/include/clang/StaticAnalyzer/Core/BugReporter/BugType.h
+++ b/safecode/tools/clang/include/clang/StaticAnalyzer/Core/BugReporter/BugType.h
@@ -14,7 +14,6 @@
 #ifndef LLVM_CLANG_ANALYSIS_BUGTYPE
 #define LLVM_CLANG_ANALYSIS_BUGTYPE
 
-#include "clang/StaticAnalyzer/Core/BugReporter/BugReporter.h"
 #include "llvm/ADT/FoldingSet.h"
 #include <string>
 
@@ -22,6 +21,7 @@
 
 namespace ento {
 
+class BugReporter;
 class ExplodedNode;
 class ExprEngine;
 
diff --git a/safecode/tools/clang/include/clang/StaticAnalyzer/Core/BugReporter/PathDiagnostic.h b/safecode/tools/clang/include/clang/StaticAnalyzer/Core/BugReporter/PathDiagnostic.h
index bfac65b..1afa546 100644
--- a/safecode/tools/clang/include/clang/StaticAnalyzer/Core/BugReporter/PathDiagnostic.h
+++ b/safecode/tools/clang/include/clang/StaticAnalyzer/Core/BugReporter/PathDiagnostic.h
@@ -52,13 +52,19 @@
   
   virtual void HandleDiagnostic(Diagnostic::Level DiagLevel,
                                 const DiagnosticInfo &Info);
-  virtual void HandlePathDiagnostic(const PathDiagnostic* D) = 0;
+  void HandlePathDiagnostic(const PathDiagnostic* D);
 
   enum PathGenerationScheme { Minimal, Extensive };
   virtual PathGenerationScheme getGenerationScheme() const { return Minimal; }
   virtual bool supportsLogicalOpControlFlow() const { return false; }
   virtual bool supportsAllBlockEdges() const { return false; }
   virtual bool useVerboseDescription() const { return true; }
+
+protected:
+  /// The actual logic for handling path diagnostics, as implemented
+  /// by subclasses of PathDiagnosticClient.
+  virtual void HandlePathDiagnosticImpl(const PathDiagnostic* D) = 0;
+
 };
 
 //===----------------------------------------------------------------------===//
diff --git a/safecode/tools/clang/include/clang/StaticAnalyzer/Core/Checker.h b/safecode/tools/clang/include/clang/StaticAnalyzer/Core/Checker.h
index c93924d..268c85b 100644
--- a/safecode/tools/clang/include/clang/StaticAnalyzer/Core/Checker.h
+++ b/safecode/tools/clang/include/clang/StaticAnalyzer/Core/Checker.h
@@ -262,10 +262,10 @@
   _checkRegionChanges(void *checker,
                       const ProgramState *state,
                       const StoreManager::InvalidatedSymbols *invalidated,
-                      const MemRegion * const *Begin,
-                      const MemRegion * const *End) {
+                      ArrayRef<const MemRegion *> Explicits,
+                      ArrayRef<const MemRegion *> Regions) {
     return ((const CHECKER *)checker)->checkRegionChanges(state, invalidated,
-                                                          Begin, End);
+                                                          Explicits, Regions);
   }
   template <typename CHECKER>
   static bool _wantsRegionChangeUpdate(void *checker,
@@ -338,6 +338,10 @@
 class CheckerBase : public ProgramPointTag {
 public:
   StringRef getTagDescription() const;
+
+  /// See CheckerManager::runCheckersForPrintState.
+  virtual void printState(raw_ostream &Out, const ProgramState *State,
+                          const char *NL, const char *Sep) const { }
 };
   
 template <typename CHECK1, typename CHECK2=check::_VoidCheck,
diff --git a/safecode/tools/clang/include/clang/StaticAnalyzer/Core/CheckerManager.h b/safecode/tools/clang/include/clang/StaticAnalyzer/Core/CheckerManager.h
index ffbeced..db94b81 100644
--- a/safecode/tools/clang/include/clang/StaticAnalyzer/Core/CheckerManager.h
+++ b/safecode/tools/clang/include/clang/StaticAnalyzer/Core/CheckerManager.h
@@ -238,11 +238,19 @@
   bool wantsRegionChangeUpdate(const ProgramState *state);
 
   /// \brief Run checkers for region changes.
+  ///
+  /// This corresponds to the check::RegionChanges callback.
+  /// \param state The current program state.
+  /// \param invalidated A set of all symbols potentially touched by the change.
+  /// \param ExplicitRegions The regions explicitly requested for invalidation.
+  ///   For example, in the case of a function call, these would be arguments.
+  /// \param Regions The transitive closure of accessible regions,
+  ///   i.e. all regions that may have been touched by this change.
   const ProgramState *
   runCheckersForRegionChanges(const ProgramState *state,
                             const StoreManager::InvalidatedSymbols *invalidated,
-                              const MemRegion * const *Begin,
-                              const MemRegion * const *End);
+                              ArrayRef<const MemRegion *> ExplicitRegions,
+                              ArrayRef<const MemRegion *> Regions);
 
   /// \brief Run checkers for handling assumptions on symbolic values.
   const ProgramState *runCheckersForEvalAssume(const ProgramState *state,
@@ -259,6 +267,17 @@
                                          AnalysisManager &mgr,
                                          BugReporter &BR);
 
+  /// \brief Run checkers for debug-printing a ProgramState.
+  ///
+  /// Unlike most other callbacks, any checker can simply implement the virtual
+  /// method CheckerBase::printState if it has custom data to print.
+  /// \param Out The output stream
+  /// \param State The state being printed
+  /// \param NL The preferred representation of a newline.
+  /// \param Sep The preferred separator between different kinds of data.
+  void runCheckersForPrintState(raw_ostream &Out, const ProgramState *State,
+                                const char *NL, const char *Sep);
+
 //===----------------------------------------------------------------------===//
 // Internal registration functions for AST traversing.
 //===----------------------------------------------------------------------===//
@@ -305,8 +324,8 @@
   
   typedef CheckerFn<const ProgramState * (const ProgramState *,
                                 const StoreManager::InvalidatedSymbols *symbols,
-                                     const MemRegion * const *begin,
-                                     const MemRegion * const *end)>
+                                    ArrayRef<const MemRegion *> ExplicitRegions,
+                                          ArrayRef<const MemRegion *> Regions)>
       CheckRegionChangesFunc;
   
   typedef CheckerFn<bool (const ProgramState *)> WantsRegionChangeUpdateFunc;
diff --git a/safecode/tools/clang/include/clang/StaticAnalyzer/Core/PathSensitive/ConstraintManager.h b/safecode/tools/clang/include/clang/StaticAnalyzer/Core/PathSensitive/ConstraintManager.h
index 4c03974..3f6ddde 100644
--- a/safecode/tools/clang/include/clang/StaticAnalyzer/Core/PathSensitive/ConstraintManager.h
+++ b/safecode/tools/clang/include/clang/StaticAnalyzer/Core/PathSensitive/ConstraintManager.h
@@ -14,8 +14,8 @@
 #ifndef LLVM_CLANG_GR_CONSTRAINT_MANAGER_H
 #define LLVM_CLANG_GR_CONSTRAINT_MANAGER_H
 
-// FIXME: Typedef LiveSymbolsTy/DeadSymbolsTy at a more appropriate place.
-#include "clang/StaticAnalyzer/Core/PathSensitive/Store.h"
+#include "clang/StaticAnalyzer/Core/PathSensitive/SymbolManager.h"
+#include "clang/StaticAnalyzer/Core/PathSensitive/SVals.h"
 
 namespace llvm {
 class APSInt;
@@ -28,7 +28,6 @@
 class ProgramState;
 class ProgramStateManager;
 class SubEngine;
-class SVal;
 
 class ConstraintManager {
 public:
diff --git a/safecode/tools/clang/include/clang/StaticAnalyzer/Core/PathSensitive/CoreEngine.h b/safecode/tools/clang/include/clang/StaticAnalyzer/Core/PathSensitive/CoreEngine.h
index fceafd7..9351827 100644
--- a/safecode/tools/clang/include/clang/StaticAnalyzer/Core/PathSensitive/CoreEngine.h
+++ b/safecode/tools/clang/include/clang/StaticAnalyzer/Core/PathSensitive/CoreEngine.h
@@ -19,7 +19,6 @@
 #include "clang/StaticAnalyzer/Core/PathSensitive/ExplodedGraph.h"
 #include "clang/StaticAnalyzer/Core/PathSensitive/WorkList.h"
 #include "clang/StaticAnalyzer/Core/PathSensitive/BlockCounter.h"
-#include "clang/StaticAnalyzer/Core/PathSensitive/SubEngine.h"
 #include "llvm/ADT/OwningPtr.h"
 
 namespace clang {
diff --git a/safecode/tools/clang/include/clang/StaticAnalyzer/Core/PathSensitive/Environment.h b/safecode/tools/clang/include/clang/StaticAnalyzer/Core/PathSensitive/Environment.h
index 802fb87..2463e23 100644
--- a/safecode/tools/clang/include/clang/StaticAnalyzer/Core/PathSensitive/Environment.h
+++ b/safecode/tools/clang/include/clang/StaticAnalyzer/Core/PathSensitive/Environment.h
@@ -14,7 +14,6 @@
 #ifndef LLVM_CLANG_GR_ENVIRONMENT_H
 #define LLVM_CLANG_GR_ENVIRONMENT_H
 
-#include "clang/StaticAnalyzer/Core/PathSensitive/Store.h"
 #include "clang/StaticAnalyzer/Core/PathSensitive/SVals.h"
 #include "llvm/ADT/ImmutableMap.h"
 
diff --git a/safecode/tools/clang/include/clang/StaticAnalyzer/Core/PathSensitive/ExprEngine.h b/safecode/tools/clang/include/clang/StaticAnalyzer/Core/PathSensitive/ExprEngine.h
index 1bdd572..2c0a935 100644
--- a/safecode/tools/clang/include/clang/StaticAnalyzer/Core/PathSensitive/ExprEngine.h
+++ b/safecode/tools/clang/include/clang/StaticAnalyzer/Core/PathSensitive/ExprEngine.h
@@ -21,7 +21,6 @@
 #include "clang/StaticAnalyzer/Core/PathSensitive/CoreEngine.h"
 #include "clang/StaticAnalyzer/Core/PathSensitive/ProgramState.h"
 #include "clang/StaticAnalyzer/Core/PathSensitive/TransferFuncs.h"
-#include "clang/StaticAnalyzer/Core/PathSensitive/ObjCMessage.h"
 #include "clang/StaticAnalyzer/Core/BugReporter/BugReporter.h"
 #include "clang/AST/Type.h"
 #include "clang/AST/ExprObjC.h"
@@ -35,6 +34,8 @@
 namespace ento {
 
 class AnalysisManager;
+class CallOrObjCMessage;
+class ObjCMessage;
 
 class ExprEngine : public SubEngine {
   AnalysisManager &AMgr;
@@ -192,8 +193,12 @@
   const ProgramState *
   processRegionChanges(const ProgramState *state,
                        const StoreManager::InvalidatedSymbols *invalidated,
-                       const MemRegion * const *Begin,
-                       const MemRegion * const *End);
+                       ArrayRef<const MemRegion *> ExplicitRegions,
+                       ArrayRef<const MemRegion *> Regions);
+
+  /// printState - Called by ProgramStateManager to print checker-specific data.
+  void printState(raw_ostream &Out, const ProgramState *State,
+                  const char *NL, const char *Sep);
 
   virtual ProgramStateManager& getStateManager() { return StateMgr; }
 
@@ -410,14 +415,17 @@
   void evalObjCMessage(ExplodedNodeSet &Dst, const ObjCMessage &msg, 
                        ExplodedNode *Pred, const ProgramState *state);
 
+  const ProgramState *invalidateArguments(const ProgramState *State,
+                                          const CallOrObjCMessage &Call,
+                                          const LocationContext *LC);
+
   const ProgramState *MarkBranch(const ProgramState *St, const Stmt *Terminator,
                             bool branchTaken);
 
   /// evalBind - Handle the semantics of binding a value to a specific location.
   ///  This method is used by evalStore, VisitDeclStmt, and others.
   void evalBind(ExplodedNodeSet &Dst, const Stmt *StoreE, ExplodedNode *Pred,
-                const ProgramState *St, SVal location, SVal Val,
-                bool atDeclInit = false);
+                SVal location, SVal Val, bool atDeclInit = false);
 
 public:
   // FIXME: 'tag' should be removed, and a LocationContext should be used
diff --git a/safecode/tools/clang/include/clang/StaticAnalyzer/Core/PathSensitive/ObjCMessage.h b/safecode/tools/clang/include/clang/StaticAnalyzer/Core/PathSensitive/ObjCMessage.h
index 247534d..bff94bc 100644
--- a/safecode/tools/clang/include/clang/StaticAnalyzer/Core/PathSensitive/ObjCMessage.h
+++ b/safecode/tools/clang/include/clang/StaticAnalyzer/Core/PathSensitive/ObjCMessage.h
@@ -18,6 +18,8 @@
 #include "clang/StaticAnalyzer/Core/PathSensitive/SVals.h"
 #include "clang/StaticAnalyzer/Core/PathSensitive/ProgramState.h"
 #include "clang/AST/ExprObjC.h"
+#include "clang/AST/ExprCXX.h"
+#include "llvm/ADT/PointerUnion.h"
 
 namespace clang {
 namespace ento {
@@ -86,6 +88,21 @@
     return 0;
   }
 
+  SVal getInstanceReceiverSVal(const ProgramState *State,
+                               const LocationContext *LC) const {
+    assert(isValid() && "This ObjCMessage is uninitialized!");
+    if (!isInstanceMessage())
+      return UndefinedVal();
+    if (const Expr *Ex = getInstanceReceiver())
+      return State->getSValAsScalarOrLoc(Ex);
+
+    // An instance message with no expression means we are sending to super.
+    // In this case the object reference is the same as 'self'.
+    const ImplicitParamDecl *SelfDecl = LC->getSelfDecl();
+    assert(SelfDecl && "No message receiver Expr, but not in an ObjC method");
+    return State->getSVal(State->getRegion(SelfDecl, LC));
+  }
+
   bool isInstanceMessage() const {
     assert(isValid() && "This ObjCMessage is uninitialized!");
     if (const ObjCMessageExpr *msgE = dyn_cast<ObjCMessageExpr>(MsgOrPropE))
@@ -96,7 +113,7 @@
   }
 
   const ObjCMethodDecl *getMethodDecl() const;
-  
+
   const ObjCInterfaceDecl *getReceiverInterface() const;
 
   SourceLocation getSuperLoc() const {
@@ -106,45 +123,58 @@
     return cast<ObjCPropertyRefExpr>(MsgOrPropE)->getReceiverLocation();
   }
 
-   SourceRange getSourceRange() const {
-     assert(isValid() && "This ObjCMessage is uninitialized!");
+  SourceRange getSourceRange() const {
+    assert(isValid() && "This ObjCMessage is uninitialized!");
     return MsgOrPropE->getSourceRange();
   }
 
-   unsigned getNumArgs() const {
-     assert(isValid() && "This ObjCMessage is uninitialized!");
-     if (const ObjCMessageExpr *msgE = dyn_cast<ObjCMessageExpr>(MsgOrPropE))
-       return msgE->getNumArgs();
-     return isPropertySetter() ? 1 : 0;
-   }
+  unsigned getNumArgs() const {
+    assert(isValid() && "This ObjCMessage is uninitialized!");
+    if (const ObjCMessageExpr *msgE = dyn_cast<ObjCMessageExpr>(MsgOrPropE))
+      return msgE->getNumArgs();
+    return isPropertySetter() ? 1 : 0;
+  }
 
-   SVal getArgSVal(unsigned i, const ProgramState *state) const {
-     assert(isValid() && "This ObjCMessage is uninitialized!");
-     assert(i < getNumArgs() && "Invalid index for argument");
-     if (const ObjCMessageExpr *msgE = dyn_cast<ObjCMessageExpr>(MsgOrPropE))
-       return state->getSVal(msgE->getArg(i));
-     assert(isPropertySetter());
-     return SetterArgV;
-   }
+  SVal getArgSVal(unsigned i, const ProgramState *state) const {
+    assert(isValid() && "This ObjCMessage is uninitialized!");
+    assert(i < getNumArgs() && "Invalid index for argument");
+    if (const ObjCMessageExpr *msgE = dyn_cast<ObjCMessageExpr>(MsgOrPropE))
+      return state->getSVal(msgE->getArg(i));
+    assert(isPropertySetter());
+    return SetterArgV;
+  }
 
-   QualType getArgType(unsigned i) const {
-     assert(isValid() && "This ObjCMessage is uninitialized!");
-     assert(i < getNumArgs() && "Invalid index for argument");
-     if (const ObjCMessageExpr *msgE = dyn_cast<ObjCMessageExpr>(MsgOrPropE))
-       return msgE->getArg(i)->getType();
-     assert(isPropertySetter());
-     return cast<ObjCPropertyRefExpr>(MsgOrPropE)->getType();
-   }
-   
-   const Expr *getArgExpr(unsigned i) const;
+  QualType getArgType(unsigned i) const {
+    assert(isValid() && "This ObjCMessage is uninitialized!");
+    assert(i < getNumArgs() && "Invalid index for argument");
+    if (const ObjCMessageExpr *msgE = dyn_cast<ObjCMessageExpr>(MsgOrPropE))
+      return msgE->getArg(i)->getType();
+    assert(isPropertySetter());
+    return cast<ObjCPropertyRefExpr>(MsgOrPropE)->getType();
+  }
 
-   SourceRange getArgSourceRange(unsigned i) const {
-     assert(isValid() && "This ObjCMessage is uninitialized!");
-     assert(i < getNumArgs() && "Invalid index for argument");
-     if (const Expr *argE = getArgExpr(i))
-       return argE->getSourceRange();
-     return OriginE->getSourceRange();
-   }
+  const Expr *getArgExpr(unsigned i) const;
+
+  SourceRange getArgSourceRange(unsigned i) const {
+    assert(isValid() && "This ObjCMessage is uninitialized!");
+    assert(i < getNumArgs() && "Invalid index for argument");
+    if (const Expr *argE = getArgExpr(i))
+      return argE->getSourceRange();
+    return OriginE->getSourceRange();
+  }
+
+  SourceRange getReceiverSourceRange() const {
+    assert(isValid() && "This ObjCMessage is uninitialized!");
+    if (const ObjCMessageExpr *msgE = dyn_cast<ObjCMessageExpr>(MsgOrPropE))
+      return msgE->getReceiverRange();
+
+    const ObjCPropertyRefExpr *propE = cast<ObjCPropertyRefExpr>(MsgOrPropE);
+    if (propE->isObjectReceiver())
+      return propE->getBase()->getSourceRange();
+
+    // FIXME: This isn't a range.
+    return propE->getReceiverLocation();
+  }
 };
 
 class ObjCPropertyGetter : public ObjCMessage {
@@ -165,64 +195,89 @@
   }
 };
 
-/// \brief Common wrapper for a call expression or an ObjC message, mainly to
-/// provide a common interface for handling their arguments.
+/// \brief Common wrapper for a call expression, ObjC message, or C++ 
+/// constructor, mainly to provide a common interface for their arguments.
 class CallOrObjCMessage {
-  const CallExpr *CallE;
+  llvm::PointerUnion<const CallExpr *, const CXXConstructExpr *> CallE;
   ObjCMessage Msg;
   const ProgramState *State;
 public:
   CallOrObjCMessage(const CallExpr *callE, const ProgramState *state)
     : CallE(callE), State(state) {}
+  CallOrObjCMessage(const CXXConstructExpr *consE, const ProgramState *state)
+    : CallE(consE), State(state) {}
   CallOrObjCMessage(const ObjCMessage &msg, const ProgramState *state)
-    : CallE(0), Msg(msg), State(state) {}
+    : CallE((CallExpr *)0), Msg(msg), State(state) {}
 
   QualType getResultType(ASTContext &ctx) const;
   
   bool isFunctionCall() const {
-    return (bool) CallE;
+    return CallE && CallE.is<const CallExpr *>();
   }
-  
+
+  bool isCXXConstructExpr() const {
+    return CallE && CallE.is<const CXXConstructExpr *>();
+  }
+
+  bool isObjCMessage() const {
+    return !CallE;
+  }
+
   bool isCXXCall() const {
-    return CallE && isa<CXXMemberCallExpr>(CallE);
+    const CallExpr *ActualCallE = CallE.dyn_cast<const CallExpr *>();
+    return ActualCallE && isa<CXXMemberCallExpr>(ActualCallE);
   }
 
   const Expr *getOriginExpr() const {
-    if (isFunctionCall())
-      return CallE;
-    return Msg.getOriginExpr();
+    if (!CallE)
+      return Msg.getOriginExpr();
+    if (const CXXConstructExpr *Ctor =
+          CallE.dyn_cast<const CXXConstructExpr *>())
+      return Ctor;
+    return CallE.get<const CallExpr *>();
   }
   
   SVal getFunctionCallee() const;
   SVal getCXXCallee() const;
+  SVal getInstanceMessageReceiver(const LocationContext *LC) const;
 
   unsigned getNumArgs() const {
-    if (CallE) return CallE->getNumArgs();
-    return Msg.getNumArgs();
+    if (!CallE)
+      return Msg.getNumArgs();
+    if (const CXXConstructExpr *Ctor =
+          CallE.dyn_cast<const CXXConstructExpr *>())
+      return Ctor->getNumArgs();
+    return CallE.get<const CallExpr *>()->getNumArgs();
   }
 
   SVal getArgSVal(unsigned i) const {
     assert(i < getNumArgs());
-    if (CallE) 
-      return State->getSVal(CallE->getArg(i));
-    return Msg.getArgSVal(i, State);
+    if (!CallE)
+      return Msg.getArgSVal(i, State);
+    return State->getSVal(getArg(i));
   }
 
-  SVal getArgSValAsScalarOrLoc(unsigned i) const;
-
   const Expr *getArg(unsigned i) const {
     assert(i < getNumArgs());
-    if (CallE)
-      return CallE->getArg(i);
-    return Msg.getArgExpr(i);
+    if (!CallE)
+      return Msg.getArgExpr(i);
+    if (const CXXConstructExpr *Ctor =
+          CallE.dyn_cast<const CXXConstructExpr *>())
+      return Ctor->getArg(i);
+    return CallE.get<const CallExpr *>()->getArg(i);
   }
 
   SourceRange getArgSourceRange(unsigned i) const {
     assert(i < getNumArgs());
     if (CallE)
-      return CallE->getArg(i)->getSourceRange();
+      return getArg(i)->getSourceRange();
     return Msg.getArgSourceRange(i);
   }
+
+  SourceRange getReceiverSourceRange() const {
+    assert(isObjCMessage());
+    return Msg.getReceiverSourceRange();
+  }
 };
 
 }
diff --git a/safecode/tools/clang/include/clang/StaticAnalyzer/Core/PathSensitive/ProgramState.h b/safecode/tools/clang/include/clang/StaticAnalyzer/Core/PathSensitive/ProgramState.h
index 40aedf3..c83792c 100644
--- a/safecode/tools/clang/include/clang/StaticAnalyzer/Core/PathSensitive/ProgramState.h
+++ b/safecode/tools/clang/include/clang/StaticAnalyzer/Core/PathSensitive/ProgramState.h
@@ -216,23 +216,13 @@
 
   const ProgramState *unbindLoc(Loc LV) const;
 
-  /// invalidateRegion - Returns the state with bindings for the given region
-  ///  cleared from the store. See invalidateRegions.
-  const ProgramState *invalidateRegion(const MemRegion *R,
-                                  const Expr *E, unsigned BlockCount,
-                                  StoreManager::InvalidatedSymbols *IS = NULL)
-                                  const {
-    return invalidateRegions(&R, &R+1, E, BlockCount, IS, false);
-  }
-
   /// invalidateRegions - Returns the state with bindings for the given regions
   ///  cleared from the store. The regions are provided as a continuous array
   ///  from Begin to End. Optionally invalidates global regions as well.
-  const ProgramState *invalidateRegions(const MemRegion * const *Begin,
-                                   const MemRegion * const *End,
+  const ProgramState *invalidateRegions(ArrayRef<const MemRegion *> Regions,
                                    const Expr *E, unsigned BlockCount,
-                                   StoreManager::InvalidatedSymbols *IS,
-                                   bool invalidateGlobals) const;
+                                   StoreManager::InvalidatedSymbols *IS = 0,
+                                   bool invalidateGlobals = false) const;
 
   /// enterStackFrame - Returns the state for entry to the given stack frame,
   ///  preserving the current state.
@@ -342,14 +332,6 @@
     return ProgramStateTrait<T>::Contains(ProgramStateTrait<T>::MakeData(d), key);
   }
 
-  // State pretty-printing.
-  class Printer {
-  public:
-    virtual ~Printer() {}
-    virtual void Print(raw_ostream &Out, const ProgramState *state,
-                       const char* nl, const char* sep) = 0;
-  };
-
   // Pretty-printing.
   void print(raw_ostream &Out, CFG &C, const char *nl = "\n",
              const char *sep = "") const;
@@ -368,11 +350,11 @@
     --refCount;
   }
   
-  const ProgramState *invalidateRegionsImpl(const MemRegion * const *Begin,
-                                       const MemRegion * const *End,
-                                       const Expr *E, unsigned BlockCount,
-                                       StoreManager::InvalidatedSymbols &IS,
-                                       bool invalidateGlobals) const;
+  const ProgramState *
+  invalidateRegionsImpl(ArrayRef<const MemRegion *> Regions,
+                        const Expr *E, unsigned BlockCount,
+                        StoreManager::InvalidatedSymbols &IS,
+                        bool invalidateGlobals) const;
 };
 
 class ProgramStateSet {
@@ -414,7 +396,6 @@
 
 class ProgramStateManager {
   friend class ProgramState;
-  friend class ExprEngine; // FIXME: Remove.
 private:
   /// Eng - The SubEngine that owns this state manager.
   SubEngine *Eng; /* Can be null. */
@@ -428,10 +409,6 @@
   typedef llvm::DenseMap<void*,std::pair<void*,void (*)(void*)> > GDMContextsTy;
   GDMContextsTy GDMContexts;
 
-  /// Printers - A set of printer objects used for pretty-printing a ProgramState.
-  ///  ProgramStateManager owns these objects.
-  std::vector<ProgramState::Printer*> Printers;
-
   /// StateSet - FoldingSet containing all the states created for analyzing
   ///  a particular function.  This is used to unique states.
   llvm::FoldingSet<ProgramState> StateSet;
diff --git a/safecode/tools/clang/include/clang/StaticAnalyzer/Core/PathSensitive/Store.h b/safecode/tools/clang/include/clang/StaticAnalyzer/Core/PathSensitive/Store.h
index 71c865c..a688d7f 100644
--- a/safecode/tools/clang/include/clang/StaticAnalyzer/Core/PathSensitive/Store.h
+++ b/safecode/tools/clang/include/clang/StaticAnalyzer/Core/PathSensitive/Store.h
@@ -187,12 +187,11 @@
   ///   even if they do not currently have bindings. Pass \c NULL if this
   ///   information will not be used.
   virtual StoreRef invalidateRegions(Store store,
-                                     const MemRegion * const *Begin,
-                                     const MemRegion * const *End,
+                                     ArrayRef<const MemRegion *> Regions,
                                      const Expr *E, unsigned Count,
                                      InvalidatedSymbols &IS,
                                      bool invalidateGlobals,
-                                     InvalidatedRegions *Regions) = 0;
+                                     InvalidatedRegions *Invalidated) = 0;
 
   /// enterStackFrame - Let the StoreManager to do something when execution
   /// engine is about to execute into a callee.
diff --git a/safecode/tools/clang/include/clang/StaticAnalyzer/Core/PathSensitive/SubEngine.h b/safecode/tools/clang/include/clang/StaticAnalyzer/Core/PathSensitive/SubEngine.h
index ef0cdc4..ae212bc 100644
--- a/safecode/tools/clang/include/clang/StaticAnalyzer/Core/PathSensitive/SubEngine.h
+++ b/safecode/tools/clang/include/clang/StaticAnalyzer/Core/PathSensitive/SubEngine.h
@@ -99,16 +99,20 @@
   virtual const ProgramState *
   processRegionChanges(const ProgramState *state,
                        const StoreManager::InvalidatedSymbols *invalidated,
-                       const MemRegion* const *Begin,
-                       const MemRegion* const *End) = 0;
+                       ArrayRef<const MemRegion *> ExplicitRegions,
+                       ArrayRef<const MemRegion *> Regions) = 0;
 
 
   inline const ProgramState *
   processRegionChange(const ProgramState *state,
                       const MemRegion* MR) {
-    return processRegionChanges(state, 0, &MR, &MR+1);
+    return processRegionChanges(state, 0, MR, MR);
   }
 
+  /// printState - Called by ProgramStateManager to print checker-specific data.
+  virtual void printState(raw_ostream &Out, const ProgramState *State,
+                          const char *NL, const char *Sep) = 0;
+
   /// Called by CoreEngine when the analysis worklist is either empty or the
   //  maximum number of analysis steps have been reached.
   virtual void processEndWorklist(bool hasWorkRemaining) = 0;
diff --git a/safecode/tools/clang/include/clang/StaticAnalyzer/Core/PathSensitive/TransferFuncs.h b/safecode/tools/clang/include/clang/StaticAnalyzer/Core/PathSensitive/TransferFuncs.h
index 35f680b..a82fd26 100644
--- a/safecode/tools/clang/include/clang/StaticAnalyzer/Core/PathSensitive/TransferFuncs.h
+++ b/safecode/tools/clang/include/clang/StaticAnalyzer/Core/PathSensitive/TransferFuncs.h
@@ -36,7 +36,6 @@
   TransferFuncs() {}
   virtual ~TransferFuncs() {}
 
-  virtual void RegisterPrinters(std::vector<ProgramState::Printer*>& Printers) {}
   virtual void RegisterChecks(ExprEngine& Eng) {}
 
 
diff --git a/safecode/tools/clang/lib/ARCMigrate/FileRemapper.cpp b/safecode/tools/clang/lib/ARCMigrate/FileRemapper.cpp
index 55ba371..604893e 100644
--- a/safecode/tools/clang/lib/ARCMigrate/FileRemapper.cpp
+++ b/safecode/tools/clang/lib/ARCMigrate/FileRemapper.cpp
@@ -59,38 +59,38 @@
     return false;
 
   std::vector<std::pair<const FileEntry *, const FileEntry *> > pairs;
+  
+  llvm::OwningPtr<llvm::MemoryBuffer> fileBuf;
+  if (llvm::error_code ec = llvm::MemoryBuffer::getFile(infoFile.c_str(),
+                                                        fileBuf))
+    return report("Error opening file: " + infoFile, Diag);
+  
+  SmallVector<StringRef, 64> lines;
+  fileBuf->getBuffer().split(lines, "\n");
 
-  std::ifstream fin(infoFile.c_str());
-  if (!fin.good())
-    return report(std::string("Error opening file: ") + infoFile, Diag);
-
-  while (true) {
-    std::string fromFilename, toFilename;
-    uint64_t timeModified;
-
-    fin >> fromFilename >> timeModified >> toFilename;
-    if (fin.eof())
-      break;
-    if (!fin.good())
-      return report(std::string("Error in format of file: ") + infoFile, Diag);
-
+  for (unsigned idx = 0; idx+3 <= lines.size(); idx += 3) {
+    StringRef fromFilename = lines[idx];
+    unsigned long long timeModified;
+    lines[idx+1].getAsInteger(10, timeModified);
+    StringRef toFilename = lines[idx+2];
+    
     const FileEntry *origFE = FileMgr->getFile(fromFilename);
     if (!origFE) {
       if (ignoreIfFilesChanged)
         continue;
-      return report(std::string("File does not exist: ") + fromFilename, Diag);
+      return report("File does not exist: " + fromFilename, Diag);
     }
     const FileEntry *newFE = FileMgr->getFile(toFilename);
     if (!newFE) {
       if (ignoreIfFilesChanged)
         continue;
-      return report(std::string("File does not exist: ") + toFilename, Diag);
+      return report("File does not exist: " + toFilename, Diag);
     }
 
     if ((uint64_t)origFE->getModificationTime() != timeModified) {
       if (ignoreIfFilesChanged)
         continue;
-      return report(std::string("File was modified: ") + fromFilename, Diag);
+      return report("File was modified: " + fromFilename, Diag);
     }
 
     pairs.push_back(std::make_pair(origFE, newFE));
@@ -107,8 +107,7 @@
 
   bool existed;
   if (fs::create_directory(outputDir, existed) != llvm::errc::success)
-    return report(std::string("Could not create directory: ") + outputDir.str(),
-                  Diag);
+    return report("Could not create directory: " + outputDir, Diag);
 
   std::string errMsg;
   std::string infoFile = getRemapInfoFile(outputDir);
@@ -138,8 +137,7 @@
       tempPath += path::extension(origFE->getName());
       int fd;
       if (fs::unique_file(tempPath.str(), fd, tempPath) != llvm::errc::success)
-        return report(std::string("Could not create file: ") + tempPath.c_str(),
-                      Diag);
+        return report("Could not create file: " + tempPath.str(), Diag);
 
       llvm::raw_fd_ostream newOut(fd, /*shouldClose=*/true);
       llvm::MemoryBuffer *mem = I->second.get<llvm::MemoryBuffer *>();
@@ -165,20 +163,15 @@
     const FileEntry *origFE = I->first;
     if (const FileEntry *newFE = I->second.dyn_cast<const FileEntry *>()) {
       if (fs::copy_file(newFE->getName(), origFE->getName(),
-                 fs::copy_option::overwrite_if_exists) != llvm::errc::success) {
-        std::string err = "Could not copy file '";
-        llvm::raw_string_ostream os(err);
-        os << "Could not copy file '" << newFE->getName() << "' to file '"
-           << origFE->getName() << "'";
-        os.flush();
-        return report(err, Diag);
-      }
+                 fs::copy_option::overwrite_if_exists) != llvm::errc::success)
+        return report(StringRef("Could not copy file '") + newFE->getName() +
+                      "' to file '" + origFE->getName() + "'", Diag);
     } else {
 
       bool fileExists = false;
       fs::exists(origFE->getName(), fileExists);
       if (!fileExists)
-        return report(std::string("File does not exist: ") + origFE->getName(),
+        return report(StringRef("File does not exist: ") + origFE->getName(),
                       Diag);
 
       std::string errMsg;
@@ -283,9 +276,10 @@
   }
 }
 
-bool FileRemapper::report(const std::string &err, Diagnostic &Diag) {
+bool FileRemapper::report(const Twine &err, Diagnostic &Diag) {
+  llvm::SmallString<128> buf;
   unsigned ID = Diag.getDiagnosticIDs()->getCustomDiagID(DiagnosticIDs::Error,
-                                                         err);
+                                                         err.toStringRef(buf));
   Diag.Report(ID);
   return true;
 }
diff --git a/safecode/tools/clang/lib/AST/ASTImporter.cpp b/safecode/tools/clang/lib/AST/ASTImporter.cpp
index 8b8308a..b6e3e62 100644
--- a/safecode/tools/clang/lib/AST/ASTImporter.cpp
+++ b/safecode/tools/clang/lib/AST/ASTImporter.cpp
@@ -3529,25 +3529,14 @@
   
   // Import the location of this declaration.
   SourceLocation Loc = Importer.Import(D->getLocation());
-
-  SmallVector<ObjCInterfaceDecl *, 4> Interfaces;
-  SmallVector<SourceLocation, 4> Locations;
-  for (ObjCClassDecl::iterator From = D->begin(), FromEnd = D->end();
-       From != FromEnd; ++From) {
-    ObjCInterfaceDecl *ToIface
-      = cast_or_null<ObjCInterfaceDecl>(Importer.Import(From->getInterface()));
-    if (!ToIface)
-      continue;
-    
-    Interfaces.push_back(ToIface);
-    Locations.push_back(Importer.Import(From->getLocation()));
-  }
-  
+  ObjCClassDecl::ObjCClassRef *From = D->getForwardDecl();
+  ObjCInterfaceDecl *ToIface
+    = cast_or_null<ObjCInterfaceDecl>(Importer.Import(From->getInterface()));
   ObjCClassDecl *ToClass = ObjCClassDecl::Create(Importer.getToContext(), DC,
-                                                 Loc, 
-                                                 Interfaces.data(),
-                                                 Locations.data(),
-                                                 Interfaces.size());
+                                        Loc,
+                                        ToIface,
+                                        Importer.Import(From->getLocation()));
+    
   ToClass->setLexicalDeclContext(LexicalDC);
   LexicalDC->addDecl(ToClass);
   Importer.Imported(D, ToClass);
diff --git a/safecode/tools/clang/lib/AST/DeclBase.cpp b/safecode/tools/clang/lib/AST/DeclBase.cpp
index 8b1acb1..27e437c 100644
--- a/safecode/tools/clang/lib/AST/DeclBase.cpp
+++ b/safecode/tools/clang/lib/AST/DeclBase.cpp
@@ -841,6 +841,22 @@
   // Notify that we have a DeclContext that is initializing.
   ExternalASTSource::Deserializing ADeclContext(Source);
 
+  // We may have already loaded just the fields of this record, in which case
+  // we remove all of the fields from the list. The fields will be reloaded
+  // from the external source as part of re-establishing the context.
+  if (const RecordDecl *RD = dyn_cast<RecordDecl>(this)) {
+    if (RD->LoadedFieldsFromExternalStorage) {
+      while (FirstDecl && isa<FieldDecl>(FirstDecl)) {
+        Decl *Next = FirstDecl->NextDeclInContext;
+        FirstDecl->NextDeclInContext = 0;
+        FirstDecl = Next;
+      }
+      
+      if (!FirstDecl)
+        LastDecl = 0;
+    }
+  }
+  
   // Load the external declarations, if any.
   SmallVector<Decl*, 64> Decls;
   ExternalLexicalStorage = false;
@@ -856,14 +872,6 @@
   if (Decls.empty())
     return;
 
-  // We may have already loaded just the fields of this record, in which case
-  // don't add the decls, just replace the FirstDecl/LastDecl chain.
-  if (const RecordDecl *RD = dyn_cast<RecordDecl>(this))
-    if (RD->LoadedFieldsFromExternalStorage) {
-      llvm::tie(FirstDecl, LastDecl) = BuildDeclChain(Decls);
-      return;
-    }
-
   // Splice the newly-read declarations into the beginning of the list
   // of declarations.
   Decl *ExternalFirst, *ExternalLast;
@@ -1022,12 +1030,10 @@
         if (D->getDeclContext() == DCtx)
           makeDeclVisibleInContextImpl(ND);
 
-      // Insert any forward-declared Objective-C interfaces into the lookup
+      // Insert any forward-declared Objective-C interface into the lookup
       // data structure.
       if (ObjCClassDecl *Class = dyn_cast<ObjCClassDecl>(*D))
-        for (ObjCClassDecl::iterator I = Class->begin(), IEnd = Class->end();
-             I != IEnd; ++I)
-          makeDeclVisibleInContextImpl(I->getInterface());
+        makeDeclVisibleInContextImpl(Class->getForwardInterfaceDecl());
       
       // If this declaration is itself a transparent declaration context or
       // inline namespace, add its members (recursively).
diff --git a/safecode/tools/clang/lib/AST/DeclObjC.cpp b/safecode/tools/clang/lib/AST/DeclObjC.cpp
index 813501f..09638fe 100644
--- a/safecode/tools/clang/lib/AST/DeclObjC.cpp
+++ b/safecode/tools/clang/lib/AST/DeclObjC.cpp
@@ -446,6 +446,7 @@
 
   // These selectors have a conventional meaning only for instance methods.
   case OMF_dealloc:
+  case OMF_finalize:
   case OMF_retain:
   case OMF_release:
   case OMF_autorelease:
@@ -851,36 +852,31 @@
 //===----------------------------------------------------------------------===//
 
 ObjCClassDecl::ObjCClassDecl(DeclContext *DC, SourceLocation L,
-                             ObjCInterfaceDecl *const *Elts,
-                             const SourceLocation *Locs,
-                             unsigned nElts,
+                             ObjCInterfaceDecl *const Elt,
+                             const SourceLocation Loc,
                              ASTContext &C)
   : Decl(ObjCClass, DC, L) {
-  setClassList(C, Elts, Locs, nElts);
-}
-
-void ObjCClassDecl::setClassList(ASTContext &C, ObjCInterfaceDecl*const*List,
-                                 const SourceLocation *Locs, unsigned Num) {
-  ForwardDecls = (ObjCClassRef*) C.Allocate(sizeof(ObjCClassRef)*Num,
-                                            llvm::alignOf<ObjCClassRef>());
-  for (unsigned i = 0; i < Num; ++i)
-    new (&ForwardDecls[i]) ObjCClassRef(List[i], Locs[i]);
-  
-  NumDecls = Num;
+  setClass(C, Elt, Loc);
 }
 
 ObjCClassDecl *ObjCClassDecl::Create(ASTContext &C, DeclContext *DC,
                                      SourceLocation L,
-                                     ObjCInterfaceDecl *const *Elts,
-                                     const SourceLocation *Locs,
-                                     unsigned nElts) {
-  return new (C) ObjCClassDecl(DC, L, Elts, Locs, nElts, C);
+                                     ObjCInterfaceDecl *const Elt,
+                                     const SourceLocation Loc) {
+  return new (C) ObjCClassDecl(DC, L, Elt, Loc, C);
 }
 
+void ObjCClassDecl::setClass(ASTContext &C, ObjCInterfaceDecl*const Cls,
+                             const SourceLocation Loc) {
+    
+  ForwardDecl = (ObjCClassRef*) C.Allocate(sizeof(ObjCClassRef),
+                                           llvm::alignOf<ObjCClassRef>());
+  new (ForwardDecl) ObjCClassRef(Cls, Loc);
+}
+    
 SourceRange ObjCClassDecl::getSourceRange() const {
   // FIXME: We should include the semicolon
-  assert(NumDecls);
-  return SourceRange(getLocation(), ForwardDecls[NumDecls-1].getLocation());
+  return SourceRange(getLocation(), ForwardDecl->getLocation());
 }
 
 //===----------------------------------------------------------------------===//
diff --git a/safecode/tools/clang/lib/AST/DeclPrinter.cpp b/safecode/tools/clang/lib/AST/DeclPrinter.cpp
index a1aff5d..3a95d13 100644
--- a/safecode/tools/clang/lib/AST/DeclPrinter.cpp
+++ b/safecode/tools/clang/lib/AST/DeclPrinter.cpp
@@ -812,11 +812,7 @@
 
 void DeclPrinter::VisitObjCClassDecl(ObjCClassDecl *D) {
   Out << "@class ";
-  for (ObjCClassDecl::iterator I = D->begin(), E = D->end();
-       I != E; ++I) {
-    if (I != D->begin()) Out << ", ";
-    Out << I->getInterface();
-  }
+  Out << D->getForwardInterfaceDecl();
 }
 
 void DeclPrinter::VisitObjCMethodDecl(ObjCMethodDecl *OMD) {
diff --git a/safecode/tools/clang/lib/AST/DumpXML.cpp b/safecode/tools/clang/lib/AST/DumpXML.cpp
index dd0147c..2568ada 100644
--- a/safecode/tools/clang/lib/AST/DumpXML.cpp
+++ b/safecode/tools/clang/lib/AST/DumpXML.cpp
@@ -742,8 +742,7 @@
 
   // ObjCClassDecl
   void visitObjCClassDeclChildren(ObjCClassDecl *D) {
-    for (ObjCClassDecl::iterator I = D->begin(), E = D->end(); I != E; ++I)
-      visitDeclRef(I->getInterface());
+    visitDeclRef(D->getForwardInterfaceDecl());
   }
 
   // ObjCInterfaceDecl
diff --git a/safecode/tools/clang/lib/Analysis/CocoaConventions.cpp b/safecode/tools/clang/lib/Analysis/CocoaConventions.cpp
index ea60f26..3926ce5 100644
--- a/safecode/tools/clang/lib/Analysis/CocoaConventions.cpp
+++ b/safecode/tools/clang/lib/Analysis/CocoaConventions.cpp
@@ -40,6 +40,7 @@
   case OMF_None:
   case OMF_autorelease:
   case OMF_dealloc:
+  case OMF_finalize:
   case OMF_release:
   case OMF_retain:
   case OMF_retainCount:
diff --git a/safecode/tools/clang/lib/Basic/IdentifierTable.cpp b/safecode/tools/clang/lib/Basic/IdentifierTable.cpp
index edf2e99..792b0c9 100644
--- a/safecode/tools/clang/lib/Basic/IdentifierTable.cpp
+++ b/safecode/tools/clang/lib/Basic/IdentifierTable.cpp
@@ -392,6 +392,7 @@
   if (sel.isUnarySelector()) {
     if (name == "autorelease") return OMF_autorelease;
     if (name == "dealloc") return OMF_dealloc;
+    if (name == "finalize") return OMF_finalize;
     if (name == "release") return OMF_release;
     if (name == "retain") return OMF_retain;
     if (name == "retainCount") return OMF_retainCount;
diff --git a/safecode/tools/clang/lib/CodeGen/CGCall.cpp b/safecode/tools/clang/lib/CodeGen/CGCall.cpp
index 846e1aa..f7cb549 100644
--- a/safecode/tools/clang/lib/CodeGen/CGCall.cpp
+++ b/safecode/tools/clang/lib/CodeGen/CGCall.cpp
@@ -1431,9 +1431,14 @@
     return emitWritebackArg(*this, args, CRE);
   }
 
-  if (type->isReferenceType())
+  assert(type->isReferenceType() == E->isGLValue() &&
+         "reference binding to unmaterialized r-value!");
+
+  if (E->isGLValue()) {
+    assert(E->getObjectKind() == OK_Ordinary);
     return args.add(EmitReferenceBindingToExpr(E, /*InitializedDecl=*/0),
                     type);
+  }
 
   if (hasAggregateLLVMType(type) && !E->getType()->isAnyComplexType() &&
       isa<ImplicitCastExpr>(E) &&
diff --git a/safecode/tools/clang/lib/CodeGen/CGException.cpp b/safecode/tools/clang/lib/CodeGen/CGException.cpp
index 0605f62..5d6f572 100644
--- a/safecode/tools/clang/lib/CodeGen/CGException.cpp
+++ b/safecode/tools/clang/lib/CodeGen/CGException.cpp
@@ -477,7 +477,6 @@
     return;
   }
 
-  CGBuilderTy::InsertPoint savedIP = CGF.Builder.saveIP();
   CGF.EmitBlockAfterUses(dispatchBlock);
 
   // If this isn't a catch-all filter, we need to check whether we got
diff --git a/safecode/tools/clang/lib/CodeGen/CGExpr.cpp b/safecode/tools/clang/lib/CodeGen/CGExpr.cpp
index 59b8fef..d26d787 100644
--- a/safecode/tools/clang/lib/CodeGen/CGExpr.cpp
+++ b/safecode/tools/clang/lib/CodeGen/CGExpr.cpp
@@ -2150,8 +2150,7 @@
 
 LValue CodeGenFunction::EmitMaterializeTemporaryExpr(
                                            const MaterializeTemporaryExpr *E) {
-  RValue RV = EmitReferenceBindingToExpr(E->GetTemporaryExpr(),
-                                         /*InitializedDecl=*/0);
+  RValue RV = EmitReferenceBindingToExpr(E, /*InitializedDecl=*/0);
   return MakeAddrLValue(RV.getScalarVal(), E->getType());
 }
 
diff --git a/safecode/tools/clang/lib/Driver/Driver.cpp b/safecode/tools/clang/lib/Driver/Driver.cpp
index 2baed75..534984b 100644
--- a/safecode/tools/clang/lib/Driver/Driver.cpp
+++ b/safecode/tools/clang/lib/Driver/Driver.cpp
@@ -1354,8 +1354,10 @@
   // Output to a temporary file?
   if ((!AtTopLevel && !C.getArgs().hasArg(options::OPT_save_temps)) ||
       CCGenDiagnostics) {
+    StringRef Name = llvm::sys::path::filename(BaseInput);
+    std::pair<StringRef, StringRef> Split = Name.split('.');
     std::string TmpName =
-      GetTemporaryPath(types::getTypeTempSuffix(JA.getType()));
+      GetTemporaryPath(Split.first, types::getTypeTempSuffix(JA.getType()));
     return C.addTempFile(C.getArgs().MakeArgString(TmpName.c_str()));
   }
 
@@ -1388,9 +1390,11 @@
   // If we're saving temps and the temp filename conflicts with the input
   // filename, then avoid overwriting input file.
   if (!AtTopLevel && C.getArgs().hasArg(options::OPT_save_temps) &&
-    NamedOutput == BaseName) {
+      NamedOutput == BaseName) {
+    StringRef Name = llvm::sys::path::filename(BaseInput);
+    std::pair<StringRef, StringRef> Split = Name.split('.');
     std::string TmpName =
-      GetTemporaryPath(types::getTypeTempSuffix(JA.getType()));
+      GetTemporaryPath(Split.first, types::getTypeTempSuffix(JA.getType()));
     return C.addTempFile(C.getArgs().MakeArgString(TmpName.c_str()));
   }
 
@@ -1475,7 +1479,8 @@
   return Name;
 }
 
-std::string Driver::GetTemporaryPath(const char *Suffix) const {
+std::string Driver::GetTemporaryPath(StringRef Prefix, const char *Suffix) 
+  const {
   // FIXME: This is lame; sys::Path should provide this function (in particular,
   // it should know how to find the temporary files dir).
   std::string Error;
@@ -1487,7 +1492,7 @@
   if (!TmpDir)
     TmpDir = "/tmp";
   llvm::sys::Path P(TmpDir);
-  P.appendComponent("cc");
+  P.appendComponent(Prefix);
   if (P.makeUnique(false, &Error)) {
     Diag(clang::diag::err_drv_unable_to_make_temp) << Error;
     return "";
diff --git a/safecode/tools/clang/lib/Driver/Tools.cpp b/safecode/tools/clang/lib/Driver/Tools.cpp
index 697ff69..2dbc18a 100644
--- a/safecode/tools/clang/lib/Driver/Tools.cpp
+++ b/safecode/tools/clang/lib/Driver/Tools.cpp
@@ -2464,103 +2464,121 @@
        it != ie;) {
 
     StringRef Option = *it;
+    bool RemoveOption = false;
 
-    // We only remove warning options.
-    if (!Option.startswith("-W")) {
-      ++it;
+    // Remove -faltivec
+    if (Option.equals("-faltivec")) {
+      it = CmdArgs.erase(it);
+      ie = CmdArgs.end();
       continue;
     }
 
-    if (Option.startswith("-Wno-"))
-      Option = Option.substr(5);
-    else
-      Option = Option.substr(2);
-
-    bool RemoveOption = llvm::StringSwitch<bool>(Option)
-      .Case("address-of-temporary", true)
-      .Case("ambiguous-member-template", true)
-      .Case("analyzer-incompatible-plugin", true)
-      .Case("array-bounds", true)
-      .Case("array-bounds-pointer-arithmetic", true)
-      .Case("bind-to-temporary-copy", true)
-      .Case("bitwise-op-parentheses", true)
-      .Case("bool-conversions", true)
-      .Case("builtin-macro-redefined", true)
-      .Case("c++-hex-floats", true)
-      .Case("c++0x-compat", true)
-      .Case("c++0x-extensions", true)
-      .Case("c++0x-narrowing", true)
-      .Case("c++0x-static-nonintegral-init", true)
-      .Case("conditional-uninitialized", true)
-      .Case("constant-conversion", true)
-      .Case("CFString-literal", true)
-      .Case("constant-logical-operand", true)
-      .Case("custom-atomic-properties", true)
-      .Case("default-arg-special-member", true)
-      .Case("delegating-ctor-cycles", true)
-      .Case("delete-non-virtual-dtor", true)
-      .Case("deprecated-implementations", true)
-      .Case("deprecated-writable-strings", true)
-      .Case("distributed-object-modifiers", true)
-      .Case("duplicate-method-arg", true)
-      .Case("dynamic-class-memaccess", true)
-      .Case("enum-compare", true)
-      .Case("exit-time-destructors", true)
-      .Case("gnu", true)
-      .Case("gnu-designator", true)
-      .Case("header-hygiene", true)
-      .Case("idiomatic-parentheses", true)
-      .Case("ignored-qualifiers", true)
-      .Case("implicit-atomic-properties", true)
-      .Case("incompatible-pointer-types", true)
-      .Case("incomplete-implementation", true)
-      .Case("initializer-overrides", true)
-      .Case("invalid-noreturn", true)
-      .Case("invalid-token-paste", true)
-      .Case("literal-conversion", true)
-      .Case("literal-range", true)
-      .Case("local-type-template-args", true)
-      .Case("logical-op-parentheses", true)
-      .Case("method-signatures", true)
-      .Case("microsoft", true)
-      .Case("mismatched-tags", true)
-      .Case("missing-method-return-type", true)
-      .Case("non-pod-varargs", true)
-      .Case("nonfragile-abi2", true)
-      .Case("null-arithmetic", true)
-      .Case("null-dereference", true)
-      .Case("out-of-line-declaration", true)
-      .Case("overriding-method-mismatch", true)
-      .Case("readonly-setter-attrs", true)
-      .Case("return-stack-address", true)
-      .Case("self-assign", true)
-      .Case("semicolon-before-method-body", true)
-      .Case("sentinel", true)
-      .Case("shift-overflow", true)
-      .Case("shift-sign-overflow", true)
-      .Case("sign-conversion", true)
-      .Case("sizeof-array-argument", true)
-      .Case("sizeof-pointer-memaccess", true)
-      .Case("string-compare", true)
-      .Case("super-class-method-mismatch", true)
-      .Case("tautological-compare", true)
-      .Case("typedef-redefinition", true)
-      .Case("typename-missing", true)
-      .Case("undefined-reinterpret-cast", true)
-      .Case("unknown-warning-option", true)
-      .Case("unnamed-type-template-args", true)
-      .Case("unneeded-internal-declaration", true)
-      .Case("unneeded-member-function", true)
-      .Case("unused-comparison", true)
-      .Case("unused-exception-parameter", true)
-      .Case("unused-member-function", true)
-      .Case("unused-result", true)
-      .Case("vector-conversions", true)
-      .Case("vla", true)
-      .Case("used-but-marked-unused", true)
-      .Case("weak-vtables", true)
-      .Default(false);
-
+    // Handle machine specific options.
+    if (Option.startswith("-m")) {
+      RemoveOption = llvm::StringSwitch<bool>(Option)
+        .Case("-mthumb", true)
+        .Case("-mno-thumb", true)
+        .Case("-mno-fused-madd", true)
+        .Case("-mlong-branch", true)
+        .Case("-mlongcall", true)
+        .Case("-mcpu=G4", true)
+        .Case("-mcpu=G5", true)
+        .Default(false);
+    }
+    
+    // Handle warning options.
+    if (Option.startswith("-W")) {
+      // Remove -W/-Wno- to reduce the number of cases.
+      if (Option.startswith("-Wno-"))
+        Option = Option.substr(5);
+      else
+        Option = Option.substr(2);
+      
+      RemoveOption = llvm::StringSwitch<bool>(Option)
+        .Case("address-of-temporary", true)
+        .Case("ambiguous-member-template", true)
+        .Case("analyzer-incompatible-plugin", true)
+        .Case("array-bounds", true)
+        .Case("array-bounds-pointer-arithmetic", true)
+        .Case("bind-to-temporary-copy", true)
+        .Case("bitwise-op-parentheses", true)
+        .Case("bool-conversions", true)
+        .Case("builtin-macro-redefined", true)
+        .Case("c++-hex-floats", true)
+        .Case("c++0x-compat", true)
+        .Case("c++0x-extensions", true)
+        .Case("c++0x-narrowing", true)
+        .Case("c++0x-static-nonintegral-init", true)
+        .Case("conditional-uninitialized", true)
+        .Case("constant-conversion", true)
+        .Case("CFString-literal", true)
+        .Case("constant-logical-operand", true)
+        .Case("custom-atomic-properties", true)
+        .Case("default-arg-special-member", true)
+        .Case("delegating-ctor-cycles", true)
+        .Case("delete-non-virtual-dtor", true)
+        .Case("deprecated-implementations", true)
+        .Case("deprecated-writable-strings", true)
+        .Case("distributed-object-modifiers", true)
+        .Case("duplicate-method-arg", true)
+        .Case("dynamic-class-memaccess", true)
+        .Case("enum-compare", true)
+        .Case("exit-time-destructors", true)
+        .Case("gnu", true)
+        .Case("gnu-designator", true)
+        .Case("header-hygiene", true)
+        .Case("idiomatic-parentheses", true)
+        .Case("ignored-qualifiers", true)
+        .Case("implicit-atomic-properties", true)
+        .Case("incompatible-pointer-types", true)
+        .Case("incomplete-implementation", true)
+        .Case("initializer-overrides", true)
+        .Case("invalid-noreturn", true)
+        .Case("invalid-token-paste", true)
+        .Case("literal-conversion", true)
+        .Case("literal-range", true)
+        .Case("local-type-template-args", true)
+        .Case("logical-op-parentheses", true)
+        .Case("method-signatures", true)
+        .Case("microsoft", true)
+        .Case("mismatched-tags", true)
+        .Case("missing-method-return-type", true)
+        .Case("non-pod-varargs", true)
+        .Case("nonfragile-abi2", true)
+        .Case("null-arithmetic", true)
+        .Case("null-dereference", true)
+        .Case("out-of-line-declaration", true)
+        .Case("overriding-method-mismatch", true)
+        .Case("readonly-setter-attrs", true)
+        .Case("return-stack-address", true)
+        .Case("self-assign", true)
+        .Case("semicolon-before-method-body", true)
+        .Case("sentinel", true)
+        .Case("shift-overflow", true)
+        .Case("shift-sign-overflow", true)
+        .Case("sign-conversion", true)
+        .Case("sizeof-array-argument", true)
+        .Case("sizeof-pointer-memaccess", true)
+        .Case("string-compare", true)
+        .Case("super-class-method-mismatch", true)
+        .Case("tautological-compare", true)
+        .Case("typedef-redefinition", true)
+        .Case("typename-missing", true)
+        .Case("undefined-reinterpret-cast", true)
+        .Case("unknown-warning-option", true)
+        .Case("unnamed-type-template-args", true)
+        .Case("unneeded-internal-declaration", true)
+        .Case("unneeded-member-function", true)
+        .Case("unused-comparison", true)
+        .Case("unused-exception-parameter", true)
+        .Case("unused-member-function", true)
+        .Case("unused-result", true)
+        .Case("vector-conversions", true)
+        .Case("vla", true)
+        .Case("used-but-marked-unused", true)
+        .Case("weak-vtables", true)
+        .Default(false);
+    } // if (Option.startswith("-W"))
     if (RemoveOption) {
       it = CmdArgs.erase(it);
       ie = CmdArgs.end();
@@ -2969,7 +2987,7 @@
     // NOTE: gcc uses a temp .s file for this, but there doesn't seem
     // to be a good reason.
     const char *TmpPath = C.getArgs().MakeArgString(
-      D.GetTemporaryPath("s"));
+      D.GetTemporaryPath("cc", "s"));
     C.addTempFile(TmpPath);
     CmdArgs.push_back(TmpPath);
 
@@ -3111,7 +3129,7 @@
   // dsymutil step.
   if (Version[0] >= 116 && D.IsUsingLTO(Args)) {
     const char *TmpPath = C.getArgs().MakeArgString(
-      D.GetTemporaryPath(types::getTypeTempSuffix(types::TY_Object)));
+      D.GetTemporaryPath("cc", types::getTypeTempSuffix(types::TY_Object)));
     C.addTempFile(TmpPath);
     CmdArgs.push_back("-object_path_lto");
     CmdArgs.push_back(TmpPath);
diff --git a/safecode/tools/clang/lib/Frontend/ASTUnit.cpp b/safecode/tools/clang/lib/Frontend/ASTUnit.cpp
index 4a5a29a..cc96d48 100644
--- a/safecode/tools/clang/lib/Frontend/ASTUnit.cpp
+++ b/safecode/tools/clang/lib/Frontend/ASTUnit.cpp
@@ -616,7 +616,7 @@
   AST->Target = TargetInfo::CreateTargetInfo(AST->getDiagnostics(),
                                              TargetOpts);
   AST->PP = new Preprocessor(AST->getDiagnostics(), LangInfo, *AST->Target,
-                             AST->getSourceManager(), HeaderInfo);
+                             AST->getSourceManager(), HeaderInfo, *AST);
   Preprocessor &PP = *AST->PP;
 
   PP.setPredefines(Reader->getSuggestedPredefines());
@@ -707,9 +707,7 @@
   }
   
   if (ObjCClassDecl *Class = dyn_cast<ObjCClassDecl>(D)) {
-    for (ObjCClassDecl::iterator I = Class->begin(), IEnd = Class->end();
-         I != IEnd; ++I)
-      AddTopLevelDeclarationToHash(I->getInterface(), Hash);
+    AddTopLevelDeclarationToHash(Class->getForwardInterfaceDecl(), Hash);
     return;
   }
 }
diff --git a/safecode/tools/clang/lib/Frontend/CompilerInstance.cpp b/safecode/tools/clang/lib/Frontend/CompilerInstance.cpp
index ec8b6dc..f53d0b0 100644
--- a/safecode/tools/clang/lib/Frontend/CompilerInstance.cpp
+++ b/safecode/tools/clang/lib/Frontend/CompilerInstance.cpp
@@ -191,52 +191,38 @@
 // Preprocessor
 
 void CompilerInstance::createPreprocessor() {
-  PP = createPreprocessor(getDiagnostics(), getLangOpts(),
-                          getPreprocessorOpts(), getHeaderSearchOpts(),
-                          getDependencyOutputOpts(), getTarget(),
-                          getFrontendOpts(), getSourceManager(),
-                          getFileManager());
-}
-
-Preprocessor *
-CompilerInstance::createPreprocessor(Diagnostic &Diags,
-                                     const LangOptions &LangInfo,
-                                     const PreprocessorOptions &PPOpts,
-                                     const HeaderSearchOptions &HSOpts,
-                                     const DependencyOutputOptions &DepOpts,
-                                     const TargetInfo &Target,
-                                     const FrontendOptions &FEOpts,
-                                     SourceManager &SourceMgr,
-                                     FileManager &FileMgr) {
+  const PreprocessorOptions &PPOpts = getPreprocessorOpts();
+  
   // Create a PTH manager if we are using some form of a token cache.
   PTHManager *PTHMgr = 0;
   if (!PPOpts.TokenCache.empty())
-    PTHMgr = PTHManager::Create(PPOpts.TokenCache, Diags);
-
+    PTHMgr = PTHManager::Create(PPOpts.TokenCache, getDiagnostics());
+  
   // Create the Preprocessor.
-  HeaderSearch *HeaderInfo = new HeaderSearch(FileMgr);
-  Preprocessor *PP = new Preprocessor(Diags, LangInfo, Target,
-                                      SourceMgr, *HeaderInfo, PTHMgr,
-                                      /*OwnsHeaderSearch=*/true);
-
+  HeaderSearch *HeaderInfo = new HeaderSearch(getFileManager());
+  PP = new Preprocessor(getDiagnostics(), getLangOpts(), getTarget(),
+                        getSourceManager(), *HeaderInfo, *this, PTHMgr,
+                        /*OwnsHeaderSearch=*/true);
+  
   // Note that this is different then passing PTHMgr to Preprocessor's ctor.
   // That argument is used as the IdentifierInfoLookup argument to
   // IdentifierTable's ctor.
   if (PTHMgr) {
-    PTHMgr->setPreprocessor(PP);
+    PTHMgr->setPreprocessor(&*PP);
     PP->setPTHManager(PTHMgr);
   }
-
+  
   if (PPOpts.DetailedRecord)
     PP->createPreprocessingRecord(
-                       PPOpts.DetailedRecordIncludesNestedMacroExpansions);
+                                  PPOpts.DetailedRecordIncludesNestedMacroExpansions);
   
-  InitializePreprocessor(*PP, PPOpts, HSOpts, FEOpts);
-
+  InitializePreprocessor(*PP, PPOpts, getHeaderSearchOpts(), getFrontendOpts());
+  
   // Handle generating dependencies, if requested.
+  const DependencyOutputOptions &DepOpts = getDependencyOutputOpts();
   if (!DepOpts.OutputFile.empty())
     AttachDependencyFileGen(*PP, DepOpts);
-
+  
   // Handle generating header include information, if requested.
   if (DepOpts.ShowHeaderIncludes)
     AttachHeaderIncludeGen(*PP);
@@ -247,8 +233,6 @@
     AttachHeaderIncludeGen(*PP, /*ShowAllHeaders=*/true, OutputPath,
                            /*ShowDepth=*/false);
   }
-
-  return PP;
 }
 
 // ASTContext
@@ -640,4 +624,68 @@
   return !getDiagnostics().getClient()->getNumErrors();
 }
 
+ModuleKey CompilerInstance::loadModule(SourceLocation ImportLoc, 
+                                       IdentifierInfo &ModuleName,
+                                       SourceLocation ModuleNameLoc) {  
+  // Determine what file we're searching from.
+  SourceManager &SourceMgr = getSourceManager();
+  SourceLocation ExpandedImportLoc = SourceMgr.getExpansionLoc(ImportLoc);
+  const FileEntry *CurFile
+    = SourceMgr.getFileEntryForID(SourceMgr.getFileID(ExpandedImportLoc));
+  if (!CurFile)
+    CurFile = SourceMgr.getFileEntryForID(SourceMgr.getMainFileID());
+
+  // Search for a module with the given name.
+  std::string Filename = ModuleName.getName().str();
+  Filename += ".pcm";
+  const DirectoryLookup *CurDir = 0;  
+  const FileEntry *ModuleFile
+    = PP->getHeaderSearchInfo().LookupFile(Filename, /*isAngled=*/false,
+                                           /*FromDir=*/0, CurDir, CurFile, 
+                                           /*SearchPath=*/0, 
+                                           /*RelativePath=*/0);
+  if (!ModuleFile) {
+    getDiagnostics().Report(ModuleNameLoc, diag::warn_module_not_found)
+      << ModuleName.getName()
+      << SourceRange(ImportLoc, ModuleNameLoc);
+    return 0;
+  }
+  
+  // If we don't already have an ASTReader, create one now.
+  if (!ModuleManager) {
+    std::string Sysroot = getHeaderSearchOpts().Sysroot;
+    const PreprocessorOptions &PPOpts = getPreprocessorOpts();
+    ModuleManager = new ASTReader(getPreprocessor(), &*Context,
+                                  Sysroot.empty() ? "" : Sysroot.c_str(),
+                                  PPOpts.DisablePCHValidation, 
+                                  PPOpts.DisableStatCache);
+    ModuleManager->setDeserializationListener(
+      getASTConsumer().GetASTDeserializationListener());
+    getASTContext().setASTMutationListener(
+      getASTConsumer().GetASTMutationListener());
+    llvm::OwningPtr<ExternalASTSource> Source;
+    Source.reset(ModuleManager);
+    getASTContext().setExternalSource(Source);
+    ModuleManager->InitializeSema(getSema());
+  }
+  
+  // Try to load the module we found.
+  switch (ModuleManager->ReadAST(ModuleFile->getName(),
+                                 serialization::MK_Module)) {
+  case ASTReader::Success:
+    break;
+
+  case ASTReader::IgnorePCH:
+    // FIXME: The ASTReader will already have complained, but can we showhorn
+    // that diagnostic information into a more useful form?
+    return 0;
+      
+  case ASTReader::Failure:
+    // Already complained.
+    return 0;
+  }
+  
+  // FIXME: The module file's FileEntry makes a poor key indeed!
+  return (ModuleKey)ModuleFile;
+}
 
diff --git a/safecode/tools/clang/lib/Frontend/CompilerInvocation.cpp b/safecode/tools/clang/lib/Frontend/CompilerInvocation.cpp
index 54d69cc..0e54e9c 100644
--- a/safecode/tools/clang/lib/Frontend/CompilerInvocation.cpp
+++ b/safecode/tools/clang/lib/Frontend/CompilerInvocation.cpp
@@ -498,10 +498,6 @@
     Res.push_back("-ast-merge");
     Res.push_back(Opts.ASTMergeFiles[i]);
   }
-  for (unsigned i = 0, e = Opts.Modules.size(); i != e; ++i) {
-    Res.push_back("-import-module");
-    Res.push_back(Opts.Modules[i]);
-  }
   for (unsigned i = 0, e = Opts.LLVMArgs.size(); i != e; ++i) {
     Res.push_back("-mllvm");
     Res.push_back(Opts.LLVMArgs[i]);
@@ -776,10 +772,6 @@
     Res.push_back("-include");
     Res.push_back(Opts.Includes[i]);
   }
-  for (unsigned i = 0, e = Opts.Modules.size(); i != e; ++i) {
-    Res.push_back("-import_module");
-    Res.push_back(Opts.Modules[i]);
-  }
   for (unsigned i = 0, e = Opts.MacroIncludes.size(); i != e; ++i) {
     Res.push_back("-imacros");
     Res.push_back(Opts.MacroIncludes[i]);
@@ -1285,7 +1277,6 @@
   Opts.ASTMergeFiles = Args.getAllArgValues(OPT_ast_merge);
   Opts.LLVMArgs = Args.getAllArgValues(OPT_mllvm);
   Opts.FixWhatYouCan = Args.hasArg(OPT_fix_what_you_can);
-  Opts.Modules = Args.getAllArgValues(OPT_import_module);
 
   Opts.ARCMTAction = FrontendOptions::ARCMT_None;
   if (const Arg *A = Args.getLastArg(OPT_arcmt_check,
@@ -1816,12 +1807,6 @@
     Opts.ChainedIncludes.push_back(A->getValue(Args));
   }
 
-  for (arg_iterator it = Args.filtered_begin(OPT_import_module),
-      ie = Args.filtered_end(); it != ie; ++it) {
-    const Arg *A = *it;
-    Opts.Modules.push_back(A->getValue(Args));
-  }
-
   // Include 'altivec.h' if -faltivec option present
   if (Args.hasArg(OPT_faltivec))
     Opts.Includes.push_back("altivec.h");
diff --git a/safecode/tools/clang/lib/Lex/Lexer.cpp b/safecode/tools/clang/lib/Lex/Lexer.cpp
index 1ec50cd..64b8744 100644
--- a/safecode/tools/clang/lib/Lex/Lexer.cpp
+++ b/safecode/tools/clang/lib/Lex/Lexer.cpp
@@ -1277,6 +1277,7 @@
     // preprocessor, which may macro expand it or something.
     if (II->isHandleIdentifierCase())
       PP->HandleIdentifier(Result);
+    
     return;
   }
 
diff --git a/safecode/tools/clang/lib/Lex/Preprocessor.cpp b/safecode/tools/clang/lib/Lex/Preprocessor.cpp
index 24d36cd..51908bd 100644
--- a/safecode/tools/clang/lib/Lex/Preprocessor.cpp
+++ b/safecode/tools/clang/lib/Lex/Preprocessor.cpp
@@ -35,6 +35,7 @@
 #include "clang/Lex/ScratchBuffer.h"
 #include "clang/Lex/LexDiagnostic.h"
 #include "clang/Lex/CodeCompletionHandler.h"
+#include "clang/Lex/ModuleLoader.h"
 #include "clang/Basic/SourceManager.h"
 #include "clang/Basic/FileManager.h"
 #include "clang/Basic/TargetInfo.h"
@@ -50,12 +51,12 @@
 
 Preprocessor::Preprocessor(Diagnostic &diags, const LangOptions &opts,
                            const TargetInfo &target, SourceManager &SM,
-                           HeaderSearch &Headers,
+                           HeaderSearch &Headers, ModuleLoader &TheModuleLoader,
                            IdentifierInfoLookup* IILookup,
                            bool OwnsHeaders)
   : Diags(&diags), Features(opts), Target(target),FileMgr(Headers.getFileMgr()),
-    SourceMgr(SM),
-    HeaderInfo(Headers), ExternalSource(0),
+    SourceMgr(SM), HeaderInfo(Headers), TheModuleLoader(TheModuleLoader),
+    ExternalSource(0), 
     Identifiers(opts, IILookup), BuiltinInfo(Target), CodeComplete(0),
     CodeCompletionFile(0), SkipMainFilePreamble(0, true), CurPPLexer(0), 
     CurDirLookup(0), Callbacks(0), MacroArgCache(0), Record(0), MIChainHead(0),
@@ -87,6 +88,8 @@
   // We haven't read anything from the external source.
   ReadMacrosFromExternalSource = false;
 
+  LexDepth = 0;
+      
   // "Poison" __VA_ARGS__, which can only appear in the expansion of a macro.
   // This gets unpoisoned where it is allowed.
   (Ident__VA_ARGS__ = getIdentifierInfo("__VA_ARGS__"))->setIsPoisoned();
@@ -507,6 +510,27 @@
     Diag(Identifier, diag::ext_token_used);
 }
 
+void Preprocessor::HandleModuleImport(Token &Import) {
+  // The token sequence 
+  //
+  //   __import__ identifier
+  //
+  // indicates a module import directive. We load the module and then 
+  // leave the token sequence for the parser.
+  Token ModuleNameTok = LookAhead(0);
+  if (ModuleNameTok.getKind() != tok::identifier)
+    return;
+  
+  (void)TheModuleLoader.loadModule(Import.getLocation(),
+                                   *ModuleNameTok.getIdentifierInfo(), 
+                                   ModuleNameTok.getLocation());
+  
+  // FIXME: Transmogrify __import__ into some kind of AST-only __import__ that
+  // is not recognized by the preprocessor but is recognized by the parser.
+  // It would also be useful to stash the ModuleKey somewhere, so we don't try
+  // to load the module twice.
+}
+
 void Preprocessor::AddCommentHandler(CommentHandler *Handler) {
   assert(Handler && "NULL comment handler");
   assert(std::find(CommentHandlers.begin(), CommentHandlers.end(), Handler) ==
@@ -535,6 +559,8 @@
   return true;
 }
 
+ModuleLoader::~ModuleLoader() { }
+
 CommentHandler::~CommentHandler() { }
 
 CodeCompletionHandler::~CodeCompletionHandler() { }
diff --git a/safecode/tools/clang/lib/Parse/ParseInit.cpp b/safecode/tools/clang/lib/Parse/ParseInit.cpp
index 2c9278a..ad7bcb2 100644
--- a/safecode/tools/clang/lib/Parse/ParseInit.cpp
+++ b/safecode/tools/clang/lib/Parse/ParseInit.cpp
@@ -90,7 +90,7 @@
     assert(Tok.is(tok::colon) && "MayBeDesignationStart not working properly!");
     SourceLocation ColonLoc = ConsumeToken();
 
-    Diag(Tok, diag::ext_gnu_old_style_field_designator)
+    Diag(NameLoc, diag::ext_gnu_old_style_field_designator)
       << FixItHint::CreateReplacement(SourceRange(NameLoc, ColonLoc),
                                       NewSyntax.str());
 
diff --git a/safecode/tools/clang/lib/Parse/ParseObjc.cpp b/safecode/tools/clang/lib/Parse/ParseObjc.cpp
index 684d8ed..17c962e 100644
--- a/safecode/tools/clang/lib/Parse/ParseObjc.cpp
+++ b/safecode/tools/clang/lib/Parse/ParseObjc.cpp
@@ -29,47 +29,59 @@
 /// [OBJC]  objc-protocol-definition
 /// [OBJC]  objc-method-definition
 /// [OBJC]  '@' 'end'
-Decl *Parser::ParseObjCAtDirectives() {
+Parser::DeclGroupPtrTy Parser::ParseObjCAtDirectives() {
   SourceLocation AtLoc = ConsumeToken(); // the "@"
 
   if (Tok.is(tok::code_completion)) {
     Actions.CodeCompleteObjCAtDirective(getCurScope());
     ConsumeCodeCompletionToken();
   }
-
+    
+  Decl *SingleDecl = 0;
   switch (Tok.getObjCKeywordID()) {
   case tok::objc_class:
     return ParseObjCAtClassDeclaration(AtLoc);
+    break;
   case tok::objc_interface: {
     ParsedAttributes attrs(AttrFactory);
-    return ParseObjCAtInterfaceDeclaration(AtLoc, attrs);
+    SingleDecl = ParseObjCAtInterfaceDeclaration(AtLoc, attrs);
+    break;
   }
   case tok::objc_protocol: {
     ParsedAttributes attrs(AttrFactory);
-    return ParseObjCAtProtocolDeclaration(AtLoc, attrs);
+    SingleDecl = ParseObjCAtProtocolDeclaration(AtLoc, attrs);
+    break;
   }
   case tok::objc_implementation:
-    return ParseObjCAtImplementationDeclaration(AtLoc);
+    SingleDecl = ParseObjCAtImplementationDeclaration(AtLoc);
+    break;
   case tok::objc_end:
-    return ParseObjCAtEndDeclaration(AtLoc);
+    SingleDecl = ParseObjCAtEndDeclaration(AtLoc);
+    break;
   case tok::objc_compatibility_alias:
-    return ParseObjCAtAliasDeclaration(AtLoc);
+    SingleDecl = ParseObjCAtAliasDeclaration(AtLoc);
+    break;
   case tok::objc_synthesize:
-    return ParseObjCPropertySynthesize(AtLoc);
+    SingleDecl = ParseObjCPropertySynthesize(AtLoc);
+    break;
   case tok::objc_dynamic:
-    return ParseObjCPropertyDynamic(AtLoc);
+    SingleDecl = ParseObjCPropertyDynamic(AtLoc);
+    break;
   default:
     Diag(AtLoc, diag::err_unexpected_at);
     SkipUntil(tok::semi);
-    return 0;
+    SingleDecl = 0;
+    break;
   }
+  return Actions.ConvertDeclToDeclGroup(SingleDecl);
 }
 
 ///
 /// objc-class-declaration:
 ///    '@' 'class' identifier-list ';'
 ///
-Decl *Parser::ParseObjCAtClassDeclaration(SourceLocation atLoc) {
+Parser::DeclGroupPtrTy
+Parser::ParseObjCAtClassDeclaration(SourceLocation atLoc) {
   ConsumeToken(); // the identifier "class"
   SmallVector<IdentifierInfo *, 8> ClassNames;
   SmallVector<SourceLocation, 8> ClassLocs;
@@ -79,7 +91,7 @@
     if (Tok.isNot(tok::identifier)) {
       Diag(Tok, diag::err_expected_ident);
       SkipUntil(tok::semi);
-      return 0;
+      return Actions.ConvertDeclToDeclGroup(0);
     }
     ClassNames.push_back(Tok.getIdentifierInfo());
     ClassLocs.push_back(Tok.getLocation());
@@ -93,7 +105,7 @@
 
   // Consume the ';'.
   if (ExpectAndConsume(tok::semi, diag::err_expected_semi_after, "@class"))
-    return 0;
+    return Actions.ConvertDeclToDeclGroup(0);
 
   return Actions.ActOnForwardClassDeclaration(atLoc, ClassNames.data(),
                                               ClassLocs.data(),
diff --git a/safecode/tools/clang/lib/Parse/Parser.cpp b/safecode/tools/clang/lib/Parse/Parser.cpp
index 0da2b43..43e0f03 100644
--- a/safecode/tools/clang/lib/Parse/Parser.cpp
+++ b/safecode/tools/clang/lib/Parse/Parser.cpp
@@ -593,10 +593,7 @@
     break;
   }
   case tok::at:
-    // @ is not a legal token unless objc is enabled, no need to check for ObjC.
-    /// FIXME: ParseObjCAtDirectives should return a DeclGroup for things like
-    /// @class foo, bar;
-    SingleDecl = ParseObjCAtDirectives();
+    return ParseObjCAtDirectives();
     break;
   case tok::minus:
   case tok::plus:
@@ -679,6 +676,9 @@
     ParseMicrosoftIfExistsExternalDeclaration();
     return DeclGroupPtrTy();
 
+  case tok::kw___import__:
+    return ParseModuleImport();
+      
   default:
   dont_know:
     // We can't tell whether this is a function-definition or declaration yet.
@@ -1541,3 +1541,24 @@
   }
   ConsumeBrace();
 }
+
+Parser::DeclGroupPtrTy Parser::ParseModuleImport() {
+  assert(Tok.is(tok::kw___import__) && "Improper start to module import");
+  SourceLocation ImportLoc = ConsumeToken();
+  
+  // Parse the module name.
+  if (!Tok.is(tok::identifier)) {
+    Diag(Tok, diag::err_module_expected_ident);
+    SkipUntil(tok::semi);
+    return DeclGroupPtrTy();
+  }
+  
+  IdentifierInfo &ModuleName = *Tok.getIdentifierInfo();
+  SourceLocation ModuleNameLoc = ConsumeToken();
+  DeclResult Import = Actions.ActOnModuleImport(ImportLoc, ModuleName, ModuleNameLoc);
+  ExpectAndConsumeSemi(diag::err_module_expected_semi);
+  if (Import.isInvalid())
+    return DeclGroupPtrTy();
+  
+  return Actions.ConvertDeclToDeclGroup(Import.get());
+}
diff --git a/safecode/tools/clang/lib/Rewrite/RewriteObjC.cpp b/safecode/tools/clang/lib/Rewrite/RewriteObjC.cpp
index 3ba7e90..ba51806 100644
--- a/safecode/tools/clang/lib/Rewrite/RewriteObjC.cpp
+++ b/safecode/tools/clang/lib/Rewrite/RewriteObjC.cpp
@@ -161,8 +161,13 @@
 
     // Top Level Driver code.
     virtual void HandleTopLevelDecl(DeclGroupRef D) {
-      for (DeclGroupRef::iterator I = D.begin(), E = D.end(); I != E; ++I)
+      for (DeclGroupRef::iterator I = D.begin(), E = D.end(); I != E; ++I) {
+        if (isa<ObjCClassDecl>((*I))) {
+          RewriteForwardClassDecl(D);
+          break;
+        }
         HandleTopLevelSingleDecl(*I);
+      }
     }
     void HandleTopLevelSingleDecl(Decl *D);
     void HandleDeclInMainFile(Decl *D);
@@ -241,7 +246,7 @@
 
     // Syntactic Rewriting.
     void RewriteInclude();
-    void RewriteForwardClassDecl(ObjCClassDecl *Dcl);
+    void RewriteForwardClassDecl(DeclGroupRef D);
     void RewritePropertyImplDecl(ObjCPropertyImplDecl *PID,
                                  ObjCImplementationDecl *IMD,
                                  ObjCCategoryImplDecl *CID);
@@ -886,30 +891,28 @@
   InsertText(onePastSemiLoc, Setr);
 }
 
-void RewriteObjC::RewriteForwardClassDecl(ObjCClassDecl *ClassDecl) {
-  // Get the start location and compute the semi location.
-  SourceLocation startLoc = ClassDecl->getLocation();
-  const char *startBuf = SM->getCharacterData(startLoc);
-  const char *semiPtr = strchr(startBuf, ';');
-
-  // Translate to typedef's that forward reference structs with the same name
-  // as the class. As a convenience, we include the original declaration
-  // as a comment.
+void RewriteObjC::RewriteForwardClassDecl(DeclGroupRef D) {
+  SourceLocation startLoc;
   std::string typedefString;
-  typedefString += "// @class ";
-  for (ObjCClassDecl::iterator I = ClassDecl->begin(), E = ClassDecl->end();
-       I != E; ++I) {
-    ObjCInterfaceDecl *ForwardDecl = I->getInterface();
-    typedefString += ForwardDecl->getNameAsString();
-    if (I+1 != E)
-      typedefString += ", ";
-    else
+  const char *startBuf = 0;
+  const char *semiPtr = 0;
+  for (DeclGroupRef::iterator I = D.begin(), E = D.end(); I != E; ++I) {
+    ObjCClassDecl *ClassDecl = cast<ObjCClassDecl>(*I);
+    ObjCInterfaceDecl *ForwardDecl = ClassDecl->getForwardInterfaceDecl();
+    if (I == D.begin()) {
+      // Get the start location and compute the semi location.
+      startLoc = ClassDecl->getLocation();
+      startBuf = SM->getCharacterData(startLoc);
+      semiPtr = strchr(startBuf, ';');
+      typedefString += "// @class ";
+      typedefString += ForwardDecl->getNameAsString();
       typedefString += ";\n";
-  }
+    }
+    // Translate to typedef's that forward reference structs with the same name
+    // as the class. As a convenience, we include the original declaration
+    // as a comment.
   
-  for (ObjCClassDecl::iterator I = ClassDecl->begin(), E = ClassDecl->end();
-       I != E; ++I) {
-    ObjCInterfaceDecl *ForwardDecl = I->getInterface();
+  
     typedefString += "#ifndef _REWRITER_typedef_";
     typedefString += ForwardDecl->getNameAsString();
     typedefString += "\n";
@@ -5887,8 +5890,8 @@
     ClassImplementation.push_back(CI);
   else if (ObjCCategoryImplDecl *CI = dyn_cast<ObjCCategoryImplDecl>(D))
     CategoryImplementation.push_back(CI);
-  else if (ObjCClassDecl *CD = dyn_cast<ObjCClassDecl>(D))
-    RewriteForwardClassDecl(CD);
+  else if (isa<ObjCClassDecl>(D))
+    assert(false && "RewriteObjC::HandleDeclInMainFile - ObjCClassDecl");
   else if (VarDecl *VD = dyn_cast<VarDecl>(D)) {
     RewriteObjCQualifiedInterfaceTypes(VD);
     if (isTopLevelBlockPointerType(VD->getType()))
diff --git a/safecode/tools/clang/lib/Sema/AnalysisBasedWarnings.cpp b/safecode/tools/clang/lib/Sema/AnalysisBasedWarnings.cpp
index 51b04a7..6c07418 100644
--- a/safecode/tools/clang/lib/Sema/AnalysisBasedWarnings.cpp
+++ b/safecode/tools/clang/lib/Sema/AnalysisBasedWarnings.cpp
@@ -508,8 +508,10 @@
   else if (VariableTy->isEnumeralType())
     return;
   else if (VariableTy->isPointerType() || VariableTy->isMemberPointerType()) {
+    if (S.Context.getLangOptions().CPlusPlus0x)
+      initialization = " = nullptr";
     // Check if 'NULL' is defined.
-    if (S.PP.getMacroInfo(&S.getASTContext().Idents.get("NULL")))
+    else if (S.PP.getMacroInfo(&S.getASTContext().Idents.get("NULL")))
       initialization = " = NULL";
     else
       initialization = " = 0";
diff --git a/safecode/tools/clang/lib/Sema/Sema.cpp b/safecode/tools/clang/lib/Sema/Sema.cpp
index d3ace9d..7bd0a4a 100644
--- a/safecode/tools/clang/lib/Sema/Sema.cpp
+++ b/safecode/tools/clang/lib/Sema/Sema.cpp
@@ -85,6 +85,7 @@
     IdResolver(pp.getLangOptions()), CXXTypeInfoDecl(0), MSVCGuidDecl(0),
     GlobalNewDeleteDeclared(false), 
     ObjCShouldCallSuperDealloc(false),
+    ObjCShouldCallSuperFinalize(false),
     TUKind(TUKind),
     NumSFINAEErrors(0), SuppressAccessChecking(false), 
     AccessCheckingSFINAE(false), InNonInstantiationSFINAEContext(false),
diff --git a/safecode/tools/clang/lib/Sema/SemaChecking.cpp b/safecode/tools/clang/lib/Sema/SemaChecking.cpp
index 530f812..30c247f 100644
--- a/safecode/tools/clang/lib/Sema/SemaChecking.cpp
+++ b/safecode/tools/clang/lib/Sema/SemaChecking.cpp
@@ -12,6 +12,7 @@
 //
 //===----------------------------------------------------------------------===//
 
+#include "clang/Sema/Initialization.h"
 #include "clang/Sema/Sema.h"
 #include "clang/Sema/SemaInternal.h"
 #include "clang/Sema/ScopeInfo.h"
@@ -396,6 +397,30 @@
   return false;
 }
 
+/// checkBuiltinArgument - Given a call to a builtin function, perform
+/// normal type-checking on the given argument, updating the call in
+/// place.  This is useful when a builtin function requires custom
+/// type-checking for some of its arguments but not necessarily all of
+/// them.
+///
+/// Returns true on error.
+static bool checkBuiltinArgument(Sema &S, CallExpr *E, unsigned ArgIndex) {
+  FunctionDecl *Fn = E->getDirectCallee();
+  assert(Fn && "builtin call without direct callee!");
+
+  ParmVarDecl *Param = Fn->getParamDecl(ArgIndex);
+  InitializedEntity Entity =
+    InitializedEntity::InitializeParameter(S.Context, Param);
+
+  ExprResult Arg = E->getArg(0);
+  Arg = S.PerformCopyInitialization(Entity, SourceLocation(), Arg);
+  if (Arg.isInvalid())
+    return true;
+
+  E->setArg(ArgIndex, Arg.take());
+  return false;
+}
+
 /// SemaBuiltinAtomicOverloaded - We have a call to a function like
 /// __sync_fetch_and_add, which is an overloaded function based on the pointer
 /// type of its first argument.  The main ActOnCallExpr routines have already
@@ -661,6 +686,10 @@
       << 0 /*function call*/ << 2 << TheCall->getNumArgs();
   }
 
+  // Type-check the first argument normally.
+  if (checkBuiltinArgument(*this, TheCall, 0))
+    return true;
+
   // Determine whether the current function is variadic or not.
   BlockScopeInfo *CurBlock = getCurBlock();
   bool isVariadic;
diff --git a/safecode/tools/clang/lib/Sema/SemaCodeComplete.cpp b/safecode/tools/clang/lib/Sema/SemaCodeComplete.cpp
index ef54fbc..5e19148 100644
--- a/safecode/tools/clang/lib/Sema/SemaCodeComplete.cpp
+++ b/safecode/tools/clang/lib/Sema/SemaCodeComplete.cpp
@@ -5405,12 +5405,11 @@
 
     // Record any forward-declared interfaces we find.
     if (ObjCClassDecl *Forward = dyn_cast<ObjCClassDecl>(*D)) {
-      for (ObjCClassDecl::iterator C = Forward->begin(), CEnd = Forward->end();
-           C != CEnd; ++C)
-        if ((!OnlyForwardDeclarations || C->getInterface()->isForwardDecl()) &&
-            (!OnlyUnimplemented || !C->getInterface()->getImplementation()))
-          Results.AddResult(Result(C->getInterface(), 0), CurContext,
-                            0, false);
+      ObjCInterfaceDecl *IDecl = Forward->getForwardInterfaceDecl();
+      if ((!OnlyForwardDeclarations || IDecl->isForwardDecl()) &&
+          (!OnlyUnimplemented || !IDecl->getImplementation()))
+        Results.AddResult(Result(IDecl, 0), CurContext,
+                          0, false);
     }
   }
 }
diff --git a/safecode/tools/clang/lib/Sema/SemaDecl.cpp b/safecode/tools/clang/lib/Sema/SemaDecl.cpp
index 9f43aa2..2f2ba7f 100644
--- a/safecode/tools/clang/lib/Sema/SemaDecl.cpp
+++ b/safecode/tools/clang/lib/Sema/SemaDecl.cpp
@@ -38,6 +38,7 @@
 // FIXME: layering (ideally, Sema shouldn't be dependent on Lex API's)
 #include "clang/Lex/Preprocessor.h"
 #include "clang/Lex/HeaderSearch.h"
+#include "clang/Lex/ModuleLoader.h"
 #include "llvm/ADT/Triple.h"
 #include <algorithm>
 #include <cstring>
@@ -6673,12 +6674,18 @@
       Diag(MD->getLocEnd(), diag::warn_objc_missing_super_dealloc);
       ObjCShouldCallSuperDealloc = false;
     }
+    if (ObjCShouldCallSuperFinalize) {
+      Diag(MD->getLocEnd(), diag::warn_objc_missing_super_finalize);
+      ObjCShouldCallSuperFinalize = false;
+    }
   } else {
     return 0;
   }
 
   assert(!ObjCShouldCallSuperDealloc && "This should only be set for "
          "ObjC methods, which should have been handled in the block above.");
+  assert(!ObjCShouldCallSuperFinalize && "This should only be set for "
+         "ObjC methods, which should have been handled in the block above.");
 
   // Verify and clean out per-function state.
   if (Body) {
@@ -9294,6 +9301,19 @@
   return New;
 }
 
+DeclResult Sema::ActOnModuleImport(SourceLocation ImportLoc,
+                                   IdentifierInfo &ModuleName,
+                                   SourceLocation ModuleNameLoc) {
+  ModuleKey Module = PP.getModuleLoader().loadModule(ImportLoc, 
+                                                     ModuleName, ModuleNameLoc);
+  if (!Module)
+    return true;
+  
+  // FIXME: Actually create a declaration to describe the module import.
+  (void)Module;
+  return DeclResult((Decl *)0);
+}
+
 void Sema::ActOnPragmaWeakID(IdentifierInfo* Name,
                              SourceLocation PragmaLoc,
                              SourceLocation NameLoc) {
diff --git a/safecode/tools/clang/lib/Sema/SemaDeclObjC.cpp b/safecode/tools/clang/lib/Sema/SemaDeclObjC.cpp
index af14aa4..9b6166b 100644
--- a/safecode/tools/clang/lib/Sema/SemaDeclObjC.cpp
+++ b/safecode/tools/clang/lib/Sema/SemaDeclObjC.cpp
@@ -162,6 +162,7 @@
   switch (family) {
   case OMF_None:
   case OMF_dealloc:
+  case OMF_finalize:
   case OMF_retain:
   case OMF_release:
   case OMF_autorelease:
@@ -267,6 +268,7 @@
 
     case OMF_None:
     case OMF_dealloc:
+    case OMF_finalize:
     case OMF_alloc:
     case OMF_init:
     case OMF_mutableCopy:
@@ -287,14 +289,16 @@
                                           dyn_cast<NamedDecl>(IMD), 
                                           MDecl->getLocation(), 0);
 
-    // If this is "dealloc", set some bit here.
+    // If this is "dealloc" or "finalize", set some bit here.
     // Then in ActOnSuperMessage() (SemaExprObjC), set it back to false.
     // Finally, in ActOnFinishFunctionBody() (SemaDecl), warn if flag is set.
     // Only do this if the current class actually has a superclass.
-    if (IC->getSuperClass())
+    if (IC->getSuperClass()) {
       ObjCShouldCallSuperDealloc = 
         !Context.getLangOptions().ObjCAutoRefCount &&      
         MDecl->getMethodFamily() == OMF_dealloc;
+      ObjCShouldCallSuperFinalize = MDecl->getMethodFamily() == OMF_finalize;
+    }
   }
 }
 
@@ -1256,6 +1260,7 @@
   case OMF_release:
   case OMF_autorelease:
   case OMF_dealloc:
+  case OMF_finalize:
   case OMF_retainCount:
   case OMF_self:
   case OMF_performSelector:
@@ -1657,13 +1662,12 @@
 }
 
 /// ActOnForwardClassDeclaration -
-Decl *
+Sema::DeclGroupPtrTy
 Sema::ActOnForwardClassDeclaration(SourceLocation AtClassLoc,
                                    IdentifierInfo **IdentList,
                                    SourceLocation *IdentLocs,
                                    unsigned NumElts) {
-  SmallVector<ObjCInterfaceDecl*, 32> Interfaces;
-
+  SmallVector<Decl *, 8> DeclsInGroup;
   for (unsigned i = 0; i != NumElts; ++i) {
     // Check for another declaration kind with the same name.
     NamedDecl *PrevDecl
@@ -1708,17 +1712,14 @@
       PushOnScopeChains(IDecl, TUScope, false);
       CurContext->makeDeclVisibleInContext(IDecl, true);
     }
-
-    Interfaces.push_back(IDecl);
+    ObjCClassDecl *CDecl = ObjCClassDecl::Create(Context, CurContext, AtClassLoc,
+                                                 IDecl, IdentLocs[i]);
+    CurContext->addDecl(CDecl);
+    CheckObjCDeclScope(CDecl);
+    DeclsInGroup.push_back(CDecl);
   }
-
-  assert(Interfaces.size() == NumElts);
-  ObjCClassDecl *CDecl = ObjCClassDecl::Create(Context, CurContext, AtClassLoc,
-                                               Interfaces.data(), IdentLocs,
-                                               Interfaces.size());
-  CurContext->addDecl(CDecl);
-  CheckObjCDeclScope(CDecl);
-  return CDecl;
+  
+  return BuildDeclaratorGroup(DeclsInGroup.data(), DeclsInGroup.size(), false);
 }
 
 static bool tryMatchRecordTypes(ASTContext &Context,
@@ -2641,6 +2642,7 @@
     case OMF_None:
     case OMF_copy:
     case OMF_dealloc:
+    case OMF_finalize:
     case OMF_mutableCopy:
     case OMF_release:
     case OMF_retainCount:
diff --git a/safecode/tools/clang/lib/Sema/SemaExpr.cpp b/safecode/tools/clang/lib/Sema/SemaExpr.cpp
index 19cd118..6327ee7 100644
--- a/safecode/tools/clang/lib/Sema/SemaExpr.cpp
+++ b/safecode/tools/clang/lib/Sema/SemaExpr.cpp
@@ -443,6 +443,24 @@
   if (Ty->isSpecificBuiltinType(BuiltinType::Float))
     E = ImpCastExprToType(E, Context.DoubleTy, CK_FloatingCast).take();
 
+  // C++ performs lvalue-to-rvalue conversion as a default argument
+  // promotion.  If we still have a gl-value after usual unary
+  // conversion, we must have an l-value of class type, so we need to
+  // initialize a temporary.  For compatibility reasons, however, we
+  // don't want to do this in unevaluated contexts; otherwise we
+  // reject metaprograms which work by passing uncopyable l-values to
+  // variadic functions.
+  if (getLangOptions().CPlusPlus && E->isGLValue() && 
+      ExprEvalContexts.back().Context != Unevaluated) {
+    ExprResult Temp = PerformCopyInitialization(
+                       InitializedEntity::InitializeTemporary(E->getType()),
+                                                E->getExprLoc(),
+                                                Owned(E));
+    if (Temp.isInvalid())
+      return ExprError();
+    E = Temp.get();
+  }
+
   return Owned(E);
 }
 
@@ -460,19 +478,13 @@
     return ExprError();
   E = ExprRes.take();
 
-  // __builtin_va_start takes the second argument as a "varargs" argument, but
-  // it doesn't actually do anything with it.  It doesn't need to be non-pod
-  // etc.
-  if (FDecl && FDecl->getBuiltinID() == Builtin::BI__builtin_va_start)
-    return Owned(E);
-  
   // Don't allow one to pass an Objective-C interface to a vararg.
   if (E->getType()->isObjCObjectType() &&
     DiagRuntimeBehavior(E->getLocStart(), 0,
                         PDiag(diag::err_cannot_pass_objc_interface_to_vararg)
                           << E->getType() << CT))
     return ExprError();
-  
+
   if (!E->getType().isPODType(Context)) {
     // C++0x [expr.call]p7:
     //   Passing a potentially-evaluated argument of class type (Clause 9) 
@@ -517,8 +529,7 @@
       ExprResult Comma = ActOnBinOp(TUScope, E->getLocStart(), tok::comma,
                                     Call.get(), E);
       if (Comma.isInvalid())
-        return ExprError();
-      
+        return ExprError();      
       E = Comma.get();
     }
   }
@@ -7408,7 +7419,7 @@
                 S.Context.getTypeDeclType(cast<RecordDecl>(Ctx)).getTypePtr());
         }
       }
-    } else if (!isa<FunctionDecl>(dcl))
+    } else if (!isa<FunctionDecl>(dcl) && !isa<NonTypeTemplateParmDecl>(dcl))
       assert(0 && "Unknown/unexpected decl type");
   }
 
diff --git a/safecode/tools/clang/lib/Sema/SemaExprObjC.cpp b/safecode/tools/clang/lib/Sema/SemaExprObjC.cpp
index db5de4c..402e54c 100644
--- a/safecode/tools/clang/lib/Sema/SemaExprObjC.cpp
+++ b/safecode/tools/clang/lib/Sema/SemaExprObjC.cpp
@@ -203,6 +203,7 @@
     case OMF_None:
     case OMF_alloc:
     case OMF_copy:
+    case OMF_finalize:
     case OMF_init:
     case OMF_mutableCopy:
     case OMF_new:
@@ -977,6 +978,8 @@
   if (Method->isInstanceMethod()) {
     if (Sel.getMethodFamily() == OMF_dealloc)
       ObjCShouldCallSuperDealloc = false;
+    if (Sel.getMethodFamily() == OMF_finalize)
+      ObjCShouldCallSuperFinalize = false;
 
     // Since we are in an instance method, this is an instance
     // message to the superclass instance.
@@ -1418,6 +1421,7 @@
     case OMF_None:
     case OMF_alloc:
     case OMF_copy:
+    case OMF_finalize:
     case OMF_mutableCopy:
     case OMF_new:
     case OMF_self:
diff --git a/safecode/tools/clang/lib/Sema/SemaLookup.cpp b/safecode/tools/clang/lib/Sema/SemaLookup.cpp
index 240eb5f..7df0498 100644
--- a/safecode/tools/clang/lib/Sema/SemaLookup.cpp
+++ b/safecode/tools/clang/lib/Sema/SemaLookup.cpp
@@ -2670,14 +2670,11 @@
           }
         }
       } else if (ObjCClassDecl *Class = dyn_cast<ObjCClassDecl>(*D)) {
-        for (ObjCClassDecl::iterator I = Class->begin(), IEnd = Class->end();
-             I != IEnd; ++I) {
-          ObjCInterfaceDecl *IFace = I->getInterface();
+          ObjCInterfaceDecl *IFace = Class->getForwardInterfaceDecl();
           if (Result.isAcceptableDecl(IFace)) {
             Consumer.FoundDecl(IFace, Visited.checkHidden(IFace), InBaseClass);
             Visited.add(IFace);
           }
-        }
       }
       
       // Visit transparent contexts and inline namespaces inside this context.
diff --git a/safecode/tools/clang/lib/Sema/SemaObjCProperty.cpp b/safecode/tools/clang/lib/Sema/SemaObjCProperty.cpp
index 46f6456..f4743ac 100644
--- a/safecode/tools/clang/lib/Sema/SemaObjCProperty.cpp
+++ b/safecode/tools/clang/lib/Sema/SemaObjCProperty.cpp
@@ -487,7 +487,9 @@
     case Qualifiers::OCL_Strong:
       S.Diag(propertyImplLoc, diag::err_arc_assign_property_ownership)
         << property->getDeclName()
-        << ivar->getDeclName();
+        << ivar->getDeclName()
+        << ((property->getPropertyAttributesAsWritten() 
+            & ObjCPropertyDecl::OBJC_PR_assign) != 0);
       break;
     }
 
@@ -1314,23 +1316,23 @@
         PropImplMap.count(Prop) || Prop->hasAttr<UnavailableAttr>())
       continue;
     if (!InsMap.count(Prop->getGetterName())) {
-      Diag(Prop->getLocation(),
+      Diag(IMPDecl->getLocation(),
            isa<ObjCCategoryDecl>(CDecl) ?
             diag::warn_setter_getter_impl_required_in_category :
             diag::warn_setter_getter_impl_required)
       << Prop->getDeclName() << Prop->getGetterName();
-      Diag(IMPDecl->getLocation(),
-           diag::note_property_impl_required);
+      Diag(Prop->getLocation(),
+           diag::note_property_declare);
     }
 
     if (!Prop->isReadOnly() && !InsMap.count(Prop->getSetterName())) {
-      Diag(Prop->getLocation(),
+      Diag(IMPDecl->getLocation(),
            isa<ObjCCategoryDecl>(CDecl) ?
            diag::warn_setter_getter_impl_required_in_category :
            diag::warn_setter_getter_impl_required)
       << Prop->getDeclName() << Prop->getSetterName();
-      Diag(IMPDecl->getLocation(),
-           diag::note_property_impl_required);
+      Diag(Prop->getLocation(),
+           diag::note_property_declare);
     }
   }
 }
diff --git a/safecode/tools/clang/lib/Sema/SemaOverload.cpp b/safecode/tools/clang/lib/Sema/SemaOverload.cpp
index 84d16ab..e3c5f83 100644
--- a/safecode/tools/clang/lib/Sema/SemaOverload.cpp
+++ b/safecode/tools/clang/lib/Sema/SemaOverload.cpp
@@ -8525,8 +8525,7 @@
         << UnaryOperator::getOpcodeStr(Opc)
         << Input->getType()
         << Input->getSourceRange();
-    CandidateSet.NoteCandidates(*this, OCD_ViableCandidates,
-                                Args, NumArgs,
+    CandidateSet.NoteCandidates(*this, OCD_ViableCandidates, Args, NumArgs,
                                 UnaryOperator::getOpcodeStr(Opc), OpLoc);
     return ExprError();
 
@@ -8536,7 +8535,8 @@
       << UnaryOperator::getOpcodeStr(Opc)
       << getDeletedOrUnavailableSuffix(Best->Function)
       << Input->getSourceRange();
-    CandidateSet.NoteCandidates(*this, OCD_AllCandidates, Args, NumArgs);
+    CandidateSet.NoteCandidates(*this, OCD_AllCandidates, Args, NumArgs,
+                                UnaryOperator::getOpcodeStr(Opc), OpLoc);
     return ExprError();
   }
 
@@ -8831,7 +8831,8 @@
         << BinaryOperator::getOpcodeStr(Opc)
         << getDeletedOrUnavailableSuffix(Best->Function)
         << Args[0]->getSourceRange() << Args[1]->getSourceRange();
-      CandidateSet.NoteCandidates(*this, OCD_AllCandidates, Args, 2);
+      CandidateSet.NoteCandidates(*this, OCD_AllCandidates, Args, 2,
+                                  BinaryOperator::getOpcodeStr(Opc), OpLoc);
       return ExprError();
   }
 
diff --git a/safecode/tools/clang/lib/Serialization/ASTReader.cpp b/safecode/tools/clang/lib/Serialization/ASTReader.cpp
index 540b9ef..2817d86 100644
--- a/safecode/tools/clang/lib/Serialization/ASTReader.cpp
+++ b/safecode/tools/clang/lib/Serialization/ASTReader.cpp
@@ -528,7 +528,6 @@
   unsigned NumFactoryMethods = ReadUnalignedLE16(d);
 
   // Load instance methods
-  ObjCMethodList *Prev = 0;
   for (unsigned I = 0; I != NumInstanceMethods; ++I) {
     if (ObjCMethodDecl *Method
           = Reader.GetLocalDeclAs<ObjCMethodDecl>(F, ReadUnalignedLE32(d)))
@@ -536,7 +535,6 @@
   }
 
   // Load factory methods
-  Prev = 0;
   for (unsigned I = 0; I != NumFactoryMethods; ++I) {
     if (ObjCMethodDecl *Method
           = Reader.GetLocalDeclAs<ObjCMethodDecl>(F, ReadUnalignedLE32(d)))
@@ -1753,7 +1751,6 @@
 
   // Read all of the records and blocks for the ASt file.
   RecordData Record;
-  bool First = true;
   while (!Stream.AtEndOfStream()) {
     unsigned Code = Stream.ReadCode();
     if (Code == llvm::bitc::END_BLOCK) {
@@ -1827,7 +1824,6 @@
         }
         break;
       }
-      First = false;
       continue;
     }
 
@@ -2468,7 +2464,6 @@
         KnownNamespaces.push_back(getGlobalDeclID(F, Record[I]));
       break;
     }
-    First = false;
   }
   Error("premature end of bitstream in AST file");
   return Failure;
@@ -2553,7 +2548,7 @@
       = static_cast<IdentifierLookupVisitor *>(UserData);
       
       ASTIdentifierLookupTable *IdTable
-      = (ASTIdentifierLookupTable *)M.IdentifierLookupTable;
+        = (ASTIdentifierLookupTable *)M.IdentifierLookupTable;
       if (!IdTable)
         return false;
       
@@ -2786,7 +2781,7 @@
 void ASTReader::InitializeContext(ASTContext &Ctx) {
   Context = &Ctx;
   assert(Context && "Passed null context!");
-
+  
   assert(PP && "Forgot to set Preprocessor ?");
   PP->getIdentifierTable().setExternalIdentifierLookup(this);
   PP->setExternalSource(this);
@@ -4163,6 +4158,7 @@
     ASTReader &Reader;
     const DeclContext *DC;
     bool (*isKindWeWant)(Decl::Kind);
+    
     SmallVectorImpl<Decl*> &Decls;
     bool PredefsVisited[NUM_PREDEF_DECL_IDS];
 
@@ -4204,9 +4200,10 @@
           This->PredefsVisited[ID->second] = true;
         }
 
-        Decl *D = This->Reader.GetLocalDecl(M, ID->second);
-        assert(D && "Null decl in lexical decls");
-        This->Decls.push_back(D);
+        if (Decl *D = This->Reader.GetLocalDecl(M, ID->second)) {
+          if (!This->DC->isDeclInLexicalTraversal(D))
+            This->Decls.push_back(D);
+        }
       }
 
       return false;
diff --git a/safecode/tools/clang/lib/Serialization/ASTReaderDecl.cpp b/safecode/tools/clang/lib/Serialization/ASTReaderDecl.cpp
index 6e7cbbf..4fa9b2c 100644
--- a/safecode/tools/clang/lib/Serialization/ASTReaderDecl.cpp
+++ b/safecode/tools/clang/lib/Serialization/ASTReaderDecl.cpp
@@ -123,8 +123,8 @@
                                             ClassTemplateSpecializationDecl *D);
     void VisitClassTemplatePartialSpecializationDecl(
                                      ClassTemplatePartialSpecializationDecl *D);
-    void VisitClassScopeFunctionSpecializationDecl(
-                                       ClassScopeFunctionSpecializationDecl *D);
+    void VisitClassScopeFunctionSpecializationDecl(

+                                       ClassScopeFunctionSpecializationDecl *D);

     void VisitTemplateTypeParmDecl(TemplateTypeParmDecl *D);
     void VisitValueDecl(ValueDecl *VD);
     void VisitEnumConstantDecl(EnumConstantDecl *ECD);
@@ -573,17 +573,9 @@
 
 void ASTDeclReader::VisitObjCClassDecl(ObjCClassDecl *CD) {
   VisitDecl(CD);
-  unsigned NumClassRefs = Record[Idx++];
-  SmallVector<ObjCInterfaceDecl *, 16> ClassRefs;
-  ClassRefs.reserve(NumClassRefs);
-  for (unsigned I = 0; I != NumClassRefs; ++I)
-    ClassRefs.push_back(ReadDeclAs<ObjCInterfaceDecl>(Record, Idx));
-  SmallVector<SourceLocation, 16> SLocs;
-  SLocs.reserve(NumClassRefs);
-  for (unsigned I = 0; I != NumClassRefs; ++I)
-    SLocs.push_back(ReadSourceLocation(Record, Idx));
-  CD->setClassList(*Reader.getContext(), ClassRefs.data(), SLocs.data(),
-                   NumClassRefs);
+  ObjCInterfaceDecl *ClassRef = ReadDeclAs<ObjCInterfaceDecl>(Record, Idx);
+  SourceLocation SLoc = ReadSourceLocation(Record, Idx);
+  CD->setClass(*Reader.getContext(), ClassRef, SLoc);
 }
 
 void ASTDeclReader::VisitObjCForwardProtocolDecl(ObjCForwardProtocolDecl *FPD) {
@@ -1211,8 +1203,8 @@
   }
 }
 
-void ASTDeclReader::VisitClassScopeFunctionSpecializationDecl(
-                                    ClassScopeFunctionSpecializationDecl *D) {
+void ASTDeclReader::VisitClassScopeFunctionSpecializationDecl(

+                                    ClassScopeFunctionSpecializationDecl *D) {

   VisitDecl(D);
   D->Specialization = ReadDeclAs<CXXMethodDecl>(Record, Idx);
 }
diff --git a/safecode/tools/clang/lib/Serialization/ASTWriterDecl.cpp b/safecode/tools/clang/lib/Serialization/ASTWriterDecl.cpp
index a0f7da2..b5d4d8f 100644
--- a/safecode/tools/clang/lib/Serialization/ASTWriterDecl.cpp
+++ b/safecode/tools/clang/lib/Serialization/ASTWriterDecl.cpp
@@ -65,8 +65,8 @@
                                             ClassTemplateSpecializationDecl *D);
     void VisitClassTemplatePartialSpecializationDecl(
                                      ClassTemplatePartialSpecializationDecl *D);
-    void VisitClassScopeFunctionSpecializationDecl(

-                                       ClassScopeFunctionSpecializationDecl *D);

+    void VisitClassScopeFunctionSpecializationDecl(
+                                       ClassScopeFunctionSpecializationDecl *D);
     void VisitTemplateTypeParmDecl(TemplateTypeParmDecl *D);
     void VisitValueDecl(ValueDecl *D);
     void VisitEnumConstantDecl(EnumConstantDecl *D);
@@ -503,11 +503,8 @@
 
 void ASTDeclWriter::VisitObjCClassDecl(ObjCClassDecl *D) {
   VisitDecl(D);
-  Record.push_back(D->size());
-  for (ObjCClassDecl::iterator I = D->begin(), IEnd = D->end(); I != IEnd; ++I)
-    Writer.AddDeclRef(I->getInterface(), Record);
-  for (ObjCClassDecl::iterator I = D->begin(), IEnd = D->end(); I != IEnd; ++I)
-    Writer.AddSourceLocation(I->getLocation(), Record);
+  Writer.AddDeclRef(D->getForwardInterfaceDecl(), Record);
+  Writer.AddSourceLocation(D->getForwardDecl()->getLocation(), Record);
   Code = serialization::DECL_OBJC_CLASS;
 }
 
@@ -1107,8 +1104,8 @@
   Code = serialization::DECL_CLASS_TEMPLATE_PARTIAL_SPECIALIZATION;
 }
 
-void ASTDeclWriter::VisitClassScopeFunctionSpecializationDecl(

-                                    ClassScopeFunctionSpecializationDecl *D) {

+void ASTDeclWriter::VisitClassScopeFunctionSpecializationDecl(
+                                    ClassScopeFunctionSpecializationDecl *D) {
   VisitDecl(D);
   Writer.AddDeclRef(D->getSpecialization(), Record);
   Code = serialization::DECL_CLASS_SCOPE_FUNCTION_SPECIALIZATION;
diff --git a/safecode/tools/clang/lib/StaticAnalyzer/Checkers/CStringChecker.cpp b/safecode/tools/clang/lib/StaticAnalyzer/Checkers/CStringChecker.cpp
index d043e2d..718d9f3 100644
--- a/safecode/tools/clang/lib/StaticAnalyzer/Checkers/CStringChecker.cpp
+++ b/safecode/tools/clang/lib/StaticAnalyzer/Checkers/CStringChecker.cpp
@@ -47,8 +47,8 @@
   const ProgramState *
     checkRegionChanges(const ProgramState *state,
                        const StoreManager::InvalidatedSymbols *,
-                       const MemRegion * const *Begin,
-                       const MemRegion * const *End) const;
+                       ArrayRef<const MemRegion *> ExplicitRegions,
+                       ArrayRef<const MemRegion *> Regions) const;
 
   typedef void (CStringChecker::*FnCheck)(CheckerContext &,
                                           const CallExpr *) const;
@@ -786,7 +786,7 @@
 
     // Invalidate this region.
     unsigned Count = C.getNodeBuilder().getCurrentBlockCount();
-    return state->invalidateRegion(R, E, Count, NULL);
+    return state->invalidateRegions(R, E, Count);
   }
 
   // If we have a non-region value by chance, just remove the binding.
@@ -1757,8 +1757,8 @@
 const ProgramState *
 CStringChecker::checkRegionChanges(const ProgramState *state,
                                    const StoreManager::InvalidatedSymbols *,
-                                   const MemRegion * const *Begin,
-                                   const MemRegion * const *End) const {
+                                   ArrayRef<const MemRegion *> ExplicitRegions,
+                                   ArrayRef<const MemRegion *> Regions) const {
   CStringLength::EntryMap Entries = state->get<CStringLength>();
   if (Entries.isEmpty())
     return state;
@@ -1767,8 +1767,9 @@
   llvm::SmallPtrSet<const MemRegion *, 32> SuperRegions;
 
   // First build sets for the changed regions and their super-regions.
-  for ( ; Begin != End; ++Begin) {
-    const MemRegion *MR = *Begin;
+  for (ArrayRef<const MemRegion *>::iterator
+       I = Regions.begin(), E = Regions.end(); I != E; ++I) {
+    const MemRegion *MR = *I;
     Invalidated.insert(MR);
 
     SuperRegions.insert(MR);
diff --git a/safecode/tools/clang/lib/StaticAnalyzer/Core/CFRefCount.cpp b/safecode/tools/clang/lib/StaticAnalyzer/Core/CFRefCount.cpp
index 4154205..a38c450 100644
--- a/safecode/tools/clang/lib/StaticAnalyzer/Core/CFRefCount.cpp
+++ b/safecode/tools/clang/lib/StaticAnalyzer/Core/CFRefCount.cpp
@@ -41,50 +41,6 @@
 using llvm::StrInStrNoCase;
 
 namespace {
-class InstanceReceiver {
-  ObjCMessage Msg;
-  const LocationContext *LC;
-public:
-  InstanceReceiver() : LC(0) { }
-  InstanceReceiver(const ObjCMessage &msg,
-                   const LocationContext *lc = 0) : Msg(msg), LC(lc) {}
-
-  bool isValid() const {
-    return Msg.isValid() && Msg.isInstanceMessage();
-  }
-  operator bool() const {
-    return isValid();
-  }
-
-  SVal getSValAsScalarOrLoc(const ProgramState *state) {
-    assert(isValid());
-    // We have an expression for the receiver?  Fetch the value
-    // of that expression.
-    if (const Expr *Ex = Msg.getInstanceReceiver())
-      return state->getSValAsScalarOrLoc(Ex);
-
-    // Otherwise we are sending a message to super.  In this case the
-    // object reference is the same as 'self'.
-    if (const ImplicitParamDecl *SelfDecl = LC->getSelfDecl())
-      return state->getSVal(state->getRegion(SelfDecl, LC));
-
-    return UnknownVal();
-  }
-
-  SourceRange getSourceRange() const {
-    assert(isValid());
-    if (const Expr *Ex = Msg.getInstanceReceiver())
-      return Ex->getSourceRange();
-
-    // Otherwise we are sending a message to super.
-    SourceLocation L = Msg.getSuperLoc();
-    assert(L.isValid());
-    return SourceRange(L, L);
-  }
-};
-}
-
-namespace {
 class GenericNodeBuilderRefCount {
   StmtNodeBuilder *SNB;
   const Stmt *S;
@@ -299,7 +255,7 @@
 
 void RefVal::print(raw_ostream &Out) const {
   if (!T.isNull())
-    Out << "Tracked Type:" << T.getAsString() << '\n';
+    Out << "Tracked " << T.getAsString() << '/';
 
   switch (getKind()) {
     default: assert(false);
@@ -1629,14 +1585,6 @@
 
 class CFRefCount : public TransferFuncs {
 public:
-  class BindingsPrinter : public ProgramState::Printer {
-  public:
-    virtual void Print(raw_ostream &Out,
-                       const ProgramState *state,
-                       const char* nl,
-                       const char* sep);
-  };
-
   const LangOptions&   LOpts;
   const bool GCEnabled;
 
@@ -1645,82 +1593,12 @@
     : LOpts(lopts), GCEnabled(gcenabled) {}
 
   void RegisterChecks(ExprEngine &Eng);
-
-  virtual void RegisterPrinters(std::vector<ProgramState::Printer*>& Printers) {
-    Printers.push_back(new BindingsPrinter());
-  }
   
   const LangOptions& getLangOptions() const { return LOpts; }
-
-  // Calls.
-
-  void evalCallOrMessage(ExplodedNodeSet &Dst, ExprEngine &Eng,
-                         StmtNodeBuilder &Builder,
-                         const CallOrObjCMessage &callOrMsg,
-                         InstanceReceiver Receiver, const MemRegion *Callee,
-                         ExplodedNode *Pred, const ProgramState *state);
-
-  virtual void evalCall(ExplodedNodeSet &Dst,
-                        ExprEngine& Eng,
-                        StmtNodeBuilder& Builder,
-                        const CallExpr *CE, SVal L,
-                        ExplodedNode *Pred);
-
-
-  virtual void evalObjCMessage(ExplodedNodeSet &Dst,
-                               ExprEngine& Engine,
-                               StmtNodeBuilder& Builder,
-                               ObjCMessage msg,
-                               ExplodedNode *Pred,
-                               const ProgramState *state);
 };
 
 } // end anonymous namespace
 
-static void PrintPool(raw_ostream &Out,
-                      SymbolRef Sym,
-                      const ProgramState *state) {
-  Out << ' ';
-  if (Sym)
-    Out << Sym->getSymbolID();
-  else
-    Out << "<pool>";
-  Out << ":{";
-
-  // Get the contents of the pool.
-  if (const ARCounts *cnts = state->get<AutoreleasePoolContents>(Sym))
-    for (ARCounts::iterator J=cnts->begin(), EJ=cnts->end(); J != EJ; ++J)
-      Out << '(' << J.getKey() << ',' << J.getData() << ')';
-
-  Out << '}';
-}
-
-void CFRefCount::BindingsPrinter::Print(raw_ostream &Out,
-                                        const ProgramState *state,
-                                        const char* nl, const char* sep) {
-
-  RefBindings B = state->get<RefBindings>();
-
-  if (!B.isEmpty())
-    Out << sep << nl;
-
-  for (RefBindings::iterator I=B.begin(), E=B.end(); I!=E; ++I) {
-    Out << (*I).first << " : ";
-    (*I).second.print(Out);
-    Out << nl;
-  }
-
-  // Print the autorelease stack.
-  Out << sep << nl << "AR pool stack:";
-  ARStack stack = state->get<AutoreleaseStack>();
-
-  PrintPool(Out, SymbolRef(), state);  // Print the caller's pool.
-  for (ARStack::iterator I=stack.begin(), E=stack.end(); I!=E; ++I)
-    PrintPool(Out, *I, state);
-
-  Out << nl;
-}
-
 //===----------------------------------------------------------------------===//
 // Error reporting.
 //===----------------------------------------------------------------------===//
@@ -2439,163 +2317,6 @@
   return RetTy;
 }
 
-
-// HACK: Symbols that have ref-count state that are referenced directly
-//  (not as structure or array elements, or via bindings) by an argument
-//  should not have their ref-count state stripped after we have
-//  done an invalidation pass.
-//
-// FIXME: This is a global to currently share between CFRefCount and
-// RetainReleaseChecker.  Eventually all functionality in CFRefCount should
-// be migrated to RetainReleaseChecker, and we can make this a non-global.
-llvm::DenseSet<SymbolRef> WhitelistedSymbols;
-namespace {
-struct ResetWhiteList {
-  ResetWhiteList() {}
-  ~ResetWhiteList() { WhitelistedSymbols.clear(); } 
-};
-}
-
-void CFRefCount::evalCallOrMessage(ExplodedNodeSet &Dst, ExprEngine &Eng,
-                                   StmtNodeBuilder &Builder,
-                                   const CallOrObjCMessage &callOrMsg,
-                                   InstanceReceiver Receiver,
-                                   const MemRegion *Callee,
-                                   ExplodedNode *Pred,
-                                   const ProgramState *state) {
-
-  SmallVector<const MemRegion*, 10> RegionsToInvalidate;
-  
-  // Use RAII to make sure the whitelist is properly cleared.
-  ResetWhiteList resetWhiteList;
-
-  // Invalidate all instance variables of the receiver of a message.
-  // FIXME: We should be able to do better with inter-procedural analysis.
-  if (Receiver) {
-    SVal V = Receiver.getSValAsScalarOrLoc(state);
-    if (SymbolRef Sym = V.getAsLocSymbol()) {
-      if (state->get<RefBindings>(Sym))
-        WhitelistedSymbols.insert(Sym);
-    }
-    if (const MemRegion *region = V.getAsRegion())
-      RegionsToInvalidate.push_back(region);
-  }
-  
-  // Invalidate all instance variables for the callee of a C++ method call.
-  // FIXME: We should be able to do better with inter-procedural analysis.
-  // FIXME: we can probably do better for const versus non-const methods.
-  if (callOrMsg.isCXXCall()) {
-    if (const MemRegion *callee = callOrMsg.getCXXCallee().getAsRegion())
-      RegionsToInvalidate.push_back(callee);
-  }
-  
-  for (unsigned idx = 0, e = callOrMsg.getNumArgs(); idx != e; ++idx) {
-    SVal V = callOrMsg.getArgSValAsScalarOrLoc(idx);
-
-    // If we are passing a location wrapped as an integer, unwrap it and
-    // invalidate the values referred by the location.
-    if (nonloc::LocAsInteger *Wrapped = dyn_cast<nonloc::LocAsInteger>(&V))
-      V = Wrapped->getLoc();
-    else if (!isa<Loc>(V))
-      continue;
-
-    if (SymbolRef Sym = V.getAsLocSymbol())
-      if (state->get<RefBindings>(Sym))
-        WhitelistedSymbols.insert(Sym);
-
-    if (const MemRegion *R = V.getAsRegion()) {
-      // Invalidate the value of the variable passed by reference.
-
-      // Are we dealing with an ElementRegion?  If the element type is
-      // a basic integer type (e.g., char, int) and the underying region
-      // is a variable region then strip off the ElementRegion.
-      // FIXME: We really need to think about this for the general case
-      //   as sometimes we are reasoning about arrays and other times
-      //   about (char*), etc., is just a form of passing raw bytes.
-      //   e.g., void *p = alloca(); foo((char*)p);
-      if (const ElementRegion *ER = dyn_cast<ElementRegion>(R)) {
-        // Checking for 'integral type' is probably too promiscuous, but
-        // we'll leave it in for now until we have a systematic way of
-        // handling all of these cases.  Eventually we need to come up
-        // with an interface to StoreManager so that this logic can be
-        // approriately delegated to the respective StoreManagers while
-        // still allowing us to do checker-specific logic (e.g.,
-        // invalidating reference counts), probably via callbacks.
-        if (ER->getElementType()->isIntegralOrEnumerationType()) {
-          const MemRegion *superReg = ER->getSuperRegion();
-          if (isa<VarRegion>(superReg) || isa<FieldRegion>(superReg) ||
-              isa<ObjCIvarRegion>(superReg))
-            R = cast<TypedRegion>(superReg);
-        }
-        // FIXME: What about layers of ElementRegions?
-      }
-
-      // Mark this region for invalidation.  We batch invalidate regions
-      // below for efficiency.
-      RegionsToInvalidate.push_back(R);
-    } else {
-      // Nuke all other arguments passed by reference.
-      // FIXME: is this necessary or correct? This handles the non-Region
-      //  cases.  Is it ever valid to store to these?
-      state = state->unbindLoc(cast<Loc>(V));
-    }
-  }
-
-  // Block calls result in all captured values passed-via-reference to be
-  // invalidated.
-  if (const BlockDataRegion *BR = dyn_cast_or_null<BlockDataRegion>(Callee))
-    RegionsToInvalidate.push_back(BR);
-
-  // Invalidate designated regions using the batch invalidation API.
-
-  // FIXME: We can have collisions on the conjured symbol if the
-  //  expression *I also creates conjured symbols.  We probably want
-  //  to identify conjured symbols by an expression pair: the enclosing
-  //  expression (the context) and the expression itself.  This should
-  //  disambiguate conjured symbols.
-  unsigned Count = Builder.getCurrentBlockCount();
-  StoreManager::InvalidatedSymbols IS;
-
-  const Expr *Ex = callOrMsg.getOriginExpr();
-
-  // NOTE: Even if RegionsToInvalidate is empty, we must still invalidate
-  //  global variables.
-  // NOTE: RetainReleaseChecker handles the actual invalidation of symbols.
-  state =
-    state->invalidateRegions(RegionsToInvalidate.data(),
-                             RegionsToInvalidate.data() +
-                             RegionsToInvalidate.size(),
-                             Ex, Count, &IS,
-                             /* invalidateGlobals = */
-                             Eng.doesInvalidateGlobals(callOrMsg));
-
-  Builder.MakeNode(Dst, Ex, Pred, state);
-}
-
-
-void CFRefCount::evalCall(ExplodedNodeSet &Dst,
-                          ExprEngine& Eng,
-                          StmtNodeBuilder& Builder,
-                          const CallExpr *CE, SVal L,
-                          ExplodedNode *Pred) {
-
-  evalCallOrMessage(Dst, Eng, Builder, CallOrObjCMessage(CE, Pred->getState()),
-                    InstanceReceiver(), L.getAsRegion(), Pred, 
-                    Pred->getState());
-}
-
-void CFRefCount::evalObjCMessage(ExplodedNodeSet &Dst,
-                                 ExprEngine& Eng,
-                                 StmtNodeBuilder& Builder,
-                                 ObjCMessage msg,
-                                 ExplodedNode *Pred,
-                                 const ProgramState *state) {
-
-  evalCallOrMessage(Dst, Eng, Builder, CallOrObjCMessage(msg, Pred->getState()),
-                    InstanceReceiver(msg, Pred->getLocationContext()),
-                    /* Callee = */ 0, Pred, state);
-}
-
 //===----------------------------------------------------------------------===//
 // Pieces of the retain/release checker implemented using a CheckerVisitor.
 // More pieces of the retain/release checker will be migrated to this interface
@@ -2611,6 +2332,7 @@
                     check::PostStmt<BlockExpr>,
                     check::PostStmt<CastExpr>,
                     check::PostStmt<CallExpr>,
+                    check::PostStmt<CXXConstructExpr>,
                     check::PostObjCMessage,
                     check::PreStmt<ReturnStmt>,
                     check::RegionChanges,
@@ -2693,7 +2415,6 @@
     switch (GCMode) {
     case LangOptions::HybridGC:
       llvm_unreachable("GC mode not set yet!");
-      return true;
     case LangOptions::NonGC:
       return false;
     case LangOptions::GCOnly:
@@ -2701,7 +2422,6 @@
     }
 
     llvm_unreachable("Invalid/unknown GC mode.");
-    return false;
   }
 
   bool isARCorGCEnabled(ASTContext &Ctx) const {
@@ -2767,24 +2487,29 @@
     }
   }
 
+  void printState(raw_ostream &Out, const ProgramState *State,
+                  const char *NL, const char *Sep) const;
+
   void checkBind(SVal loc, SVal val, CheckerContext &C) const;
   void checkPostStmt(const BlockExpr *BE, CheckerContext &C) const;
   void checkPostStmt(const CastExpr *CE, CheckerContext &C) const;
 
   void checkPostStmt(const CallExpr *CE, CheckerContext &C) const;
+  void checkPostStmt(const CXXConstructExpr *CE, CheckerContext &C) const;
   void checkPostObjCMessage(const ObjCMessage &Msg, CheckerContext &C) const;
   void checkSummary(const RetainSummary &Summ, const CallOrObjCMessage &Call,
-                    InstanceReceiver Receiver, CheckerContext &C) const;
+                    CheckerContext &C) const;
 
   bool evalCall(const CallExpr *CE, CheckerContext &C) const;
 
   const ProgramState *evalAssume(const ProgramState *state, SVal Cond,
                                  bool Assumption) const;
 
-  const ProgramState *checkRegionChanges(const ProgramState *state,
-                          const StoreManager::InvalidatedSymbols *invalidated,
-                                         const MemRegion * const *begin,
-                                         const MemRegion * const *end) const;
+  const ProgramState *
+  checkRegionChanges(const ProgramState *state,
+                     const StoreManager::InvalidatedSymbols *invalidated,
+                     ArrayRef<const MemRegion *> ExplicitRegions,
+                     ArrayRef<const MemRegion *> Regions) const;
                                         
   bool wantsRegionChangeUpdate(const ProgramState *state) const {
     return true;
@@ -2914,11 +2639,18 @@
 const ProgramState *
 RetainReleaseChecker::checkRegionChanges(const ProgramState *state,
                             const StoreManager::InvalidatedSymbols *invalidated,
-                                         const MemRegion * const *begin,
-                                         const MemRegion * const *end) const {
+                                    ArrayRef<const MemRegion *> ExplicitRegions,
+                                    ArrayRef<const MemRegion *> Regions) const {
   if (!invalidated)
     return state;
 
+  llvm::SmallPtrSet<SymbolRef, 8> WhitelistedSymbols;
+  for (ArrayRef<const MemRegion *>::iterator I = ExplicitRegions.begin(),
+       E = ExplicitRegions.end(); I != E; ++I) {
+    if (const SymbolicRegion *SR = (*I)->StripCasts()->getAs<SymbolicRegion>())
+      WhitelistedSymbols.insert(SR->getSymbol());
+  }
+
   for (StoreManager::InvalidatedSymbols::const_iterator I=invalidated->begin(),
        E = invalidated->end(); I!=E; ++I) {
     SymbolRef sym = *I;
@@ -3035,7 +2767,24 @@
   if (!Summ)
     return;
 
-  checkSummary(*Summ, CallOrObjCMessage(CE, state), InstanceReceiver(), C);
+  checkSummary(*Summ, CallOrObjCMessage(CE, state), C);
+}
+
+void RetainReleaseChecker::checkPostStmt(const CXXConstructExpr *CE,
+                                         CheckerContext &C) const {
+  const CXXConstructorDecl *Ctor = CE->getConstructor();
+  if (!Ctor)
+    return;
+
+  RetainSummaryManager &Summaries = getSummaryManager(C.getASTContext());
+  RetainSummary *Summ = Summaries.getSummary(Ctor);
+
+  // If we didn't get a summary, this constructor doesn't affect retain counts.
+  if (!Summ)
+    return;
+
+  const ProgramState *state = C.getState();
+  checkSummary(*Summ, CallOrObjCMessage(CE, state), C);
 }
 
 void RetainReleaseChecker::checkPostObjCMessage(const ObjCMessage &Msg, 
@@ -3057,13 +2806,11 @@
   if (!Summ)
     return;
 
-  checkSummary(*Summ, CallOrObjCMessage(Msg, state),
-               InstanceReceiver(Msg, Pred->getLocationContext()), C);
+  checkSummary(*Summ, CallOrObjCMessage(Msg, state), C);
 }
 
 void RetainReleaseChecker::checkSummary(const RetainSummary &Summ,
                                         const CallOrObjCMessage &CallOrMsg,
-                                        InstanceReceiver Receiver,
                                         CheckerContext &C) const {
   const ProgramState *state = C.getState();
 
@@ -3073,7 +2820,7 @@
   SymbolRef ErrorSym = 0;
 
   for (unsigned idx = 0, e = CallOrMsg.getNumArgs(); idx != e; ++idx) {
-    SVal V = CallOrMsg.getArgSValAsScalarOrLoc(idx);
+    SVal V = CallOrMsg.getArgSVal(idx);
 
     if (SymbolRef Sym = V.getAsLocSymbol()) {
       if (RefBindings::data_type *T = state->get<RefBindings>(Sym)) {
@@ -3089,13 +2836,15 @@
 
   // Evaluate the effect on the message receiver.
   bool ReceiverIsTracked = false;
-  if (!hasErr && Receiver) {
-    if (SymbolRef Sym = Receiver.getSValAsScalarOrLoc(state).getAsLocSymbol()) {
+  if (!hasErr && CallOrMsg.isObjCMessage()) {
+    const LocationContext *LC = C.getPredecessor()->getLocationContext();
+    SVal Receiver = CallOrMsg.getInstanceMessageReceiver(LC);
+    if (SymbolRef Sym = Receiver.getAsLocSymbol()) {
       if (const RefVal *T = state->get<RefBindings>(Sym)) {
         ReceiverIsTracked = true;
         state = updateSymbol(state, Sym, *T, Summ.getReceiverEffect(), hasErr);
         if (hasErr) {
-          ErrorRange = Receiver.getSourceRange();
+          ErrorRange = CallOrMsg.getReceiverSourceRange();
           ErrorSym = Sym;
         }
       }
@@ -3436,7 +3185,7 @@
 
     // Invalidate the argument region.
     unsigned Count = C.getNodeBuilder().getCurrentBlockCount();
-    state = state->invalidateRegion(ArgRegion, CE, Count);
+    state = state->invalidateRegions(ArgRegion, CE, Count);
 
     // Restore the refcount status of the argument.
     if (Binding)
@@ -3821,6 +3570,62 @@
 }
 
 //===----------------------------------------------------------------------===//
+// Debug printing of refcount bindings and autorelease pools.
+//===----------------------------------------------------------------------===//
+
+static void PrintPool(raw_ostream &Out, SymbolRef Sym,
+                      const ProgramState *State) {
+  Out << ' ';
+  if (Sym)
+    Out << Sym->getSymbolID();
+  else
+    Out << "<pool>";
+  Out << ":{";
+
+  // Get the contents of the pool.
+  if (const ARCounts *Cnts = State->get<AutoreleasePoolContents>(Sym))
+    for (ARCounts::iterator I = Cnts->begin(), E = Cnts->end(); I != E; ++I)
+      Out << '(' << I.getKey() << ',' << I.getData() << ')';
+
+  Out << '}';
+}
+
+bool UsesAutorelease(const ProgramState *state) {
+  // A state uses autorelease if it allocated an autorelease pool or if it has
+  // objects in the caller's autorelease pool.
+  return !state->get<AutoreleaseStack>().isEmpty() ||
+          state->get<AutoreleasePoolContents>(SymbolRef());
+}
+
+void RetainReleaseChecker::printState(raw_ostream &Out,
+                                      const ProgramState *State,
+                                      const char *NL, const char *Sep) const {
+
+  RefBindings B = State->get<RefBindings>();
+
+  if (!B.isEmpty())
+    Out << Sep << NL;
+
+  for (RefBindings::iterator I = B.begin(), E = B.end(); I != E; ++I) {
+    Out << I->first << " : ";
+    I->second.print(Out);
+    Out << NL;
+  }
+
+  // Print the autorelease stack.
+  if (UsesAutorelease(State)) {
+    Out << Sep << NL << "AR pool stack:";
+    ARStack Stack = State->get<AutoreleaseStack>();
+
+    PrintPool(Out, SymbolRef(), State);  // Print the caller's pool.
+    for (ARStack::iterator I = Stack.begin(), E = Stack.end(); I != E; ++I)
+      PrintPool(Out, *I, State);
+
+    Out << NL;
+  }
+}
+
+//===----------------------------------------------------------------------===//
 // Transfer function creation for external clients.
 //===----------------------------------------------------------------------===//
 
diff --git a/safecode/tools/clang/lib/StaticAnalyzer/Core/CheckerManager.cpp b/safecode/tools/clang/lib/StaticAnalyzer/Core/CheckerManager.cpp
index bcba98f..3e451fd 100644
--- a/safecode/tools/clang/lib/StaticAnalyzer/Core/CheckerManager.cpp
+++ b/safecode/tools/clang/lib/StaticAnalyzer/Core/CheckerManager.cpp
@@ -346,14 +346,15 @@
 const ProgramState *
 CheckerManager::runCheckersForRegionChanges(const ProgramState *state,
                             const StoreManager::InvalidatedSymbols *invalidated,
-                                            const MemRegion * const *Begin,
-                                            const MemRegion * const *End) {
+                                    ArrayRef<const MemRegion *> ExplicitRegions,
+                                          ArrayRef<const MemRegion *> Regions) {
   for (unsigned i = 0, e = RegionChangesCheckers.size(); i != e; ++i) {
     // If any checker declares the state infeasible (or if it starts that way),
     // bail out.
     if (!state)
       return NULL;
-    state = RegionChangesCheckers[i].CheckFn(state, invalidated, Begin, End);
+    state = RegionChangesCheckers[i].CheckFn(state, invalidated, 
+                                             ExplicitRegions, Regions);
   }
   return state;
 }
@@ -425,6 +426,14 @@
     EndOfTranslationUnitCheckers[i](TU, mgr, BR);
 }
 
+void CheckerManager::runCheckersForPrintState(raw_ostream &Out,
+                                              const ProgramState *State,
+                                              const char *NL, const char *Sep) {
+  for (llvm::DenseMap<CheckerTag, CheckerRef>::iterator
+        I = CheckerTags.begin(), E = CheckerTags.end(); I != E; ++I)
+    I->second->printState(Out, State, NL, Sep);
+}
+
 //===----------------------------------------------------------------------===//
 // Internal registration functions for AST traversing.
 //===----------------------------------------------------------------------===//
diff --git a/safecode/tools/clang/lib/StaticAnalyzer/Core/ExprEngine.cpp b/safecode/tools/clang/lib/StaticAnalyzer/Core/ExprEngine.cpp
index 6c318f7..9dd2884 100644
--- a/safecode/tools/clang/lib/StaticAnalyzer/Core/ExprEngine.cpp
+++ b/safecode/tools/clang/lib/StaticAnalyzer/Core/ExprEngine.cpp
@@ -67,7 +67,6 @@
 
   // FIXME: Eventually remove the TF object entirely.
   TF->RegisterChecks(*this);
-  TF->RegisterPrinters(getStateManager().Printers);
   
   if (mgr.shouldEagerlyTrimExplodedGraph()) {
     // Enable eager node reclaimation when constructing the ExplodedGraph.  
@@ -172,17 +171,8 @@
 /// evalAssume - Called by ConstraintManager. Used to call checker-specific
 ///  logic for handling assumptions on symbolic values.
 const ProgramState *ExprEngine::processAssume(const ProgramState *state,
-                                              SVal cond,
-                                              bool assumption) {
-
-  state = getCheckerManager().runCheckersForEvalAssume(state, cond,
-                                                       assumption);
-
-  // If the state is infeasible at this point, bail out.
-  if (!state)
-    return NULL;
-
-  return TF->evalAssume(state, cond, assumption);
+                                              SVal cond, bool assumption) {
+  return getCheckerManager().runCheckersForEvalAssume(state, cond, assumption);
 }
 
 bool ExprEngine::wantsRegionChangeUpdate(const ProgramState *state) {
@@ -192,10 +182,15 @@
 const ProgramState *
 ExprEngine::processRegionChanges(const ProgramState *state,
                             const StoreManager::InvalidatedSymbols *invalidated,
-                                 const MemRegion * const *Begin,
-                                 const MemRegion * const *End) {
+                                 ArrayRef<const MemRegion *> Explicits,
+                                 ArrayRef<const MemRegion *> Regions) {
   return getCheckerManager().runCheckersForRegionChanges(state, invalidated,
-                                                         Begin, End);
+                                                         Explicits, Regions);
+}
+
+void ExprEngine::printState(raw_ostream &Out, const ProgramState *State,
+                            const char *NL, const char *Sep) {
+  getCheckerManager().runCheckersForPrintState(Out, State, NL, Sep);
 }
 
 void ExprEngine::processEndWorklist(bool hasWorkRemaining) {
@@ -279,23 +274,15 @@
 
     // Call checkers with the non-cleaned state so that they could query the
     // values of the soon to be dead symbols.
-    // FIXME: This should soon be removed.
-    ExplodedNodeSet Tmp2;
-    getTF().evalDeadSymbols(Tmp2, *this, *Builder, EntryNode,
-                            EntryState, SymReaper);
-    if (Tmp2.empty()) {
-      Builder->MakeNode(Tmp2, currentStmt, EntryNode, EntryState);
-    }
-
-    ExplodedNodeSet Tmp3;
-    getCheckerManager().runCheckersForDeadSymbols(Tmp3, Tmp2,
+    ExplodedNodeSet CheckedSet;
+    getCheckerManager().runCheckersForDeadSymbols(CheckedSet, EntryNode,
                                                  SymReaper, currentStmt, *this);
 
-    // For each node in Tmp3, generate CleanedNodes that have the environment,
-    // the store, and the constraints cleaned up but have the user supplied
-    // states as the predecessors.
-    for (ExplodedNodeSet::const_iterator I = Tmp3.begin(), E = Tmp3.end();
-                                         I != E; ++I) {
+    // For each node in CheckedSet, generate CleanedNodes that have the
+    // environment, the store, and the constraints cleaned up but have the
+    // user-supplied states as the predecessors.
+    for (ExplodedNodeSet::const_iterator
+          I = CheckedSet.begin(), E = CheckedSet.end(); I != E; ++I) {
       const ProgramState *CheckerState = (*I)->getState();
 
       // The constraint manager has not been cleaned up yet, so clean up now.
@@ -1067,7 +1054,6 @@
 /// ProcessEndPath - Called by CoreEngine.  Used to generate end-of-path
 ///  nodes when the control reaches the end of a function.
 void ExprEngine::processEndOfFunction(EndOfFunctionNodeBuilder& builder) {
-  getTF().evalEndPath(*this, builder);
   StateMgr.EndPath(builder.getState());
   getCheckerManager().runCheckersForEndPath(builder, *this);
 }
@@ -1294,55 +1280,29 @@
 /// evalBind - Handle the semantics of binding a value to a specific location.
 ///  This method is used by evalStore and (soon) VisitDeclStmt, and others.
 void ExprEngine::evalBind(ExplodedNodeSet &Dst, const Stmt *StoreE,
-                            ExplodedNode *Pred, const ProgramState *state,
-                            SVal location, SVal Val, bool atDeclInit) {
-
+                          ExplodedNode *Pred,
+                          SVal location, SVal Val, bool atDeclInit) {
 
   // Do a previsit of the bind.
-  ExplodedNodeSet CheckedSet, Src;
-  Src.Add(Pred);
-  getCheckerManager().runCheckersForBind(CheckedSet, Src, location, Val, StoreE,
-                                         *this);
+  ExplodedNodeSet CheckedSet;
+  getCheckerManager().runCheckersForBind(CheckedSet, Pred, location, Val,
+                                         StoreE, *this);
 
   for (ExplodedNodeSet::iterator I = CheckedSet.begin(), E = CheckedSet.end();
        I!=E; ++I) {
 
-    if (Pred != *I)
-      state = (*I)->getState();
-
-    const ProgramState *newState = 0;
+    const ProgramState *state = (*I)->getState();
 
     if (atDeclInit) {
       const VarRegion *VR =
         cast<VarRegion>(cast<loc::MemRegionVal>(location).getRegion());
 
-      newState = state->bindDecl(VR, Val);
-    }
-    else {
-      if (location.isUnknown()) {
-        // We know that the new state will be the same as the old state since
-        // the location of the binding is "unknown".  Consequently, there
-        // is no reason to just create a new node.
-        newState = state;
-      }
-      else {
-        // We are binding to a value other than 'unknown'.  Perform the binding
-        // using the StoreManager.
-        newState = state->bindLoc(cast<Loc>(location), Val);
-      }
+      state = state->bindDecl(VR, Val);
+    } else {
+      state = state->bindLoc(location, Val);
     }
 
-    // The next thing to do is check if the TransferFuncs object wants to
-    // update the state based on the new binding.  If the GRTransferFunc object
-    // doesn't do anything, just auto-propagate the current state.
-    
-    // NOTE: We use 'AssignE' for the location of the PostStore if 'AssignE'
-    // is non-NULL.  Checkers typically care about 
-    
-    StmtNodeBuilderRef BuilderRef(Dst, *Builder, *this, *I, newState, StoreE,
-                                    true);
-
-    getTF().evalBind(BuilderRef, location, Val);
+    MakeNode(Dst, StoreE, *I, state);
   }
 }
 
@@ -1386,7 +1346,7 @@
                                                    ProgramPoint::PostStoreKind);
 
   for (ExplodedNodeSet::iterator NI=Tmp.begin(), NE=Tmp.end(); NI!=NE; ++NI)
-    evalBind(Dst, StoreE, *NI, (*NI)->getState(), location, Val);
+    evalBind(Dst, StoreE, *NI, location, Val);
 }
 
 void ExprEngine::evalLoad(ExplodedNodeSet &Dst, const Expr *Ex,
diff --git a/safecode/tools/clang/lib/StaticAnalyzer/Core/ExprEngineC.cpp b/safecode/tools/clang/lib/StaticAnalyzer/Core/ExprEngineC.cpp
index a4e640c..47debad 100644
--- a/safecode/tools/clang/lib/StaticAnalyzer/Core/ExprEngineC.cpp
+++ b/safecode/tools/clang/lib/StaticAnalyzer/Core/ExprEngineC.cpp
@@ -361,8 +361,7 @@
                                                    Builder->getCurrentBlockCount());
       }
       
-      evalBind(Dst, DS, N, state,
-               loc::MemRegionVal(state->getRegion(VD, LC)), InitVal, true);
+      evalBind(Dst, DS, N, state->getLValue(VD, LC), InitVal, true);
     }
     else {
       MakeNode(Dst, DS, N, state->bindDeclWithNoInit(state->getRegion(VD, LC)));
diff --git a/safecode/tools/clang/lib/StaticAnalyzer/Core/ExprEngineCXX.cpp b/safecode/tools/clang/lib/StaticAnalyzer/Core/ExprEngineCXX.cpp
index d34afba..de3b312 100644
--- a/safecode/tools/clang/lib/StaticAnalyzer/Core/ExprEngineCXX.cpp
+++ b/safecode/tools/clang/lib/StaticAnalyzer/Core/ExprEngineCXX.cpp
@@ -198,17 +198,6 @@
 #endif
   
   // Default semantics: invalidate all regions passed as arguments.
-  SmallVector<const MemRegion*, 10> regionsToInvalidate;
-
-  // FIXME: We can have collisions on the conjured symbol if the
-  //  expression *I also creates conjured symbols.  We probably want
-  //  to identify conjured symbols by an expression pair: the enclosing
-  //  expression (the context) and the expression itself.  This should
-  //  disambiguate conjured symbols.
-  unsigned blockCount = Builder->getCurrentBlockCount();
-  
-  // NOTE: Even if RegionsToInvalidate is empty, we must still invalidate
-  //  global variables.
   ExplodedNodeSet destCall;
 
   for (ExplodedNodeSet::iterator
@@ -216,25 +205,10 @@
        i != e; ++i)
   {
     ExplodedNode *Pred = *i;
+    const LocationContext *LC = Pred->getLocationContext();
     const ProgramState *state = Pred->getState();
 
-    // Accumulate list of regions that are invalidated.
-    for (CXXConstructExpr::const_arg_iterator
-          ai = E->arg_begin(), ae = E->arg_end();
-          ai != ae; ++ai)
-    {
-      SVal val = state->getSVal(*ai);
-      if (const MemRegion *region = val.getAsRegion())
-        regionsToInvalidate.push_back(region);
-    }
-    
-    // Invalidate the regions.    
-    state = state->invalidateRegions(regionsToInvalidate.data(),
-                                     regionsToInvalidate.data() +
-                                     regionsToInvalidate.size(),
-                                     E, blockCount, 0,
-                                     /* invalidateGlobals = */ true);
-    
+    state = invalidateArguments(state, CallOrObjCMessage(E, state), LC);
     Builder->MakeNode(destCall, E, Pred, state);
   }
   
@@ -317,17 +291,13 @@
     if (ObjTy->isRecordType()) {
       regionsToInvalidate.push_back(EleReg);
       // Invalidate the regions.
-      state = state->invalidateRegions(regionsToInvalidate.data(),
-                                       regionsToInvalidate.data() +
-                                       regionsToInvalidate.size(),
+      state = state->invalidateRegions(regionsToInvalidate,
                                        CNE, blockCount, 0,
                                        /* invalidateGlobals = */ true);
       
     } else {
       // Invalidate the regions.
-      state = state->invalidateRegions(regionsToInvalidate.data(),
-                                       regionsToInvalidate.data() +
-                                       regionsToInvalidate.size(),
+      state = state->invalidateRegions(regionsToInvalidate,
                                        CNE, blockCount, 0,
                                        /* invalidateGlobals = */ true);
 
diff --git a/safecode/tools/clang/lib/StaticAnalyzer/Core/ExprEngineCallAndReturn.cpp b/safecode/tools/clang/lib/StaticAnalyzer/Core/ExprEngineCallAndReturn.cpp
index e49d376..6d377b9 100644
--- a/safecode/tools/clang/lib/StaticAnalyzer/Core/ExprEngineCallAndReturn.cpp
+++ b/safecode/tools/clang/lib/StaticAnalyzer/Core/ExprEngineCallAndReturn.cpp
@@ -13,6 +13,7 @@
 
 #include "clang/StaticAnalyzer/Core/CheckerManager.h"
 #include "clang/StaticAnalyzer/Core/PathSensitive/ExprEngine.h"
+#include "clang/StaticAnalyzer/Core/PathSensitive/ObjCMessage.h"
 #include "clang/AST/DeclCXX.h"
 #include "clang/Analysis/Support/SaveAndRestore.h"
 
@@ -63,6 +64,100 @@
   B.generateNode(state);
 }
 
+const ProgramState *
+ExprEngine::invalidateArguments(const ProgramState *State,
+                                const CallOrObjCMessage &Call,
+                                const LocationContext *LC) {
+  SmallVector<const MemRegion *, 8> RegionsToInvalidate;
+
+  if (Call.isObjCMessage()) {
+    // Invalidate all instance variables of the receiver of an ObjC message.
+    // FIXME: We should be able to do better with inter-procedural analysis.
+    if (const MemRegion *MR = Call.getInstanceMessageReceiver(LC).getAsRegion())
+      RegionsToInvalidate.push_back(MR);
+
+  } else if (Call.isCXXCall()) {
+    // Invalidate all instance variables for the callee of a C++ method call.
+    // FIXME: We should be able to do better with inter-procedural analysis.
+    // FIXME: We can probably do better for const versus non-const methods.
+    if (const MemRegion *Callee = Call.getCXXCallee().getAsRegion())
+      RegionsToInvalidate.push_back(Callee);
+
+  } else if (Call.isFunctionCall()) {
+    // Block calls invalidate all captured-by-reference values.
+    if (const MemRegion *Callee = Call.getFunctionCallee().getAsRegion()) {
+      if (isa<BlockDataRegion>(Callee))
+        RegionsToInvalidate.push_back(Callee);
+    }
+  }
+
+  for (unsigned idx = 0, e = Call.getNumArgs(); idx != e; ++idx) {
+    SVal V = Call.getArgSVal(idx);
+
+    // If we are passing a location wrapped as an integer, unwrap it and
+    // invalidate the values referred by the location.
+    if (nonloc::LocAsInteger *Wrapped = dyn_cast<nonloc::LocAsInteger>(&V))
+      V = Wrapped->getLoc();
+    else if (!isa<Loc>(V))
+      continue;
+
+    if (const MemRegion *R = V.getAsRegion()) {
+      // Invalidate the value of the variable passed by reference.
+
+      // Are we dealing with an ElementRegion?  If the element type is
+      // a basic integer type (e.g., char, int) and the underying region
+      // is a variable region then strip off the ElementRegion.
+      // FIXME: We really need to think about this for the general case
+      //   as sometimes we are reasoning about arrays and other times
+      //   about (char*), etc., is just a form of passing raw bytes.
+      //   e.g., void *p = alloca(); foo((char*)p);
+      if (const ElementRegion *ER = dyn_cast<ElementRegion>(R)) {
+        // Checking for 'integral type' is probably too promiscuous, but
+        // we'll leave it in for now until we have a systematic way of
+        // handling all of these cases.  Eventually we need to come up
+        // with an interface to StoreManager so that this logic can be
+        // approriately delegated to the respective StoreManagers while
+        // still allowing us to do checker-specific logic (e.g.,
+        // invalidating reference counts), probably via callbacks.
+        if (ER->getElementType()->isIntegralOrEnumerationType()) {
+          const MemRegion *superReg = ER->getSuperRegion();
+          if (isa<VarRegion>(superReg) || isa<FieldRegion>(superReg) ||
+              isa<ObjCIvarRegion>(superReg))
+            R = cast<TypedRegion>(superReg);
+        }
+        // FIXME: What about layers of ElementRegions?
+      }
+
+      // Mark this region for invalidation.  We batch invalidate regions
+      // below for efficiency.
+      RegionsToInvalidate.push_back(R);
+    } else {
+      // Nuke all other arguments passed by reference.
+      // FIXME: is this necessary or correct? This handles the non-Region
+      //  cases.  Is it ever valid to store to these?
+      State = State->unbindLoc(cast<Loc>(V));
+    }
+  }
+
+  // Invalidate designated regions using the batch invalidation API.
+
+  // FIXME: We can have collisions on the conjured symbol if the
+  //  expression *I also creates conjured symbols.  We probably want
+  //  to identify conjured symbols by an expression pair: the enclosing
+  //  expression (the context) and the expression itself.  This should
+  //  disambiguate conjured symbols.
+  assert(Builder && "Invalidating arguments outside of a statement context");
+  unsigned Count = Builder->getCurrentBlockCount();
+  StoreManager::InvalidatedSymbols IS;
+
+  // NOTE: Even if RegionsToInvalidate is empty, we may still invalidate
+  //  global variables.
+  return State->invalidateRegions(RegionsToInvalidate,
+                                  Call.getOriginExpr(), Count,
+                                  &IS, doesInvalidateGlobals(Call));
+
+}
+
 void ExprEngine::VisitCallExpr(const CallExpr *CE, ExplodedNode *Pred,
                                ExplodedNodeSet &dst) {
   // Perform the previsit of the CallExpr.
@@ -108,22 +203,15 @@
       unsigned Count = Builder.getCurrentBlockCount();
       SVal RetVal = SVB.getConjuredSymbolVal(0, CE, ResultTy, Count);
 
-      // Generate a new ExplodedNode with the return value set.
+      // Generate a new state with the return value set.
       state = state->BindExpr(CE, RetVal);
-      Pred = Builder.generateNode(CE, state, Pred);
 
-      // Then handle everything else.
-      unsigned oldSize = Dst.size();
-      SaveOr OldHasGen(Builder.hasGeneratedNode);
-      
-      // Dispatch to transfer function logic to handle the rest of the call.
-      Eng.getTF().evalCall(Dst, Eng, Builder, CE, L, Pred);
-      
-      // Handle the case where no nodes where generated.  Auto-generate that
-      // contains the updated state if we aren't generating sinks.
-      if (!Builder.BuildSinks && Dst.size() == oldSize &&
-          !Builder.hasGeneratedNode)
-        Eng.MakeNode(Dst, CE, Pred, state);
+      // Invalidate the arguments.
+      const LocationContext *LC = Pred->getLocationContext();
+      state = Eng.invalidateArguments(state, CallOrObjCMessage(CE, state), LC);
+
+      // And make the result node.
+      Eng.MakeNode(Dst, CE, Pred, state);
     }
   };
   
@@ -161,25 +249,5 @@
     Src.Add(Pred);
   }
   
-  ExplodedNodeSet CheckedSet;
-  getCheckerManager().runCheckersForPreStmt(CheckedSet, Src, RS, *this);
-  
-  for (ExplodedNodeSet::iterator I = CheckedSet.begin(), E = CheckedSet.end();
-       I != E; ++I) {
-    
-    assert(Builder && "StmtNodeBuilder must be defined.");
-    
-    Pred = *I;
-    unsigned size = Dst.size();
-    
-    SaveAndRestore<bool> OldSink(Builder->BuildSinks);
-    SaveOr OldHasGen(Builder->hasGeneratedNode);
-    
-    getTF().evalReturn(Dst, *this, *Builder, RS, Pred);
-    
-    // Handle the case where no nodes where generated.
-    if (!Builder->BuildSinks && Dst.size() == size &&
-        !Builder->hasGeneratedNode)
-      MakeNode(Dst, RS, Pred, Pred->getState());
-  }
+  getCheckerManager().runCheckersForPreStmt(Dst, Src, RS, *this);
 }
diff --git a/safecode/tools/clang/lib/StaticAnalyzer/Core/ExprEngineObjC.cpp b/safecode/tools/clang/lib/StaticAnalyzer/Core/ExprEngineObjC.cpp
index 6cfe8cd..1a68657 100644
--- a/safecode/tools/clang/lib/StaticAnalyzer/Core/ExprEngineObjC.cpp
+++ b/safecode/tools/clang/lib/StaticAnalyzer/Core/ExprEngineObjC.cpp
@@ -142,7 +142,6 @@
     
     ExplodedNode *Pred = *DI;
     bool RaisesException = false;
-    unsigned oldSize = dstEval.size();
     SaveAndRestore<bool> OldSink(Builder->BuildSinks);
     SaveOr OldHasGen(Builder->hasGeneratedNode);
     
@@ -225,12 +224,8 @@
       // Dispatch to plug-in transfer function.
       evalObjCMessage(dstEval, msg, Pred, Pred->getState());
     }
-    
-    // Handle the case where no nodes where generated.  Auto-generate that
-    // contains the updated state if we aren't generating sinks.
-    if (!Builder->BuildSinks && dstEval.size() == oldSize &&
-        !Builder->hasGeneratedNode)
-      MakeNode(dstEval, msg.getOriginExpr(), Pred, Pred->getState());
+
+    assert(Builder->BuildSinks || Builder->hasGeneratedNode);
   }
   
   // Finally, perform the post-condition check of the ObjCMessageExpr and store
@@ -273,7 +268,11 @@
   // Bind the return value.
   state = state->BindExpr(currentStmt, ReturnValue);
 
-  // Now we can handle the other aspects of the message.
-  getTF().evalObjCMessage(Dst, *this, *Builder, msg, Pred, state);
+  // Invalidate the arguments (and the receiver)
+  const LocationContext *LC = Pred->getLocationContext();
+  state = invalidateArguments(state, CallOrObjCMessage(msg, state), LC);
+
+  // And create the new node.
+  MakeNode(Dst, msg.getOriginExpr(), Pred, state);
 }
 
diff --git a/safecode/tools/clang/lib/StaticAnalyzer/Core/HTMLDiagnostics.cpp b/safecode/tools/clang/lib/StaticAnalyzer/Core/HTMLDiagnostics.cpp
index 68a6618..2b377d0 100644
--- a/safecode/tools/clang/lib/StaticAnalyzer/Core/HTMLDiagnostics.cpp
+++ b/safecode/tools/clang/lib/StaticAnalyzer/Core/HTMLDiagnostics.cpp
@@ -47,7 +47,7 @@
 
   virtual void FlushDiagnostics(SmallVectorImpl<std::string> *FilesMade);
 
-  virtual void HandlePathDiagnostic(const PathDiagnostic* D);
+  virtual void HandlePathDiagnosticImpl(const PathDiagnostic* D);
 
   virtual StringRef getName() const {
     return "HTMLDiagnostics";
@@ -88,7 +88,7 @@
 // Report processing.
 //===----------------------------------------------------------------------===//
 
-void HTMLDiagnostics::HandlePathDiagnostic(const PathDiagnostic* D) {
+void HTMLDiagnostics::HandlePathDiagnosticImpl(const PathDiagnostic* D) {
   if (!D)
     return;
 
diff --git a/safecode/tools/clang/lib/StaticAnalyzer/Core/ObjCMessage.cpp b/safecode/tools/clang/lib/StaticAnalyzer/Core/ObjCMessage.cpp
index 40ed83b..112c468 100644
--- a/safecode/tools/clang/lib/StaticAnalyzer/Core/ObjCMessage.cpp
+++ b/safecode/tools/clang/lib/StaticAnalyzer/Core/ObjCMessage.cpp
@@ -112,18 +112,22 @@
   QualType resultTy;
   bool isLVal = false;
 
-  if (CallE) {
-    isLVal = CallE->isLValue();
-    const Expr *Callee = CallE->getCallee();
-    if (const FunctionDecl *FD = State->getSVal(Callee).getAsFunctionDecl())
-      resultTy = FD->getResultType();
-    else
-      resultTy = CallE->getType();
-  }
-  else {
+  if (isObjCMessage()) {
     isLVal = isa<ObjCMessageExpr>(Msg.getOriginExpr()) &&
              Msg.getOriginExpr()->isLValue();
     resultTy = Msg.getResultType(ctx);
+  } else if (const CXXConstructExpr *Ctor =
+              CallE.dyn_cast<const CXXConstructExpr *>()) {
+    resultTy = Ctor->getType();
+  } else {
+    const CallExpr *FunctionCall = CallE.get<const CallExpr *>();
+
+    isLVal = FunctionCall->isLValue();
+    const Expr *Callee = FunctionCall->getCallee();
+    if (const FunctionDecl *FD = State->getSVal(Callee).getAsFunctionDecl())
+      resultTy = FD->getResultType();
+    else
+      resultTy = FunctionCall->getType();
   }
 
   if (isLVal)
@@ -132,25 +136,23 @@
   return resultTy;
 }
 
-SVal CallOrObjCMessage::getArgSValAsScalarOrLoc(unsigned i) const {
-  assert(i < getNumArgs());
-  if (CallE) return State->getSValAsScalarOrLoc(CallE->getArg(i));
-  QualType argT = Msg.getArgType(i);
-  if (Loc::isLocType(argT) || argT->isIntegerType())
-    return Msg.getArgSVal(i, State);
-  return UnknownVal();
-}
-
 SVal CallOrObjCMessage::getFunctionCallee() const {
   assert(isFunctionCall());
   assert(!isCXXCall());
-  const Expr *callee = CallE->getCallee()->IgnoreParens();
-  return State->getSVal(callee);
+  const Expr *Fun = CallE.get<const CallExpr *>()->getCallee()->IgnoreParens();
+  return State->getSVal(Fun);
 }
 
 SVal CallOrObjCMessage::getCXXCallee() const {
   assert(isCXXCall());
+  const CallExpr *ActualCall = CallE.get<const CallExpr *>();
   const Expr *callee =
-    cast<CXXMemberCallExpr>(CallE)->getImplicitObjectArgument();
+    cast<CXXMemberCallExpr>(ActualCall)->getImplicitObjectArgument();
   return State->getSVal(callee);  
 }
+
+SVal
+CallOrObjCMessage::getInstanceMessageReceiver(const LocationContext *LC) const {
+  assert(isObjCMessage());
+  return Msg.getInstanceReceiverSVal(State, LC);
+}
diff --git a/safecode/tools/clang/lib/StaticAnalyzer/Core/PathDiagnostic.cpp b/safecode/tools/clang/lib/StaticAnalyzer/Core/PathDiagnostic.cpp
index 7f95c95..e56f157 100644
--- a/safecode/tools/clang/lib/StaticAnalyzer/Core/PathDiagnostic.cpp
+++ b/safecode/tools/clang/lib/StaticAnalyzer/Core/PathDiagnostic.cpp
@@ -117,6 +117,13 @@
   HandlePathDiagnostic(D);
 }
 
+void PathDiagnosticClient::HandlePathDiagnostic(const PathDiagnostic *D) {
+  // For now this simply forwards to HandlePathDiagnosticImpl.  In the future
+  // we can use this indirection to control for multi-threaded access to
+  // the PathDiagnosticClient from multiple bug reporters.
+  HandlePathDiagnosticImpl(D);
+}
+
 //===----------------------------------------------------------------------===//
 // PathDiagnosticLocation methods.
 //===----------------------------------------------------------------------===//
diff --git a/safecode/tools/clang/lib/StaticAnalyzer/Core/PlistDiagnostics.cpp b/safecode/tools/clang/lib/StaticAnalyzer/Core/PlistDiagnostics.cpp
index cae5bc9..3133be7 100644
--- a/safecode/tools/clang/lib/StaticAnalyzer/Core/PlistDiagnostics.cpp
+++ b/safecode/tools/clang/lib/StaticAnalyzer/Core/PlistDiagnostics.cpp
@@ -74,7 +74,7 @@
 
     void FlushDiagnostics(SmallVectorImpl<std::string> *FilesMade);
     
-    void HandlePathDiagnostic(const PathDiagnostic* D);
+    void HandlePathDiagnosticImpl(const PathDiagnostic* D);
     
     virtual StringRef getName() const {
       return "PlistDiagnostics";
@@ -321,7 +321,7 @@
   }
 }
 
-void PlistDiagnostics::HandlePathDiagnostic(const PathDiagnostic* D) {
+void PlistDiagnostics::HandlePathDiagnosticImpl(const PathDiagnostic* D) {
   if (!D)
     return;
 
diff --git a/safecode/tools/clang/lib/StaticAnalyzer/Core/ProgramState.cpp b/safecode/tools/clang/lib/StaticAnalyzer/Core/ProgramState.cpp
index 046de0d..54da7b5 100644
--- a/safecode/tools/clang/lib/StaticAnalyzer/Core/ProgramState.cpp
+++ b/safecode/tools/clang/lib/StaticAnalyzer/Core/ProgramState.cpp
@@ -51,10 +51,6 @@
 }
 
 ProgramStateManager::~ProgramStateManager() {
-  for (std::vector<ProgramState::Printer*>::iterator I=Printers.begin(),
-        E=Printers.end(); I!=E; ++I)
-    delete *I;
-
   for (GDMContextsTy::iterator I=GDMContexts.begin(), E=GDMContexts.end();
        I!=E; ++I)
     I->second.second(I->second.first);
@@ -136,41 +132,38 @@
            new_state;
 }
 
-const ProgramState *ProgramState::invalidateRegions(const MemRegion * const *Begin,
-                                          const MemRegion * const *End,
-                                          const Expr *E, unsigned Count,
-                                          StoreManager::InvalidatedSymbols *IS,
-                                          bool invalidateGlobals) const {
+const ProgramState *
+ProgramState::invalidateRegions(ArrayRef<const MemRegion *> Regions,
+                                const Expr *E, unsigned Count,
+                                StoreManager::InvalidatedSymbols *IS,
+                                bool invalidateGlobals) const {
   if (!IS) {
     StoreManager::InvalidatedSymbols invalidated;
-    return invalidateRegionsImpl(Begin, End, E, Count,
-                             invalidated, invalidateGlobals);
+    return invalidateRegionsImpl(Regions, E, Count,
+                                 invalidated, invalidateGlobals);
   }
-  return invalidateRegionsImpl(Begin, End, E, Count, *IS, invalidateGlobals);
+  return invalidateRegionsImpl(Regions, E, Count, *IS, invalidateGlobals);
 }
 
 const ProgramState *
-ProgramState::invalidateRegionsImpl(const MemRegion * const *Begin,
-                               const MemRegion * const *End,
-                               const Expr *E, unsigned Count,
-                               StoreManager::InvalidatedSymbols &IS,
-                               bool invalidateGlobals) const {
+ProgramState::invalidateRegionsImpl(ArrayRef<const MemRegion *> Regions,
+                                    const Expr *E, unsigned Count,
+                                    StoreManager::InvalidatedSymbols &IS,
+                                    bool invalidateGlobals) const {
   ProgramStateManager &Mgr = getStateManager();
   SubEngine* Eng = Mgr.getOwningEngine();
  
   if (Eng && Eng->wantsRegionChangeUpdate(this)) {
-    StoreManager::InvalidatedRegions Regions;
+    StoreManager::InvalidatedRegions Invalidated;
     const StoreRef &newStore
-      = Mgr.StoreMgr->invalidateRegions(getStore(), Begin, End, E, Count, IS,
-                                        invalidateGlobals, &Regions);
+      = Mgr.StoreMgr->invalidateRegions(getStore(), Regions, E, Count, IS,
+                                        invalidateGlobals, &Invalidated);
     const ProgramState *newState = makeWithStore(newStore);
-    return Eng->processRegionChanges(newState, &IS,
-                                     &Regions.front(),
-                                     &Regions.back()+1);
+    return Eng->processRegionChanges(newState, &IS, Regions, Invalidated);
   }
 
   const StoreRef &newStore =
-    Mgr.StoreMgr->invalidateRegions(getStore(), Begin, End, E, Count, IS,
+    Mgr.StoreMgr->invalidateRegions(getStore(), Regions, E, Count, IS,
                                     invalidateGlobals, NULL);
   return makeWithStore(newStore);
 }
@@ -392,11 +385,11 @@
   return (bool) (((uintptr_t) S) & 0x1);
 }
 
-void ProgramState::print(raw_ostream &Out, CFG &C, const char* nl,
-                    const char* sep) const {
+void ProgramState::print(raw_ostream &Out, CFG &C,
+                         const char *NL, const char *Sep) const {
   // Print the store.
   ProgramStateManager &Mgr = getStateManager();
-  Mgr.getStoreManager().print(getStore(), Out, nl, sep);
+  Mgr.getStoreManager().print(getStore(), Out, NL, Sep);
 
   // Print Subexpression bindings.
   bool isFirst = true;
@@ -407,10 +400,11 @@
       continue;
 
     if (isFirst) {
-      Out << nl << nl << "Sub-Expressions:" << nl;
+      Out << NL << NL << "Sub-Expressions:" << NL;
       isFirst = false;
+    } else {
+      Out << NL;
     }
-    else { Out << nl; }
 
     Out << " (" << (void*) I.getKey() << ") ";
     LangOptions LO; // FIXME.
@@ -426,10 +420,11 @@
       continue;
 
     if (isFirst) {
-      Out << nl << nl << "Block-level Expressions:" << nl;
+      Out << NL << NL << "Block-level Expressions:" << NL;
       isFirst = false;
+    } else {
+      Out << NL;
     }
-    else { Out << nl; }
 
     Out << " (" << (void*) I.getKey() << ") ";
     LangOptions LO; // FIXME.
@@ -445,10 +440,11 @@
       continue;
     
     if (isFirst) {
-      Out << nl << nl << "Load/store locations:" << nl;
+      Out << NL << NL << "Load/store locations:" << NL;
       isFirst = false;
+    } else {
+      Out << NL;
     }
-    else { Out << nl; }
 
     const Stmt *S = (Stmt*) (((uintptr_t) I.getKey()) & ((uintptr_t) ~0x1));
     
@@ -458,13 +454,10 @@
     Out << " : " << I.getData();
   }
 
-  Mgr.getConstraintManager().print(this, Out, nl, sep);
+  Mgr.getConstraintManager().print(this, Out, NL, Sep);
 
   // Print checker-specific data.
-  for (std::vector<Printer*>::iterator I = Mgr.Printers.begin(),
-                                       E = Mgr.Printers.end(); I != E; ++I) {
-    (*I)->Print(Out, this, nl, sep);
-  }
+  Mgr.getOwningEngine()->printState(Out, this, NL, Sep);
 }
 
 void ProgramState::printDOT(raw_ostream &Out, CFG &C) const {
diff --git a/safecode/tools/clang/lib/StaticAnalyzer/Core/RegionStore.cpp b/safecode/tools/clang/lib/StaticAnalyzer/Core/RegionStore.cpp
index 30028c7..04c274d 100644
--- a/safecode/tools/clang/lib/StaticAnalyzer/Core/RegionStore.cpp
+++ b/safecode/tools/clang/lib/StaticAnalyzer/Core/RegionStore.cpp
@@ -236,13 +236,11 @@
   // Binding values to regions.
   //===-------------------------------------------------------------------===//
 
-  StoreRef invalidateRegions(Store store,
-                             const MemRegion * const *Begin,
-                             const MemRegion * const *End,
+  StoreRef invalidateRegions(Store store, ArrayRef<const MemRegion *> Regions,
                              const Expr *E, unsigned Count,
                              InvalidatedSymbols &IS,
                              bool invalidateGlobals,
-                             InvalidatedRegions *Regions);
+                             InvalidatedRegions *Invalidated);
 
 public:   // Made public for helper classes.
 
@@ -721,21 +719,21 @@
 }
 
 StoreRef RegionStoreManager::invalidateRegions(Store store,
-                                               const MemRegion * const *I,
-                                               const MemRegion * const *E,
+                                            ArrayRef<const MemRegion *> Regions,
                                                const Expr *Ex, unsigned Count,
                                                InvalidatedSymbols &IS,
                                                bool invalidateGlobals,
-                                               InvalidatedRegions *Regions) {
+                                              InvalidatedRegions *Invalidated) {
   invalidateRegionsWorker W(*this, StateMgr,
                             RegionStoreManager::GetRegionBindings(store),
-                            Ex, Count, IS, Regions, invalidateGlobals);
+                            Ex, Count, IS, Invalidated, invalidateGlobals);
 
   // Scan the bindings and generate the clusters.
   W.GenerateClusters();
 
-  // Add I .. E to the worklist.
-  for ( ; I != E; ++I)
+  // Add the regions to the worklist.
+  for (ArrayRef<const MemRegion *>::iterator
+       I = Regions.begin(), E = Regions.end(); I != E; ++I)
     W.AddToWorkList(*I);
 
   W.RunWorkList();
@@ -755,8 +753,8 @@
 
     // Even if there are no bindings in the global scope, we still need to
     // record that we touched it.
-    if (Regions)
-      Regions->push_back(GS);
+    if (Invalidated)
+      Invalidated->push_back(GS);
   }
 
   return StoreRef(B.getRootWithoutRetain(), *this);
diff --git a/safecode/tools/clang/lib/StaticAnalyzer/Core/TextPathDiagnostics.cpp b/safecode/tools/clang/lib/StaticAnalyzer/Core/TextPathDiagnostics.cpp
index c4665ef..e91b48d 100644
--- a/safecode/tools/clang/lib/StaticAnalyzer/Core/TextPathDiagnostics.cpp
+++ b/safecode/tools/clang/lib/StaticAnalyzer/Core/TextPathDiagnostics.cpp
@@ -31,7 +31,7 @@
   TextPathDiagnostics(const std::string& output, Diagnostic &diag)
     : OutputFile(output), Diag(diag) {}
 
-  void HandlePathDiagnostic(const PathDiagnostic* D);
+  void HandlePathDiagnosticImpl(const PathDiagnostic* D);
 
   void FlushDiagnostics(SmallVectorImpl<std::string> *FilesMade) { }
   
@@ -53,7 +53,7 @@
   return new TextPathDiagnostics(out, PP.getDiagnostics());
 }
 
-void TextPathDiagnostics::HandlePathDiagnostic(const PathDiagnostic* D) {
+void TextPathDiagnostics::HandlePathDiagnosticImpl(const PathDiagnostic* D) {
   if (!D)
     return;
 
diff --git a/safecode/tools/clang/lib/StaticAnalyzer/Frontend/AnalysisConsumer.cpp b/safecode/tools/clang/lib/StaticAnalyzer/Frontend/AnalysisConsumer.cpp
index 24f19cd..4b5a882 100644
--- a/safecode/tools/clang/lib/StaticAnalyzer/Frontend/AnalysisConsumer.cpp
+++ b/safecode/tools/clang/lib/StaticAnalyzer/Frontend/AnalysisConsumer.cpp
@@ -162,6 +162,7 @@
 
   virtual void HandleTranslationUnit(ASTContext &C);
   void HandleDeclContext(ASTContext &C, DeclContext *dc);
+  void HandleDeclContextDecl(ASTContext &C, Decl *D);
 
   void HandleCode(Decl *D);
 };
@@ -172,61 +173,67 @@
 //===----------------------------------------------------------------------===//
 
 void AnalysisConsumer::HandleDeclContext(ASTContext &C, DeclContext *dc) {
-  BugReporter BR(*Mgr);
   for (DeclContext::decl_iterator I = dc->decls_begin(), E = dc->decls_end();
        I != E; ++I) {
-    Decl *D = *I;
+    HandleDeclContextDecl(C, *I);
+  }
+}
+
+void AnalysisConsumer::HandleDeclContextDecl(ASTContext &C, Decl *D) {
+  { // Handle callbacks for arbitrary decls.
+    BugReporter BR(*Mgr);
     checkerMgr->runCheckersOnASTDecl(D, *Mgr, BR);
+  }
 
-    switch (D->getKind()) {
-      case Decl::Namespace: {
-        HandleDeclContext(C, cast<NamespaceDecl>(D));
-        break;
-      }
-      case Decl::CXXConstructor:
-      case Decl::CXXDestructor:
-      case Decl::CXXConversion:
-      case Decl::CXXMethod:
-      case Decl::Function: {
-        FunctionDecl *FD = cast<FunctionDecl>(D);
-        // We skip function template definitions, as their semantics is
-        // only determined when they are instantiated.
-        if (FD->isThisDeclarationADefinition() &&
-            !FD->isDependentContext()) {
-          if (!Opts.AnalyzeSpecificFunction.empty() &&
-              FD->getDeclName().getAsString() != Opts.AnalyzeSpecificFunction)
-            break;
-          DisplayFunction(FD);
-          HandleCode(FD);
-        }
-        break;
-      }
-       
-      case Decl::ObjCCategoryImpl:
-      case Decl::ObjCImplementation: {
-        ObjCImplDecl *ID = cast<ObjCImplDecl>(*I);
-        HandleCode(ID);
-        
-        for (ObjCContainerDecl::method_iterator MI = ID->meth_begin(), 
-             ME = ID->meth_end(); MI != ME; ++MI) {
-          checkerMgr->runCheckersOnASTDecl(*MI, *Mgr, BR);
-
-          if ((*MI)->isThisDeclarationADefinition()) {
-            if (!Opts.AnalyzeSpecificFunction.empty() &&
-                Opts.AnalyzeSpecificFunction != 
-                  (*MI)->getSelector().getAsString())
-              break;
-            DisplayFunction(*MI);
-            HandleCode(*MI);
-          }
-        }
-        break;
-      }
-        
-      default:
-        break;
+  switch (D->getKind()) {
+    case Decl::Namespace: {
+      HandleDeclContext(C, cast<NamespaceDecl>(D));
+      break;
     }
-  }  
+    case Decl::CXXConstructor:
+    case Decl::CXXDestructor:
+    case Decl::CXXConversion:
+    case Decl::CXXMethod:
+    case Decl::Function: {
+      FunctionDecl *FD = cast<FunctionDecl>(D);
+      // We skip function template definitions, as their semantics is
+      // only determined when they are instantiated.
+      if (FD->isThisDeclarationADefinition() &&
+          !FD->isDependentContext()) {
+        if (!Opts.AnalyzeSpecificFunction.empty() &&
+            FD->getDeclName().getAsString() != Opts.AnalyzeSpecificFunction)
+          break;
+        DisplayFunction(FD);
+        HandleCode(FD);
+      }
+      break;
+    }
+     
+    case Decl::ObjCCategoryImpl:
+    case Decl::ObjCImplementation: {
+      ObjCImplDecl *ID = cast<ObjCImplDecl>(D);
+      HandleCode(ID);
+      
+      for (ObjCContainerDecl::method_iterator MI = ID->meth_begin(), 
+           ME = ID->meth_end(); MI != ME; ++MI) {
+        BugReporter BR(*Mgr);
+        checkerMgr->runCheckersOnASTDecl(*MI, *Mgr, BR);
+
+        if ((*MI)->isThisDeclarationADefinition()) {
+          if (!Opts.AnalyzeSpecificFunction.empty() &&
+              Opts.AnalyzeSpecificFunction != 
+                (*MI)->getSelector().getAsString())
+            break;
+          DisplayFunction(*MI);
+          HandleCode(*MI);
+        }
+      }
+      break;
+    }
+      
+    default:
+      break;
+  }
 }
 
 void AnalysisConsumer::HandleTranslationUnit(ASTContext &C) {
diff --git a/safecode/tools/clang/test/ARCMT/migrate-space-in-path.m b/safecode/tools/clang/test/ARCMT/migrate-space-in-path.m
new file mode 100644
index 0000000..8f45cc7
--- /dev/null
+++ b/safecode/tools/clang/test/ARCMT/migrate-space-in-path.m
@@ -0,0 +1,9 @@
+// XFAIL: win32
+
+// RUN: mkdir -p %t/"with space"
+// RUN: cp %S/Inputs/* %t/"with space"
+// RUN: %clang_cc1 -arcmt-migrate -arcmt-migrate-directory %t.migrate %t/"with space"/test1.m.in -x objective-c -fobjc-nonfragile-abi
+// RUN: %clang_cc1 -arcmt-migrate -arcmt-migrate-directory %t.migrate %t/"with space"/test2.m.in -x objective-c -fobjc-nonfragile-abi
+// RUN: c-arcmt-test -arcmt-migrate-directory %t.migrate | arcmt-test -verify-transformed-files %t/"with space"/test1.m.in.result %t/"with space"/test2.m.in.result %t/"with space"/test.h.result
+// RUN: rm -rf %t.migrate
+// RUN: rm -rf %t
diff --git a/safecode/tools/clang/test/Analysis/objc-arc.m b/safecode/tools/clang/test/Analysis/objc-arc.m
index 6b22fd0..8e18877 100644
--- a/safecode/tools/clang/test/Analysis/objc-arc.m
+++ b/safecode/tools/clang/test/Analysis/objc-arc.m
@@ -147,3 +147,9 @@
   (void) x;
 }
 
+// Previously this resulted in a "return of stack address" warning.
+id test_return() {
+  id x = (__bridge_transfer id) CFCreateString();
+  return x; // no-warning
+}
+
diff --git a/safecode/tools/clang/test/CXX/special/class.temporary/p1.cpp b/safecode/tools/clang/test/CXX/special/class.temporary/p1.cpp
new file mode 100644
index 0000000..07890eb
--- /dev/null
+++ b/safecode/tools/clang/test/CXX/special/class.temporary/p1.cpp
@@ -0,0 +1,58 @@
+// RUN: %clang_cc1 -std=c++0x -fsyntax-only -verify %s
+
+namespace test0 {
+  struct A {
+    A() = default;
+    int x;
+    int y;
+
+    A(const A&) = delete; // expected-note {{function has been explicitly marked deleted here}}
+  };
+
+  void foo(...);
+
+  void test() {
+    A a;
+    foo(a); // expected-error {{call to deleted constructor of 'test0::A'}}
+  }
+}
+
+namespace test1 {
+  struct A {
+    A() = default;
+    int x;
+    int y;
+
+  private:
+    A(const A&) = default; // expected-note {{declared private here}}
+  };
+
+  void foo(...);
+
+  void test() {
+    A a;
+    // FIXME: this error about variadics is bogus
+    foo(a); // expected-error {{calling a private constructor of class 'test1::A'}} expected-error {{cannot pass object of non-trivial type 'test1::A' through variadic function}}
+  }
+}
+
+// Don't enforce this in an unevaluated context.
+namespace test2 {
+  struct A {
+    A(const A&) = delete; // expected-note {{marked deleted here}}
+  };
+
+  typedef char one[1];
+  typedef char two[2];
+
+  one &meta(bool);
+  two &meta(...);
+
+  void a(A &a) {
+    char check[sizeof(meta(a)) == 2 ? 1 : -1];
+  }
+
+  void b(A &a) {
+    meta(a); // expected-error {{call to deleted constructor}}
+  }
+}
diff --git a/safecode/tools/clang/test/CodeGenCXX/varargs.cpp b/safecode/tools/clang/test/CodeGenCXX/varargs.cpp
index d469ae4..af34336 100644
--- a/safecode/tools/clang/test/CodeGenCXX/varargs.cpp
+++ b/safecode/tools/clang/test/CodeGenCXX/varargs.cpp
@@ -1,17 +1,43 @@
-// RUN: %clang_cc1 -emit-llvm %s -o - | FileCheck %s
+// RUN: %clang_cc1 -triple x86_64-apple-darwin10 -emit-llvm %s -o - | FileCheck %s
+
 // rdar://7309675
 // PR4678
+namespace test0 {
+  // test1 should be compmiled to be a varargs function in the IR even
+  // though there is no way to do a va_begin.  Otherwise, the optimizer
+  // will warn about 'dropped arguments' at the call site.
 
-// test1 should be compmiled to be a varargs function in the IR even
-// though there is no way to do a va_begin.  Otherwise, the optimizer
-// will warn about 'dropped arguments' at the call site.
+  // CHECK: define i32 @_ZN5test05test1Ez(...)
+  int test1(...) {
+    return -1;
+  }
 
-// CHECK: define i32 @_Z5test1z(...)
-int test1(...) {
-  return -1;
+  // CHECK: call i32 (...)* @_ZN5test05test1Ez(i32 0)
+  void test() {
+    test1(0);
+  }
 }
 
-// CHECK: call i32 (...)* @_Z5test1z(i32 0)
-void test() {
-  test1(0);
+namespace test1 {
+  struct A {
+    int x;
+    int y;
+  };
+
+  void foo(...);
+
+  void test() {
+    A x;
+    foo(x);
+  }
+  // CHECK:    define void @_ZN5test14testEv()
+  // CHECK:      [[X:%.*]] = alloca [[A:%.*]], align 4
+  // CHECK-NEXT: [[TMP:%.*]] = alloca [[A]], align 4
+  // CHECK-NEXT: [[T0:%.*]] = bitcast [[A]]* [[TMP]] to i8*
+  // CHECK-NEXT: [[T1:%.*]] = bitcast [[A]]* [[X]] to i8*
+  // CHECK-NEXT: call void @llvm.memcpy.p0i8.p0i8.i64(i8* [[T0]], i8* [[T1]], i64 8, i32 4, i1 false)
+  // CHECK-NEXT: [[T0:%.*]] = bitcast [[A]]* [[TMP]] to i64*
+  // CHECK-NEXT: [[T1:%.*]] = load i64* [[T0]], align 1
+  // CHECK-NEXT: call void (...)* @_ZN5test13fooEz(i64 [[T1]])
+  // CHECK-NEXT: ret void
 }
diff --git a/safecode/tools/clang/test/CodeGenObjCXX/arc-references.mm b/safecode/tools/clang/test/CodeGenObjCXX/arc-references.mm
index 3d0313d..b1a12e4 100644
--- a/safecode/tools/clang/test/CodeGenObjCXX/arc-references.mm
+++ b/safecode/tools/clang/test/CodeGenObjCXX/arc-references.mm
@@ -61,8 +61,9 @@
 
 // CHECK: define void @_Z5test5RU8__strongP11objc_object
 void test5(__strong id &x) {
-  // CHECK: [[OBJ_ID:%[a-zA-Z0-9]+]] = call i8* @objc_retain
-  // CHECK-NEXT: [[OBJ_A:%[a-zA-Z0-9]+]] = bitcast i8* [[OBJ_ID]] to [[A:%[a-zA-Z0-9]+]]*
+  // CHECK:      [[REFTMP:%.*]] = alloca {{%.*}}*, align 8
+  // CHECK:      [[OBJ_ID:%.*]] = call i8* @objc_retain(
+  // CHECK-NEXT: [[OBJ_A:%.*]] = bitcast i8* [[OBJ_ID]] to [[A:%[a-zA-Z0-9]+]]*
   // CHECK-NEXT: store [[A]]* [[OBJ_A]], [[A]]** [[REFTMP:%[a-zA-Z0-9]+]]
   // CHECK-NEXT: call void @_Z4sinkOU8__strongP1A
   sink(x);  
diff --git a/safecode/tools/clang/test/Driver/apple-kext-i386.cpp b/safecode/tools/clang/test/Driver/apple-kext-i386.cpp
index 80c8bfc..aebe33f 100644
--- a/safecode/tools/clang/test/Driver/apple-kext-i386.cpp
+++ b/safecode/tools/clang/test/Driver/apple-kext-i386.cpp
@@ -16,8 +16,8 @@
 // CHECK-MKERNEL: "-mkernel"
 
 // RUN: %clang -ccc-host-triple i386-apple-darwin10 \
-// RUN:   -Wno-self-assign -Wc++0x-extensions \
-// RUN:   -Wno-microsoft -Wmicrosoft \
+// RUN:   -Wno-self-assign -Wc++0x-extensions -Wno-microsoft -Wmicrosoft -Wvla \
+// RUN:   -faltivec -mthumb -mcpu=G4 -mlongcall -mno-longcall -msoft-float \
 // RUN:   -fapple-kext -### -fsyntax-only %s 2> %t
 // RUN: FileCheck --check-prefix=CHECK-UNSUPPORTED < %t %s
 
@@ -26,3 +26,10 @@
 // CHECK-UNSUPPORTED-NOT: "-Wc++0x-extensions"
 // CHECK-UNSUPPORTED-NOT: "-Wno-microsoft"
 // CHECK-UNSUPPORTED-NOT: "-Wmicrosoft"
+// CHECK-UNSUPPORTED-NOT: "-Wvla"
+// CHECK-UNSUPPORTED-NOT: "-faltivec"
+// CHECK-UNSUPPORTED-NOT: "-mthumb"
+// CHECK-UNSUPPORTED-NOT: "-mlongcall"
+// CHECK-UNSUPPORTED: "-mno-longcall"
+// CHECK-UNSUPPORTED: "-msoft-float"
+
diff --git a/safecode/tools/clang/test/Misc/warning-flags.c b/safecode/tools/clang/test/Misc/warning-flags.c
index b89ce41..e29fbea 100644
--- a/safecode/tools/clang/test/Misc/warning-flags.c
+++ b/safecode/tools/clang/test/Misc/warning-flags.c
@@ -17,7 +17,7 @@
 
 The list of warnings below should NEVER grow.  It should gradually shrink to 0.
 
-CHECK: Warnings without flags (312):
+CHECK: Warnings without flags (313):
 CHECK-NEXT:   auto_storage_class
 CHECK-NEXT:   backslash_newline_space
 CHECK-NEXT:   charize_microsoft_ext
@@ -230,6 +230,7 @@
 CHECK-NEXT:   warn_missing_dependent_template_keyword
 CHECK-NEXT:   warn_missing_exception_specification
 CHECK-NEXT:   warn_missing_whitespace_after_macro_name
+CHECK-NEXT:   warn_module_not_found
 CHECK-NEXT:   warn_multiple_method_decl
 CHECK-NEXT:   warn_no_constructor_for_refconst
 CHECK-NEXT:   warn_nonnull_pointers_only
diff --git a/safecode/tools/clang/test/Modules/Inputs/diamond_bottom.h b/safecode/tools/clang/test/Modules/Inputs/diamond_bottom.h
index 40afc9b..6351d02 100644
--- a/safecode/tools/clang/test/Modules/Inputs/diamond_bottom.h
+++ b/safecode/tools/clang/test/Modules/Inputs/diamond_bottom.h
@@ -1 +1,4 @@
+__import__ diamond_left;
+__import__ diamond_right;
+
 char bottom(char *x);
diff --git a/safecode/tools/clang/test/Modules/Inputs/diamond_left.h b/safecode/tools/clang/test/Modules/Inputs/diamond_left.h
index 9758b85..8da494c 100644
--- a/safecode/tools/clang/test/Modules/Inputs/diamond_left.h
+++ b/safecode/tools/clang/test/Modules/Inputs/diamond_left.h
@@ -1,3 +1,5 @@
+__import__ diamond_top;
+
 float left(float *);
 
 int top_left(char *c);
diff --git a/safecode/tools/clang/test/Modules/Inputs/diamond_right.h b/safecode/tools/clang/test/Modules/Inputs/diamond_right.h
index 9adeb6a..2efa277 100644
--- a/safecode/tools/clang/test/Modules/Inputs/diamond_right.h
+++ b/safecode/tools/clang/test/Modules/Inputs/diamond_right.h
@@ -1,3 +1,5 @@
+__import__ diamond_top;
+
 double right(double *);
 
 struct left_and_right {
diff --git a/safecode/tools/clang/test/Modules/Inputs/load_failure.h b/safecode/tools/clang/test/Modules/Inputs/load_failure.h
new file mode 100644
index 0000000..5bcb44d
--- /dev/null
+++ b/safecode/tools/clang/test/Modules/Inputs/load_failure.h
@@ -0,0 +1 @@
+int fail(int);
diff --git a/safecode/tools/clang/test/Modules/diamond.c b/safecode/tools/clang/test/Modules/diamond.c
index f9b283a..94381f2 100644
--- a/safecode/tools/clang/test/Modules/diamond.c
+++ b/safecode/tools/clang/test/Modules/diamond.c
@@ -1,4 +1,10 @@
+
+
+
 // in diamond-bottom.h: expected-note{{passing argument to parameter 'x' here}}
+
+__import__ diamond_bottom;
+
 void test_diamond(int i, float f, double d, char c) {
   top(&i);
   left(&f);
@@ -14,8 +20,8 @@
   lr.left = 17;
 }
 
-// RUN: %clang_cc1 -emit-pch -o %t_top.h.pch %S/Inputs/diamond_top.h
-// RUN: %clang_cc1 -import-module %t_top.h.pch -emit-pch -o %t_left.h.pch %S/Inputs/diamond_left.h
-// RUN: %clang_cc1 -import-module %t_top.h.pch -emit-pch -o %t_right.h.pch %S/Inputs/diamond_right.h
-// RUN: %clang_cc1 -import-module %t_left.h.pch -import-module %t_right.h.pch -emit-pch -o %t_bottom.h.pch %S/Inputs/diamond_bottom.h
-// RUN: %clang_cc1 -import-module %t_bottom.h.pch -verify %s 
+// RUN: %clang_cc1 -emit-module -o %T/diamond_top.pcm %S/Inputs/diamond_top.h
+// RUN: %clang_cc1 -I %T -emit-module -o %T/diamond_left.pcm %S/Inputs/diamond_left.h
+// RUN: %clang_cc1 -I %T -emit-module -o %T/diamond_right.pcm %S/Inputs/diamond_right.h
+// RUN: %clang_cc1 -I %T -emit-module -o %T/diamond_bottom.pcm %S/Inputs/diamond_bottom.h
+// RUN: %clang_cc1 -I %T %s -verify
diff --git a/safecode/tools/clang/test/Modules/load_failure.c b/safecode/tools/clang/test/Modules/load_failure.c
new file mode 100644
index 0000000..5b5df38
--- /dev/null
+++ b/safecode/tools/clang/test/Modules/load_failure.c
@@ -0,0 +1,17 @@
+#ifdef NONEXISTENT
+__import__ load_nonexistent;
+#endif
+
+#ifdef FAILURE
+__import__ load_failure;
+#endif
+
+// RUN: %clang_cc1 -x c++ -emit-module -o %T/load_failure.pcm %S/Inputs/load_failure.h
+// RUN: %clang_cc1 -I %T %s -DNONEXISTENT 2>&1 | FileCheck -check-prefix=CHECK-NONEXISTENT %s
+// CHECK-NONEXISTENT: load_failure.c:2:12: fatal error: module 'load_nonexistent' not found
+
+// RUN: %clang_cc1 -I %T %s -DFAILURE 2>&1 | FileCheck -check-prefix=CHECK-FAILURE %s
+// FIXME: Clean up diagnostic text below and give it a location
+// CHECK-FAILURE: error: C99 support was disabled in PCH file but is currently enabled
+
+
diff --git a/safecode/tools/clang/test/Modules/lookup.cpp b/safecode/tools/clang/test/Modules/lookup.cpp
index e9f52b7..cae6621 100644
--- a/safecode/tools/clang/test/Modules/lookup.cpp
+++ b/safecode/tools/clang/test/Modules/lookup.cpp
@@ -1,3 +1,9 @@
+
+#define import __import__
+import lookup_left_cxx;
+#define IMPORT(X) __import__ X
+IMPORT(lookup_right_cxx);
+
 void test(int i, float f) {
   // unqualified lookup
   f0(&i);
@@ -8,10 +14,10 @@
   ::f0(&f);
 }
 
-// RUN: %clang_cc1 -emit-module -x c++ -verify -o %t_lookup_left.h.pch %S/Inputs/lookup_left.hpp
-// RUN: %clang_cc1 -emit-module -x c++ -o %t_lookup_right.h.pch %S/Inputs/lookup_right.hpp
-// RUN: %clang_cc1 -x c++ -import-module %t_lookup_left.h.pch -import-module %t_lookup_right.h.pch -verify %s
-// RUN: %clang_cc1 -ast-print -x c++ -import-module %t_lookup_left.h.pch -import-module %t_lookup_right.h.pch %s | FileCheck -check-prefix=CHECK-PRINT %s
+// RUN: %clang_cc1 -emit-module -x c++ -verify -o %T/lookup_left_cxx.pcm %S/Inputs/lookup_left.hpp
+// RUN: %clang_cc1 -emit-module -x c++ -o %T/lookup_right_cxx.pcm %S/Inputs/lookup_right.hpp
+// RUN: %clang_cc1 -x c++ -I %T %s -verify
+// RUN: %clang_cc1 -ast-print -x c++ -I %T %s | FileCheck -check-prefix=CHECK-PRINT %s
 
 // CHECK-PRINT: int *f0(int *);
 // CHECK-PRINT: float *f0(float *);
diff --git a/safecode/tools/clang/test/Modules/lookup.m b/safecode/tools/clang/test/Modules/lookup.m
index 85f1dd9..48d0ba9 100644
--- a/safecode/tools/clang/test/Modules/lookup.m
+++ b/safecode/tools/clang/test/Modules/lookup.m
@@ -1,15 +1,17 @@
 
 // lookup_left.h: expected-note{{using}}
 // lookup_right.h: expected-note{{also found}}
+__import__ lookup_left_objc;
+__import__ lookup_right_objc;
 
 void test(id x) {
   [x method]; // expected-warning{{multiple methods named 'method' found}}
 }
 
-// RUN: %clang_cc1 -emit-module -x objective-c -o %t_lookup_left.h.pch %S/Inputs/lookup_left.h
-// RUN: %clang_cc1 -emit-module -x objective-c -o %t_lookup_right.h.pch %S/Inputs/lookup_right.h
-// RUN: %clang_cc1 -x objective-c -import-module %t_lookup_left.h.pch -import-module %t_lookup_right.h.pch -verify %s
-// RUN: %clang_cc1 -ast-print -x objective-c -import-module %t_lookup_left.h.pch -import-module %t_lookup_right.h.pch %s | FileCheck -check-prefix=CHECK-PRINT %s
+// RUN: %clang_cc1 -emit-module -x objective-c -o %T/lookup_left_objc.pcm %S/Inputs/lookup_left.h
+// RUN: %clang_cc1 -emit-module -x objective-c -o %T/lookup_right_objc.pcm %S/Inputs/lookup_right.h
+// RUN: %clang_cc1 -x objective-c -I %T -verify %s
+// RUN: %clang_cc1 -ast-print -x objective-c -I %T %s | FileCheck -check-prefix=CHECK-PRINT %s
 
 // CHECK-PRINT: - (int) method;
 // CHECK-PRINT: - (double) method
diff --git a/safecode/tools/clang/test/Rewriter/rewrite-forward-class.m b/safecode/tools/clang/test/Rewriter/rewrite-forward-class.m
index 5a50f53..1d3af6f 100644
--- a/safecode/tools/clang/test/Rewriter/rewrite-forward-class.m
+++ b/safecode/tools/clang/test/Rewriter/rewrite-forward-class.m
@@ -1,4 +1,5 @@
-// RUN: %clang_cc1 -rewrite-objc -o - %s
+// RUN: %clang_cc1 -x objective-c -Wno-return-type -fblocks -fms-extensions -rewrite-objc %s -o %t-rw.cpp
+// RUN: %clang_cc1 -fsyntax-only -fblocks -Wno-address-of-temporary -D"id=void*" -D"SEL=void*" -D"__declspec(X)=" %t-rw.cpp
 // rdar://6969189
 
 @class XX;
@@ -6,3 +7,29 @@
 @class ISyncClient, SMSession, ISyncManager, ISyncSession, SMDataclassInfo, SMClientInfo,
     DMCConfiguration, DMCStatusEntry;
 
+@interface QQ
+
+@end
+
+@interface SMDataclassInfo : QQ
+- (XX*) Meth;
+- (DMCStatusEntry*)Meth2;
+@end
+
+@implementation SMDataclassInfo
+- (XX*) Meth { return 0; }
+- (DMCStatusEntry*)Meth2 { return 0; }
+@end
+
+@interface YY 
+{
+  ISyncClient *p1;
+  ISyncSession *p2;
+}
+@property (copy) ISyncClient *p1;
+@end
+
+@implementation YY
+@synthesize p1;
+@end
+
diff --git a/safecode/tools/clang/test/Sema/format-strings.c b/safecode/tools/clang/test/Sema/format-strings.c
index b47d3ca..20c665b 100644
--- a/safecode/tools/clang/test/Sema/format-strings.c
+++ b/safecode/tools/clang/test/Sema/format-strings.c
@@ -372,3 +372,13 @@
   printf("%c", x); // no-warning
   printf("%hhu", y); // no-warning
 }
+
+// Test suppression of individual warnings.
+
+void test_suppress_invalid_specifier() {
+#pragma clang diagnostic push
+#pragma clang diagnostic ignored "-Wformat-invalid-specifier"
+  printf("%@", 12); // no-warning
+#pragma clang diagnostic pop
+}
+
diff --git a/safecode/tools/clang/test/SemaCXX/deleted-operator.cpp b/safecode/tools/clang/test/SemaCXX/deleted-operator.cpp
new file mode 100644
index 0000000..1c8a537
--- /dev/null
+++ b/safecode/tools/clang/test/SemaCXX/deleted-operator.cpp
@@ -0,0 +1,13 @@
+// RUN: %clang_cc1 -fsyntax-only -verify -std=c++0x %s
+
+struct PR10757 {
+  bool operator~() = delete; // expected-note {{explicitly deleted}}
+  bool operator==(const PR10757&) = delete; // expected-note {{explicitly deleted}}
+  operator float();
+};
+int PR10757f() {
+  PR10757 a1;
+  // FIXME: We get a ridiculous number of "built-in candidate" notes here...
+  if(~a1) {} // expected-error {{overload resolution selected deleted operator}} expected-note 6 {{built-in candidate}}
+  if(a1==a1) {} // expected-error {{overload resolution selected deleted operator}} expected-note 81 {{built-in candidate}}
+}
diff --git a/safecode/tools/clang/test/SemaObjC/arc-property-lifetime.m b/safecode/tools/clang/test/SemaObjC/arc-property-lifetime.m
index b1c84c7..88321e2 100644
--- a/safecode/tools/clang/test/SemaObjC/arc-property-lifetime.m
+++ b/safecode/tools/clang/test/SemaObjC/arc-property-lifetime.m
@@ -79,7 +79,7 @@
 
 @implementation Gorf
 @synthesize x;
-@synthesize y; // expected-error {{existing ivar 'y' for unsafe_unretained property 'y' must be __unsafe_unretained}}
+@synthesize y; // expected-error {{existing ivar 'y' for property 'y' with  assign attribute must be __unsafe_unretained}}
 @synthesize z;
 @end
 
@@ -94,7 +94,7 @@
 
 @implementation Gorf2
 @synthesize x;
-@synthesize y; // expected-error {{existing ivar 'y' for unsafe_unretained property 'y' must be __unsafe_unretained}}
+@synthesize y; // expected-error {{existing ivar 'y' for property 'y' with unsafe_unretained attribute must be __unsafe_unretained}}
 @synthesize z;
 @end
 
diff --git a/safecode/tools/clang/test/SemaObjC/default-synthesize.m b/safecode/tools/clang/test/SemaObjC/default-synthesize.m
index 33e3bd6..c9454d2 100644
--- a/safecode/tools/clang/test/SemaObjC/default-synthesize.m
+++ b/safecode/tools/clang/test/SemaObjC/default-synthesize.m
@@ -97,10 +97,10 @@
 // rdar://7920807
 @interface C @end
 @interface C (Category)
-@property int p; // expected-warning {{property 'p' requires method 'p' to be defined }} \
-                 // expected-warning {{property 'p' requires method 'setP:' to be defined}}
+@property int p; // expected-note 2 {{property declared here}}
 @end
-@implementation C (Category) // expected-note 2 {{implementation is here}}
+@implementation C (Category) // expected-warning {{property 'p' requires method 'p' to be defined}} \
+                             // expected-warning {{property 'p' requires method 'setP:' to be defined}}
 @end
 
 // Don't complain if a property is already @synthesized by usr.
diff --git a/safecode/tools/clang/test/SemaObjC/property-category-1.m b/safecode/tools/clang/test/SemaObjC/property-category-1.m
index 26e7313..6382826 100644
--- a/safecode/tools/clang/test/SemaObjC/property-category-1.m
+++ b/safecode/tools/clang/test/SemaObjC/property-category-1.m
@@ -37,7 +37,7 @@
 ///
 
 @interface I0
-@property(readonly) int p0;	// expected-warning {{property 'p0' requires method 'p0' to be defined}}
+@property(readonly) int p0;	// expected-note {{property declared here}}
 @end 
 
 @interface I0 (Cat0)
@@ -46,7 +46,7 @@
 @interface I0 (Cat1)
 @end 
   
-@implementation I0	// expected-note {{implementation is here}}
+@implementation I0	// expected-warning {{property 'p0' requires method 'p0' to be define}}
 - (void) foo {
   self.p0 = 0; // expected-error {{assigning to property with 'readonly' attribute not allowed}}
 }
diff --git a/safecode/tools/clang/test/SemaObjC/property-category-2.m b/safecode/tools/clang/test/SemaObjC/property-category-2.m
index e63672b..ecc3681 100644
--- a/safecode/tools/clang/test/SemaObjC/property-category-2.m
+++ b/safecode/tools/clang/test/SemaObjC/property-category-2.m
@@ -4,8 +4,7 @@
 
 @protocol MyProtocol
 @property float  myFloat;
-@property float  anotherFloat; // expected-warning {{property 'anotherFloat' requires method 'anotherFloat' to be defined - use @dynamic}} \
-                               // expected-warning {{property 'anotherFloat' requires method 'setAnotherFloat:' to be defined }}
+@property float  anotherFloat; // expected-note 2 {{property declared}}
 @end
 
 @interface MyObject { float anotherFloat; }
@@ -14,7 +13,8 @@
 @interface MyObject (CAT) <MyProtocol>
 @end
 
-@implementation MyObject (CAT)	// expected-note 2 {{implementation is here}}
+@implementation MyObject (CAT)	// expected-warning  {{property 'anotherFloat' requires method}} \
+                                // expected-warning {{property 'anotherFloat' requires method 'setAnotherFloat:'}}
 @dynamic myFloat;	// OK
 @synthesize anotherFloat; // expected-error {{@synthesize not allowed in a category's implementation}}
 @end
diff --git a/safecode/tools/clang/test/SemaObjC/property-category-impl.m b/safecode/tools/clang/test/SemaObjC/property-category-impl.m
index 9979497..21fdf1b 100644
--- a/safecode/tools/clang/test/SemaObjC/property-category-impl.m
+++ b/safecode/tools/clang/test/SemaObjC/property-category-impl.m
@@ -24,8 +24,8 @@
 @end
 
 @interface MyClass (public)
-@property(readwrite)    int        foo;	// expected-warning {{property 'foo' requires method 'setFoo:' to be defined }}
+@property(readwrite)    int        foo;	// expected-note {{property declared here}}
 @end
 
-@implementation MyClass (public)// expected-note {{implementation is here}}
+@implementation MyClass (public)// expected-warning {{property 'foo' requires method 'setFoo:' to be defined }}
 @end 
diff --git a/safecode/tools/clang/test/SemaObjC/property.m b/safecode/tools/clang/test/SemaObjC/property.m
index 4d00bd2..62291bb 100644
--- a/safecode/tools/clang/test/SemaObjC/property.m
+++ b/safecode/tools/clang/test/SemaObjC/property.m
@@ -11,8 +11,7 @@
 @end
 
 @interface I(CAT)
-@property int d1;	// expected-warning {{property 'd1' requires method 'd1' to be defined }} \
-			// expected-warning {{property 'd1' requires method 'setD1:' to be defined }}
+@property int d1;	// expected-note 2 {{property declared here}}
 @end
 
 @implementation I
@@ -23,7 +22,8 @@
 @synthesize name;	// OK! property with same name as an accessible ivar of same name
 @end
 
-@implementation I(CAT)  // expected-note 2 {{implementation is here}}
+@implementation I(CAT)  // expected-warning {{property 'd1' requires method 'd1' to be defined }} \
+                        // expected-warning {{property 'd1' requires method 'setD1:' to be defined }}
 @synthesize d1;		// expected-error {{@synthesize not allowed in a category's implementation}}
 @dynamic bad;		// expected-error {{property implementation must have its declaration in the category 'CAT'}}
 @end
diff --git a/safecode/tools/clang/test/SemaObjC/super-class-protocol-conformance.m b/safecode/tools/clang/test/SemaObjC/super-class-protocol-conformance.m
index bf19c83..32d5392 100644
--- a/safecode/tools/clang/test/SemaObjC/super-class-protocol-conformance.m
+++ b/safecode/tools/clang/test/SemaObjC/super-class-protocol-conformance.m
@@ -4,7 +4,7 @@
 @interface NSObject @end
 
 @protocol TopProtocol
-  @property (readonly) id myString; // expected-warning {{property 'myString' requires method 'myString' to be defined}}
+  @property (readonly) id myString; // expected-note {{property}}
 @end
 
 @protocol SubProtocol <TopProtocol>
@@ -21,7 +21,7 @@
 
 @implementation SubClass1 @end // Test1 - No Warning
 
-@implementation TopClass  // expected-note {{implementation is here}}
+@implementation TopClass  // expected-warning {{property 'myString' requires method 'myString' to be defined}}
 @end
 
 @implementation SubClass // Test3 - No Warning 
@@ -39,11 +39,11 @@
 @implementation SubClass4 @end	// Test 5 - No Warning
 
 @protocol NewProtocol
-  @property (readonly) id myNewString; // expected-warning {{property 'myNewString' requires method 'myNewString' to be defined}}
+  @property (readonly) id myNewString;  // expected-note {{property}}
 @end
 
 @interface SubClass5 : SubClass4 <NewProtocol> @end
-@implementation SubClass5 @end   // expected-note {{implementation is here}}
+@implementation SubClass5 @end   // expected-warning {{property 'myNewString' requires method 'myNewString' to be defined}}
 
 
 // Radar 8035776
@@ -54,10 +54,10 @@
 @end
 
 @protocol ProtocolWithProperty <SuperProtocol>
-@property (readonly, assign) id invalidationBacktrace; // expected-warning {{property 'invalidationBacktrace' requires method 'invalidationBacktrace' to be defined}}
+@property (readonly, assign) id invalidationBacktrace; // expected-note {{property}}
 @end
 
 @interface INTF : Super <ProtocolWithProperty> 
 @end
 
-@implementation INTF @end // expected-note {{implementation is here}}
+@implementation INTF @end // expected-warning{{property 'invalidationBacktrace' requires method 'invalidationBacktrace' to be defined}}
diff --git a/safecode/tools/clang/test/SemaObjC/unimplemented-protocol-prop.m b/safecode/tools/clang/test/SemaObjC/unimplemented-protocol-prop.m
index d3de50e..0805202 100644
--- a/safecode/tools/clang/test/SemaObjC/unimplemented-protocol-prop.m
+++ b/safecode/tools/clang/test/SemaObjC/unimplemented-protocol-prop.m
@@ -2,14 +2,12 @@
 
 @protocol PROTOCOL0
 @required
-@property float MyProperty0; // expected-warning {{property 'MyProperty0' requires method 'MyProperty0' to be defined }} \
-			     // expected-warning {{property 'MyProperty0' requires method 'setMyProperty0:' to be defined}}
+@property float MyProperty0; // expected-note 2 {{property declared}}
 @end
 
 @protocol PROTOCOL<PROTOCOL0>
 @required
-@property float MyProperty; // expected-warning {{property 'MyProperty' requires method 'MyProperty' to be defined}} \
-			// expected-warning {{property 'MyProperty' requires method 'setMyProperty:' to be defined}}
+@property float MyProperty; // expected-note 2 {{property declared}}
 @optional
 @property float OptMyProperty;
 @end
@@ -17,4 +15,7 @@
 @interface I <PROTOCOL>
 @end
 
-@implementation I @end // expected-note 4 {{implementation is here}}
+@implementation I @end // expected-warning {{property 'MyProperty0' requires method 'MyProperty0' to be defined}} \
+                       // expected-warning {{property 'MyProperty0' requires method 'setMyProperty0:' to be defined}}\
+                       // expected-warning {{property 'MyProperty' requires method 'MyProperty' to be defined}} \
+                       // expected-warning {{property 'MyProperty' requires method 'setMyProperty:' to be defined}}
diff --git a/safecode/tools/clang/test/SemaObjC/warn-missing-super.m b/safecode/tools/clang/test/SemaObjC/warn-missing-super.m
index 19c6b62..ff0c415 100644
--- a/safecode/tools/clang/test/SemaObjC/warn-missing-super.m
+++ b/safecode/tools/clang/test/SemaObjC/warn-missing-super.m
@@ -8,31 +8,43 @@
 - (void)dealloc {
   // Root class, shouldn't warn
 }
+- (void)finalize {
+  // Root class, shouldn't warn
+}
 @end
 
 @interface Subclass1 : NSObject
 - (void)dealloc;
+- (void)finalize;
 @end
 
 @implementation Subclass1
 - (void)dealloc {
 }
+- (void)finalize {
+}
 @end
 
 @interface Subclass2 : NSObject
 - (void)dealloc;
+- (void)finalize;
 @end
 
 @implementation Subclass2
 - (void)dealloc {
   [super dealloc];  // Shouldn't warn
 }
+- (void)finalize {
+  [super finalize];  // Shouldn't warn
+}
 @end
 
 // RUN: %clang_cc1 -fsyntax-only %s 2>&1 | FileCheck %s
-// CHECK: warn-missing-super.m:19:1: warning: method possibly missing a [super dealloc] call
-// CHECK: 1 warning generated.
+// CHECK: warn-missing-super.m:23:1: warning: method possibly missing a [super dealloc] call
+// CHECK: warn-missing-super.m:25:1: warning: method possibly missing a [super finalize] call
+// CHECK: 2 warnings generated.
 
 // RUN: %clang_cc1 -fsyntax-only -triple x86_64-apple-darwin10 -fobjc-nonfragile-abi -fobjc-arc %s 2>&1 | FileCheck --check-prefix=CHECK-ARC %s
-// CHECK-ARC: warn-missing-super.m:28:4: error: ARC forbids explicit message send of 'dealloc'
-// CHECK-ARC: 1 error generated.
+// CHECK-ARC: warn-missing-super.m:25:1: warning: method possibly missing a [super finalize] call
+// CHECK-ARC: warn-missing-super.m:35:4: error: ARC forbids explicit message send of 'dealloc'
+// CHECK-ARC: 1 warning and 1 error generated.
diff --git a/safecode/tools/clang/test/SemaTemplate/temp_arg_nontype.cpp b/safecode/tools/clang/test/SemaTemplate/temp_arg_nontype.cpp
index f90bb11..e93cfa3 100644
--- a/safecode/tools/clang/test/SemaTemplate/temp_arg_nontype.cpp
+++ b/safecode/tools/clang/test/SemaTemplate/temp_arg_nontype.cpp
@@ -320,3 +320,6 @@
   }
 
 }
+
+template <int& I> struct PR10766 { static int *ip; };
+template <int& I> int* PR10766<I>::ip = &I;
diff --git a/safecode/tools/clang/test/lit.cfg b/safecode/tools/clang/test/lit.cfg
index 850c0cf..8062aa7 100644
--- a/safecode/tools/clang/test/lit.cfg
+++ b/safecode/tools/clang/test/lit.cfg
@@ -165,7 +165,10 @@
 ###
 
 # Set available features we allow tests to conditionalize on.
-config.available_features.add('crash-recovery')
+#
+# As of 2011.08, crash-recovery tests still do not pass on FreeBSD.
+if platform.system() not in ['FreeBSD']:
+    config.available_features.add('crash-recovery')
 
 # Shell execution
 if platform.system() not in ['Windows'] or lit.getBashPath() != '':
diff --git a/safecode/tools/clang/tools/libclang/CIndex.cpp b/safecode/tools/clang/tools/libclang/CIndex.cpp
index c7e492e..c9b1fa8 100644
--- a/safecode/tools/clang/tools/libclang/CIndex.cpp
+++ b/safecode/tools/clang/tools/libclang/CIndex.cpp
@@ -1100,10 +1100,9 @@
 }
 
 bool CursorVisitor::VisitObjCClassDecl(ObjCClassDecl *D) {
-  for (ObjCClassDecl::iterator C = D->begin(), CEnd = D->end(); C != CEnd; ++C)
-    if (Visit(MakeCursorObjCClassRef(C->getInterface(), C->getLocation(), TU)))
+  if (Visit(MakeCursorObjCClassRef(D->getForwardInterfaceDecl(), 
+                                   D->getForwardDecl()->getLocation(), TU)))
       return true;
-
   return false;
 }
 
@@ -4219,8 +4218,8 @@
   Decl *D = Storage.get<Decl*>();
   if (UsingDecl *Using = dyn_cast<UsingDecl>(D))
     return Using->shadow_size();
-  if (ObjCClassDecl *Classes = dyn_cast<ObjCClassDecl>(D))
-    return Classes->size();
+  if (isa<ObjCClassDecl>(D))
+    return 1;
   if (ObjCForwardProtocolDecl *Protocols =dyn_cast<ObjCForwardProtocolDecl>(D))
     return Protocols->protocol_size();
   
@@ -4250,10 +4249,8 @@
     std::advance(Pos, index);
     return MakeCXCursor(cast<UsingShadowDecl>(*Pos)->getTargetDecl(), TU);
   }
-  
   if (ObjCClassDecl *Classes = dyn_cast<ObjCClassDecl>(D))
-    return MakeCXCursor(Classes->begin()[index].getInterface(), TU);
-  
+    return MakeCXCursor(Classes->getForwardInterfaceDecl(), TU);
   if (ObjCForwardProtocolDecl *Protocols = dyn_cast<ObjCForwardProtocolDecl>(D))
     return MakeCXCursor(Protocols->protocol_begin()[index], TU);
   
diff --git a/safecode/tools/clang/tools/scan-build/scan-build b/safecode/tools/clang/tools/scan-build/scan-build
index f835ca3..dae86f4 100755
--- a/safecode/tools/clang/tools/scan-build/scan-build
+++ b/safecode/tools/clang/tools/scan-build/scan-build
@@ -61,7 +61,7 @@
   Diag ("The analyzer encountered problems on some source files.\n");
   Diag ("Preprocessed versions of these sources were deposited in '$Dir/failures'.\n");
   Diag ("Please consider submitting a bug report using these files:\n");
-  Diag ("  http://clang.llvm.org/StaticAnalysisUsage.html#filingbugs\n")
+  Diag ("  http://clang-analyzer.llvm.org/filing_bugs.html\n")
 }
 
 sub DieDiag {
@@ -802,7 +802,7 @@
       }
       print OUT "</table>\n";
     }    
-    print OUT "<p>Please consider submitting preprocessed files as <a href=\"http://clang.llvm.org/StaticAnalysisUsage.html#filingbugs\">bug reports</a>. <!-- REPORTCRASHES --> </p>\n";
+    print OUT "<p>Please consider submitting preprocessed files as <a href=\"http://clang-analyzer.llvm.org/filing_bugs.html\">bug reports</a>. <!-- REPORTCRASHES --> </p>\n";
   }
   
   print OUT "</body></html>\n";