1 /* vim:tw=78:ts=8:sw=4:set ft=c: */
3 Copyright (C) 2006-2007 Ben Kibbey <bjk@luxsci.net>
5 This program is free software; you can redistribute it and/or modify
6 it under the terms of the GNU General Public License as published by
7 the Free Software Foundation; either version 2 of the License, or
8 (at your option) any later version.
10 This program is distributed in the hope that it will be useful,
11 but WITHOUT ANY WARRANTY; without even the implied warranty of
12 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
13 GNU General Public License for more details.
15 You should have received a copy of the GNU General Public License
16 along with this program; if not, write to the Free Software
17 Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111-1307 USA
35 #include "pwmd_error.h"
38 gboolean
valid_xml_element(const xmlChar
*element
)
42 if (!element
|| !*element
|| isdigit(*element
))
45 for (p
= element
; *p
; p
++) {
50 if (xmlStrncasecmp(element
, (xmlChar
*)"?xml", 4) == 0)
56 gboolean
new_account(xmlDocPtr doc
, gchar
*name
)
58 xmlNodePtr root
= xmlDocGetRootElement(doc
);
65 n
= xmlNewNode(NULL
, (xmlChar
*)"account");
66 n
= xmlAddChild(root
, n
);
67 a
= xmlNewProp(n
, (xmlChar
*)"name", (xmlChar
*)name
);
75 "<?xml version=\"1.0\"?>\n"
76 "<!DOCTYPE accounts [\n"
77 "<!ELEMENT accounts (account*)>\n"
78 "<!ATTLIST account name CDATA #REQUIRED>\n"
82 if ((buf
= gcry_malloc(strlen(line
) + 1)) == NULL
)
89 gboolean
list_accounts(xmlTextReaderPtr reader
, gchar
**dst
, gint
*pwmd_errno
)
97 * "fast forward" to the first account.
99 while (xmlTextReaderRead(reader
) == 1) {
100 if ((n
= xmlTextReaderCurrentNode(reader
)) == NULL
) {
101 *pwmd_errno
= EPWMD_LIBXML_ERROR
;
105 if (xmlTextReaderDepth(reader
) == 1 &&
106 xmlStrcmp(n
->name
, (xmlChar
*)"account") == 0 &&
107 xmlTextReaderNodeType(reader
) == XML_READER_TYPE_ELEMENT
) {
108 xmlChar
*p
= xmlTextReaderGetAttribute(reader
, (xmlChar
*)"name");
113 str
= g_realloc(str
, (i
+ 2) * sizeof(gchar
*));
114 str
[i
++] = g_strdup((gchar
*)p
);
121 *pwmd_errno
= EPWMD_EMPTY_ELEMENT
;
125 line
= g_strjoinv("\n", str
);
131 gboolean
find_account(xmlTextReaderPtr reader
, gchar
*name
)
135 while (xmlTextReaderRead(reader
) == 1) {
136 if ((n
= xmlTextReaderCurrentNode(reader
)) == NULL
)
139 if (xmlTextReaderDepth(reader
) == 1 &&
140 xmlStrcmp(n
->name
, (xmlChar
*)"account") == 0 &&
141 xmlTextReaderNodeType(reader
) == XML_READER_TYPE_ELEMENT
) {
142 xmlChar
*p
= xmlTextReaderGetAttribute(reader
, (xmlChar
*)"name");
144 // Shouldn't happen (DTD).
148 if (xmlStrcmp(p
, (xmlChar
*)name
) == 0) {
160 gboolean
find_element(xmlTextReaderPtr reader
, gchar
*e
, gint more
)
164 while (xmlTextReaderRead(reader
) == 1) {
165 if ((n
= xmlTextReaderCurrentNode(reader
)) == NULL
)
169 * Stop processing after the closing account element to prevent
170 * finding element names that may exist in another account.
172 if (xmlTextReaderDepth(reader
) == 1 &&
173 xmlStrcmp(n
->name
, (xmlChar
*)"account") == 0 &&
174 xmlTextReaderNodeType(reader
) == XML_READER_TYPE_END_ELEMENT
)
177 if (xmlStrcmp(n
->name
, (xmlChar
*)e
) == 0 &&
178 xmlTextReaderNodeType(reader
) == XML_READER_TYPE_ELEMENT
)
185 xmlNodePtr
find_node(xmlNodePtr root
, xmlChar
*name
)
189 for (n
= root
->children
; n
; n
= n
->next
) {
190 if (g_ascii_strcasecmp((gchar
*)name
, (gchar
*)n
->name
) == 0)
197 gint
open_xml(const gchar
*data
, gsize size
, xmlDocPtr
*doc
,
198 xmlTextReaderPtr
*reader
)
200 if ((*doc
= xmlReadMemory(data
, size
, NULL
, "UTF-8",
201 XML_PARSE_NOBLANKS
)) == NULL
)
204 if ((*reader
= xmlReaderWalker(*doc
)) == NULL
)