blob: ea7cf0e6e1524ddbfc2da0f325a0074e821af3e6 [file] [log] [blame]
//===--- JsonCompileCommandLineDatabase - Simple JSON database --*- C++ -*-===//
//
// The LLVM Compiler Infrastructure
//
// This file is distributed under the University of Illinois Open Source
// License. See LICENSE.TXT for details.
//
//===----------------------------------------------------------------------===//
//
// This file implements reading a compile command line database, as written
// out for example by CMake. It only supports the subset of the JSON standard
// that is needed to parse the CMake output.
// See http://www.json.org/ for the full standard.
//
//===----------------------------------------------------------------------===//
#ifndef LLVM_CLANG_TOOLING_JSON_COMPILE_COMMAND_LINE_DATABASE_H
#define LLVM_CLANG_TOOLING_JSON_COMPILE_COMMAND_LINE_DATABASE_H
#include "llvm/ADT/StringRef.h"
#include <string>
#include <vector>
namespace clang {
namespace tooling {
/// \brief Converts a JSON escaped command line to a vector of arguments.
///
/// \param JsonEscapedCommandLine The escaped command line as a string. This
/// is assumed to be escaped as a JSON string (e.g. " and \ are escaped).
/// In addition, any arguments containing spaces are assumed to be \-escaped
///
/// For example, the input (|| denoting non C-escaped strings):
/// |./call a \"b \\\" c \\\\ \" d|
/// would yield:
/// [ |./call|, |a|, |b " c \ |, |d| ].
std::vector<std::string> UnescapeJsonCommandLine(
llvm::StringRef JsonEscapedCommandLine);
/// \brief Interface for users of the JsonCompileCommandLineParser.
class CompileCommandHandler {
public:
virtual ~CompileCommandHandler() {}
/// \brief Called after all translation units are parsed.
virtual void EndTranslationUnits() {}
/// \brief Called at the end of a single translation unit.
virtual void EndTranslationUnit() {}
/// \brief Called for every (Key, Value) pair in a translation unit
/// description.
virtual void HandleKeyValue(llvm::StringRef Key, llvm::StringRef Value) {}
};
/// \brief A JSON parser that supports the subset of JSON needed to parse
/// JSON compile command line databases as written out by CMake.
///
/// The supported subset describes a list of compile command lines for
/// each processed translation unit. The translation units are stored in a
/// JSON array, where each translation unit is described by a JSON object
/// containing (Key, Value) pairs for the working directory the compile command
/// line was executed from, the main C/C++ input file of the translation unit
/// and the actual compile command line, for example:
/// [
/// {
/// "file":"/file.cpp",
/// "directory":"/",
/// "command":"/cc /file.cpp"
/// }
/// ]
class JsonCompileCommandLineParser {
public:
/// \brief Create a parser on 'Input', calling 'CommandHandler' to handle the
/// parsed constructs. 'CommandHandler' may be NULL in order to just check
/// the validity of 'Input'.
JsonCompileCommandLineParser(const llvm::StringRef Input,
CompileCommandHandler *CommandHandler);
/// \brief Parses the specified input. Returns true if no parsing errors were
/// found.
bool Parse();
/// \brief Returns an error message if Parse() returned false previously.
std::string GetErrorMessage() const;
private:
bool ParseTranslationUnits();
bool ParseTranslationUnit(bool First);
bool ParseObjectKeyValuePairs();
bool ParseString(llvm::StringRef &String);
bool Consume(char C);
bool ConsumeOrError(char C, llvm::StringRef Message);
void NextNonWhitespace();
bool IsWhitespace();
void SetExpectError(char C, llvm::StringRef Message);
const llvm::StringRef Input;
llvm::StringRef::iterator Position;
std::string ErrorMessage;
CompileCommandHandler * const CommandHandler;
};
} // end namespace tooling
} // end namespace clang
#endif // LLVM_CLANG_TOOLING_JSON_COMPILE_COMMAND_LINE_DATABASE_H