Key decisions about 'bool' vs '_Bool' to be based on a new flag in langoptions.

This is simple enough, but then I thought it would be nice to make PrintingPolicy
get a LangOptions so that various things can key off "bool" and "C++" independently.
This spiraled out of control.  There are many fixme's, but I think things are slightly
better than they were before.

One thing that can be improved: CFG should probably have an ASTContext pointer in it,
which would simplify its clients.



git-svn-id: https://llvm.org/svn/llvm-project/cfe/trunk@74493 91177308-0d34-0410-b5e6-96231b3b80d8
diff --git a/lib/AST/ASTContext.cpp b/lib/AST/ASTContext.cpp
index 7683d5a..fc78842 100644
--- a/lib/AST/ASTContext.cpp
+++ b/lib/AST/ASTContext.cpp
@@ -38,11 +38,10 @@
   GlobalNestedNameSpecifier(0), CFConstantStringTypeDecl(0), 
   ObjCFastEnumerationStateTypeDecl(0), SourceMgr(SM), LangOpts(LOpts), 
   FreeMemory(FreeMem), Target(t), Idents(idents), Selectors(sels),
-  BuiltinInfo(builtins), ExternalSource(0) {  
+  BuiltinInfo(builtins), ExternalSource(0), PrintingPolicy(LOpts) {  
   if (size_reserve > 0) Types.reserve(size_reserve);    
   InitBuiltinTypes();
   TUDecl = TranslationUnitDecl::Create(*this);
-  PrintingPolicy.CPlusPlus = LangOpts.CPlusPlus;
 }
 
 ASTContext::~ASTContext() {
diff --git a/lib/AST/CFG.cpp b/lib/AST/CFG.cpp
index d7a8307..d3087c2 100644
--- a/lib/AST/CFG.cpp
+++ b/lib/AST/CFG.cpp
@@ -1484,10 +1484,11 @@
   StmtMapTy StmtMap;
   signed CurrentBlock;
   unsigned CurrentStmt;
-
+  const LangOptions &LangOpts;
 public:
 
-  StmtPrinterHelper(const CFG* cfg) : CurrentBlock(0), CurrentStmt(0) {
+  StmtPrinterHelper(const CFG* cfg, const LangOptions &LO)
+    : CurrentBlock(0), CurrentStmt(0), LangOpts(LO) {
     for (CFG::const_iterator I = cfg->begin(), E = cfg->end(); I != E; ++I ) {
       unsigned j = 1;
       for (CFGBlock::const_iterator BI = I->begin(), BEnd = I->end() ;
@@ -1498,6 +1499,7 @@
             
   virtual ~StmtPrinterHelper() {}
   
+  const LangOptions &getLangOpts() const { return LangOpts; }
   void setBlockID(signed i) { CurrentBlock = i; }
   void setStmtID(unsigned i) { CurrentStmt = i; }
   
@@ -1516,7 +1518,10 @@
     return true;
   }
 };
+} // end anonymous namespace
 
+
+namespace {
 class VISIBILITY_HIDDEN CFGBlockTerminatorPrint
   : public StmtVisitor<CFGBlockTerminatorPrint,void> {
   
@@ -1526,7 +1531,7 @@
 
 public:
   CFGBlockTerminatorPrint(llvm::raw_ostream& os, StmtPrinterHelper* helper,
-                          const PrintingPolicy &Policy = PrintingPolicy())
+                          const PrintingPolicy &Policy)
     : OS(os), Helper(helper), Policy(Policy) {}
   
   void VisitIfStmt(IfStmt* I) {
@@ -1602,9 +1607,11 @@
     E->printPretty(OS, Helper, Policy);
   }                                                       
 };
+} // end anonymous namespace
+
   
-  
-void print_stmt(llvm::raw_ostream&OS, StmtPrinterHelper* Helper, Stmt* Terminator) {    
+static void print_stmt(llvm::raw_ostream &OS, StmtPrinterHelper* Helper,
+                       Stmt* Terminator) {
   if (Helper) {
     // special printing for statement-expressions.
     if (StmtExpr* SE = dyn_cast<StmtExpr>(Terminator)) {
@@ -1629,14 +1636,15 @@
     }  
   }
   
-  Terminator->printPretty(OS, Helper, /*FIXME:*/PrintingPolicy());
+  Terminator->printPretty(OS, Helper, PrintingPolicy(Helper->getLangOpts()));
   
   // Expressions need a newline.
   if (isa<Expr>(Terminator)) OS << '\n';
 }
   
-void print_block(llvm::raw_ostream& OS, const CFG* cfg, const CFGBlock& B,
-                 StmtPrinterHelper* Helper, bool print_edges) {
+static void print_block(llvm::raw_ostream& OS, const CFG* cfg,
+                        const CFGBlock& B,
+                        StmtPrinterHelper* Helper, bool print_edges) {
  
   if (Helper) Helper->setBlockID(B.getBlockID());
   
@@ -1662,10 +1670,12 @@
       OS << L->getName();
     else if (CaseStmt* C = dyn_cast<CaseStmt>(Terminator)) {
       OS << "case ";
-      C->getLHS()->printPretty(OS, Helper, /*FIXME:*/PrintingPolicy());
+      C->getLHS()->printPretty(OS, Helper,
+                               PrintingPolicy(Helper->getLangOpts()));
       if (C->getRHS()) {
         OS << " ... ";
-        C->getRHS()->printPretty(OS, Helper, /*FIXME:*/PrintingPolicy());
+        C->getRHS()->printPretty(OS, Helper,
+                                 PrintingPolicy(Helper->getLangOpts()));
       }
     }  
     else if (isa<DefaultStmt>(Terminator))
@@ -1703,7 +1713,8 @@
     
     if (Helper) Helper->setBlockID(-1);
     
-    CFGBlockTerminatorPrint TPrinter(OS, Helper, /*FIXME*/PrintingPolicy());
+    CFGBlockTerminatorPrint TPrinter(OS, Helper,
+                                     PrintingPolicy(Helper->getLangOpts()));
     TPrinter.Visit(const_cast<Stmt*>(B.getTerminator()));
     OS << '\n';
   }
@@ -1741,15 +1752,13 @@
   }
 }                   
 
-} // end anonymous namespace
 
 /// dump - A simple pretty printer of a CFG that outputs to stderr.
-void CFG::dump() const { print(llvm::errs()); }
+void CFG::dump(const LangOptions &LO) const { print(llvm::errs(), LO); }
 
 /// print - A simple pretty printer of a CFG that outputs to an ostream.
-void CFG::print(llvm::raw_ostream& OS) const {
-  
-  StmtPrinterHelper Helper(this);
+void CFG::print(llvm::raw_ostream &OS, const LangOptions &LO) const {
+  StmtPrinterHelper Helper(this, LO);
   
   // Print the entry block.
   print_block(OS, this, getEntry(), &Helper, true);
@@ -1769,18 +1778,22 @@
 }  
 
 /// dump - A simply pretty printer of a CFGBlock that outputs to stderr.
-void CFGBlock::dump(const CFG* cfg) const { print(llvm::errs(), cfg); }
+void CFGBlock::dump(const CFG* cfg, const LangOptions &LO) const {
+  print(llvm::errs(), cfg, LO);
+}
 
 /// print - A simple pretty printer of a CFGBlock that outputs to an ostream.
 ///   Generally this will only be called from CFG::print.
-void CFGBlock::print(llvm::raw_ostream& OS, const CFG* cfg) const {
-  StmtPrinterHelper Helper(cfg);
+void CFGBlock::print(llvm::raw_ostream& OS, const CFG* cfg,
+                     const LangOptions &LO) const {
+  StmtPrinterHelper Helper(cfg, LO);
   print_block(OS, cfg, *this, &Helper, true);
 }
 
 /// printTerminator - A simple pretty printer of the terminator of a CFGBlock.
-void CFGBlock::printTerminator(llvm::raw_ostream& OS) const {  
-  CFGBlockTerminatorPrint TPrinter(OS,NULL);
+void CFGBlock::printTerminator(llvm::raw_ostream &OS,
+                               const LangOptions &LO) const {  
+  CFGBlockTerminatorPrint TPrinter(OS, NULL, PrintingPolicy(LO));
   TPrinter.Visit(const_cast<Stmt*>(getTerminator()));
 }
 
@@ -1872,9 +1885,9 @@
 static StmtPrinterHelper* GraphHelper;  
 #endif
 
-void CFG::viewCFG() const {
+void CFG::viewCFG(const LangOptions &LO) const {
 #ifndef NDEBUG
-  StmtPrinterHelper H(this);
+  StmtPrinterHelper H(this, LO);
   GraphHelper = &H;
   llvm::ViewGraph(this,"CFG");
   GraphHelper = NULL;
diff --git a/lib/AST/Decl.cpp b/lib/AST/Decl.cpp
index fa4d93c..77fb20c 100644
--- a/lib/AST/Decl.cpp
+++ b/lib/AST/Decl.cpp
@@ -226,8 +226,7 @@
     if (const ClassTemplateSpecializationDecl *Spec 
           = dyn_cast<ClassTemplateSpecializationDecl>(Ctx)) {
       const TemplateArgumentList &TemplateArgs = Spec->getTemplateArgs();
-      PrintingPolicy Policy;
-      Policy.CPlusPlus = true;
+      PrintingPolicy Policy(getASTContext().getLangOptions());
       std::string TemplateArgsStr
         = TemplateSpecializationType::PrintTemplateArgumentList(
                                            TemplateArgs.getFlatArgumentList(),
diff --git a/lib/AST/NestedNameSpecifier.cpp b/lib/AST/NestedNameSpecifier.cpp
index 09522a2..90ec4d3 100644
--- a/lib/AST/NestedNameSpecifier.cpp
+++ b/lib/AST/NestedNameSpecifier.cpp
@@ -153,8 +153,6 @@
   Context.Deallocate((void *)this);
 }
 
-void NestedNameSpecifier::dump() {
-  PrintingPolicy Policy;
-  Policy.CPlusPlus = true;
-  print(llvm::errs(), Policy);
+void NestedNameSpecifier::dump(const LangOptions &LO) {
+  print(llvm::errs(), PrintingPolicy(LO));
 }
diff --git a/lib/AST/StmtDumper.cpp b/lib/AST/StmtDumper.cpp
index b24e912..bc096bf 100644
--- a/lib/AST/StmtDumper.cpp
+++ b/lib/AST/StmtDumper.cpp
@@ -41,7 +41,6 @@
     const char *LastLocFilename;
     unsigned LastLocLine;
 
-    PrintingPolicy Policy;
   public:
     StmtDumper(SourceManager *sm, FILE *f, unsigned maxDepth)
       : SM(sm), F(f), IndentLevel(0-1), MaxDepth(maxDepth) {
@@ -226,7 +225,8 @@
     }
     
     std::string Name = VD->getNameAsString();
-    VD->getType().getAsStringInternal(Name, Policy);
+    VD->getType().getAsStringInternal(Name, 
+                          PrintingPolicy(VD->getASTContext().getLangOptions()));
     fprintf(F, "%s", Name.c_str());
     
     // If this is a vardecl with an initializer, emit it.
diff --git a/lib/AST/StmtPrinter.cpp b/lib/AST/StmtPrinter.cpp
index b300940..189400b 100644
--- a/lib/AST/StmtPrinter.cpp
+++ b/lib/AST/StmtPrinter.cpp
@@ -35,7 +35,7 @@
 
   public:
     StmtPrinter(llvm::raw_ostream &os, ASTContext &C, PrinterHelper* helper, 
-                const PrintingPolicy &Policy = PrintingPolicy(),
+                const PrintingPolicy &Policy,
                 unsigned Indentation = 0)
       : OS(os), Context(C), IndentLevel(Indentation), Helper(helper),
         Policy(Policy) {}
@@ -861,7 +861,7 @@
 }
 
 void StmtPrinter::VisitImplicitValueInitExpr(ImplicitValueInitExpr *Node) {
-  if (Policy.CPlusPlus)
+  if (Policy.LangOpts.CPlusPlus)
     OS << "/*implicit*/" << Node->getType().getAsString(Policy) << "()";
   else {
     OS << "/*implicit*/(" << Node->getType().getAsString(Policy) << ")";
@@ -1216,7 +1216,8 @@
 //===----------------------------------------------------------------------===//
 
 void Stmt::dumpPretty(ASTContext& Context) const {
-  printPretty(llvm::errs(), Context, 0, PrintingPolicy());
+  printPretty(llvm::errs(), Context, 0,
+              PrintingPolicy(Context.getLangOptions()));
 }
 
 void Stmt::printPretty(llvm::raw_ostream &OS, ASTContext& Context,
diff --git a/lib/AST/TemplateName.cpp b/lib/AST/TemplateName.cpp
index 3613da7..5b671c1 100644
--- a/lib/AST/TemplateName.cpp
+++ b/lib/AST/TemplateName.cpp
@@ -15,6 +15,7 @@
 #include "clang/AST/DeclTemplate.h"
 #include "clang/AST/NestedNameSpecifier.h"
 #include "clang/AST/PrettyPrinter.h"
+#include "clang/Basic/LangOptions.h"
 #include "llvm/Support/raw_ostream.h"
 using namespace clang;
 
@@ -59,7 +60,8 @@
 }
 
 void TemplateName::dump() const {
-  PrintingPolicy Policy;
-  Policy.CPlusPlus = true;
-  print(llvm::errs(), Policy);
+  LangOptions LO;  // FIXME!
+  LO.CPlusPlus = true;
+  LO.Bool = true;
+  print(llvm::errs(), PrintingPolicy(LO));
 }
diff --git a/lib/AST/Type.cpp b/lib/AST/Type.cpp
index 4153661..eaa7d3b 100644
--- a/lib/AST/Type.cpp
+++ b/lib/AST/Type.cpp
@@ -938,11 +938,11 @@
   }
 }
 
-const char *BuiltinType::getName(bool CPlusPlus) const {
+const char *BuiltinType::getName(const LangOptions &LO) const {
   switch (getKind()) {
   default: assert(0 && "Unknown builtin type!");
   case Void:              return "void";
-  case Bool:              return CPlusPlus? "bool" : "_Bool";
+  case Bool:              return LO.Bool ? "bool" : "_Bool";
   case Char_S:            return "char";
   case Char_U:            return "char";
   case SChar:             return "signed char";
@@ -1160,9 +1160,9 @@
 //===----------------------------------------------------------------------===//
 
 void QualType::dump(const char *msg) const {
-  PrintingPolicy Policy;
   std::string R = "identifier";
-  getAsStringInternal(R, Policy);
+  LangOptions LO;
+  getAsStringInternal(R, PrintingPolicy(LO));
   if (msg)
     fprintf(stderr, "%s: %s\n", msg, R.c_str());
   else
@@ -1174,7 +1174,8 @@
 
 void Type::dump() const {
   std::string S = "identifier";
-  getAsStringInternal(S, PrintingPolicy());
+  LangOptions LO;
+  getAsStringInternal(S, PrintingPolicy(LO));
   fprintf(stderr, "%s\n", S.c_str());
 }
 
@@ -1193,7 +1194,8 @@
 
 std::string QualType::getAsString() const {
   std::string S;
-  getAsStringInternal(S, PrintingPolicy());
+  LangOptions LO;
+  getAsStringInternal(S, PrintingPolicy(LO));
   return S;
 }
 
@@ -1224,11 +1226,11 @@
 void BuiltinType::getAsStringInternal(std::string &S, 
                                       const PrintingPolicy &Policy) const {
   if (S.empty()) {
-    S = getName(Policy.CPlusPlus);
+    S = getName(Policy.LangOpts);
   } else {
     // Prefix the basic type, e.g. 'int X'.
     S = ' ' + S;
-    S = getName(Policy.CPlusPlus) + S;
+    S = getName(Policy.LangOpts) + S;
   }
 }
 
@@ -1470,7 +1472,7 @@
     if (getNumArgs())
       S += ", ";
     S += "...";
-  } else if (getNumArgs() == 0 && !Policy.CPlusPlus) {
+  } else if (getNumArgs() == 0 && !Policy.LangOpts.CPlusPlus) {
     // Do not emit int() if we have a proto, emit 'int(void)'.
     S += "void";
   }