add filtering conditions message greater than, smaller than, and exactly matching...
[claws.git] / src / mgutils.c
1 /*
2  * Sylpheed -- a GTK+ based, lightweight, and fast e-mail client
3  * Copyright (C) 2001 Match Grun
4  *
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.
9  *
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.
14  *
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.
18  */
19
20 /*
21  * General functions for create common address book entries.
22  */
23
24 #include <glib.h>
25 #include <stdio.h>
26 #include <string.h>
27
28 #include "mgutils.h"
29
30 /*
31 * Dump linked list of character strings (for debug).
32 */
33 void mgu_print_list( GSList *list, FILE *stream ) {
34         GSList *node = list;
35         while( node ) {
36                 fprintf( stream, "\t- >%s<\n", (gchar *)node->data );
37                 node = g_slist_next( node );
38         }
39 }
40
41 /*
42 * Dump linked list of character strings (for debug).
43 */
44 void mgu_print_dlist( GList *list, FILE *stream ) {
45         GList *node = list;
46         while( node ) {
47                 fprintf( stream, "\t- >%s<\n", (gchar *)node->data );
48                 node = g_list_next( node );
49         }
50 }
51
52 /*
53 * Free linked list of character strings.
54 */
55 void mgu_free_list( GSList *list ) {
56         GSList *node = list;
57         while( node ) {
58                 g_free( node->data );
59                 node->data = NULL;
60                 node = g_slist_next( node );
61         }
62         g_slist_free( list );
63 }
64
65 /*
66 * Free linked list of character strings.
67 */
68 void mgu_free_dlist( GList *list ) {
69         GList *node = list;
70         while( node ) {
71                 g_free( node->data );
72                 node->data = NULL;
73                 node = g_list_next( node );
74         }
75         g_list_free( list );
76 }
77
78 /*
79 * Coalesce linked list of characaters into one long string.
80 */
81 gchar *mgu_list_coalesce( GSList *list ) {
82         gchar *str = NULL;
83         gchar *buf = NULL;
84         gchar *start = NULL;
85         GSList *node = NULL;
86         gint len;
87
88         if( ! list ) return NULL;
89
90         /* Calculate maximum length of text */
91         len = 0;
92         node = list;
93         while( node ) {
94                 str = node->data;
95                 len += 1 + strlen( str );
96                 node = g_slist_next( node );
97         }
98
99         /* Create new buffer. */
100         buf = g_new0( gchar, len+1 );
101         start = buf;
102         node = list;
103         while( node ) {
104                 str = node->data;
105                 len = strlen( str );
106                 strcpy( start, str );
107                 start += len;
108                 node = g_slist_next( node );
109         }
110         return buf;
111 }
112
113 struct mgu_error_entry {
114         gint    e_code;
115         gchar   *e_reason;
116 };
117
118 static const struct mgu_error_entry mgu_error_list[] = {
119         { MGU_SUCCESS,          "Success" },
120         { MGU_BAD_ARGS,         "Bad arguments" },
121         { MGU_NO_FILE,          "File not specified" },
122         { MGU_OPEN_FILE,        "Error opening file" },
123         { MGU_ERROR_READ,       "Error reading file" },
124         { MGU_EOF,              "End of file encountered" },
125         { MGU_OO_MEMORY,        "Error allocating memory" },
126         { MGU_BAD_FORMAT,       "Bad file format" },
127         { MGU_LDAP_CONNECT,     "Error connecting to LDAP server" },
128         { MGU_LDAP_INIT,        "Error initializing LDAP" },
129         { MGU_LDAP_BIND,        "Error binding to LDAP server" },
130         { MGU_LDAP_SEARCH,      "Error searching LDAP database" },
131         { MGU_LDAP_TIMEOUT,     "Timeout performing LDAP operation" },
132         { MGU_LDAP_CRITERIA,    "Error in LDAP search criteria" },
133         { MGU_LDAP_CRITERIA,    "Error in LDAP search criteria" },
134         { MGU_LDAP_NOENTRIES,   "No LDAP entries found for search criteria" },
135         { MGU_ERROR_WRITE,      "Error writing to file" },
136         { MGU_OPEN_DIRECTORY,   "Error opening directory" },
137         { MGU_NO_PATH,          "No path specified" },
138         { -999,                 NULL }
139 };
140
141 static const struct mgu_error_entry *mgu_error_find( gint err ) {
142         gint i;
143         for ( i = 0; mgu_error_list[i].e_code != -999; i++ ) {
144                 if ( err == mgu_error_list[i].e_code )
145                         return & mgu_error_list[i];
146         }
147         return NULL;
148 }
149
150 /*
151 * Return error message for specified error code.
152 */
153 gchar *mgu_error2string( gint err ) {
154         const struct mgu_error_entry *e;
155         e = mgu_error_find( err );
156         return ( e != NULL ) ? e->e_reason : "Unknown error";
157 }
158
159 /*
160 * Replace existing string with new string.
161 */
162 gchar *mgu_replace_string( gchar *str, const gchar *value ) {
163         if( str ) g_free( str );
164         if( value ) {
165                 str = g_strdup( value );
166                 g_strstrip( str );
167         }
168         else {
169                 str = NULL;
170         }
171         return str;
172 }
173
174 /*
175 * Clear a linked list by setting node data pointers to NULL. Note that
176 * items are not freed.
177 */
178 void mgu_clear_slist( GSList *list ) {
179         GSList *node = list;
180         while( node ) {
181                 node->data = NULL;
182                 node = g_slist_next( node );
183         }
184 }
185
186 /*
187 * Clear a linked list by setting node data pointers to NULL. Note that
188 * items are not freed.
189 */
190 void mgu_clear_list( GList *list ) {
191         GList *node = list;
192         while( node ) {
193                 node->data = NULL;
194                 node = g_list_next( node );
195         }
196 }
197
198 /*
199 * Test and reformat an email address.
200 * Enter:  address.
201 * Return: Address, or NULL if address is empty.
202 * Note: Leading and trailing white space is removed.
203 */
204 gchar *mgu_email_check_empty( gchar *address ) {
205         gchar *retVal = NULL;
206         if( address ) {
207                 retVal = g_strdup( address );
208                 retVal = g_strchug( retVal );
209                 retVal = g_strchomp( retVal );
210                 if( *retVal == '\0' ) {
211                         g_free( retVal );
212                         retVal = NULL;
213                 }
214         }
215         return retVal;
216 }
217
218 /*
219 * Parse string into linked list. Whitespace is used as a delimiter in parsing.
220 * Strings are parsed until maxTokens - 1 is reached. The remainder of the
221 * input string is copied into last element of list.
222 * Enter: line      String to parse.
223 *        maxTokens Maximum number of tokens to parse.
224 *        tokenCnt  If arg supplied, update with count of number of token parsed.
225 * Return: Linked list. The list contents should be g_free'd and list should
226 * freed when done.
227 */
228 GList *mgu_parse_string( gchar *line, const gint maxTokens, gint *tokenCnt ) {
229         gchar *ptr, *pStart, *pFound, *str;
230         gint  args = 0;
231         GList *list = NULL;
232         gboolean done = FALSE;
233
234         if( tokenCnt ) *tokenCnt = 0;
235         if( line == NULL ) return NULL;
236         if( maxTokens < 1 ) return NULL;
237
238         ptr = line;
239         while( ! done ) {
240                 args++;
241                 /* Skip over leading spaces */
242                 while( *ptr ) {
243                         if( ! isspace( *ptr ) ) break;
244                         ptr++;  
245                 }
246
247                 /* Find terminating space */
248                 pFound = NULL;
249                 pStart = ptr;
250                 while( *ptr ) {
251                         if( isspace( *ptr ) ) {
252                                 pFound = pStart;
253                                 break;
254                         }
255                         ptr++;
256                 }
257
258                 if( pFound ) {
259                         if( args == maxTokens ) {
260                                 /* Rest of string */
261                                 str = g_strdup( pStart );
262                                 done = TRUE;
263                         }
264                         else {
265                                 /* Extract part of string */
266                                 str = g_strndup( pStart, ptr - pFound );
267                         }
268                 }
269                 else {
270                         /* Nothing there - treat as rest of string */
271                         str = g_strdup( pStart );
272                         done = TRUE;
273                 }
274                 list = g_list_append( list, str );
275         }
276         if( tokenCnt ) *tokenCnt = args;
277         return list;
278 }
279
280 /*
281 * End of Source.
282 */