blob: 1e106c59f1886875324f468e4aec96deda979559 [file] [log] [blame]
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +00001//===- unittests/AST/CommentParser.cpp ------ Comment parser tests --------===//
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/Basic/SourceManager.h"
11#include "clang/Basic/FileManager.h"
12#include "clang/Basic/Diagnostic.h"
13#include "clang/AST/Comment.h"
14#include "clang/AST/CommentLexer.h"
15#include "clang/AST/CommentParser.h"
16#include "clang/AST/CommentSema.h"
17#include "llvm/ADT/STLExtras.h"
18#include "llvm/Support/Allocator.h"
19#include <vector>
20
21#include "gtest/gtest.h"
22
23using namespace llvm;
24using namespace clang;
25
26namespace clang {
27namespace comments {
28
29namespace {
30
31const bool DEBUG = true;
32
33class CommentParserTest : public ::testing::Test {
34protected:
35 CommentParserTest()
36 : FileMgr(FileMgrOpts),
37 DiagID(new DiagnosticIDs()),
38 Diags(DiagID, new IgnoringDiagConsumer()),
39 SourceMgr(Diags, FileMgr) {
40 }
41
42 FileSystemOptions FileMgrOpts;
43 FileManager FileMgr;
44 IntrusiveRefCntPtr<DiagnosticIDs> DiagID;
45 DiagnosticsEngine Diags;
46 SourceManager SourceMgr;
47 llvm::BumpPtrAllocator Allocator;
48
49 FullComment *parseString(const char *Source);
50};
51
52FullComment *CommentParserTest::parseString(const char *Source) {
53 MemoryBuffer *Buf = MemoryBuffer::getMemBuffer(Source);
54 FileID File = SourceMgr.createFileIDForMemBuffer(Buf);
55 SourceLocation Begin = SourceMgr.getLocForStartOfFile(File);
56
Dmitri Gribenko477a9f52012-07-27 20:37:06 +000057 comments::Lexer L(Allocator, Begin, CommentOptions(),
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +000058 Source, Source + strlen(Source));
59
Dmitri Gribenkoa5ef44f2012-07-11 21:38:39 +000060 comments::Sema S(Allocator, SourceMgr, Diags);
61 comments::Parser P(L, S, Allocator, SourceMgr, Diags);
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +000062 comments::FullComment *FC = P.parseFullComment();
63
64 if (DEBUG) {
65 llvm::errs() << "=== Source:\n" << Source << "\n=== AST:\n";
66 FC->dump(SourceMgr);
67 }
68
69 Token Tok;
70 L.lex(Tok);
71 if (Tok.is(tok::eof))
72 return FC;
73 else
74 return NULL;
75}
76
77::testing::AssertionResult HasChildCount(const Comment *C, size_t Count) {
78 if (!C)
79 return ::testing::AssertionFailure() << "Comment is NULL";
80
81 if (Count != C->child_count())
82 return ::testing::AssertionFailure()
83 << "Count = " << Count
84 << ", child_count = " << C->child_count();
85
86 return ::testing::AssertionSuccess();
87}
88
89template <typename T>
90::testing::AssertionResult GetChildAt(const Comment *C,
91 size_t Idx,
92 T *&Child) {
93 if (!C)
94 return ::testing::AssertionFailure() << "Comment is NULL";
95
96 if (Idx >= C->child_count())
97 return ::testing::AssertionFailure()
98 << "Idx out of range. Idx = " << Idx
99 << ", child_count = " << C->child_count();
100
101 Comment::child_iterator I = C->child_begin() + Idx;
102 Comment *CommentChild = *I;
103 if (!CommentChild)
104 return ::testing::AssertionFailure() << "Child is NULL";
105
106 Child = dyn_cast<T>(CommentChild);
107 if (!Child)
108 return ::testing::AssertionFailure()
109 << "Child is not of requested type, but a "
110 << CommentChild->getCommentKindName();
111
112 return ::testing::AssertionSuccess();
113}
114
115::testing::AssertionResult HasTextAt(const Comment *C,
116 size_t Idx,
117 StringRef Text) {
118 TextComment *TC;
119 ::testing::AssertionResult AR = GetChildAt(C, Idx, TC);
120 if (!AR)
121 return AR;
122
123 StringRef ActualText = TC->getText();
124 if (ActualText != Text)
125 return ::testing::AssertionFailure()
126 << "TextComment has text \"" << ActualText.str() << "\", "
127 "expected \"" << Text.str() << "\"";
128
129 if (TC->hasTrailingNewline())
130 return ::testing::AssertionFailure()
131 << "TextComment has a trailing newline";
132
133 return ::testing::AssertionSuccess();
134}
135
136::testing::AssertionResult HasTextWithNewlineAt(const Comment *C,
137 size_t Idx,
138 StringRef Text) {
139 TextComment *TC;
140 ::testing::AssertionResult AR = GetChildAt(C, Idx, TC);
141 if (!AR)
142 return AR;
143
144 StringRef ActualText = TC->getText();
145 if (ActualText != Text)
146 return ::testing::AssertionFailure()
147 << "TextComment has text \"" << ActualText.str() << "\", "
148 "expected \"" << Text.str() << "\"";
149
150 if (!TC->hasTrailingNewline())
151 return ::testing::AssertionFailure()
152 << "TextComment has no trailing newline";
153
154 return ::testing::AssertionSuccess();
155}
156
157::testing::AssertionResult HasBlockCommandAt(const Comment *C,
158 size_t Idx,
159 BlockCommandComment *&BCC,
160 StringRef Name,
161 ParagraphComment *&Paragraph) {
162 ::testing::AssertionResult AR = GetChildAt(C, Idx, BCC);
163 if (!AR)
164 return AR;
165
166 StringRef ActualName = BCC->getCommandName();
167 if (ActualName != Name)
168 return ::testing::AssertionFailure()
169 << "BlockCommandComment has name \"" << ActualName.str() << "\", "
170 "expected \"" << Name.str() << "\"";
171
172 Paragraph = BCC->getParagraph();
173
174 return ::testing::AssertionSuccess();
175}
176
177::testing::AssertionResult HasParamCommandAt(
178 const Comment *C,
179 size_t Idx,
180 ParamCommandComment *&PCC,
181 StringRef CommandName,
182 ParamCommandComment::PassDirection Direction,
183 bool IsDirectionExplicit,
184 StringRef ParamName,
185 ParagraphComment *&Paragraph) {
186 ::testing::AssertionResult AR = GetChildAt(C, Idx, PCC);
187 if (!AR)
188 return AR;
189
190 StringRef ActualCommandName = PCC->getCommandName();
191 if (ActualCommandName != CommandName)
192 return ::testing::AssertionFailure()
193 << "ParamCommandComment has name \"" << ActualCommandName.str() << "\", "
194 "expected \"" << CommandName.str() << "\"";
195
196 if (PCC->getDirection() != Direction)
197 return ::testing::AssertionFailure()
198 << "ParamCommandComment has direction " << PCC->getDirection() << ", "
199 "expected " << Direction;
200
201 if (PCC->isDirectionExplicit() != IsDirectionExplicit)
202 return ::testing::AssertionFailure()
203 << "ParamCommandComment has "
204 << (PCC->isDirectionExplicit() ? "explicit" : "implicit")
205 << " direction, "
206 "expected " << (IsDirectionExplicit ? "explicit" : "implicit");
207
Dmitri Gribenko8a903932012-08-06 23:48:44 +0000208 if (!ParamName.empty() && !PCC->hasParamName())
Dmitri Gribenko0c43a922012-07-24 18:23:31 +0000209 return ::testing::AssertionFailure()
210 << "ParamCommandComment has no parameter name";
211
Dmitri Gribenko8a903932012-08-06 23:48:44 +0000212 StringRef ActualParamName = PCC->hasParamName() ? PCC->getParamName() : "";
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000213 if (ActualParamName != ParamName)
214 return ::testing::AssertionFailure()
Dmitri Gribenko0c43a922012-07-24 18:23:31 +0000215 << "ParamCommandComment has parameter name \"" << ActualParamName.str()
216 << "\", "
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000217 "expected \"" << ParamName.str() << "\"";
218
219 Paragraph = PCC->getParagraph();
220
221 return ::testing::AssertionSuccess();
222}
223
Dmitri Gribenko96b09862012-07-31 22:37:06 +0000224::testing::AssertionResult HasTParamCommandAt(
225 const Comment *C,
226 size_t Idx,
227 TParamCommandComment *&TPCC,
228 StringRef CommandName,
229 StringRef ParamName,
230 ParagraphComment *&Paragraph) {
231 ::testing::AssertionResult AR = GetChildAt(C, Idx, TPCC);
232 if (!AR)
233 return AR;
234
235 StringRef ActualCommandName = TPCC->getCommandName();
236 if (ActualCommandName != CommandName)
237 return ::testing::AssertionFailure()
238 << "TParamCommandComment has name \"" << ActualCommandName.str() << "\", "
239 "expected \"" << CommandName.str() << "\"";
240
Dmitri Gribenko8a903932012-08-06 23:48:44 +0000241 if (!ParamName.empty() && !TPCC->hasParamName())
Dmitri Gribenko96b09862012-07-31 22:37:06 +0000242 return ::testing::AssertionFailure()
243 << "TParamCommandComment has no parameter name";
244
Dmitri Gribenko8a903932012-08-06 23:48:44 +0000245 StringRef ActualParamName = TPCC->hasParamName() ? TPCC->getParamName() : "";
Dmitri Gribenko96b09862012-07-31 22:37:06 +0000246 if (ActualParamName != ParamName)
247 return ::testing::AssertionFailure()
248 << "TParamCommandComment has parameter name \"" << ActualParamName.str()
249 << "\", "
250 "expected \"" << ParamName.str() << "\"";
251
252 Paragraph = TPCC->getParagraph();
253
254 return ::testing::AssertionSuccess();
255}
256
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000257::testing::AssertionResult HasInlineCommandAt(const Comment *C,
258 size_t Idx,
259 InlineCommandComment *&ICC,
260 StringRef Name) {
261 ::testing::AssertionResult AR = GetChildAt(C, Idx, ICC);
262 if (!AR)
263 return AR;
264
265 StringRef ActualName = ICC->getCommandName();
266 if (ActualName != Name)
267 return ::testing::AssertionFailure()
268 << "InlineCommandComment has name \"" << ActualName.str() << "\", "
269 "expected \"" << Name.str() << "\"";
270
271 return ::testing::AssertionSuccess();
272}
273
274struct NoArgs {};
275
276::testing::AssertionResult HasInlineCommandAt(const Comment *C,
277 size_t Idx,
278 InlineCommandComment *&ICC,
279 StringRef Name,
280 NoArgs) {
281 ::testing::AssertionResult AR = HasInlineCommandAt(C, Idx, ICC, Name);
282 if (!AR)
283 return AR;
284
Dmitri Gribenko0eaf69d2012-07-13 19:02:42 +0000285 if (ICC->getNumArgs() != 0)
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000286 return ::testing::AssertionFailure()
Dmitri Gribenko0eaf69d2012-07-13 19:02:42 +0000287 << "InlineCommandComment has " << ICC->getNumArgs() << " arg(s), "
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000288 "expected 0";
289
290 return ::testing::AssertionSuccess();
291}
292
293::testing::AssertionResult HasInlineCommandAt(const Comment *C,
294 size_t Idx,
295 InlineCommandComment *&ICC,
296 StringRef Name,
297 StringRef Arg) {
298 ::testing::AssertionResult AR = HasInlineCommandAt(C, Idx, ICC, Name);
299 if (!AR)
300 return AR;
301
Dmitri Gribenko0eaf69d2012-07-13 19:02:42 +0000302 if (ICC->getNumArgs() != 1)
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000303 return ::testing::AssertionFailure()
Dmitri Gribenko0eaf69d2012-07-13 19:02:42 +0000304 << "InlineCommandComment has " << ICC->getNumArgs() << " arg(s), "
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000305 "expected 1";
306
307 StringRef ActualArg = ICC->getArgText(0);
308 if (ActualArg != Arg)
309 return ::testing::AssertionFailure()
310 << "InlineCommandComment has argument \"" << ActualArg.str() << "\", "
311 "expected \"" << Arg.str() << "\"";
312
313 return ::testing::AssertionSuccess();
314}
315
Dmitri Gribenko3f38bf22012-07-13 00:44:24 +0000316::testing::AssertionResult HasHTMLStartTagAt(const Comment *C,
317 size_t Idx,
318 HTMLStartTagComment *&HST,
319 StringRef TagName) {
320 ::testing::AssertionResult AR = GetChildAt(C, Idx, HST);
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000321 if (!AR)
322 return AR;
323
Dmitri Gribenko3f38bf22012-07-13 00:44:24 +0000324 StringRef ActualTagName = HST->getTagName();
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000325 if (ActualTagName != TagName)
326 return ::testing::AssertionFailure()
Dmitri Gribenko3f38bf22012-07-13 00:44:24 +0000327 << "HTMLStartTagComment has name \"" << ActualTagName.str() << "\", "
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000328 "expected \"" << TagName.str() << "\"";
329
330 return ::testing::AssertionSuccess();
331}
332
Dmitri Gribenkoa5ef44f2012-07-11 21:38:39 +0000333struct SelfClosing {};
334
Dmitri Gribenko3f38bf22012-07-13 00:44:24 +0000335::testing::AssertionResult HasHTMLStartTagAt(const Comment *C,
336 size_t Idx,
337 HTMLStartTagComment *&HST,
338 StringRef TagName,
339 SelfClosing) {
340 ::testing::AssertionResult AR = HasHTMLStartTagAt(C, Idx, HST, TagName);
Dmitri Gribenkoa5ef44f2012-07-11 21:38:39 +0000341 if (!AR)
342 return AR;
343
Dmitri Gribenko3f38bf22012-07-13 00:44:24 +0000344 if (!HST->isSelfClosing())
Dmitri Gribenkoa5ef44f2012-07-11 21:38:39 +0000345 return ::testing::AssertionFailure()
Dmitri Gribenko3f38bf22012-07-13 00:44:24 +0000346 << "HTMLStartTagComment is not self-closing";
Dmitri Gribenkoa5ef44f2012-07-11 21:38:39 +0000347
348 return ::testing::AssertionSuccess();
349}
350
351
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000352struct NoAttrs {};
353
Dmitri Gribenko3f38bf22012-07-13 00:44:24 +0000354::testing::AssertionResult HasHTMLStartTagAt(const Comment *C,
355 size_t Idx,
356 HTMLStartTagComment *&HST,
357 StringRef TagName,
358 NoAttrs) {
359 ::testing::AssertionResult AR = HasHTMLStartTagAt(C, Idx, HST, TagName);
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000360 if (!AR)
361 return AR;
362
Dmitri Gribenko3f38bf22012-07-13 00:44:24 +0000363 if (HST->isSelfClosing())
Dmitri Gribenkoa5ef44f2012-07-11 21:38:39 +0000364 return ::testing::AssertionFailure()
Dmitri Gribenko3f38bf22012-07-13 00:44:24 +0000365 << "HTMLStartTagComment is self-closing";
Dmitri Gribenkoa5ef44f2012-07-11 21:38:39 +0000366
Dmitri Gribenko0eaf69d2012-07-13 19:02:42 +0000367 if (HST->getNumAttrs() != 0)
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000368 return ::testing::AssertionFailure()
Dmitri Gribenko0eaf69d2012-07-13 19:02:42 +0000369 << "HTMLStartTagComment has " << HST->getNumAttrs() << " attr(s), "
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000370 "expected 0";
371
372 return ::testing::AssertionSuccess();
373}
374
Dmitri Gribenko3f38bf22012-07-13 00:44:24 +0000375::testing::AssertionResult HasHTMLStartTagAt(const Comment *C,
376 size_t Idx,
377 HTMLStartTagComment *&HST,
378 StringRef TagName,
379 StringRef AttrName,
380 StringRef AttrValue) {
381 ::testing::AssertionResult AR = HasHTMLStartTagAt(C, Idx, HST, TagName);
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000382 if (!AR)
383 return AR;
384
Dmitri Gribenko3f38bf22012-07-13 00:44:24 +0000385 if (HST->isSelfClosing())
Dmitri Gribenkoa5ef44f2012-07-11 21:38:39 +0000386 return ::testing::AssertionFailure()
Dmitri Gribenko3f38bf22012-07-13 00:44:24 +0000387 << "HTMLStartTagComment is self-closing";
Dmitri Gribenkoa5ef44f2012-07-11 21:38:39 +0000388
Dmitri Gribenko0eaf69d2012-07-13 19:02:42 +0000389 if (HST->getNumAttrs() != 1)
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000390 return ::testing::AssertionFailure()
Dmitri Gribenko0eaf69d2012-07-13 19:02:42 +0000391 << "HTMLStartTagComment has " << HST->getNumAttrs() << " attr(s), "
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000392 "expected 1";
393
Dmitri Gribenko3f38bf22012-07-13 00:44:24 +0000394 StringRef ActualName = HST->getAttr(0).Name;
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000395 if (ActualName != AttrName)
396 return ::testing::AssertionFailure()
Dmitri Gribenko3f38bf22012-07-13 00:44:24 +0000397 << "HTMLStartTagComment has attr \"" << ActualName.str() << "\", "
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000398 "expected \"" << AttrName.str() << "\"";
399
Dmitri Gribenko3f38bf22012-07-13 00:44:24 +0000400 StringRef ActualValue = HST->getAttr(0).Value;
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000401 if (ActualValue != AttrValue)
402 return ::testing::AssertionFailure()
Dmitri Gribenko3f38bf22012-07-13 00:44:24 +0000403 << "HTMLStartTagComment has attr value \"" << ActualValue.str() << "\", "
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000404 "expected \"" << AttrValue.str() << "\"";
405
406 return ::testing::AssertionSuccess();
407}
408
Dmitri Gribenko3f38bf22012-07-13 00:44:24 +0000409::testing::AssertionResult HasHTMLEndTagAt(const Comment *C,
410 size_t Idx,
411 HTMLEndTagComment *&HET,
412 StringRef TagName) {
413 ::testing::AssertionResult AR = GetChildAt(C, Idx, HET);
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000414 if (!AR)
415 return AR;
416
Dmitri Gribenko3f38bf22012-07-13 00:44:24 +0000417 StringRef ActualTagName = HET->getTagName();
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000418 if (ActualTagName != TagName)
419 return ::testing::AssertionFailure()
Dmitri Gribenko3f38bf22012-07-13 00:44:24 +0000420 << "HTMLEndTagComment has name \"" << ActualTagName.str() << "\", "
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000421 "expected \"" << TagName.str() << "\"";
422
423 return ::testing::AssertionSuccess();
424}
425
Dmitri Gribenkodebd16f2012-07-23 23:09:32 +0000426::testing::AssertionResult HasParagraphCommentAt(const Comment *C,
427 size_t Idx,
428 StringRef Text) {
429 ParagraphComment *PC;
430
431 {
432 ::testing::AssertionResult AR = GetChildAt(C, Idx, PC);
433 if (!AR)
434 return AR;
435 }
436
437 {
438 ::testing::AssertionResult AR = HasChildCount(PC, 1);
439 if (!AR)
440 return AR;
441 }
442
443 {
444 ::testing::AssertionResult AR = HasTextAt(PC, 0, Text);
445 if (!AR)
446 return AR;
447 }
448
449 return ::testing::AssertionSuccess();
450}
451
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000452::testing::AssertionResult HasVerbatimBlockAt(const Comment *C,
453 size_t Idx,
454 VerbatimBlockComment *&VBC,
Dmitri Gribenko9f08f492012-07-20 20:18:53 +0000455 StringRef Name,
456 StringRef CloseName) {
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000457 ::testing::AssertionResult AR = GetChildAt(C, Idx, VBC);
458 if (!AR)
459 return AR;
460
461 StringRef ActualName = VBC->getCommandName();
462 if (ActualName != Name)
463 return ::testing::AssertionFailure()
464 << "VerbatimBlockComment has name \"" << ActualName.str() << "\", "
465 "expected \"" << Name.str() << "\"";
466
Dmitri Gribenko9f08f492012-07-20 20:18:53 +0000467 StringRef ActualCloseName = VBC->getCloseName();
468 if (ActualCloseName != CloseName)
469 return ::testing::AssertionFailure()
470 << "VerbatimBlockComment has closing command name \""
471 << ActualCloseName.str() << "\", "
472 "expected \"" << CloseName.str() << "\"";
473
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000474 return ::testing::AssertionSuccess();
475}
476
477struct NoLines {};
Dmitri Gribenko9f08f492012-07-20 20:18:53 +0000478struct Lines {};
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000479
480::testing::AssertionResult HasVerbatimBlockAt(const Comment *C,
481 size_t Idx,
482 VerbatimBlockComment *&VBC,
483 StringRef Name,
Dmitri Gribenko9f08f492012-07-20 20:18:53 +0000484 StringRef CloseName,
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000485 NoLines) {
Dmitri Gribenko9f08f492012-07-20 20:18:53 +0000486 ::testing::AssertionResult AR = HasVerbatimBlockAt(C, Idx, VBC, Name,
487 CloseName);
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000488 if (!AR)
489 return AR;
490
Dmitri Gribenko0eaf69d2012-07-13 19:02:42 +0000491 if (VBC->getNumLines() != 0)
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000492 return ::testing::AssertionFailure()
Dmitri Gribenko0eaf69d2012-07-13 19:02:42 +0000493 << "VerbatimBlockComment has " << VBC->getNumLines() << " lines(s), "
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000494 "expected 0";
495
496 return ::testing::AssertionSuccess();
497}
498
499::testing::AssertionResult HasVerbatimBlockAt(const Comment *C,
500 size_t Idx,
501 VerbatimBlockComment *&VBC,
502 StringRef Name,
Dmitri Gribenko9f08f492012-07-20 20:18:53 +0000503 StringRef CloseName,
504 Lines,
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000505 StringRef Line0) {
Dmitri Gribenko9f08f492012-07-20 20:18:53 +0000506 ::testing::AssertionResult AR = HasVerbatimBlockAt(C, Idx, VBC, Name,
507 CloseName);
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000508 if (!AR)
509 return AR;
510
Dmitri Gribenko0eaf69d2012-07-13 19:02:42 +0000511 if (VBC->getNumLines() != 1)
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000512 return ::testing::AssertionFailure()
Dmitri Gribenko0eaf69d2012-07-13 19:02:42 +0000513 << "VerbatimBlockComment has " << VBC->getNumLines() << " lines(s), "
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000514 "expected 1";
515
516 StringRef ActualLine0 = VBC->getText(0);
517 if (ActualLine0 != Line0)
518 return ::testing::AssertionFailure()
519 << "VerbatimBlockComment has lines[0] \"" << ActualLine0.str() << "\", "
520 "expected \"" << Line0.str() << "\"";
521
522 return ::testing::AssertionSuccess();
523}
524
525::testing::AssertionResult HasVerbatimBlockAt(const Comment *C,
526 size_t Idx,
527 VerbatimBlockComment *&VBC,
528 StringRef Name,
Dmitri Gribenko9f08f492012-07-20 20:18:53 +0000529 StringRef CloseName,
530 Lines,
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000531 StringRef Line0,
532 StringRef Line1) {
Dmitri Gribenko9f08f492012-07-20 20:18:53 +0000533 ::testing::AssertionResult AR = HasVerbatimBlockAt(C, Idx, VBC, Name,
534 CloseName);
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000535 if (!AR)
536 return AR;
537
Dmitri Gribenko0eaf69d2012-07-13 19:02:42 +0000538 if (VBC->getNumLines() != 2)
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000539 return ::testing::AssertionFailure()
Dmitri Gribenko0eaf69d2012-07-13 19:02:42 +0000540 << "VerbatimBlockComment has " << VBC->getNumLines() << " lines(s), "
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000541 "expected 2";
542
543 StringRef ActualLine0 = VBC->getText(0);
544 if (ActualLine0 != Line0)
545 return ::testing::AssertionFailure()
546 << "VerbatimBlockComment has lines[0] \"" << ActualLine0.str() << "\", "
547 "expected \"" << Line0.str() << "\"";
548
549 StringRef ActualLine1 = VBC->getText(1);
550 if (ActualLine1 != Line1)
551 return ::testing::AssertionFailure()
552 << "VerbatimBlockComment has lines[1] \"" << ActualLine1.str() << "\", "
553 "expected \"" << Line1.str() << "\"";
554
555 return ::testing::AssertionSuccess();
556}
557
558::testing::AssertionResult HasVerbatimLineAt(const Comment *C,
559 size_t Idx,
560 VerbatimLineComment *&VLC,
561 StringRef Name,
562 StringRef Text) {
563 ::testing::AssertionResult AR = GetChildAt(C, Idx, VLC);
564 if (!AR)
565 return AR;
566
567 StringRef ActualName = VLC->getCommandName();
568 if (ActualName != Name)
569 return ::testing::AssertionFailure()
570 << "VerbatimLineComment has name \"" << ActualName.str() << "\", "
571 "expected \"" << Name.str() << "\"";
572
573 StringRef ActualText = VLC->getText();
574 if (ActualText != Text)
575 return ::testing::AssertionFailure()
576 << "VerbatimLineComment has text \"" << ActualText.str() << "\", "
577 "expected \"" << Text.str() << "\"";
578
579 return ::testing::AssertionSuccess();
580}
581
582
583TEST_F(CommentParserTest, Basic1) {
584 const char *Source = "//";
585
586 FullComment *FC = parseString(Source);
587 ASSERT_TRUE(HasChildCount(FC, 0));
588}
589
590TEST_F(CommentParserTest, Basic2) {
591 const char *Source = "// Meow";
592
593 FullComment *FC = parseString(Source);
594 ASSERT_TRUE(HasChildCount(FC, 1));
595
Dmitri Gribenkodebd16f2012-07-23 23:09:32 +0000596 ASSERT_TRUE(HasParagraphCommentAt(FC, 0, " Meow"));
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000597}
598
599TEST_F(CommentParserTest, Basic3) {
600 const char *Source =
601 "// Aaa\n"
602 "// Bbb";
603
604 FullComment *FC = parseString(Source);
605 ASSERT_TRUE(HasChildCount(FC, 1));
606
607 {
608 ParagraphComment *PC;
609 ASSERT_TRUE(GetChildAt(FC, 0, PC));
610
611 ASSERT_TRUE(HasChildCount(PC, 2));
612 ASSERT_TRUE(HasTextWithNewlineAt(PC, 0, " Aaa"));
613 ASSERT_TRUE(HasTextAt(PC, 1, " Bbb"));
614 }
615}
616
617TEST_F(CommentParserTest, Paragraph1) {
618 const char *Sources[] = {
619 "// Aaa\n"
620 "//\n"
621 "// Bbb",
622
623 "// Aaa\n"
624 "//\n"
625 "//\n"
626 "// Bbb",
627 };
628
629
630 for (size_t i = 0, e = array_lengthof(Sources); i != e; i++) {
631 FullComment *FC = parseString(Sources[i]);
632 ASSERT_TRUE(HasChildCount(FC, 2));
633
Dmitri Gribenkodebd16f2012-07-23 23:09:32 +0000634 ASSERT_TRUE(HasParagraphCommentAt(FC, 0, " Aaa"));
635 ASSERT_TRUE(HasParagraphCommentAt(FC, 1, " Bbb"));
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000636 }
637}
638
639TEST_F(CommentParserTest, Paragraph2) {
640 const char *Source =
641 "// \\brief Aaa\n"
642 "//\n"
643 "// Bbb";
644
645 FullComment *FC = parseString(Source);
646 ASSERT_TRUE(HasChildCount(FC, 3));
647
Dmitri Gribenkodebd16f2012-07-23 23:09:32 +0000648 ASSERT_TRUE(HasParagraphCommentAt(FC, 0, " "));
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000649 {
650 BlockCommandComment *BCC;
651 ParagraphComment *PC;
652 ASSERT_TRUE(HasBlockCommandAt(FC, 1, BCC, "brief", PC));
653
Dmitri Gribenkodebd16f2012-07-23 23:09:32 +0000654 ASSERT_TRUE(HasParagraphCommentAt(BCC, 0, " Aaa"));
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000655 }
Dmitri Gribenkodebd16f2012-07-23 23:09:32 +0000656 ASSERT_TRUE(HasParagraphCommentAt(FC, 2, " Bbb"));
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000657}
658
659TEST_F(CommentParserTest, Paragraph3) {
660 const char *Source = "// \\brief \\author";
661
662 FullComment *FC = parseString(Source);
663 ASSERT_TRUE(HasChildCount(FC, 3));
664
Dmitri Gribenkodebd16f2012-07-23 23:09:32 +0000665 ASSERT_TRUE(HasParagraphCommentAt(FC, 0, " "));
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000666 {
667 BlockCommandComment *BCC;
668 ParagraphComment *PC;
669 ASSERT_TRUE(HasBlockCommandAt(FC, 1, BCC, "brief", PC));
670
Dmitri Gribenkodebd16f2012-07-23 23:09:32 +0000671 ASSERT_TRUE(HasParagraphCommentAt(BCC, 0, " "));
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000672 }
673 {
674 BlockCommandComment *BCC;
675 ParagraphComment *PC;
676 ASSERT_TRUE(HasBlockCommandAt(FC, 2, BCC, "author", PC));
677
678 ASSERT_TRUE(GetChildAt(BCC, 0, PC));
679 ASSERT_TRUE(HasChildCount(PC, 0));
680 }
681}
682
683TEST_F(CommentParserTest, Paragraph4) {
684 const char *Source =
685 "// \\brief Aaa\n"
686 "// Bbb \\author\n"
687 "// Ccc";
688
689 FullComment *FC = parseString(Source);
690 ASSERT_TRUE(HasChildCount(FC, 3));
691
Dmitri Gribenkodebd16f2012-07-23 23:09:32 +0000692 ASSERT_TRUE(HasParagraphCommentAt(FC, 0, " "));
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000693 {
694 BlockCommandComment *BCC;
695 ParagraphComment *PC;
696 ASSERT_TRUE(HasBlockCommandAt(FC, 1, BCC, "brief", PC));
697
698 ASSERT_TRUE(GetChildAt(BCC, 0, PC));
699 ASSERT_TRUE(HasChildCount(PC, 2));
700 ASSERT_TRUE(HasTextWithNewlineAt(PC, 0, " Aaa"));
701 ASSERT_TRUE(HasTextAt(PC, 1, " Bbb "));
702 }
703 {
704 BlockCommandComment *BCC;
705 ParagraphComment *PC;
706 ASSERT_TRUE(HasBlockCommandAt(FC, 2, BCC, "author", PC));
707
Dmitri Gribenkodebd16f2012-07-23 23:09:32 +0000708 ASSERT_TRUE(HasParagraphCommentAt(BCC, 0, " Ccc"));
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000709 }
710}
711
712TEST_F(CommentParserTest, ParamCommand1) {
Dmitri Gribenko3ccc1732012-07-30 16:52:51 +0000713 const char *Source = "// \\param aaa";
714
715 FullComment *FC = parseString(Source);
716 ASSERT_TRUE(HasChildCount(FC, 2));
717
718 ASSERT_TRUE(HasParagraphCommentAt(FC, 0, " "));
719 {
720 ParamCommandComment *PCC;
721 ParagraphComment *PC;
722 ASSERT_TRUE(HasParamCommandAt(FC, 1, PCC, "param",
723 ParamCommandComment::In,
724 /* IsDirectionExplicit = */ false,
725 "aaa", PC));
726 ASSERT_TRUE(HasChildCount(PCC, 1));
727 ASSERT_TRUE(HasChildCount(PC, 0));
728 }
729}
730
731TEST_F(CommentParserTest, ParamCommand2) {
Dmitri Gribenko8a903932012-08-06 23:48:44 +0000732 const char *Source = "// \\param\\brief";
733
734 FullComment *FC = parseString(Source);
735 ASSERT_TRUE(HasChildCount(FC, 3));
736
737 ASSERT_TRUE(HasParagraphCommentAt(FC, 0, " "));
738 {
739 ParamCommandComment *PCC;
740 ParagraphComment *PC;
741 ASSERT_TRUE(HasParamCommandAt(FC, 1, PCC, "param",
742 ParamCommandComment::In,
743 /* IsDirectionExplicit = */ false,
744 "", PC));
745 ASSERT_TRUE(HasChildCount(PCC, 1));
746 ASSERT_TRUE(HasChildCount(PC, 0));
747 }
748 {
749 BlockCommandComment *BCC;
750 ParagraphComment *PC;
751 ASSERT_TRUE(HasBlockCommandAt(FC, 2, BCC, "brief", PC));
752 ASSERT_TRUE(HasChildCount(PC, 0));
753 }
754}
755
756TEST_F(CommentParserTest, ParamCommand3) {
Dmitri Gribenko0c43a922012-07-24 18:23:31 +0000757 const char *Sources[] = {
758 "// \\param aaa Bbb\n",
759 "// \\param\n"
760 "// aaa Bbb\n",
761 "// \\param \n"
762 "// aaa Bbb\n",
763 "// \\param aaa\n"
764 "// Bbb\n"
765 };
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000766
Dmitri Gribenko0c43a922012-07-24 18:23:31 +0000767 for (size_t i = 0, e = array_lengthof(Sources); i != e; i++) {
768 FullComment *FC = parseString(Sources[i]);
769 ASSERT_TRUE(HasChildCount(FC, 2));
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000770
Dmitri Gribenko0c43a922012-07-24 18:23:31 +0000771 ASSERT_TRUE(HasParagraphCommentAt(FC, 0, " "));
772 {
773 ParamCommandComment *PCC;
774 ParagraphComment *PC;
775 ASSERT_TRUE(HasParamCommandAt(FC, 1, PCC, "param",
776 ParamCommandComment::In,
777 /* IsDirectionExplicit = */ false,
778 "aaa", PC));
779 ASSERT_TRUE(HasChildCount(PCC, 1));
780 ASSERT_TRUE(HasParagraphCommentAt(PCC, 0, " Bbb"));
781 }
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000782 }
Dmitri Gribenkoe68c2292012-07-23 23:37:11 +0000783}
784
Dmitri Gribenko8a903932012-08-06 23:48:44 +0000785TEST_F(CommentParserTest, ParamCommand4) {
Dmitri Gribenko0c43a922012-07-24 18:23:31 +0000786 const char *Sources[] = {
787 "// \\param [in] aaa Bbb\n",
Dmitri Gribenkod076e012012-08-01 23:49:32 +0000788 "// \\param[in] aaa Bbb\n",
Dmitri Gribenko0c43a922012-07-24 18:23:31 +0000789 "// \\param\n"
790 "// [in] aaa Bbb\n",
791 "// \\param [in]\n"
792 "// aaa Bbb\n",
793 "// \\param [in] aaa\n"
794 "// Bbb\n",
795 };
Dmitri Gribenkoe68c2292012-07-23 23:37:11 +0000796
Dmitri Gribenko0c43a922012-07-24 18:23:31 +0000797 for (size_t i = 0, e = array_lengthof(Sources); i != e; i++) {
798 FullComment *FC = parseString(Sources[i]);
799 ASSERT_TRUE(HasChildCount(FC, 2));
Dmitri Gribenkoe68c2292012-07-23 23:37:11 +0000800
Dmitri Gribenko0c43a922012-07-24 18:23:31 +0000801 ASSERT_TRUE(HasParagraphCommentAt(FC, 0, " "));
802 {
803 ParamCommandComment *PCC;
804 ParagraphComment *PC;
805 ASSERT_TRUE(HasParamCommandAt(FC, 1, PCC, "param",
806 ParamCommandComment::In,
807 /* IsDirectionExplicit = */ true,
808 "aaa", PC));
809 ASSERT_TRUE(HasChildCount(PCC, 1));
810 ASSERT_TRUE(HasParagraphCommentAt(PCC, 0, " Bbb"));
811 }
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000812 }
Dmitri Gribenkoe68c2292012-07-23 23:37:11 +0000813}
814
Dmitri Gribenko8a903932012-08-06 23:48:44 +0000815TEST_F(CommentParserTest, ParamCommand5) {
Dmitri Gribenko0c43a922012-07-24 18:23:31 +0000816 const char *Sources[] = {
817 "// \\param [out] aaa Bbb\n",
Dmitri Gribenkod076e012012-08-01 23:49:32 +0000818 "// \\param[out] aaa Bbb\n",
Dmitri Gribenko0c43a922012-07-24 18:23:31 +0000819 "// \\param\n"
820 "// [out] aaa Bbb\n",
821 "// \\param [out]\n"
822 "// aaa Bbb\n",
823 "// \\param [out] aaa\n"
824 "// Bbb\n",
825 };
Dmitri Gribenkoe68c2292012-07-23 23:37:11 +0000826
Dmitri Gribenko0c43a922012-07-24 18:23:31 +0000827 for (size_t i = 0, e = array_lengthof(Sources); i != e; i++) {
828 FullComment *FC = parseString(Sources[i]);
829 ASSERT_TRUE(HasChildCount(FC, 2));
Dmitri Gribenkoe68c2292012-07-23 23:37:11 +0000830
Dmitri Gribenko0c43a922012-07-24 18:23:31 +0000831 ASSERT_TRUE(HasParagraphCommentAt(FC, 0, " "));
832 {
833 ParamCommandComment *PCC;
834 ParagraphComment *PC;
835 ASSERT_TRUE(HasParamCommandAt(FC, 1, PCC, "param",
836 ParamCommandComment::Out,
837 /* IsDirectionExplicit = */ true,
838 "aaa", PC));
839 ASSERT_TRUE(HasChildCount(PCC, 1));
840 ASSERT_TRUE(HasParagraphCommentAt(PCC, 0, " Bbb"));
841 }
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000842 }
843}
844
Dmitri Gribenko8a903932012-08-06 23:48:44 +0000845TEST_F(CommentParserTest, ParamCommand6) {
Dmitri Gribenkoe68c2292012-07-23 23:37:11 +0000846 const char *Sources[] = {
847 "// \\param [in,out] aaa Bbb\n",
Dmitri Gribenkod076e012012-08-01 23:49:32 +0000848 "// \\param[in,out] aaa Bbb\n",
Dmitri Gribenko0c43a922012-07-24 18:23:31 +0000849 "// \\param [in, out] aaa Bbb\n",
850 "// \\param [in,\n"
851 "// out] aaa Bbb\n",
852 "// \\param [in,out]\n"
853 "// aaa Bbb\n",
854 "// \\param [in,out] aaa\n"
855 "// Bbb\n"
Dmitri Gribenkoe68c2292012-07-23 23:37:11 +0000856 };
857
858 for (size_t i = 0, e = array_lengthof(Sources); i != e; i++) {
859 FullComment *FC = parseString(Sources[i]);
860 ASSERT_TRUE(HasChildCount(FC, 2));
861
862 ASSERT_TRUE(HasParagraphCommentAt(FC, 0, " "));
863 {
864 ParamCommandComment *PCC;
865 ParagraphComment *PC;
866 ASSERT_TRUE(HasParamCommandAt(FC, 1, PCC, "param",
867 ParamCommandComment::InOut,
868 /* IsDirectionExplicit = */ true,
869 "aaa", PC));
870 ASSERT_TRUE(HasChildCount(PCC, 1));
871 ASSERT_TRUE(HasParagraphCommentAt(PCC, 0, " Bbb"));
872 }
873 }
874}
875
Dmitri Gribenko8a903932012-08-06 23:48:44 +0000876TEST_F(CommentParserTest, ParamCommand7) {
Dmitri Gribenkofd939162012-07-24 16:10:47 +0000877 const char *Source =
878 "// \\param aaa \\% Bbb \\$ ccc\n";
879
880 FullComment *FC = parseString(Source);
881 ASSERT_TRUE(HasChildCount(FC, 2));
882
883 ASSERT_TRUE(HasParagraphCommentAt(FC, 0, " "));
884 {
885 ParamCommandComment *PCC;
886 ParagraphComment *PC;
887 ASSERT_TRUE(HasParamCommandAt(FC, 1, PCC, "param",
888 ParamCommandComment::In,
889 /* IsDirectionExplicit = */ false,
890 "aaa", PC));
891 ASSERT_TRUE(HasChildCount(PCC, 1));
892
893 ASSERT_TRUE(HasChildCount(PC, 5));
894 ASSERT_TRUE(HasTextAt(PC, 0, " "));
895 ASSERT_TRUE(HasTextAt(PC, 1, "%"));
896 ASSERT_TRUE(HasTextAt(PC, 2, " Bbb "));
897 ASSERT_TRUE(HasTextAt(PC, 3, "$"));
898 ASSERT_TRUE(HasTextAt(PC, 4, " ccc"));
899 }
900}
Dmitri Gribenkoe68c2292012-07-23 23:37:11 +0000901
Dmitri Gribenko96b09862012-07-31 22:37:06 +0000902TEST_F(CommentParserTest, TParamCommand1) {
903 const char *Sources[] = {
904 "// \\tparam aaa Bbb\n",
905 "// \\tparam\n"
906 "// aaa Bbb\n",
907 "// \\tparam \n"
908 "// aaa Bbb\n",
909 "// \\tparam aaa\n"
910 "// Bbb\n"
911 };
912
913 for (size_t i = 0, e = array_lengthof(Sources); i != e; i++) {
914 FullComment *FC = parseString(Sources[i]);
915 ASSERT_TRUE(HasChildCount(FC, 2));
916
917 ASSERT_TRUE(HasParagraphCommentAt(FC, 0, " "));
918 {
919 TParamCommandComment *TPCC;
920 ParagraphComment *PC;
921 ASSERT_TRUE(HasTParamCommandAt(FC, 1, TPCC, "tparam",
922 "aaa", PC));
923 ASSERT_TRUE(HasChildCount(TPCC, 1));
924 ASSERT_TRUE(HasParagraphCommentAt(TPCC, 0, " Bbb"));
925 }
926 }
927}
928
Dmitri Gribenko8a903932012-08-06 23:48:44 +0000929TEST_F(CommentParserTest, TParamCommand2) {
930 const char *Source = "// \\tparam\\brief";
931
932 FullComment *FC = parseString(Source);
933 ASSERT_TRUE(HasChildCount(FC, 3));
934
935 ASSERT_TRUE(HasParagraphCommentAt(FC, 0, " "));
936 {
937 TParamCommandComment *TPCC;
938 ParagraphComment *PC;
939 ASSERT_TRUE(HasTParamCommandAt(FC, 1, TPCC, "tparam", "", PC));
940 ASSERT_TRUE(HasChildCount(TPCC, 1));
941 ASSERT_TRUE(HasChildCount(PC, 0));
942 }
943 {
944 BlockCommandComment *BCC;
945 ParagraphComment *PC;
946 ASSERT_TRUE(HasBlockCommandAt(FC, 2, BCC, "brief", PC));
947 ASSERT_TRUE(HasChildCount(PC, 0));
948 }
949}
950
951
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +0000952TEST_F(CommentParserTest, InlineCommand1) {
953 const char *Source = "// \\c";
954
955 FullComment *FC = parseString(Source);
956 ASSERT_TRUE(HasChildCount(FC, 1));
957
958 {
959 ParagraphComment *PC;
960 InlineCommandComment *ICC;
961 ASSERT_TRUE(GetChildAt(FC, 0, PC));
962
963 ASSERT_TRUE(HasChildCount(PC, 2));
964 ASSERT_TRUE(HasTextAt(PC, 0, " "));
965 ASSERT_TRUE(HasInlineCommandAt(PC, 1, ICC, "c", NoArgs()));
966 }
967}
968
969TEST_F(CommentParserTest, InlineCommand2) {
970 const char *Source = "// \\c ";
971
972 FullComment *FC = parseString(Source);
973 ASSERT_TRUE(HasChildCount(FC, 1));
974
975 {
976 ParagraphComment *PC;
977 InlineCommandComment *ICC;
978 ASSERT_TRUE(GetChildAt(FC, 0, PC));
979
980 ASSERT_TRUE(HasChildCount(PC, 3));
981 ASSERT_TRUE(HasTextAt(PC, 0, " "));
982 ASSERT_TRUE(HasInlineCommandAt(PC, 1, ICC, "c", NoArgs()));
983 ASSERT_TRUE(HasTextAt(PC, 2, " "));
984 }
985}
986
987TEST_F(CommentParserTest, InlineCommand3) {
988 const char *Source = "// \\c aaa\n";
989
990 FullComment *FC = parseString(Source);
991 ASSERT_TRUE(HasChildCount(FC, 1));
992
993 {
994 ParagraphComment *PC;
995 InlineCommandComment *ICC;
996 ASSERT_TRUE(GetChildAt(FC, 0, PC));
997
998 ASSERT_TRUE(HasChildCount(PC, 2));
999 ASSERT_TRUE(HasTextAt(PC, 0, " "));
1000 ASSERT_TRUE(HasInlineCommandAt(PC, 1, ICC, "c", "aaa"));
1001 }
1002}
1003
1004TEST_F(CommentParserTest, InlineCommand4) {
1005 const char *Source = "// \\c aaa bbb";
1006
1007 FullComment *FC = parseString(Source);
1008 ASSERT_TRUE(HasChildCount(FC, 1));
1009
1010 {
1011 ParagraphComment *PC;
1012 InlineCommandComment *ICC;
1013 ASSERT_TRUE(GetChildAt(FC, 0, PC));
1014
1015 ASSERT_TRUE(HasChildCount(PC, 3));
1016 ASSERT_TRUE(HasTextAt(PC, 0, " "));
1017 ASSERT_TRUE(HasInlineCommandAt(PC, 1, ICC, "c", "aaa"));
1018 ASSERT_TRUE(HasTextAt(PC, 2, " bbb"));
1019 }
1020}
1021
1022TEST_F(CommentParserTest, InlineCommand5) {
1023 const char *Source = "// \\unknown aaa\n";
1024
1025 FullComment *FC = parseString(Source);
1026 ASSERT_TRUE(HasChildCount(FC, 1));
1027
1028 {
1029 ParagraphComment *PC;
1030 InlineCommandComment *ICC;
1031 ASSERT_TRUE(GetChildAt(FC, 0, PC));
1032
1033 ASSERT_TRUE(HasChildCount(PC, 3));
1034 ASSERT_TRUE(HasTextAt(PC, 0, " "));
1035 ASSERT_TRUE(HasInlineCommandAt(PC, 1, ICC, "unknown", NoArgs()));
1036 ASSERT_TRUE(HasTextAt(PC, 2, " aaa"));
1037 }
1038}
1039
1040TEST_F(CommentParserTest, HTML1) {
1041 const char *Sources[] = {
1042 "// <a",
1043 "// <a>",
1044 "// <a >"
1045 };
1046
1047 for (size_t i = 0, e = array_lengthof(Sources); i != e; i++) {
1048 FullComment *FC = parseString(Sources[i]);
1049 ASSERT_TRUE(HasChildCount(FC, 1));
1050
1051 {
1052 ParagraphComment *PC;
Dmitri Gribenko3f38bf22012-07-13 00:44:24 +00001053 HTMLStartTagComment *HST;
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +00001054 ASSERT_TRUE(GetChildAt(FC, 0, PC));
1055
1056 ASSERT_TRUE(HasChildCount(PC, 2));
1057 ASSERT_TRUE(HasTextAt(PC, 0, " "));
Dmitri Gribenko3f38bf22012-07-13 00:44:24 +00001058 ASSERT_TRUE(HasHTMLStartTagAt(PC, 1, HST, "a", NoAttrs()));
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +00001059 }
1060 }
1061}
1062
1063TEST_F(CommentParserTest, HTML2) {
1064 const char *Sources[] = {
Dmitri Gribenkoa5ef44f2012-07-11 21:38:39 +00001065 "// <br/>",
1066 "// <br />"
1067 };
1068
1069 for (size_t i = 0, e = array_lengthof(Sources); i != e; i++) {
1070 FullComment *FC = parseString(Sources[i]);
1071 ASSERT_TRUE(HasChildCount(FC, 1));
1072
1073 {
1074 ParagraphComment *PC;
Dmitri Gribenko3f38bf22012-07-13 00:44:24 +00001075 HTMLStartTagComment *HST;
Dmitri Gribenkoa5ef44f2012-07-11 21:38:39 +00001076 ASSERT_TRUE(GetChildAt(FC, 0, PC));
1077
1078 ASSERT_TRUE(HasChildCount(PC, 2));
1079 ASSERT_TRUE(HasTextAt(PC, 0, " "));
Dmitri Gribenko3f38bf22012-07-13 00:44:24 +00001080 ASSERT_TRUE(HasHTMLStartTagAt(PC, 1, HST, "br", SelfClosing()));
Dmitri Gribenkoa5ef44f2012-07-11 21:38:39 +00001081 }
1082 }
1083}
1084
1085TEST_F(CommentParserTest, HTML3) {
1086 const char *Sources[] = {
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +00001087 "// <a href",
1088 "// <a href ",
1089 "// <a href>",
1090 "// <a href >",
1091 };
1092
1093 for (size_t i = 0, e = array_lengthof(Sources); i != e; i++) {
1094 FullComment *FC = parseString(Sources[i]);
1095 ASSERT_TRUE(HasChildCount(FC, 1));
1096
1097 {
1098 ParagraphComment *PC;
Dmitri Gribenko3f38bf22012-07-13 00:44:24 +00001099 HTMLStartTagComment *HST;
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +00001100 ASSERT_TRUE(GetChildAt(FC, 0, PC));
1101
1102 ASSERT_TRUE(HasChildCount(PC, 2));
1103 ASSERT_TRUE(HasTextAt(PC, 0, " "));
Dmitri Gribenko3f38bf22012-07-13 00:44:24 +00001104 ASSERT_TRUE(HasHTMLStartTagAt(PC, 1, HST, "a", "href", ""));
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +00001105 }
1106 }
1107}
1108
Dmitri Gribenkoa5ef44f2012-07-11 21:38:39 +00001109TEST_F(CommentParserTest, HTML4) {
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +00001110 const char *Sources[] = {
1111 "// <a href=\"bbb\"",
1112 "// <a href=\"bbb\">",
1113 };
1114
1115 for (size_t i = 0, e = array_lengthof(Sources); i != e; i++) {
1116 FullComment *FC = parseString(Sources[i]);
1117 ASSERT_TRUE(HasChildCount(FC, 1));
1118
1119 {
1120 ParagraphComment *PC;
Dmitri Gribenko3f38bf22012-07-13 00:44:24 +00001121 HTMLStartTagComment *HST;
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +00001122 ASSERT_TRUE(GetChildAt(FC, 0, PC));
1123
1124 ASSERT_TRUE(HasChildCount(PC, 2));
1125 ASSERT_TRUE(HasTextAt(PC, 0, " "));
Dmitri Gribenko3f38bf22012-07-13 00:44:24 +00001126 ASSERT_TRUE(HasHTMLStartTagAt(PC, 1, HST, "a", "href", "bbb"));
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +00001127 }
1128 }
1129}
1130
Dmitri Gribenkoa5ef44f2012-07-11 21:38:39 +00001131TEST_F(CommentParserTest, HTML5) {
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +00001132 const char *Sources[] = {
1133 "// </a",
1134 "// </a>",
1135 "// </a >"
1136 };
1137
1138 for (size_t i = 0, e = array_lengthof(Sources); i != e; i++) {
1139 FullComment *FC = parseString(Sources[i]);
1140 ASSERT_TRUE(HasChildCount(FC, 1));
1141
1142 {
1143 ParagraphComment *PC;
Dmitri Gribenko3f38bf22012-07-13 00:44:24 +00001144 HTMLEndTagComment *HET;
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +00001145 ASSERT_TRUE(GetChildAt(FC, 0, PC));
1146
1147 ASSERT_TRUE(HasChildCount(PC, 2));
1148 ASSERT_TRUE(HasTextAt(PC, 0, " "));
Dmitri Gribenko3f38bf22012-07-13 00:44:24 +00001149 ASSERT_TRUE(HasHTMLEndTagAt(PC, 1, HET, "a"));
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +00001150 }
1151 }
1152}
1153
Dmitri Gribenkoa5ef44f2012-07-11 21:38:39 +00001154TEST_F(CommentParserTest, HTML6) {
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +00001155 const char *Source =
1156 "// <pre>\n"
1157 "// Aaa\n"
1158 "// Bbb\n"
1159 "// </pre>\n";
1160
1161 FullComment *FC = parseString(Source);
1162 ASSERT_TRUE(HasChildCount(FC, 1));
1163
1164 {
1165 ParagraphComment *PC;
Dmitri Gribenko3f38bf22012-07-13 00:44:24 +00001166 HTMLStartTagComment *HST;
1167 HTMLEndTagComment *HET;
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +00001168 ASSERT_TRUE(GetChildAt(FC, 0, PC));
1169
1170 ASSERT_TRUE(HasChildCount(PC, 6));
1171 ASSERT_TRUE(HasTextAt(PC, 0, " "));
Dmitri Gribenko3f38bf22012-07-13 00:44:24 +00001172 ASSERT_TRUE(HasHTMLStartTagAt(PC, 1, HST, "pre", NoAttrs()));
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +00001173 ASSERT_TRUE(HasTextWithNewlineAt(PC, 2, " Aaa"));
1174 ASSERT_TRUE(HasTextWithNewlineAt(PC, 3, " Bbb"));
1175 ASSERT_TRUE(HasTextAt(PC, 4, " "));
Dmitri Gribenko3f38bf22012-07-13 00:44:24 +00001176 ASSERT_TRUE(HasHTMLEndTagAt(PC, 5, HET, "pre"));
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +00001177 }
1178}
1179
1180TEST_F(CommentParserTest, VerbatimBlock1) {
1181 const char *Source = "// \\verbatim\\endverbatim\n";
1182
1183 FullComment *FC = parseString(Source);
1184 ASSERT_TRUE(HasChildCount(FC, 2));
1185
Dmitri Gribenkodebd16f2012-07-23 23:09:32 +00001186 ASSERT_TRUE(HasParagraphCommentAt(FC, 0, " "));
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +00001187 {
1188 VerbatimBlockComment *VCC;
Dmitri Gribenko9f08f492012-07-20 20:18:53 +00001189 ASSERT_TRUE(HasVerbatimBlockAt(FC, 1, VCC, "verbatim", "endverbatim",
1190 NoLines()));
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +00001191 }
1192}
1193
1194TEST_F(CommentParserTest, VerbatimBlock2) {
1195 const char *Source = "// \\verbatim Aaa \\endverbatim\n";
1196
1197 FullComment *FC = parseString(Source);
1198 ASSERT_TRUE(HasChildCount(FC, 2));
1199
Dmitri Gribenkodebd16f2012-07-23 23:09:32 +00001200 ASSERT_TRUE(HasParagraphCommentAt(FC, 0, " "));
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +00001201 {
1202 VerbatimBlockComment *VBC;
Dmitri Gribenko9f08f492012-07-20 20:18:53 +00001203 ASSERT_TRUE(HasVerbatimBlockAt(FC, 1, VBC, "verbatim", "endverbatim",
1204 Lines(), " Aaa "));
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +00001205 }
1206}
1207
1208TEST_F(CommentParserTest, VerbatimBlock3) {
Dmitri Gribenko9f08f492012-07-20 20:18:53 +00001209 const char *Source = "// \\verbatim Aaa\n";
1210
1211 FullComment *FC = parseString(Source);
1212 ASSERT_TRUE(HasChildCount(FC, 2));
1213
Dmitri Gribenkodebd16f2012-07-23 23:09:32 +00001214 ASSERT_TRUE(HasParagraphCommentAt(FC, 0, " "));
Dmitri Gribenko9f08f492012-07-20 20:18:53 +00001215 {
1216 VerbatimBlockComment *VBC;
1217 ASSERT_TRUE(HasVerbatimBlockAt(FC, 1, VBC, "verbatim", "",
1218 Lines(), " Aaa"));
1219 }
1220}
1221
1222TEST_F(CommentParserTest, VerbatimBlock4) {
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +00001223 const char *Source =
1224 "//\\verbatim\n"
1225 "//\\endverbatim\n";
1226
1227 FullComment *FC = parseString(Source);
1228 ASSERT_TRUE(HasChildCount(FC, 1));
1229
1230 {
1231 VerbatimBlockComment *VBC;
Dmitri Gribenko9f08f492012-07-20 20:18:53 +00001232 ASSERT_TRUE(HasVerbatimBlockAt(FC, 0, VBC, "verbatim", "endverbatim",
1233 NoLines()));
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +00001234 }
1235}
1236
Dmitri Gribenko9f08f492012-07-20 20:18:53 +00001237TEST_F(CommentParserTest, VerbatimBlock5) {
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +00001238 const char *Sources[] = {
1239 "//\\verbatim\n"
1240 "// Aaa\n"
1241 "//\\endverbatim\n",
1242
1243 "/*\\verbatim\n"
1244 " * Aaa\n"
1245 " *\\endverbatim*/"
1246 };
1247
1248 for (size_t i = 0, e = array_lengthof(Sources); i != e; i++) {
1249 FullComment *FC = parseString(Sources[i]);
1250 ASSERT_TRUE(HasChildCount(FC, 1));
1251
1252 {
1253 VerbatimBlockComment *VBC;
Dmitri Gribenko9f08f492012-07-20 20:18:53 +00001254 ASSERT_TRUE(HasVerbatimBlockAt(FC, 0, VBC, "verbatim", "endverbatim",
1255 Lines(), " Aaa"));
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +00001256 }
1257 }
1258}
1259
Dmitri Gribenko9f08f492012-07-20 20:18:53 +00001260TEST_F(CommentParserTest, VerbatimBlock6) {
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +00001261 const char *Sources[] = {
1262 "// \\verbatim\n"
1263 "// Aaa\n"
1264 "// \\endverbatim\n",
1265
1266 "/* \\verbatim\n"
1267 " * Aaa\n"
1268 " * \\endverbatim*/"
1269 };
1270
1271 for (size_t i = 0, e = array_lengthof(Sources); i != e; i++) {
1272 FullComment *FC = parseString(Sources[i]);
1273 ASSERT_TRUE(HasChildCount(FC, 2));
1274
Dmitri Gribenkodebd16f2012-07-23 23:09:32 +00001275 ASSERT_TRUE(HasParagraphCommentAt(FC, 0, " "));
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +00001276 {
1277 VerbatimBlockComment *VBC;
Dmitri Gribenko9f08f492012-07-20 20:18:53 +00001278 ASSERT_TRUE(HasVerbatimBlockAt(FC, 1, VBC, "verbatim", "endverbatim",
1279 Lines(), " Aaa"));
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +00001280 }
1281 }
1282}
1283
Dmitri Gribenko9f08f492012-07-20 20:18:53 +00001284TEST_F(CommentParserTest, VerbatimBlock7) {
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +00001285 const char *Sources[] = {
1286 "// \\verbatim\n"
1287 "// Aaa\n"
Dmitri Gribenko64da4e52012-07-18 23:01:58 +00001288 "// Bbb\n"
1289 "// \\endverbatim\n",
1290
1291 "/* \\verbatim\n"
1292 " * Aaa\n"
1293 " * Bbb\n"
1294 " * \\endverbatim*/"
1295 };
1296
1297 for (size_t i = 0, e = array_lengthof(Sources); i != e; i++) {
1298 FullComment *FC = parseString(Sources[i]);
1299 ASSERT_TRUE(HasChildCount(FC, 2));
1300
Dmitri Gribenkodebd16f2012-07-23 23:09:32 +00001301 ASSERT_TRUE(HasParagraphCommentAt(FC, 0, " "));
Dmitri Gribenko64da4e52012-07-18 23:01:58 +00001302 {
1303 VerbatimBlockComment *VBC;
Dmitri Gribenko9f08f492012-07-20 20:18:53 +00001304 ASSERT_TRUE(HasVerbatimBlockAt(FC, 1, VBC, "verbatim", "endverbatim",
1305 Lines(), " Aaa", " Bbb"));
Dmitri Gribenko64da4e52012-07-18 23:01:58 +00001306 }
1307 }
1308}
1309
Dmitri Gribenko9f08f492012-07-20 20:18:53 +00001310TEST_F(CommentParserTest, VerbatimBlock8) {
Dmitri Gribenko64da4e52012-07-18 23:01:58 +00001311 const char *Sources[] = {
1312 "// \\verbatim\n"
1313 "// Aaa\n"
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +00001314 "//\n"
1315 "// Bbb\n"
1316 "// \\endverbatim\n",
1317
1318 "/* \\verbatim\n"
1319 " * Aaa\n"
1320 " *\n"
1321 " * Bbb\n"
1322 " * \\endverbatim*/"
1323 };
1324 for (size_t i = 0, e = array_lengthof(Sources); i != e; i++) {
Dmitri Gribenko64da4e52012-07-18 23:01:58 +00001325 FullComment *FC = parseString(Sources[i]);
1326 ASSERT_TRUE(HasChildCount(FC, 2));
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +00001327
Dmitri Gribenkodebd16f2012-07-23 23:09:32 +00001328 ASSERT_TRUE(HasParagraphCommentAt(FC, 0, " "));
Dmitri Gribenko64da4e52012-07-18 23:01:58 +00001329 {
1330 VerbatimBlockComment *VBC;
Dmitri Gribenko9f08f492012-07-20 20:18:53 +00001331 ASSERT_TRUE(HasVerbatimBlockAt(FC, 1, VBC, "verbatim", "endverbatim"));
Dmitri Gribenko64da4e52012-07-18 23:01:58 +00001332 ASSERT_EQ(3U, VBC->getNumLines());
1333 ASSERT_EQ(" Aaa", VBC->getText(0));
1334 ASSERT_EQ("", VBC->getText(1));
1335 ASSERT_EQ(" Bbb", VBC->getText(2));
1336 }
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +00001337 }
1338}
1339
1340TEST_F(CommentParserTest, VerbatimLine1) {
1341 const char *Sources[] = {
1342 "// \\fn",
1343 "// \\fn\n"
1344 };
1345
1346 for (size_t i = 0, e = array_lengthof(Sources); i != e; i++) {
1347 FullComment *FC = parseString(Sources[i]);
1348 ASSERT_TRUE(HasChildCount(FC, 2));
1349
Dmitri Gribenkodebd16f2012-07-23 23:09:32 +00001350 ASSERT_TRUE(HasParagraphCommentAt(FC, 0, " "));
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +00001351 {
1352 VerbatimLineComment *VLC;
1353 ASSERT_TRUE(HasVerbatimLineAt(FC, 1, VLC, "fn", ""));
1354 }
1355 }
1356}
1357
1358TEST_F(CommentParserTest, VerbatimLine2) {
1359 const char *Sources[] = {
1360 "/// \\fn void *foo(const char *zzz = \"\\$\");\n//",
1361 "/** \\fn void *foo(const char *zzz = \"\\$\");*/"
1362 };
1363
1364 for (size_t i = 0, e = array_lengthof(Sources); i != e; i++) {
1365 FullComment *FC = parseString(Sources[i]);
1366 ASSERT_TRUE(HasChildCount(FC, 2));
1367
Dmitri Gribenkodebd16f2012-07-23 23:09:32 +00001368 ASSERT_TRUE(HasParagraphCommentAt(FC, 0, " "));
Dmitri Gribenko8d3ba232012-07-06 00:28:32 +00001369 {
1370 VerbatimLineComment *VLC;
1371 ASSERT_TRUE(HasVerbatimLineAt(FC, 1, VLC, "fn",
1372 " void *foo(const char *zzz = \"\\$\");"));
1373 }
1374 }
1375}
1376
1377} // unnamed namespace
1378
1379} // end namespace comments
1380} // end namespace clang
1381