commit fd6d076e7d99ca7f404449c2cee7d54abed91af4
parent c007a54a3e7afecb3e4a61d0b7b0720cd6bff25d
Author: Drew DeVault <sir@cmpwn.com>
Date: Sat, 10 Apr 2021 11:21:07 -0400
format::xml: implement CDATA
Diffstat:
1 file changed, 34 insertions(+), 2 deletions(-)
diff --git a/format/xml/parser.ha b/format/xml/parser.ha
@@ -154,9 +154,12 @@ fn scan_comment(par: *parser) (token | void | error) = {
'-' => { // Comments
want(par, '-')?;
},
- '[' => { // CDATA
+ '[' => {
want(par, "CDATA[")?;
- abort(); // TODO
+ if (par.state != state::ELEMENT) {
+ return syntaxerr;
+ };
+ return scan_cdata(par)?;
},
* => return syntaxerr,
},
@@ -181,6 +184,35 @@ fn scan_comment(par: *parser) (token | void | error) = {
return scan(par);
};
+fn scan_cdata(par: *parser) (text | error) = {
+ strio::reset(par.textbuf);
+ for (true) {
+ let rn = match (bufio::scanrune(par.in)?) {
+ io::EOF => return syntaxerr,
+ rn: rune => rn,
+ };
+ if (rn != ']') {
+ strio::appendrune(par.textbuf, rn);
+ continue;
+ };
+ let rn = match (bufio::scanrune(par.in)?) {
+ io::EOF => return syntaxerr,
+ rn: rune => rn,
+ };
+ if (rn != ']') {
+ strio::appendrune(par.textbuf, rn);
+ continue;
+ };
+ let rn = match (bufio::scanrune(par.in)?) {
+ io::EOF => return syntaxerr,
+ rn: rune => rn,
+ };
+ if (rn == '>') break;
+ strio::appendrune(par.textbuf, rn);
+ };
+ return strio::string(par.textbuf): text;
+};
+
fn scan_content(par: *parser) (text | error) = {
strio::reset(par.textbuf);
for (true) match (bufio::scanrune(par.in)?) {