comparison mcabber/libjabber/expat.c @ 417:c3ae9251c197

Sync libjabber with upstream Sync with jabberd-1.4.4.
author Mikael Berthe <mikael@lilotux.net>
date Thu, 01 Sep 2005 23:29:21 +0200
parents bf3d6e241714
children
comparison
equal deleted inserted replaced
416:48e7808c4191 417:c3ae9251c197
17 * Copyright (C) 1998-1999 The Jabber Team http://jabber.org/ 17 * Copyright (C) 1998-1999 The Jabber Team http://jabber.org/
18 */ 18 */
19 19
20 #include <libxode.h> 20 #include <libxode.h>
21 21
22 /**
23 * callback function used for start elements
24 *
25 * This function is used internally by expat.c as a callback function
26 * given to expat. It will create a new xmlnode and add it to the
27 * already created xmlnode tree.
28 *
29 * @param userdata pointer to the parent xmlnode instance (NULL if this function is called for the root note)
30 * @param name name of the starting element
31 * @param atts attributes that are contained in the start element
32 */
22 void expat_startElement(void* userdata, const char* name, const char** atts) 33 void expat_startElement(void* userdata, const char* name, const char** atts)
23 { 34 {
24 /* get the xmlnode pointed to by the userdata */ 35 /* get the xmlnode pointed to by the userdata */
25 xmlnode *x = userdata; 36 xmlnode *x = userdata;
26 xmlnode current = *x; 37 xmlnode current = *x;
37 *x = xmlnode_insert_tag(current, name); 48 *x = xmlnode_insert_tag(current, name);
38 xmlnode_put_expat_attribs(*x, atts); 49 xmlnode_put_expat_attribs(*x, atts);
39 } 50 }
40 } 51 }
41 52
53 /**
54 * callback function used for end elements
55 *
56 * This function is used internally by expat.c as a callback function
57 * given to expat. It will complete an xmlnode and update the userdata pointer
58 * to point to the node that is parent of the next starting element.
59 *
60 * @param userdata pointer to the current xmlnode
61 * @param name name of the ending element (ignored by this function)
62 */
42 void expat_endElement(void* userdata, const char* name) 63 void expat_endElement(void* userdata, const char* name)
43 { 64 {
44 xmlnode *x = userdata; 65 xmlnode *x = userdata;
45 xmlnode current = *x; 66 xmlnode current = *x;
46 67
50 /* if it's NULL we've hit the top folks, otherwise back up a level */ 71 /* if it's NULL we've hit the top folks, otherwise back up a level */
51 if(current != NULL) 72 if(current != NULL)
52 *x = current; 73 *x = current;
53 } 74 }
54 75
76 /**
77 * callback function for CDATA nodes
78 *
79 * This function will insert CDATA in an xmlnode
80 *
81 * @param userdata pointer to the current xmlnode
82 * @param s pointer to the CDATA string (not zero terminated!)
83 * @param len length of the CDATA string
84 */
55 void expat_charData(void* userdata, const char* s, int len) 85 void expat_charData(void* userdata, const char* s, int len)
56 { 86 {
57 xmlnode *x = userdata; 87 xmlnode *x = userdata;
58 xmlnode current = *x; 88 xmlnode current = *x;
59 89
60 xmlnode_insert_cdata(current, s, len); 90 xmlnode_insert_cdata(current, s, len);
61 } 91 }
62 92
63 93 /**
94 * create an xmlnode instance (possibly including other xmlnode instances) by parsing a string
95 *
96 * This function will parse a string containing an XML document and create an xmlnode graph
97 *
98 * @param str the string containing the XML document (not necessarily zero terminated)
99 * @param len the length of the string (without the zero byte, if present)
100 * @return the graph of xmlnodes that represent the parsed document, NULL on failure
101 */
64 xmlnode xmlnode_str(char *str, int len) 102 xmlnode xmlnode_str(char *str, int len)
65 { 103 {
66 XML_Parser p; 104 XML_Parser p;
67 xmlnode *x, node; /* pointer to an xmlnode */ 105 xmlnode *x, node; /* pointer to an xmlnode */
68 106
86 free(x); 124 free(x);
87 XML_ParserFree(p); 125 XML_ParserFree(p);
88 return node; /* return the xmlnode x points to */ 126 return node; /* return the xmlnode x points to */
89 } 127 }
90 128
129 /**
130 * create an xmlnode instance (possibly including other xmlnode instances) by parsing a file
131 *
132 * This function will parse a file containing an XML document and create an xmlnode graph
133 *
134 * @param file the filename
135 * @return the graph of xmlnodes that represent the parsed document, NULL on failure
136 */
91 xmlnode xmlnode_file(char *file) 137 xmlnode xmlnode_file(char *file)
92 { 138 {
93 XML_Parser p; 139 XML_Parser p;
94 xmlnode *x, node; /* pointer to an xmlnode */ 140 xmlnode *x, node; /* pointer to an xmlnode */
95 char buf[BUFSIZ]; 141 char buf[BUFSIZ];
126 free(x); 172 free(x);
127 close(fd); 173 close(fd);
128 return node; /* return the xmlnode x points to */ 174 return node; /* return the xmlnode x points to */
129 } 175 }
130 176
177 /**
178 * write an xmlnode to a file (without a size limit)
179 *
180 * @param file the target file
181 * @param node the xmlnode that should be written
182 * @return 1 on success, -1 on failure
183 */
131 int xmlnode2file(char *file, xmlnode node) 184 int xmlnode2file(char *file, xmlnode node)
132 { 185 {
133 char *doc; 186 return xmlnode2file_limited(file, node, 0);
187 }
188
189 /**
190 * write an xmlnode to a file, limited by size
191 *
192 * @param file the target file
193 * @param node the xmlnode that should be written
194 * @param sizelimit the maximum length of the file to be written
195 * @return 1 on success, 0 if failed due to size limit, -1 on failure
196 */
197 int xmlnode2file_limited(char *file, xmlnode node, size_t sizelimit)
198 {
199 char *doc, *ftmp;
134 int fd, i; 200 int fd, i;
201 size_t doclen;
135 202
136 if(file == NULL || node == NULL) 203 if(file == NULL || node == NULL)
137 return -1; 204 return -1;
138 205
139 fd = open(file, O_CREAT | O_WRONLY | O_TRUNC, 0600); 206 ftmp = spools(xmlnode_pool(node),file,".t.m.p",xmlnode_pool(node));
207 fd = open(ftmp, O_CREAT | O_WRONLY | O_TRUNC, 0600);
140 if(fd < 0) 208 if(fd < 0)
141 return -1; 209 return -1;
142 210
143 doc = xmlnode2str(node); 211 doc = xmlnode2str(node);
144 i = write(fd,doc,strlen(doc)); 212 doclen = strlen(doc);
213
214 if (sizelimit > 0 && doclen > sizelimit)
215 {
216 close(fd);
217 return 0;
218 }
219
220 i = write(fd,doc,doclen);
145 if(i < 0) 221 if(i < 0)
146 return -1; 222 return -1;
147 223
148 close(fd); 224 close(fd);
225
226 if(rename(ftmp,file) < 0)
227 {
228 unlink(ftmp);
229 return -1;
230 }
149 return 1; 231 return 1;
150 } 232 }
151 233
234 /**
235 * append attributes in the expat format to an existing xmlnode
236 *
237 * @param owner where to add the attributes
238 * @param atts the attributes in expat format (even indexes are the attribute names, odd indexes the values)
239 */
152 void xmlnode_put_expat_attribs(xmlnode owner, const char** atts) 240 void xmlnode_put_expat_attribs(xmlnode owner, const char** atts)
153 { 241 {
154 int i = 0; 242 int i = 0;
155 if (atts == NULL) return; 243 if (atts == NULL) return;
156 while (atts[i] != '\0') 244 while (atts[i] != '\0')