Re: Patch for parsing CDATA sections.

Sam Steingold <[email protected]> Fri, 16 Jul 2004 11:33:41 -0400
Newsgroups gmane.lisp.clocc.general
Message-ID <[email protected]>
> * Lars Magne Ingebrigtsen <[email protected]> [2004-07-16 13:55:22 +0200]:
>
> We've just gotten a news feed that looks like this:
>
> <ARTIKKEL>
> <TITTEL><![CDATA[Stalltips fra Warren]]></TITTEL>
> <KATEGORI><![CDATA[Aksjetips]]></KATEGORI>
> <DATO><![CDATA[16.07.04 10:56]]></DATO>
> </ARTIKKEL>
>
> This is, according to people who know XML, valid.

indeed.

> clocc doesn't seem to be able to parse this -- it just gives a
> backtrace.

oops!

> So here's a quick patch that reads a marked section and just returns
> the text in the section.

Thanks.
For the future, I prefer "cvs diff -uw".
Please try the appended patch.


-- 
Sam Steingold (http://www.podval.org/~sds) running w2k
<http://www.camera.org> <http://www.iris.org.il> <http://www.memri.org/>
<http://www.mideasttruth.com/> <http://www.honestreporting.com>
Those who don't know lisp are destined to reinvent it, poorly.


--- xml.lisp	26 Sep 2003 11:28:57 -0400	2.46
+++ xml.lisp	16 Jul 2004 11:16:21 -0400	
@@ -745,12 +745,25 @@
                         'read-xml stream last)
                 (make-xml-decl :name name :args (nbutlast atts))))
          (#\!
-          (if (char= #\- (peek-char nil stream))
+          (case (peek-char nil stream)
+            (#\-                ; comment <!-- ... -->
               (let ((ch (progn (read-char stream) (read-char stream t nil t))))
                 (assert (char= #\- ch) (ch)
                         "~s: cannot handle: <!-~c" 'read-xml ch)
-                (make-xml-comment :data (xml-read-comment stream)))
-              (let ((obj (read stream t nil t)))
+               (make-xml-comment :data (xml-read-comment stream))))
+            (#\[                ; character data <![CDATA[ ... ]]>
+             (let ((res (make-array 20 :adjustable t :element-type 'character
+                                    :fill-pointer #.(length "[CDATA["))))
+               (assert (and (= (read-sequence res stream) 7)
+                            (string= res "[CDATA["))
+                       (res) "~s: cannot handle: <!~a" 'read-xml res)
+               (setf (fill-pointer res) 0)
+               (loop :for len = (vector-push-extend
+                                 (read-char stream t nil t) res)
+                 :until (and (>= len 3) (string= "]]>" res :start2 (- len 2)))
+                 :finally (setf (fill-pointer res) (- len 2)))
+               res))
+            (t (let ((obj (read stream t nil t)))
                 (case obj
                   (xml-tags::entity (make-xml-comment
                                      :data (xml-read-entity stream)))
@@ -761,7 +774,7 @@
                   (t (warn "~s: what is `~s'? proceed, with fingers crossed..."
                            'read-xml obj)
                      (cons obj (xml-list-to-alist
-                                (read-delimited-list #\> stream t))))))))
+                                 (read-delimited-list #\> stream t)))))))))
          (t (unread-char ch stream)
             (xml-read-tag stream)))))
     ;; do not need `xml-list-to-alist' in <!DOCTYPE foo [...]>


-------------------------------------------------------
This SF.Net email is sponsored by BEA Weblogic Workshop
FREE Java Enterprise J2EE developer tools!
Get your free copy of BEA WebLogic Workshop 8.1 today.
http://ads.osdn.com/?ad_id=4721&alloc_id=10040&op=click