[cfe-commits] [clang-tools-extra] r173178 - in /clang-tools-extra/trunk: cpp11-migrate/ cpp11-migrate/UseNullptr/ test/cpp11-migrate/Combined/ test/cpp11-migrate/UseNullptr/ test/cpp11-migrate/UseNullptr/Inputs/

Edwin Vane edwin.vane at intel.com
Tue Jan 22 10:31:50 PST 2013


Author: revane
Date: Tue Jan 22 12:31:49 2013
New Revision: 173178

URL: http://llvm.org/viewvc/llvm-project?rev=173178&view=rev
Log:
Add use-nullptr transform to cpp11-migrate

This transform converts the usage of null pointer constants (e.g. NULL, 0,
etc.) in legacy C++ code and converts them to use the new C++11 nullptr
keyword.
- Added use-nullptr transform.
- Added C++11 support to the final syntax check. Used ArgumentAdjuster class to
  add -std=c++11 option to the command line options.
- Added tests for use-nullptr transform.
- Added tests that exercises both loop-convert and use-nullptr in the source
  file.

TODO: There's a known bug when using both -loop-convert and -use-nullptr at the
      same time.

Author: Tareq A Siraj <tareq.a.siraj at intel.com>
Reviewers: klimek, gribozavr

Added:
    clang-tools-extra/trunk/cpp11-migrate/UseNullptr/
    clang-tools-extra/trunk/cpp11-migrate/UseNullptr/NullptrActions.cpp
    clang-tools-extra/trunk/cpp11-migrate/UseNullptr/NullptrActions.h
    clang-tools-extra/trunk/cpp11-migrate/UseNullptr/NullptrMatchers.cpp
    clang-tools-extra/trunk/cpp11-migrate/UseNullptr/NullptrMatchers.h
    clang-tools-extra/trunk/cpp11-migrate/UseNullptr/UseNullptr.cpp
    clang-tools-extra/trunk/cpp11-migrate/UseNullptr/UseNullptr.h
    clang-tools-extra/trunk/test/cpp11-migrate/Combined/
    clang-tools-extra/trunk/test/cpp11-migrate/Combined/combined.cpp
    clang-tools-extra/trunk/test/cpp11-migrate/UseNullptr/
    clang-tools-extra/trunk/test/cpp11-migrate/UseNullptr/Inputs/
    clang-tools-extra/trunk/test/cpp11-migrate/UseNullptr/Inputs/basic.h
    clang-tools-extra/trunk/test/cpp11-migrate/UseNullptr/basic.cpp
    clang-tools-extra/trunk/test/cpp11-migrate/UseNullptr/basic_failing.cpp
Modified:
    clang-tools-extra/trunk/cpp11-migrate/CMakeLists.txt
    clang-tools-extra/trunk/cpp11-migrate/Cpp11Migrate.cpp
    clang-tools-extra/trunk/cpp11-migrate/Makefile
    clang-tools-extra/trunk/cpp11-migrate/Transforms.cpp

Modified: clang-tools-extra/trunk/cpp11-migrate/CMakeLists.txt
URL: http://llvm.org/viewvc/llvm-project/clang-tools-extra/trunk/cpp11-migrate/CMakeLists.txt?rev=173178&r1=173177&r2=173178&view=diff
==============================================================================
--- clang-tools-extra/trunk/cpp11-migrate/CMakeLists.txt (original)
+++ clang-tools-extra/trunk/cpp11-migrate/CMakeLists.txt Tue Jan 22 12:31:49 2013
@@ -12,6 +12,9 @@
 file(GLOB_RECURSE LoopConvertSources "LoopConvert/*.cpp")
 list(APPEND Cpp11MigrateSources ${LoopConvertSources})
 
+file(GLOB_RECURSE UseNullptrSources "UseNullptr/*.cpp")
+list(APPEND Cpp11MigrateSources ${UseNullptrSources})
+
 add_clang_executable(cpp11-migrate
   ${Cpp11MigrateSources}
   )

Modified: clang-tools-extra/trunk/cpp11-migrate/Cpp11Migrate.cpp
URL: http://llvm.org/viewvc/llvm-project/clang-tools-extra/trunk/cpp11-migrate/Cpp11Migrate.cpp?rev=173178&r1=173177&r2=173178&view=diff
==============================================================================
--- clang-tools-extra/trunk/cpp11-migrate/Cpp11Migrate.cpp (original)
+++ clang-tools-extra/trunk/cpp11-migrate/Cpp11Migrate.cpp Tue Jan 22 12:31:49 2013
@@ -49,6 +49,15 @@
                clEnumValEnd),
     cl::init(RL_Reasonable));
 
+class EndSyntaxArgumentsAdjuster : public ArgumentsAdjuster {
+  CommandLineArguments Adjust(const CommandLineArguments &Args) {
+    CommandLineArguments AdjustedArgs = Args;
+    AdjustedArgs.push_back("-fsyntax-only");
+    AdjustedArgs.push_back("-std=c++11");
+    return AdjustedArgs;
+  }
+};
+
 int main(int argc, const char **argv) {
   llvm::sys::PrintStackTraceOnErrorSignal();
   Transforms TransformManager;
@@ -102,6 +111,10 @@
   // Final Syntax check.
   ClangTool EndSyntaxTool(OptionsParser.getCompilations(),
                           OptionsParser.getSourcePathList());
+
+  // Add c++11 support to clang.
+  EndSyntaxTool.setArgumentsAdjuster(new EndSyntaxArgumentsAdjuster);
+
   for (FileContentsByPath::const_iterator I = InputFileStates->begin(),
                                           E = InputFileStates->end();
        I != E; ++I) {

Modified: clang-tools-extra/trunk/cpp11-migrate/Makefile
URL: http://llvm.org/viewvc/llvm-project/clang-tools-extra/trunk/cpp11-migrate/Makefile?rev=173178&r1=173177&r2=173178&view=diff
==============================================================================
--- clang-tools-extra/trunk/cpp11-migrate/Makefile (original)
+++ clang-tools-extra/trunk/cpp11-migrate/Makefile Tue Jan 22 12:31:49 2013
@@ -24,6 +24,8 @@
 # transform subdirectories. See below for more on .objdir.
 SOURCES += $(addprefix LoopConvert/,$(notdir $(wildcard $(PROJ_SRC_DIR)/LoopConvert/*.cpp)))
 BUILT_SOURCES = $(ObjDir)/LoopConvert/.objdir
+SOURCES += $(addprefix UseNullptr/,$(notdir $(wildcard $(PROJ_SRC_DIR)/UseNullptr/*.cpp)))
+BUILT_SOURCES += $(ObjDir)/UseNullptr/.objdir
 
 LINK_COMPONENTS := $(TARGETS_TO_BUILD) asmparser bitreader support mc
 USEDLIBS = clangTooling.a clangFrontend.a clangSerialization.a clangDriver.a \

Modified: clang-tools-extra/trunk/cpp11-migrate/Transforms.cpp
URL: http://llvm.org/viewvc/llvm-project/clang-tools-extra/trunk/cpp11-migrate/Transforms.cpp?rev=173178&r1=173177&r2=173178&view=diff
==============================================================================
--- clang-tools-extra/trunk/cpp11-migrate/Transforms.cpp (original)
+++ clang-tools-extra/trunk/cpp11-migrate/Transforms.cpp Tue Jan 22 12:31:49 2013
@@ -14,6 +14,7 @@
 
 #include "Transforms.h"
 #include "LoopConvert/LoopConvert.h"
+#include "UseNullptr/UseNullptr.h"
 
 namespace cl = llvm::cl;
 
@@ -40,6 +41,12 @@
         cl::desc("Make use of range-based for loops where possible")),
       &ConstructTransform<LoopConvertTransform>));
 
+  Options.push_back(
+    OptionVec::value_type(
+      new cl::opt<bool>("use-nullptr",
+        cl::desc("Make use of nullptr keyword where possible")),
+      &ConstructTransform<UseNullptrTransform>));
+
   // Add more transform options here.
 }
 

Added: clang-tools-extra/trunk/cpp11-migrate/UseNullptr/NullptrActions.cpp
URL: http://llvm.org/viewvc/llvm-project/clang-tools-extra/trunk/cpp11-migrate/UseNullptr/NullptrActions.cpp?rev=173178&view=auto
==============================================================================
--- clang-tools-extra/trunk/cpp11-migrate/UseNullptr/NullptrActions.cpp (added)
+++ clang-tools-extra/trunk/cpp11-migrate/UseNullptr/NullptrActions.cpp Tue Jan 22 12:31:49 2013
@@ -0,0 +1,115 @@
+//===-- nullptr-convert/NullptrActions.cpp - Matcher callback -------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+///
+///  \file
+///  \brief This file contains the definition of the NullptrFixer class which is
+///  used as an ASTMatcher callback. Also within this file is a helper AST
+///  visitor class used to identify sequences of explicit casts.
+///
+//===----------------------------------------------------------------------===//
+
+#include "NullptrActions.h"
+#include "NullptrMatchers.h"
+
+#include "clang/AST/ASTContext.h"
+#include "clang/AST/RecursiveASTVisitor.h"
+
+
+using namespace clang::ast_matchers;
+using namespace clang::tooling;
+using namespace clang;
+
+/// \brief Looks for a sequences of 0 or more explicit casts with an implicit
+/// null-to-pointer cast within.
+///
+/// The matcher this visitor is used with will find a top-most explicit cast
+/// (i.e. it has no explicit casts as an ancestor) where an implicit cast is
+/// nested within. However, there is no guarantee that only explicit casts
+/// exist between the found top-most explicit cast and the possibly more than
+/// one nested implicit cast. This visitor finds all cast sequences with an
+/// implicit cast to null within and creates a replacement.
+class CastSequenceVisitor : public RecursiveASTVisitor<CastSequenceVisitor> {
+public:
+  CastSequenceVisitor(tooling::Replacements &R, SourceManager &SM,
+                      unsigned &AcceptedChanges) :
+    Replace(R), SM(SM), AcceptedChanges(AcceptedChanges), FirstCast(0) {}
+
+  // Only VisitStmt is overridden as we shouldn't find other base AST types
+  // within a cast expression.
+  bool VisitStmt(Stmt *S) {
+    CastExpr *C = dyn_cast<CastExpr>(S);
+
+    if (!C) {
+      ResetFirstCast();
+      return true;
+    } else if (!FirstCast) {
+      FirstCast = C;
+    }
+
+    if (C->getCastKind() == CK_NullToPointer ||
+        C->getCastKind() == CK_NullToMemberPointer) {
+      SourceLocation StartLoc = FirstCast->getLocStart();
+      SourceLocation EndLoc = FirstCast->getLocEnd();
+
+      if (SM.getFileID(StartLoc) == SM.getFileID(EndLoc) &&
+          SM.isFromMainFile(StartLoc) && SM.isFromMainFile(EndLoc)) {
+        CharSourceRange Range(SourceRange(StartLoc, EndLoc), true);
+        Replace.insert(tooling::Replacement(SM, Range, "nullptr"));
+        ++AcceptedChanges;
+      }
+      ResetFirstCast();
+    }
+
+    return true;
+  }
+
+private:
+  void ResetFirstCast() { FirstCast = 0; }
+
+private:
+  tooling::Replacements &Replace;
+  SourceManager &SM;
+  unsigned &AcceptedChanges;
+  CastExpr *FirstCast;
+};
+
+
+void NullptrFixer::run(const ast_matchers::MatchFinder::MatchResult &Result) {
+  SourceManager &SM = *Result.SourceManager;
+
+  const CastExpr *NullCast = Result.Nodes.getNodeAs<CastExpr>(CastSequence);
+  if (NullCast) {
+    // Given an explicit cast with an implicit null-to-pointer cast within
+    // use CastSequenceVisitor to identify sequences of explicit casts that can
+    // be converted into 'nullptr'.
+    CastSequenceVisitor Visitor(Replace, SM, AcceptedChanges);
+    Visitor.TraverseStmt(const_cast<CastExpr*>(NullCast));
+  }
+
+  const CastExpr *Cast = Result.Nodes.getNodeAs<CastExpr>(ImplicitCastNode);
+  if (Cast) {
+    SourceLocation StartLoc = Cast->getLocStart();
+    SourceLocation EndLoc = Cast->getLocEnd();
+
+    if (SM.getFileID(StartLoc) != SM.getFileID(EndLoc))
+      return;
+
+    if (StartLoc.isMacroID())
+      StartLoc = SM.getExpansionLoc(StartLoc);
+    if (EndLoc.isMacroID())
+      EndLoc = SM.getExpansionLoc(EndLoc);
+
+    if (!SM.isFromMainFile(StartLoc) || !SM.isFromMainFile(EndLoc))
+      return;
+
+    CharSourceRange Range(SourceRange(StartLoc, EndLoc), true);
+    Replace.insert(tooling::Replacement(SM, Range, "nullptr"));
+    ++AcceptedChanges;
+  }
+}

Added: clang-tools-extra/trunk/cpp11-migrate/UseNullptr/NullptrActions.h
URL: http://llvm.org/viewvc/llvm-project/clang-tools-extra/trunk/cpp11-migrate/UseNullptr/NullptrActions.h?rev=173178&view=auto
==============================================================================
--- clang-tools-extra/trunk/cpp11-migrate/UseNullptr/NullptrActions.h (added)
+++ clang-tools-extra/trunk/cpp11-migrate/UseNullptr/NullptrActions.h Tue Jan 22 12:31:49 2013
@@ -0,0 +1,40 @@
+//===-- nullptr-convert/NullptrActions.h - Matcher callback ------*- C++ -*-==//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+///
+///  \file
+///  \brief This file contains the declaration of the NullptrFixer class which
+///  is used as a ASTMatcher callback.
+///
+//===----------------------------------------------------------------------===//
+#ifndef LLVM_TOOLS_CLANG_TOOLS_EXTRA_CPP11_MIGRATE_NULLPTR_ACTIONS_H
+#define LLVM_TOOLS_CLANG_TOOLS_EXTRA_CPP11_MIGRATE_NULLPTR_ACTIONS_H
+
+#include "Transform.h"
+#include "clang/ASTMatchers/ASTMatchFinder.h"
+#include "clang/Tooling/Refactoring.h"
+
+/// \brief The callback to be used for nullptr migration matchers.
+///
+class NullptrFixer : public clang::ast_matchers::MatchFinder::MatchCallback {
+public:
+  NullptrFixer(clang::tooling::Replacements &Replace,
+               unsigned &AcceptedChanges,
+               RiskLevel) :
+  Replace(Replace),
+  AcceptedChanges(AcceptedChanges) { }
+
+  /// \brief Entry point to the callback called when matches are made.
+  virtual void run(const clang::ast_matchers::MatchFinder::MatchResult &Result);
+
+private:
+  clang::tooling::Replacements &Replace;
+  unsigned &AcceptedChanges;
+};
+
+#endif // LLVM_TOOLS_CLANG_TOOLS_EXTRA_CPP11_MIGRATE_NULLPTR_ACTIONS_H

Added: clang-tools-extra/trunk/cpp11-migrate/UseNullptr/NullptrMatchers.cpp
URL: http://llvm.org/viewvc/llvm-project/clang-tools-extra/trunk/cpp11-migrate/UseNullptr/NullptrMatchers.cpp?rev=173178&view=auto
==============================================================================
--- clang-tools-extra/trunk/cpp11-migrate/UseNullptr/NullptrMatchers.cpp (added)
+++ clang-tools-extra/trunk/cpp11-migrate/UseNullptr/NullptrMatchers.cpp Tue Jan 22 12:31:49 2013
@@ -0,0 +1,53 @@
+//===-- nullptr-convert/Matchers.cpp - Matchers for null casts ------------===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+///
+///  \file
+///  \brief This file contains the definitions for matcher-generating functions
+///  and a custom AST_MATCHER for identifying casts of type CK_NullTo*.
+///
+//===----------------------------------------------------------------------===//
+#include "NullptrMatchers.h"
+#include "clang/AST/ASTContext.h"
+
+using namespace clang::ast_matchers;
+using namespace clang;
+
+const char *ImplicitCastNode = "cast";
+const char *CastSequence = "sequence";
+
+namespace clang {
+namespace ast_matchers {
+/// \brief Matches cast expressions that have a cast kind of CK_NullToPointer
+/// or CK_NullToMemberPointer.
+///
+/// Given
+/// \code
+///   int *p = 0;
+/// \endcode
+/// implicitCastExpr(isNullToPointer()) matches the implicit cast clang adds
+/// around \c 0.
+AST_MATCHER(CastExpr, isNullToPointer) {
+  return Node.getCastKind() == CK_NullToPointer ||
+    Node.getCastKind() == CK_NullToMemberPointer;
+}
+
+} // end namespace ast_matchers
+} // end namespace clang
+
+StatementMatcher makeImplicitCastMatcher() {
+  return implicitCastExpr(allOf(unless(hasAncestor(explicitCastExpr())),
+                                isNullToPointer())).bind(ImplicitCastNode);
+}
+
+StatementMatcher makeCastSequenceMatcher() {
+  return explicitCastExpr(
+            allOf(unless(hasAncestor(explicitCastExpr())),
+                  hasDescendant(implicitCastExpr(isNullToPointer())))
+            ).bind(CastSequence);
+}

Added: clang-tools-extra/trunk/cpp11-migrate/UseNullptr/NullptrMatchers.h
URL: http://llvm.org/viewvc/llvm-project/clang-tools-extra/trunk/cpp11-migrate/UseNullptr/NullptrMatchers.h?rev=173178&view=auto
==============================================================================
--- clang-tools-extra/trunk/cpp11-migrate/UseNullptr/NullptrMatchers.h (added)
+++ clang-tools-extra/trunk/cpp11-migrate/UseNullptr/NullptrMatchers.h Tue Jan 22 12:31:49 2013
@@ -0,0 +1,38 @@
+//===-- nullptr-convert/Matchers.h - Matchers for null casts ---*- C++ -*--===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+///
+///  \file
+///  \brief This file contains the declarations for matcher-generating functions
+///  and names for bound nodes found by AST matchers.
+///
+//===----------------------------------------------------------------------===//
+#ifndef LLVM_TOOLS_CLANG_TOOLS_EXTRA_CPP11_MIGRATE_USE_NULLPTR_MATCHERS_H
+#define LLVM_TOOLS_CLANG_TOOLS_EXTRA_CPP11_MIGRATE_USE_NULLPTR_MATCHERS_H
+
+#include "clang/ASTMatchers/ASTMatchers.h"
+
+// Names to bind with matched expressions.
+extern const char *ImplicitCastNode;
+extern const char *CastSequence;
+
+/// \brief Create a matcher to find the implicit casts clang inserts
+/// when writing null to a pointer.
+///
+/// However, don't match those implicit casts that have explicit casts as
+/// an ancestor. Explicit casts are handled by makeCastSequenceMatcher().
+clang::ast_matchers::StatementMatcher makeImplicitCastMatcher();
+
+/// \brief Create a matcher that finds the head of a sequence of nested explicit
+/// casts that have an implicit cast to null within.
+///
+/// This matcher is necessary so that an entire sequence of explicit casts can
+/// be replaced instead of just the inner-most implicit cast.
+clang::ast_matchers::StatementMatcher makeCastSequenceMatcher();
+
+#endif // LLVM_TOOLS_CLANG_TOOLS_EXTRA_CPP11_MIGRATE_USE_NULLPTR_MATCHERS_H

Added: clang-tools-extra/trunk/cpp11-migrate/UseNullptr/UseNullptr.cpp
URL: http://llvm.org/viewvc/llvm-project/clang-tools-extra/trunk/cpp11-migrate/UseNullptr/UseNullptr.cpp?rev=173178&view=auto
==============================================================================
--- clang-tools-extra/trunk/cpp11-migrate/UseNullptr/UseNullptr.cpp (added)
+++ clang-tools-extra/trunk/cpp11-migrate/UseNullptr/UseNullptr.cpp Tue Jan 22 12:31:49 2013
@@ -0,0 +1,68 @@
+//===-- LoopConvert/LoopConvert.cpp - C++11 for-loop migration --*- C++ -*-===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+///
+/// \file
+/// \brief This file provides the implementation of the UseNullptrTransform
+/// class.
+///
+//===----------------------------------------------------------------------===//
+
+#include "UseNullptr.h"
+#include "NullptrActions.h"
+#include "NullptrMatchers.h"
+#include "clang/Frontend/FrontendActions.h"
+#include "clang/Rewrite/Core/Rewriter.h"
+#include "clang/Tooling/Refactoring.h"
+#include "clang/Tooling/Tooling.h"
+
+using clang::ast_matchers::MatchFinder;
+using namespace clang::tooling;
+using namespace clang;
+
+int UseNullptrTransform::apply(const FileContentsByPath &InputStates,
+                               RiskLevel MaxRisk,
+                               const CompilationDatabase &Database,
+                               const std::vector<std::string> &SourcePaths,
+                               FileContentsByPath &ResultStates) {
+  RefactoringTool UseNullptrTool(Database, SourcePaths);
+
+  for (FileContentsByPath::const_iterator I = InputStates.begin(),
+       E = InputStates.end();
+       I != E; ++I) {
+    UseNullptrTool.mapVirtualFile(I->first, I->second);
+  }
+
+  unsigned AcceptedChanges = 0;
+
+  MatchFinder Finder;
+  NullptrFixer Fixer(UseNullptrTool.getReplacements(),
+                     AcceptedChanges,
+                     MaxRisk);
+
+  Finder.addMatcher(makeImplicitCastMatcher(), &Fixer);
+  Finder.addMatcher(makeCastSequenceMatcher(), &Fixer);
+
+  if (int result = UseNullptrTool.run(newFrontendActionFactory(&Finder))) {
+    llvm::errs() << "Error encountered during translation.\n";
+    return result;
+  }
+
+  RewriterContainer Rewrite(UseNullptrTool.getFiles());
+
+  // FIXME: Do something if some replacements didn't get applied?
+  UseNullptrTool.applyAllReplacements(Rewrite.getRewriter());
+
+  collectResults(Rewrite.getRewriter(), ResultStates);
+
+  if (AcceptedChanges > 0) {
+    setChangesMade();
+  }
+
+  return 0;
+}

Added: clang-tools-extra/trunk/cpp11-migrate/UseNullptr/UseNullptr.h
URL: http://llvm.org/viewvc/llvm-project/clang-tools-extra/trunk/cpp11-migrate/UseNullptr/UseNullptr.h?rev=173178&view=auto
==============================================================================
--- clang-tools-extra/trunk/cpp11-migrate/UseNullptr/UseNullptr.h (added)
+++ clang-tools-extra/trunk/cpp11-migrate/UseNullptr/UseNullptr.h Tue Jan 22 12:31:49 2013
@@ -0,0 +1,34 @@
+//===-- LoopConvert/LoopConvert.h - C++11 for-loop migration ----*- C++ -*-===//
+//
+//                     The LLVM Compiler Infrastructure
+//
+// This file is distributed under the University of Illinois Open Source
+// License. See LICENSE.TXT for details.
+//
+//===----------------------------------------------------------------------===//
+///
+/// \file
+/// \brief This file provides the definition of the UseNullptrTransform
+/// class which is the main interface to the use-nullptr transform
+/// that tries to make use of nullptr where possible.
+///
+//===----------------------------------------------------------------------===//
+#ifndef LLVM_TOOLS_CLANG_TOOLS_EXTRA_CPP11_MIGRATE_USE_NULLPTR_H
+#define LLVM_TOOLS_CLANG_TOOLS_EXTRA_CPP11_MIGRATE_USE_NULLPTR_H
+
+#include "Transform.h"
+#include "llvm/Support/Compiler.h" // For LLVM_OVERRIDE
+
+/// \brief Subclass of Transform that transforms null pointer constants into
+/// C++11's nullptr keyword where possible.
+class UseNullptrTransform : public Transform {
+public:
+  /// \see Transform::run().
+  virtual int apply(const FileContentsByPath &InputStates,
+                    RiskLevel MaxRiskLEvel,
+                    const clang::tooling::CompilationDatabase &Database,
+                    const std::vector<std::string> &SourcePaths,
+                    FileContentsByPath &ResultStates) LLVM_OVERRIDE;
+};
+
+#endif // LLVM_TOOLS_CLANG_TOOLS_EXTRA_CPP11_MIGRATE_USE_NULLPTR_H

Added: clang-tools-extra/trunk/test/cpp11-migrate/Combined/combined.cpp
URL: http://llvm.org/viewvc/llvm-project/clang-tools-extra/trunk/test/cpp11-migrate/Combined/combined.cpp?rev=173178&view=auto
==============================================================================
--- clang-tools-extra/trunk/test/cpp11-migrate/Combined/combined.cpp (added)
+++ clang-tools-extra/trunk/test/cpp11-migrate/Combined/combined.cpp Tue Jan 22 12:31:49 2013
@@ -0,0 +1,47 @@
+// RUN: grep -Ev "// *[A-Z-]+:" %s > %t.cpp
+// RUN: grep -Ev "// *[A-Z-]+:" %s > %t_risky.cpp
+// RUN: cpp11-migrate -loop-convert -use-nullptr %t.cpp --
+// RUN: FileCheck -input-file=%t.cpp %s
+// RUN: cpp11-migrate -loop-convert -use-nullptr -risk=risky %t_risky.cpp --
+// RUN: FileCheck -check-prefix=RISKY -input-file=%t_risky.cpp %s
+// REQUIRES: shell
+// XFAIL: *
+
+#define NULL 0
+
+struct T {
+  struct iterator {
+    int *& operator*();
+    const int *& operator*() const;
+    iterator & operator++();
+    bool operator!=(const iterator &other);
+    void insert(int *);
+    int *x;
+  };
+
+  iterator begin();
+  iterator end();
+};
+
+void test_loopconvert_and_nullptr_iterator() {
+  T t;
+
+  for (T::iterator it = t.begin(); it != t.end(); ++it) {
+    *it = NULL;
+  }
+
+  // CHECK: for ({{[a-zA-Z_ ]+&? ?}}[[VAR:[a-z_]+]] : t)
+  // CHECK-NEXT: [[VAR]] = nullptr;
+}
+
+void test_loopconvert_and_nullptr_risky() {
+  const int N = 10;
+  int *(*pArr)[N];
+
+  for (int i = 0; i < N; ++i) {
+    (*pArr)[i] = NULL;
+  }
+
+  // RISKY: for (auto & [[VAR:[a-z_]+]] : *pArr)
+  // RISKY-NEXT: [[VAR:[a-z_]+]] = nullptr;
+}

Added: clang-tools-extra/trunk/test/cpp11-migrate/UseNullptr/Inputs/basic.h
URL: http://llvm.org/viewvc/llvm-project/clang-tools-extra/trunk/test/cpp11-migrate/UseNullptr/Inputs/basic.h?rev=173178&view=auto
==============================================================================
--- clang-tools-extra/trunk/test/cpp11-migrate/UseNullptr/Inputs/basic.h (added)
+++ clang-tools-extra/trunk/test/cpp11-migrate/UseNullptr/Inputs/basic.h Tue Jan 22 12:31:49 2013
@@ -0,0 +1,2 @@
+int *global_p = 0;
+// CHECK: int *global_p = 0;

Added: clang-tools-extra/trunk/test/cpp11-migrate/UseNullptr/basic.cpp
URL: http://llvm.org/viewvc/llvm-project/clang-tools-extra/trunk/test/cpp11-migrate/UseNullptr/basic.cpp?rev=173178&view=auto
==============================================================================
--- clang-tools-extra/trunk/test/cpp11-migrate/UseNullptr/basic.cpp (added)
+++ clang-tools-extra/trunk/test/cpp11-migrate/UseNullptr/basic.cpp Tue Jan 22 12:31:49 2013
@@ -0,0 +1,181 @@
+// RUN: grep -Ev "// *[A-Z-]+:" %s > %t.cpp
+// RUN: grep -Ev "// *[A-Z-]+:" %S/Inputs/basic.h > %T/basic.h
+// RUN: cpp11-migrate -use-nullptr %t.cpp -- -I %S
+// RUN: FileCheck -input-file=%t.cpp %s
+// RUN: FileCheck -input-file=%T/basic.h %S/Inputs/basic.h
+// REQUIRES: shell
+
+#include "Inputs/basic.h"
+
+const unsigned int g_null = 0;
+#define NULL 0
+
+void test_assignment() {
+  int *p1 = 0;
+  // CHECK: int *p1 = nullptr;
+  p1 = 0;
+  // CHECK: p1 = nullptr;
+
+  int *p2 = NULL;
+  // CHECK: int *p2 = nullptr;
+
+  p2 = p1;
+  // CHECK: p2 = p1;
+
+  const int null = 0;
+  int *p3 = null;
+  // CHECK: int *p3 = nullptr;
+
+  p3 = NULL;
+  // CHECK: p3 = nullptr;
+
+  int *p4 = p3;
+  // CHECK: int *p4 = p3;
+
+  p4 = null;
+  // CHECK: p4 = nullptr;
+
+  int i1 = 0;
+  // CHECK: int i1 = 0;
+
+  int i2 = NULL;
+  // CHECK: int i2 = NULL;
+
+  int i3 = null;
+  // CHECK: int i3 = null;
+
+  int *p5, *p6, *p7;
+  p5 = p6 = p7 = NULL;
+  // CHECK: p5 = p6 = p7 = nullptr;
+}
+
+struct Foo {
+  Foo(int *p = NULL) : m_p1(p) {}
+  // CHECK: Foo(int *p = nullptr) : m_p1(p) {}
+
+  void bar(int *p = 0) {}
+  // CHECK: void bar(int *p = nullptr) {}
+
+  void baz(int i = 0) {}
+  // CHECK: void baz(int i = 0) {}
+
+  int *m_p1;
+  static int *m_p2;
+};
+
+int *Foo::m_p2 = NULL;
+// CHECK: int *Foo::m_p2 = nullptr;
+
+template <typename T>
+struct Bar {
+  Bar(T *p) : m_p(p) {
+    m_p = static_cast<T*>(NULL);
+    // CHECK: m_p = nullptr;
+
+    m_p = static_cast<T*>(reinterpret_cast<int*>((void*)NULL));
+    // CHECK: m_p = nullptr;
+
+    m_p = static_cast<T*>(p ? p : static_cast<void*>(g_null));
+    // CHECK: m_p = static_cast<T*>(p ? p : nullptr);
+
+    T *p2 = static_cast<T*>(reinterpret_cast<int*>((void*)NULL));
+    // CHECK: T *p2 = nullptr;
+
+    m_p = NULL;
+    // CHECK: m_p = nullptr;
+
+    int i = static_cast<int>(0.f);
+    // CHECK: int i = static_cast<int>(0.f);
+    T *i2 = static_cast<int>(0.f);
+    // CHECK: T *i2 = nullptr;
+  }
+
+  T *m_p;
+};
+
+struct Baz {
+  Baz() : i(0) {}
+  int i;
+};
+
+void test_cxx_cases() {
+  Foo f(g_null);
+  // CHECK: Foo f(nullptr);
+
+  f.bar(NULL);
+  // CHECK: f.bar(nullptr);
+
+  f.baz(g_null);
+  // CHECK: f.baz(g_null);
+
+  f.m_p1 = 0;
+  // CHECK: f.m_p1 = nullptr;
+
+  Bar<int> b(g_null);
+  // CHECK: Bar<int> b(nullptr);
+
+  Baz b2;
+  int Baz::*memptr(0);
+  // CHECK: int Baz::*memptr(nullptr);
+
+  memptr = 0;
+  // CHECK: memptr = nullptr;
+}
+
+void test_function_default_param1(void *p = 0);
+// CHECK: void test_function_default_param1(void *p = nullptr);
+
+void test_function_default_param2(void *p = NULL);
+// CHECK: void test_function_default_param2(void *p = nullptr);
+
+void test_function_default_param3(void *p = g_null);
+// CHECK: void test_function_default_param3(void *p = nullptr);
+
+void test_function(int *p) {}
+// CHECK: void test_function(int *p) {}
+
+void test_function_no_ptr_param(int i) {}
+
+void test_function_call() {
+  test_function(0);
+  // CHECK: test_function(nullptr);
+
+  test_function(NULL);
+  // CHECK: test_function(nullptr);
+
+  test_function(g_null);
+  // CHECK: test_function(nullptr);
+
+  test_function_no_ptr_param(0);
+  // CHECK: test_function_no_ptr_param(0);
+}
+
+char *test_function_return1() {
+  return 0;
+  // CHECK: return nullptr;
+}
+
+void *test_function_return2() {
+  return NULL;
+  // CHECK: return nullptr;
+}
+
+long *test_function_return3() {
+  return g_null;
+  // CHECK: return nullptr;
+}
+
+int test_function_return4() {
+  return 0;
+  // CHECK: return 0;
+}
+
+int test_function_return5() {
+  return NULL;
+  // CHECK: return NULL;
+}
+
+int test_function_return6() {
+  return g_null;
+  // CHECK: return g_null;
+}

Added: clang-tools-extra/trunk/test/cpp11-migrate/UseNullptr/basic_failing.cpp
URL: http://llvm.org/viewvc/llvm-project/clang-tools-extra/trunk/test/cpp11-migrate/UseNullptr/basic_failing.cpp?rev=173178&view=auto
==============================================================================
--- clang-tools-extra/trunk/test/cpp11-migrate/UseNullptr/basic_failing.cpp (added)
+++ clang-tools-extra/trunk/test/cpp11-migrate/UseNullptr/basic_failing.cpp Tue Jan 22 12:31:49 2013
@@ -0,0 +1,28 @@
+// RUN: grep -Ev "// *[A-Z-]+:" %s > %t.cpp
+// RUN: cpp11-migrate -use-nullptr %t.cpp -- -I %S
+// RUN: FileCheck -input-file=%t.cpp %s
+// REQUIRES: shell
+// XFAIL: *
+
+#define NULL 0
+
+template <typename T>
+class A {
+public:
+  A(T *p = NULL) {}
+  // CHECK: A(T *p = nullptr) {}
+
+  void f() {
+    Ptr = NULL;
+    // CHECK: Ptr = nullptr;
+  }
+
+  T *Ptr;
+};
+
+template <typename T>
+T *f2(T *a = NULL) {
+  // CHECK: T *f2(T *a = nullptr) {
+  return a ? a : NULL;
+  // CHECK: return a ? a : nullptr;
+}





More information about the cfe-commits mailing list