Merge "Kill psGlobal and g_callbacks"
diff --git a/aidl.cpp b/aidl.cpp
index 2faba66..0436fb3 100644
--- a/aidl.cpp
+++ b/aidl.cpp
@@ -110,42 +110,6 @@
 }
 
 // ==========================================================
-struct import_info {
-    const char* from;
-    const char* filename;
-    buffer_type statement;
-    const char* neededClass;
-    document_item_type* doc;
-    struct import_info* next;
-};
-
-document_item_type* g_document = NULL;
-import_info* g_imports = NULL;
-
-static void
-main_document_parsed(document_item_type* d)
-{
-    g_document = d;
-}
-
-static void
-main_import_parsed(buffer_type* statement)
-{
-    import_info* import = (import_info*)malloc(sizeof(import_info));
-    memset(import, 0, sizeof(import_info));
-    import->from = strdup(psGlobal->FileName().c_str());
-    import->statement.lineno = statement->lineno;
-    import->statement.data = strdup(statement->data);
-    import->statement.extra = NULL;
-    import->next = g_imports;
-    import->neededClass = parse_import_statement(statement->data);
-    g_imports = import;
-}
-
-static ParserCallbacks g_mainCallbacks = {
-    &main_document_parsed,
-    &main_import_parsed
-};
 
 char*
 parse_import_statement(const char* text)
@@ -601,7 +565,8 @@
 
 // ==========================================================
 void
-generate_dep_file(const JavaOptions& options, const document_item_type* items)
+generate_dep_file(const JavaOptions& options, const document_item_type* items,
+                  const Parser& p)
 {
     /* we open the file in binary mode to ensure that the same output is
      * generated on all platforms !!
@@ -619,7 +584,7 @@
     }
 
     const char* slash = "\\";
-    import_info* import = g_imports;
+    import_info* import = p.GetImports();
     if (import == NULL) {
         slash = "";
     }
@@ -650,7 +615,7 @@
 
     // Output "<imported_file>: " so make won't fail if the imported file has
     // been deleted, moved or renamed in incremental build.
-    import = g_imports;
+    import = p.GetImports();
     while (import) {
         if (import->filename) {
             fprintf(to, "%s :\n", import->filename);
@@ -919,14 +884,14 @@
     }
 
     // parse the main file
-    g_callbacks = &g_mainCallbacks;
-    err = parse_aidl(options.input_file_name_.c_str());
-    document_item_type* mainDoc = g_document;
-    g_document = NULL;
+    Parser p{options.input_file_name_};
+    if (!p.OpenFileFromDisk())
+        return -1;
+    err = p.RunParser();
+    document_item_type* mainDoc = p.GetDocument();
 
     // parse the imports
-    g_callbacks = &g_mainCallbacks;
-    import_info* import = g_imports;
+    import_info* import = p.GetImports();
     while (import) {
         if (NAMES.Find(import->neededClass) == NULL) {
             import->filename = find_import_file(import->neededClass);
@@ -936,8 +901,11 @@
                         import->neededClass);
                 err |= 1;
             } else {
-                err |= parse_aidl(import->filename);
-                import->doc = g_document;
+                Parser p{import->filename};
+                err |= p.OpenFileFromDisk() ? 0 : 1;
+                if (! err)
+                    err |= p.RunParser();
+                import->doc = p.GetDocument();
                 if (import->doc == NULL) {
                     err |= 1;
                 }
@@ -953,7 +921,7 @@
 
     // complain about ones that aren't in the right files
     err |= check_filenames(options.input_file_name_.c_str(), mainDoc);
-    import = g_imports;
+    import = p.GetImports();
     while (import) {
         err |= check_filenames(import->filename, import->doc);
         import = import->next;
@@ -961,7 +929,7 @@
 
     // gather the types that have been declared
     err |= gather_types(options.input_file_name_.c_str(), mainDoc);
-    import = g_imports;
+    import = p.GetImports();
     while (import) {
         err |= gather_types(import->filename, import->doc);
         import = import->next;
@@ -1012,7 +980,7 @@
             !(onlyParcelable && options.fail_on_parcelable_)) {
         // make sure the folders of the output file all exists
         check_outputFilePath(output_file_name);
-        generate_dep_file(options, mainDoc);
+        generate_dep_file(options, mainDoc, p);
     }
 
     // they didn't ask to fail on parcelables, so just exit quietly.
@@ -1038,12 +1006,14 @@
     // read files
     int N = options.files_to_preprocess_.size();
     for (int i=0; i<N; i++) {
-        g_callbacks = &g_mainCallbacks;
-        err = parse_aidl(options.files_to_preprocess_[i].c_str());
+        Parser p{options.files_to_preprocess_[i]};
+        if (! p.OpenFileFromDisk())
+            return 1;
+        err = p.RunParser();
         if (err != 0) {
             return err;
         }
-        document_item_type* doc = g_document;
+        document_item_type* doc = p.GetDocument();
         string line;
         if (doc->item_type == USER_DATA_TYPE) {
             user_data_type* parcelable = (user_data_type*)doc;
diff --git a/aidl_language.cpp b/aidl_language.cpp
index 522fe00..2814ba2 100644
--- a/aidl_language.cpp
+++ b/aidl_language.cpp
@@ -16,7 +16,7 @@
 using std::cerr;
 using std::endl;
 
-ParseState *psGlobal = NULL;
+Parser *psGlobal = NULL;
 ParserCallbacks* g_callbacks = NULL; // &k_parserCallbacks;
 char const* g_currentPackage = NULL;
 
@@ -24,40 +24,26 @@
 void yylex_init(void **);
 void yylex_destroy(void *);
 void yyset_in(FILE *f, void *);
-int yyparse(ParseState*);
+int yyparse(Parser*);
 
-ParseState::ParseState() : ParseState("") {}
-
-ParseState::ParseState(const string& filename)
+Parser::Parser(const string& filename)
     : filename_(filename) {
   yylex_init(&scanner_);
 }
 
-ParseState::~ParseState() {
+Parser::~Parser() {
   yylex_destroy(scanner_);
 }
 
-string ParseState::FileName() {
+string Parser::FileName() {
   return filename_;
 }
 
-string ParseState::Package() {
+string Parser::Package() {
   return g_currentPackage;
 }
 
-void ParseState::ProcessDocument(const document_item_type& items) {
-  /* The cast is not my fault. I didn't write the code on the other side. */
-  /* TODO(sadmac): b/23977313 */
-  g_callbacks->document((document_item_type *)&items);
-}
-
-void ParseState::ProcessImport(const buffer_type& statement) {
-  /* The cast is not my fault. I didn't write the code on the other side. */
-  /* TODO(sadmac): b/23977313 */
-  g_callbacks->import((buffer_type *)&statement);
-}
-
-void ParseState::ReportError(const string& err) {
+void Parser::ReportError(const string& err) {
   /* FIXME: We're printing out the line number as -1. We used to use yylineno
    * (which was NEVER correct even before reentrant parsing). Now we'll need
    * another way.
@@ -66,15 +52,15 @@
   error_ = 1;
 }
 
-bool ParseState::FoundNoErrors() {
+bool Parser::FoundNoErrors() {
   return error_ == 0;
 }
 
-void *ParseState::Scanner() {
+void *Parser::Scanner() {
   return scanner_;
 }
 
-bool ParseState::OpenFileFromDisk() {
+bool Parser::OpenFileFromDisk() {
   FILE *in = fopen(FileName().c_str(), "r");
 
   if (! in)
@@ -84,14 +70,42 @@
   return true;
 }
 
-int ParseState::RunParser() {
+bool Parser::RunParser() {
   int ret = yy::parser(this).parse();
 
   free((void *)g_currentPackage);
   g_currentPackage = NULL;
 
   if (error_)
-    return 1;
+    return true;
 
   return ret;
 }
+
+void Parser::SetDocument(document_item_type *d)
+{
+  document_ = d;
+}
+
+void Parser::AddImport(const buffer_type& statement)
+{
+  import_info* import = (import_info*)malloc(sizeof(import_info));
+  memset(import, 0, sizeof(import_info));
+  import->from = strdup(this->FileName().c_str());
+  import->statement.lineno = statement.lineno;
+  import->statement.data = strdup(statement.data);
+  import->statement.extra = NULL;
+  import->next = imports_;
+  import->neededClass = android::aidl::parse_import_statement(statement.data);
+  imports_ = import;
+}
+
+document_item_type *Parser::GetDocument() const
+{
+  return document_;
+}
+
+import_info *Parser::GetImports() const
+{
+  return imports_;
+}
diff --git a/aidl_language.h b/aidl_language.h
index fdfea19..a74c9b8 100644
--- a/aidl_language.h
+++ b/aidl_language.h
@@ -109,8 +109,6 @@
 extern "C" {
 #endif
 
-int parse_aidl(char const *);
-
 // in, out or inout
 enum {
     IN_PARAMETER = 1,
@@ -136,14 +134,22 @@
 
 void init_buffer_type(buffer_type* buf, int lineno);
 
-class ParseState {
+struct import_info {
+    const char* from;
+    const char* filename;
+    buffer_type statement;
+    const char* neededClass;
+    document_item_type* doc;
+    struct import_info* next;
+};
+
+class Parser {
  public:
-  ParseState();
-  ParseState(const std::string& filename);
-  ~ParseState();
+  Parser(const std::string& filename);
+  ~Parser();
 
   bool OpenFileFromDisk();
-  int RunParser();
+  bool RunParser();
   void ReportError(const std::string& err);
 
   bool FoundNoErrors();
@@ -151,23 +157,25 @@
   std::string Package();
   void *Scanner();
 
-  void ProcessDocument(const document_item_type& items);
-  void ProcessImport(const buffer_type& statement);
+  void SetDocument(document_item_type *items);
+  void AddImport(const buffer_type& statement);
+
+  document_item_type *GetDocument() const;
+  import_info *GetImports() const;
 
  private:
   int error_ = 0;
   std::string filename_;
   std::string package_;
   void *scanner_ = nullptr;
+  document_item_type* document_ = nullptr;
+  import_info* imports_ = nullptr;
 
-  DISALLOW_COPY_AND_ASSIGN(ParseState);
+  DISALLOW_COPY_AND_ASSIGN(Parser);
 };
 
-extern ParseState *psGlobal;
-
 #if __cplusplus
 }
 #endif
 
-
 #endif // AIDL_AIDL_LANGUAGE_H_
diff --git a/aidl_language_l.l b/aidl_language_l.l
index 3460cad..320da37 100644
--- a/aidl_language_l.l
+++ b/aidl_language_l.l
@@ -182,18 +182,3 @@
     if (g_currentPackage) free((void*)g_currentPackage);
     g_currentPackage = android::aidl::parse_import_statement(importText);
 }
-
-
-// main parse function
-// ================================================
-int parse_aidl(char const *filename) {
-  ParseState ps(filename);
-  psGlobal = &ps;
-
-  if (!ps.OpenFileFromDisk()) {
-    fprintf(stderr, "aidl: unable to open file for read: %s\n", filename);
-    return 1;
-  }
-
-  return ps.RunParser();
-}
diff --git a/aidl_language_y.y b/aidl_language_y.y
index 409ede3..ace46c7 100644
--- a/aidl_language_y.y
+++ b/aidl_language_y.y
@@ -13,7 +13,7 @@
 
 %}
 
-%parse-param { ParseState* ps }
+%parse-param { Parser* ps }
 %lex-param { void *lex_scanner }
 
 %pure-parser
@@ -45,8 +45,8 @@
 %type<buffer> error
 %%
 document:
-        document_items                          { ps->ProcessDocument(*$1); }
-    |   headers document_items                  { ps->ProcessDocument(*$2); }
+        document_items                          { ps->SetDocument($1); }
+    |   headers document_items                  { ps->SetDocument($2); }
     ;
 
 headers:
@@ -60,8 +60,8 @@
     ;
 
 imports:
-        IMPORT                                  { ps->ProcessImport($1); }
-    |   IMPORT imports                          { ps->ProcessImport($1); }
+        IMPORT                                  { ps->AddImport($1); }
+    |   IMPORT imports                          { ps->AddImport($1); }
     ;
 
 document_items: