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 "<!ELEMENT account (username?, password?, smtp?, pop?, imap?)>\n"
79 "<!ATTLIST account name CDATA #REQUIRED>\n"
80 "<!ELEMENT username (#PCDATA)>\n"
81 "<!ELEMENT password (#PCDATA)>\n"
82 "<!ELEMENT smtp (hostname, port, ssl, sslfingerprint)>\n"
83 "<!ELEMENT pop (hostname, port, ssl, sslfingerprint)>\n"
84 "<!ELEMENT imap (hostname, port, ssl, sslfingerprint)>\n"
85 "<!ELEMENT hostname (#PCDATA)>\n"
86 "<!ELEMENT port (#PCDATA)>\n"
87 "<!ELEMENT ssl (#PCDATA)>\n"
88 "<!ELEMENT sslfingerprint (#PCDATA)>\n"
92 if ((buf
= gcry_malloc(strlen(line
) + 1)) == NULL
)
99 gboolean
list_accounts(xmlTextReaderPtr reader
, gchar
**dst
, gint
*pwmd_errno
)
107 * "fast forward" to the first account.
109 while (xmlTextReaderRead(reader
) == 1) {
110 if ((n
= xmlTextReaderCurrentNode(reader
)) == NULL
) {
111 *pwmd_errno
= EPWMD_LIBXML_ERROR
;
115 if (xmlTextReaderDepth(reader
) == 1 &&
116 xmlStrcmp(n
->name
, (xmlChar
*)"account") == 0 &&
117 xmlTextReaderNodeType(reader
) == XML_READER_TYPE_ELEMENT
) {
118 xmlChar
*p
= xmlTextReaderGetAttribute(reader
, (xmlChar
*)"name");
123 str
= g_realloc(str
, (i
+ 2) * sizeof(gchar
*));
124 str
[i
++] = g_strdup((gchar
*)p
);
131 *pwmd_errno
= EPWMD_EMPTY_ELEMENT
;
135 line
= g_strjoinv("\n", str
);
141 gboolean
find_account(xmlTextReaderPtr reader
, gchar
*name
)
145 while (xmlTextReaderRead(reader
) == 1) {
146 if ((n
= xmlTextReaderCurrentNode(reader
)) == NULL
)
149 if (xmlTextReaderDepth(reader
) == 1 &&
150 xmlStrcmp(n
->name
, (xmlChar
*)"account") == 0 &&
151 xmlTextReaderNodeType(reader
) == XML_READER_TYPE_ELEMENT
) {
152 xmlChar
*p
= xmlTextReaderGetAttribute(reader
, (xmlChar
*)"name");
154 // Shouldn't happen (DTD).
158 if (xmlStrcmp(p
, (xmlChar
*)name
) == 0) {
170 gboolean
find_element(xmlTextReaderPtr reader
, gchar
*e
, gint more
)
174 while (xmlTextReaderRead(reader
) == 1) {
175 if ((n
= xmlTextReaderCurrentNode(reader
)) == NULL
)
179 * Stop processing after the closing account element to prevent
180 * finding element names that may exist in another account.
182 if (xmlTextReaderDepth(reader
) == 1 &&
183 xmlStrcmp(n
->name
, (xmlChar
*)"account") == 0 &&
184 xmlTextReaderNodeType(reader
) == XML_READER_TYPE_END_ELEMENT
)
187 if (xmlStrcmp(n
->name
, (xmlChar
*)e
) == 0 &&
188 xmlTextReaderNodeType(reader
) == XML_READER_TYPE_ELEMENT
)
195 xmlNodePtr
find_node(xmlNodePtr root
, xmlChar
*name
)
199 for (n
= root
->children
; n
; n
= n
->next
) {
200 if (g_ascii_strcasecmp((gchar
*)name
, (gchar
*)n
->name
) == 0)
207 gint
open_xml(const gchar
*data
, gsize size
, xmlDocPtr
*doc
,
208 xmlTextReaderPtr
*reader
)
210 if ((*doc
= xmlReadMemory(data
, size
, NULL
, "UTF-8",
211 XML_PARSE_NOBLANKS
)) == NULL
)
214 if ((*reader
= xmlReaderWalker(*doc
)) == NULL
)