1document
2  = _ ignore* _ "<doxygen " _ attr:attr* _ ">" body:elements _ "</doxygen>" _ { return body; }
3
4
5elements
6  = element*
7
8element
9  = _ "<" startTag:id _ attr:attr* _ ">" _ children:elements _ "</" endTag:id ">" _ {
10    if (startTag != endTag) {
11      throw new Error("Expected </" + startTag + "> but </" + endTag + "> found.");
12    }
13    return {name: startTag, attr: attr, children: children }
14  }
15  / "<" tag:id _ attr:attr* _ "/>" _ {
16    return {name: tag, attr: attr }
17  }
18  / _ text:text _ { return text }
19
20ignore
21  = "<?xml" _ attr* _ "?>" { return }
22
23attr
24  = name:id _ "=" _ value:string { return { name:name, value:value } }
25
26string
27  = '"' '"' _           { return ""; }
28  / "'" "'" _           { return ""; }
29  / '"' text:quoted '"' _ { return text; }
30  / "'" text:quoted "'" _ { return text; }
31
32quoted
33  = chars:[^<>'" \t\n\r]+  { return chars.join(""); }
34
35text
36  = chars:[^<> \t\n\r]+  { return chars.join(""); }
37
38id
39  = chars:[^<>/'"=? \t\n\r]+  { return chars.join(""); }
40
41_ "whitespace"
42  = whitespace*
43
44whitespace
45  = [ \t\n\r]
46