blob: 4b01b997a17895ffcc9abe56e4d39aa65c0c3f20 [file] [log] [blame]
Manuel Klimekf7f295f2013-05-14 09:13:00 +00001//===--- Diagnostics.cpp - Helper class for error diagnostics -----*- C++ -*-===//
2//
3// The LLVM Compiler Infrastructure
4//
5// This file is distributed under the University of Illinois Open Source
6// License. See LICENSE.TXT for details.
7//
8//===----------------------------------------------------------------------===//
9
10#include "clang/ASTMatchers/Dynamic/Diagnostics.h"
11
12namespace clang {
13namespace ast_matchers {
14namespace dynamic {
15
16Diagnostics::ArgStream &
17Diagnostics::ArgStream::operator<<(const Twine &Arg) {
18 Out->push_back(Arg.str());
19 return *this;
20}
21
22Diagnostics::ArgStream Diagnostics::pushErrorFrame(const SourceRange &Range,
23 ErrorType Error) {
24 Frames.insert(Frames.begin(), ErrorFrame());
25 ErrorFrame &Last = Frames.front();
26 Last.Range = Range;
27 Last.Type = Error;
28 ArgStream Out = { &Last.Args };
29 return Out;
30}
31
32StringRef ErrorTypeToString(Diagnostics::ErrorType Type) {
33 switch (Type) {
34 case Diagnostics::ET_RegistryNotFound:
35 return "Matcher not found: $0";
36 case Diagnostics::ET_RegistryWrongArgCount:
37 return "Incorrect argument count. (Expected = $0) != (Actual = $1)";
38 case Diagnostics::ET_RegistryWrongArgType:
39 return "Incorrect type on function $0 for arg $1.";
Samuel Benzaquen4f37d922013-06-03 19:31:08 +000040 case Diagnostics::ET_RegistryNotBindable:
41 return "Matcher does not support binding.";
Manuel Klimekf7f295f2013-05-14 09:13:00 +000042
43 case Diagnostics::ET_ParserStringError:
44 return "Error parsing string token: <$0>";
45 case Diagnostics::ET_ParserMatcherArgFailure:
46 return "Error parsing argument $0 for matcher $1.";
47 case Diagnostics::ET_ParserMatcherFailure:
48 return "Error building matcher $0.";
49 case Diagnostics::ET_ParserNoOpenParen:
50 return "Error parsing matcher. Found token <$0> while looking for '('.";
51 case Diagnostics::ET_ParserNoCloseParen:
52 return "Error parsing matcher. Found end-of-code while looking for ')'.";
53 case Diagnostics::ET_ParserNoComma:
54 return "Error parsing matcher. Found token <$0> while looking for ','.";
55 case Diagnostics::ET_ParserNoCode:
56 return "End of code found while looking for token.";
57 case Diagnostics::ET_ParserNotAMatcher:
58 return "Input value is not a matcher expression.";
59 case Diagnostics::ET_ParserInvalidToken:
60 return "Invalid token <$0> found when looking for a value.";
Samuel Benzaquen4f37d922013-06-03 19:31:08 +000061 case Diagnostics::ET_ParserMalformedBindExpr:
62 return "Malformed bind() expression.";
63 case Diagnostics::ET_ParserTrailingCode:
64 return "Expected end of code.";
Manuel Klimekf7f295f2013-05-14 09:13:00 +000065
66 case Diagnostics::ET_None:
67 return "<N/A>";
68 }
69 llvm_unreachable("Unknown ErrorType value.");
70}
71
72std::string FormatErrorString(StringRef FormatString,
73 ArrayRef<std::string> Args) {
74 std::string Out;
75 while (!FormatString.empty()) {
76 std::pair<StringRef, StringRef> Pieces = FormatString.split("$");
77 Out += Pieces.first.str();
78 if (Pieces.second.empty()) break;
79
80 const char Next = Pieces.second.front();
81 FormatString = Pieces.second.drop_front();
82 if (Next >= '0' && Next <= '9') {
83 const unsigned Index = Next - '0';
84 if (Index < Args.size()) {
85 Out += Args[Index];
86 } else {
87 Out += "<Argument_Not_Provided>";
88 }
89 }
90 }
91 return Out;
92}
93
94std::string Diagnostics::ErrorFrame::ToString() const {
95 StringRef FormatString = ErrorTypeToString(Type);
96 std::string ErrorOut = FormatErrorString(FormatString, Args);
97 if (Range.Start.Line > 0 && Range.Start.Column > 0)
98 return (Twine(Range.Start.Line) + ":" + Twine(Range.Start.Column) + ": " +
99 ErrorOut).str();
100 return ErrorOut;
101}
102
103std::string Diagnostics::ToString() const {
104 if (Frames.empty()) return "";
105 return Frames[Frames.size() - 1].ToString();
106}
107
108std::string Diagnostics::ToStringFull() const {
109 std::string Result;
110 for (size_t i = 0, end = Frames.size(); i != end; ++i) {
111 if (i > 0) Result += "\n";
112 Result += Frames[i].ToString();
113 }
114 return Result;
115}
116
117} // namespace dynamic
118} // namespace ast_matchers
119} // namespace clang