1 /*
2  *  Copyright 2004 The WebRTC Project Authors. All rights reserved.
3  *
4  *  Use of this source code is governed by a BSD-style license
5  *  that can be found in the LICENSE file in the root of the source
6  *  tree. An additional intellectual property rights grant can be found
7  *  in the file PATENTS.  All contributing project authors may
8  *  be found in the AUTHORS file in the root of the source tree.
9  */
10 
11 #include "webrtc/libjingle/xmpp/xmppstanzaparser.h"
12 
13 #include "webrtc/libjingle/xmllite/xmlelement.h"
14 #include "webrtc/libjingle/xmpp/constants.h"
15 #include "webrtc/base/common.h"
16 #ifdef EXPAT_RELATIVE_PATH
17 #include "expat.h"
18 #else
19 #include "third_party/expat/v2_0_1/Source/lib/expat.h"
20 #endif
21 
22 namespace buzz {
23 
XmppStanzaParser(XmppStanzaParseHandler * psph)24 XmppStanzaParser::XmppStanzaParser(XmppStanzaParseHandler *psph) :
25   psph_(psph),
26   innerHandler_(this),
27   parser_(&innerHandler_),
28   depth_(0),
29   builder_() {
30 }
31 
32 void
Reset()33 XmppStanzaParser::Reset() {
34   parser_.Reset();
35   depth_ = 0;
36   builder_.Reset();
37 }
38 
39 void
IncomingStartElement(XmlParseContext * pctx,const char * name,const char ** atts)40 XmppStanzaParser::IncomingStartElement(
41     XmlParseContext * pctx, const char * name, const char ** atts) {
42   if (depth_++ == 0) {
43     XmlElement * pelStream = XmlBuilder::BuildElement(pctx, name, atts);
44     if (pelStream == NULL) {
45       pctx->RaiseError(XML_ERROR_SYNTAX);
46       return;
47     }
48     psph_->StartStream(pelStream);
49     delete pelStream;
50     return;
51   }
52 
53   builder_.StartElement(pctx, name, atts);
54 }
55 
56 void
IncomingCharacterData(XmlParseContext * pctx,const char * text,int len)57 XmppStanzaParser::IncomingCharacterData(
58     XmlParseContext * pctx, const char * text, int len) {
59   if (depth_ > 1) {
60     builder_.CharacterData(pctx, text, len);
61   }
62 }
63 
64 void
IncomingEndElement(XmlParseContext * pctx,const char * name)65 XmppStanzaParser::IncomingEndElement(
66     XmlParseContext * pctx, const char * name) {
67   if (--depth_ == 0) {
68     psph_->EndStream();
69     return;
70   }
71 
72   builder_.EndElement(pctx, name);
73 
74   if (depth_ == 1) {
75     XmlElement *element = builder_.CreateElement();
76     psph_->Stanza(element);
77     delete element;
78   }
79 }
80 
81 void
IncomingError(XmlParseContext * pctx,XML_Error errCode)82 XmppStanzaParser::IncomingError(
83     XmlParseContext * pctx, XML_Error errCode) {
84   RTC_UNUSED(pctx);
85   RTC_UNUSED(errCode);
86   psph_->XmlError();
87 }
88 
89 }
90