Bug Summary

File:src/tools/addressbook-export/addressbook-export.c
Warning:line 183, column 1
Opened stream never closed. Potential resource leak

Annotated Source Code

Press '?' to see keyboard shortcuts

clang -cc1 -cc1 -triple x86_64-redhat-linux-gnu -O3 -analyze -disable-free -clear-ast-before-backend -disable-llvm-verifier -discard-value-names -main-file-name addressbook-export.c -analyzer-checker=core -analyzer-checker=apiModeling -analyzer-checker=unix -analyzer-checker=deadcode -analyzer-checker=security.insecureAPI.UncheckedReturn -analyzer-checker=security.insecureAPI.getpw -analyzer-checker=security.insecureAPI.gets -analyzer-checker=security.insecureAPI.mktemp -analyzer-checker=security.insecureAPI.mkstemp -analyzer-checker=security.insecureAPI.vfork -analyzer-checker=nullability.NullPassedToNonnull -analyzer-checker=nullability.NullReturnedFromNonnull -analyzer-output plist -w -setup-static-analyzer -mrelocation-model pic -pic-level 2 -pic-is-pie -mframe-pointer=none -relaxed-aliasing -fmath-errno -ffp-contract=on -fno-rounding-math -mconstructor-aliases -funwind-tables=2 -target-cpu x86-64 -tune-cpu generic -debugger-tuning=gdb -fdebug-compilation-dir=/builds/GNOME/evolution-data-server/_build -fcoverage-compilation-dir=/builds/GNOME/evolution-data-server/_build -resource-dir /usr/bin/../lib/clang/22 -D GLIB_VERSION_MAX_ALLOWED=GLIB_VERSION_2_68 -D GLIB_VERSION_MIN_REQUIRED=GLIB_VERSION_2_68 -D G_LOG_DOMAIN="addressbook-export" -D LDAP_DEPRECATED -D LOCALEDIR="/home/user/_prefix/share/locale" -D SOUP_VERSION_MAX_ALLOWED=SOUP_VERSION_3_2 -D SOUP_VERSION_MIN_REQUIRED=SOUP_VERSION_3_2 -D _LARGEFILE64_SOURCE=1 -I /builds/GNOME/evolution-data-server/_build -I /builds/GNOME/evolution-data-server/_build/src -I /builds/GNOME/evolution-data-server/_build/src/addressbook -I /builds/GNOME/evolution-data-server/src -I /builds/GNOME/evolution-data-server/src/addressbook -I /builds/GNOME/evolution-data-server/_build/src/tools/addressbook-export -I /usr/include/libxml2 -I /usr/include/libsoup-3.0 -I /usr/include/glib-2.0 -I /usr/lib64/glib-2.0/include -I /usr/include/libmount -I /usr/include/blkid -I /usr/include/sysprof-6 -I /home/user/_prefix/include -I /builds/GNOME/evolution-data-server/_build/src/private -I /builds/GNOME/evolution-data-server/src/private -I /builds/GNOME/evolution-data-server/_build/src/addressbook/libebook -I /builds/GNOME/evolution-data-server/src/addressbook/libebook -I /usr/include/nss3 -I /usr/include/nspr4 -I /builds/GNOME/evolution-data-server/_build/src/camel -I /builds/GNOME/evolution-data-server/src/camel -I /builds/GNOME/evolution-data-server/_build/src/libebackend -I /builds/GNOME/evolution-data-server/src/libebackend -I /usr/include/gio-unix-2.0 -I /builds/GNOME/evolution-data-server/_build/src/libedataserver -I /builds/GNOME/evolution-data-server/src/libedataserver -I /usr/include/libsecret-1 -I /usr/include/p11-kit-1 -I /usr/include/json-glib-1.0 -I /usr/include/uuid -I /builds/GNOME/evolution-data-server/_build/src/addressbook/libebook-contacts -I /builds/GNOME/evolution-data-server/src/addressbook/libebook-contacts -I /builds/GNOME/evolution-data-server/_build/src/addressbook/libedata-book -D NDEBUG -I /usr/include/libxml2 -I /usr/include -I /usr/include/libsoup-3.0 -I /usr/include/glib-2.0 -I /usr/lib64/glib-2.0/include -I /usr/include/libmount -I /usr/include/blkid -I /usr/include/sysprof-6 -D WITH_GZFILEOP -D I18N_PHONENUMBERS_USE_BOOST -I /usr/include/nss3 -I /usr/include/nspr4 -I /usr/include/gio-unix-2.0 -I /usr/include/libsecret-1 -I /usr/include/p11-kit-1 -I /usr/include/json-glib-1.0 -I /usr/include/uuid -internal-isystem /usr/bin/../lib/clang/22/include -internal-isystem /usr/local/include -internal-isystem /usr/bin/../lib/gcc/x86_64-redhat-linux/16/../../../../x86_64-redhat-linux/include -internal-externc-isystem /include -internal-externc-isystem /usr/include -Wno-unused-parameter -Wno-sign-compare -Wno-missing-field-initializers -Wno-missing-include-dirs -Wno-deprecated-declarations -Wno-cast-function-type -Wwrite-strings -fconst-strings -ferror-limit 19 -fgnuc-version=4.2.1 -fskip-odr-check-in-gmf -vectorize-loops -vectorize-slp -analyzer-output=html -faddrsig -fdwarf2-cfi-asm -o /builds/GNOME/evolution-data-server/_build/scan-build/2026-08-11-054813-10-1 -x c /builds/GNOME/evolution-data-server/src/tools/addressbook-export/addressbook-export.c
1/*
2 * SPDX-FileCopyrightText: (C) 1999-2008 Novell, Inc. (www.novell.com)
3 * SPDX-License-Identifier: LGPL-2.0-or-later
4 * SPDX-FileContributor: Gilbert Fang <gilbert.fang@sun.com>
5 */
6
7#include "evolution-data-server-config.h"
8
9#include <locale.h>
10#include <stdlib.h>
11#include <string.h>
12#include <glib/gi18n.h>
13#include <glib/gstdio.h>
14
15#include <libebook/libebook.h>
16#include <libedataserver/libedataserver.h>
17
18#define COMMA_SEPARATOR"," ","
19
20#define SUCCESS0 0
21#define FAILED-1 -1
22
23typedef enum {
24 ACTION_NOTHING = 0,
25 ACTION_LIST,
26 ACTION_LIST_WITH_COUNT,
27 ACTION_EXPORT
28} ActionType;
29
30#define DEFAULT_SIZE_NUMBER100 100
31
32struct _ActionContext {
33 GMainLoop *main_loop;
34 ActionType action_type;
35
36 ESourceRegistry *registry;
37 const gchar *output_file;
38
39 /* for cards only */
40 gint IsCSV;
41 gint IsVCard;
42 const gchar *addressbook_source_uid;
43};
44
45typedef struct _ActionContext ActionContext;
46
47typedef struct _SortData {
48 ESourceRegistry *registry;
49 GHashTable *parents; /* gchar *parent_uid ~> gchar *display_name */
50} SortData;
51
52static const gchar *
53sort_sources_get_parent_display_name (SortData *sd,
54 ESource *source)
55{
56 const gchar *parent_uid, *res;
57
58 if (!sd || !source)
59 return NULL((void*)0);
60
61 parent_uid = e_source_get_parent (source);
62 if (!parent_uid)
63 parent_uid = "";
64
65 res = g_hash_table_lookup (sd->parents, parent_uid);
66 if (!res) {
67 ESource *parent;
68 gchar *display_name;
69
70 parent = e_source_registry_ref_source (sd->registry, parent_uid);
71 display_name = parent ? e_source_dup_display_name (parent) : g_strdup (parent_uid)g_strdup_inline (parent_uid);
72 g_clear_object (&parent)do { _Static_assert (sizeof *((&parent)) == sizeof (gpointer
), "Expression evaluates to false"); __typeof__ (((&parent
))) _pp = ((&parent)); __typeof__ (*((&parent))) _ptr
= *_pp; *_pp = ((void*)0); if (_ptr) (g_object_unref) (_ptr)
; } while (0)
;
73
74 g_hash_table_insert (sd->parents, g_strdup (parent_uid)g_strdup_inline (parent_uid), display_name);
75
76 res = display_name;
77 }
78
79 return res;
80}
81
82static gint
83sort_sources_by_parent_cb (gconstpointer aa,
84 gconstpointer bb,
85 gpointer user_data)
86{
87 SortData *sd = user_data;
88 ESource *source_a = (ESource *) aa;
89 ESource *source_b = (ESource *) bb;
90 gint res;
91
92 res = g_strcmp0 (sort_sources_get_parent_display_name (sd, source_a),
93 sort_sources_get_parent_display_name (sd, source_b));
94
95 if (res == 0)
96 res = g_strcmp0 (e_source_get_display_name (source_a), e_source_get_display_name (source_b));
97
98 return res;
99}
100
101static void
102action_list_init (ActionContext *p_actctx,
103 gboolean with_count)
104{
105 ESourceRegistry *registry;
106 GList *list, *iter;
107 FILE *outputfile = NULL((void*)0);
108 SortData sd;
109 const gchar *extension_name;
110
111 registry = p_actctx->registry;
112
113 if (p_actctx->output_file != NULL((void*)0)) {
7
Assuming field 'output_file' is not equal to NULL
8
Taking true branch
114 if (!(outputfile = g_fopenfopen (p_actctx->output_file, "w"))) {
9
Stream opened here
10
Assuming that 'fopen' is successful
11
Assuming 'outputfile' is non-null
12
Taking false branch
115 g_warning (_("Can not open file")dcgettext (((void*)0), "Can not open file", 5));
116 exit (-1);
117 }
118 } else {
119 outputfile = stdoutstdout;
120 }
121
122 extension_name = E_SOURCE_EXTENSION_ADDRESS_BOOK"Address Book";
123 list = e_source_registry_list_sources (registry, extension_name);
124
125 sd.registry = registry;
126 sd.parents = g_hash_table_new_full (g_str_hash, g_str_equal, g_free, g_free);
127 list = g_list_sort_with_data (list, sort_sources_by_parent_cb, &sd);
128 g_hash_table_destroy (sd.parents);
129
130 for (iter = list; iter != NULL((void*)0); iter = g_list_next (iter)((iter) ? (((GList *)(iter))->next) : ((void*)0))) {
13
Assuming 'iter' is equal to NULL
14
Loop condition is false. Execution continues on line 179
131 ESource *source;
132 gchar *full_name;
133 const gchar *uid;
134 gint count = -1;
135
136 source = E_SOURCE (iter->data)((((ESource*) (void *) ((iter->data)))));
137 uid = e_source_get_uid (source);
138 full_name = e_util_get_source_full_name (registry, source);
139
140 if (with_count) {
141 EClient *client;
142 EBookClient *book_client;
143 GSList *contact_uids = NULL((void*)0);
144 GError *error = NULL((void*)0);
145
146 client = e_book_client_connect_sync (source, 5, NULL((void*)0), &error);
147
148 /* Sanity check. */
149 g_warn_if_fail (do { if (__builtin_expect (__extension__ ({ int _g_boolean_var_14
= 0; if (((client != ((void*)0)) && (error == ((void
*)0))) || ((client == ((void*)0)) && (error != ((void
*)0)))) _g_boolean_var_14 = 1; _g_boolean_var_14; }), 1)) ; else
g_warn_message ("addressbook-export", "/builds/GNOME/evolution-data-server/src/tools/addressbook-export/addressbook-export.c"
, 151, ((const char*) (__func__)), "((client != NULL) && (error == NULL)) || ((client == NULL) && (error != NULL))"
); } while (0)
150 ((client != NULL) && (error == NULL)) ||do { if (__builtin_expect (__extension__ ({ int _g_boolean_var_14
= 0; if (((client != ((void*)0)) && (error == ((void
*)0))) || ((client == ((void*)0)) && (error != ((void
*)0)))) _g_boolean_var_14 = 1; _g_boolean_var_14; }), 1)) ; else
g_warn_message ("addressbook-export", "/builds/GNOME/evolution-data-server/src/tools/addressbook-export/addressbook-export.c"
, 151, ((const char*) (__func__)), "((client != NULL) && (error == NULL)) || ((client == NULL) && (error != NULL))"
); } while (0)
151 ((client == NULL) && (error != NULL)))do { if (__builtin_expect (__extension__ ({ int _g_boolean_var_14
= 0; if (((client != ((void*)0)) && (error == ((void
*)0))) || ((client == ((void*)0)) && (error != ((void
*)0)))) _g_boolean_var_14 = 1; _g_boolean_var_14; }), 1)) ; else
g_warn_message ("addressbook-export", "/builds/GNOME/evolution-data-server/src/tools/addressbook-export/addressbook-export.c"
, 151, ((const char*) (__func__)), "((client != NULL) && (error == NULL)) || ((client == NULL) && (error != NULL))"
); } while (0)
;
152
153 if (error != NULL((void*)0)) {
154 g_warning (_("Failed to open client “%s”: %s")dcgettext (((void*)0), "Failed to open client “%s”: %s", 5
)
, full_name, error->message);
155 g_error_free (error);
156 g_free (full_name);
157 continue;
158 }
159
160 book_client = E_BOOK_CLIENT (client)((((EBookClient*) (void *) ((client)))));
161
162 if (!e_book_client_get_contacts_uids_sync (book_client, "#t", &contact_uids, NULL((void*)0), NULL((void*)0)))
163 contact_uids = NULL((void*)0);
164
165 count = g_slist_length (contact_uids);
166
167 g_slist_free_full (contact_uids, g_free);
168 g_object_unref (book_client);
169 }
170
171 if (count != -1)
172 fprintf (outputfile, "\"%s\",\"%s\",%d\n", uid, full_name, count);
173 else
174 fprintf (outputfile, "\"%s\",\"%s\"\n", uid, full_name);
175
176 g_free (full_name);
177 }
178
179 g_list_free_full (list, (GDestroyNotify) g_object_unref);
180
181 if (outputfile
14.1
'outputfile' is non-null
&& outputfile != stdoutstdout)
15
Assuming 'outputfile' is equal to 'stdout'
16
Taking false branch
182 fclose (outputfile);
183}
17
Opened stream never closed. Potential resource leak
184
185typedef enum _CARD_FORMAT CARD_FORMAT;
186typedef enum _DeliveryAddressField DeliveryAddressField;
187typedef enum _EContactFieldCSV EContactFieldCSV;
188typedef struct _EContactCSVFieldData EContactCSVFieldData;
189
190enum _CARD_FORMAT
191{
192 CARD_FORMAT_CSV,
193 CARD_FORMAT_VCARD
194};
195
196enum _DeliveryAddressField
197{
198 DELIVERY_ADDRESS_STREET,
199 DELIVERY_ADDRESS_EXT,
200 DELIVERY_ADDRESS_LOCALITY,
201 DELIVERY_ADDRESS_REGION,
202 DELIVERY_ADDRESS_CODE,
203 DELIVERY_ADDRESS_COUNTRY
204};
205
206enum _EContactFieldCSV
207{
208 E_CONTACT_CSV_FILE_AS,
209 E_CONTACT_CSV_FULL_NAME,
210 E_CONTACT_CSV_EMAIL_1,
211 E_CONTACT_CSV_EMAIL_2,
212 E_CONTACT_CSV_EMAIL_3,
213 E_CONTACT_CSV_EMAIL_4,
214 E_CONTACT_CSV_PHONE_PRIMARY,
215 E_CONTACT_CSV_PHONE_ASSISTANT,
216 E_CONTACT_CSV_PHONE_BUSINESS,
217 E_CONTACT_CSV_PHONE_CALLBACK,
218 E_CONTACT_CSV_PHONE_COMPANY,
219 E_CONTACT_CSV_PHONE_HOME,
220 E_CONTACT_CSV_ORG,
221 /*E_CONTACT_CSV_ADDRESS_BUSINESS, */
222 E_CONTACT_CSV_ADDRESS_BUSINESS_STREET,
223 E_CONTACT_CSV_ADDRESS_BUSINESS_EXT,
224 E_CONTACT_CSV_ADDRESS_BUSINESS_CITY,
225 E_CONTACT_CSV_ADDRESS_BUSINESS_REGION,
226 E_CONTACT_CSV_ADDRESS_BUSINESS_POSTCODE,
227 E_CONTACT_CSV_ADDRESS_BUSINESS_COUNTRY,
228 /*E_CONTACT_CSV_ADDRESS_HOME, */
229 E_CONTACT_CSV_ADDRESS_HOME_STREET,
230 E_CONTACT_CSV_ADDRESS_HOME_EXT,
231 E_CONTACT_CSV_ADDRESS_HOME_CITY,
232 E_CONTACT_CSV_ADDRESS_HOME_REGION,
233 E_CONTACT_CSV_ADDRESS_HOME_POSTCODE,
234 E_CONTACT_CSV_ADDRESS_HOME_COUNTRY,
235 E_CONTACT_CSV_PHONE_MOBILE,
236 E_CONTACT_CSV_PHONE_CAR,
237 E_CONTACT_CSV_PHONE_BUSINESS_FAX,
238 E_CONTACT_CSV_PHONE_HOME_FAX,
239 E_CONTACT_CSV_PHONE_BUSINESS_2,
240 E_CONTACT_CSV_PHONE_HOME_2,
241 E_CONTACT_CSV_PHONE_ISDN,
242 E_CONTACT_CSV_PHONE_OTHER,
243 E_CONTACT_CSV_PHONE_OTHER_FAX,
244 E_CONTACT_CSV_PHONE_PAGER,
245 E_CONTACT_CSV_PHONE_RADIO,
246 E_CONTACT_CSV_PHONE_TELEX,
247 E_CONTACT_CSV_PHONE_TTYTDD,
248 /*E_CONTACT_CSV_ADDRESS_OTHER, */
249 E_CONTACT_CSV_ADDRESS_OTHER_STREET,
250 E_CONTACT_CSV_ADDRESS_OTHER_EXT,
251 E_CONTACT_CSV_ADDRESS_OTHER_CITY,
252 E_CONTACT_CSV_ADDRESS_OTHER_REGION,
253 E_CONTACT_CSV_ADDRESS_OTHER_POSTCODE,
254 E_CONTACT_CSV_ADDRESS_OTHER_COUNTRY,
255 E_CONTACT_CSV_HOMEPAGE_URL,
256 E_CONTACT_CSV_ORG_UNIT,
257 E_CONTACT_CSV_OFFICE,
258 E_CONTACT_CSV_TITLE,
259 E_CONTACT_CSV_ROLE,
260 E_CONTACT_CSV_MANAGER,
261 E_CONTACT_CSV_ASSISTANT,
262 E_CONTACT_CSV_NICKNAME,
263 E_CONTACT_CSV_SPOUSE,
264 E_CONTACT_CSV_NOTE,
265 E_CONTACT_CSV_CALENDAR_URI,
266 E_CONTACT_CSV_FREEBUSY_URL,
267 /*E_CONTACT_CSV_ANNIVERSARY, */
268 E_CONTACT_CSV_ANNIVERSARY_YEAR,
269 E_CONTACT_CSV_ANNIVERSARY_MONTH,
270 E_CONTACT_CSV_ANNIVERSARY_DAY,
271 /*E_CONTACT_CSV_BIRTH_DATE, */
272 E_CONTACT_CSV_BIRTH_DATE_YEAR,
273 E_CONTACT_CSV_BIRTH_DATE_MONTH,
274 E_CONTACT_CSV_BIRTH_DATE_DAY,
275 E_CONTACT_CSV_MAILER,
276 E_CONTACT_CSV_NAME_OR_ORG,
277 E_CONTACT_CSV_CATEGORIES,
278 E_CONTACT_CSV_FAMILY_NAME,
279 E_CONTACT_CSV_GIVEN_NAME,
280 E_CONTACT_CSV_WANTS_HTML,
281 E_CONTACT_CSV_IS_LIST,
282 E_CONTACT_CSV_MIDDLE_NAME,
283 E_CONTACT_CSV_NAME_TITLE,
284 E_CONTACT_CSV_NAME_SUFFIX,
285 E_CONTACT_CSV_LAST
286};
287
288typedef enum {
289 DT_STRING,
290 DT_BOOLEAN
291} EContactCSVDataType;
292
293struct _EContactCSVFieldData
294{
295 gint csv_field;
296 gint contact_field;
297 const gchar *csv_name;
298 EContactCSVDataType data_type;
299};
300
301#define NOMAP-1 -1
302static EContactCSVFieldData csv_field_data[] = {
303 {E_CONTACT_CSV_FILE_AS, E_CONTACT_FILE_AS, "", DT_STRING},
304 {E_CONTACT_CSV_FULL_NAME, E_CONTACT_FULL_NAME, "", DT_STRING},
305 {E_CONTACT_CSV_EMAIL_1, E_CONTACT_EMAIL_1, "", DT_STRING},
306 {E_CONTACT_CSV_EMAIL_2, E_CONTACT_EMAIL_2, "", DT_STRING},
307 {E_CONTACT_CSV_EMAIL_3, E_CONTACT_EMAIL_3, "", DT_STRING},
308 {E_CONTACT_CSV_EMAIL_4, E_CONTACT_EMAIL_4, "", DT_STRING},
309 {E_CONTACT_CSV_PHONE_PRIMARY, E_CONTACT_PHONE_PRIMARY, "", DT_STRING},
310 {E_CONTACT_CSV_PHONE_ASSISTANT, E_CONTACT_PHONE_ASSISTANT, "", DT_STRING},
311 {E_CONTACT_CSV_PHONE_BUSINESS, E_CONTACT_PHONE_BUSINESS, "", DT_STRING},
312 {E_CONTACT_CSV_PHONE_CALLBACK, E_CONTACT_PHONE_CALLBACK, "", DT_STRING},
313 {E_CONTACT_CSV_PHONE_COMPANY, E_CONTACT_PHONE_COMPANY, "", DT_STRING},
314 {E_CONTACT_CSV_PHONE_HOME, E_CONTACT_PHONE_HOME, "", DT_STRING},
315 {E_CONTACT_CSV_ORG, E_CONTACT_ORG, "", DT_STRING},
316 /*E_CONTACT_CSV_ADDRESS_BUSINESS, */
317 {E_CONTACT_CSV_ADDRESS_BUSINESS_STREET, NOMAP-1, "Business Address", DT_STRING},
318 {E_CONTACT_CSV_ADDRESS_BUSINESS_EXT, NOMAP-1, "Business Address2", DT_STRING},
319 {E_CONTACT_CSV_ADDRESS_BUSINESS_CITY, NOMAP-1, "Business Address City", DT_STRING},
320 {E_CONTACT_CSV_ADDRESS_BUSINESS_REGION, NOMAP-1, "Business Address State", DT_STRING},
321 {E_CONTACT_CSV_ADDRESS_BUSINESS_POSTCODE, NOMAP-1, "Business Address PostCode", DT_STRING},
322 {E_CONTACT_CSV_ADDRESS_BUSINESS_COUNTRY, NOMAP-1, "Business Address Country", DT_STRING},
323 /*E_CONTACT_CSV_ADDRESS_HOME, */
324 {E_CONTACT_CSV_ADDRESS_HOME_STREET, NOMAP-1, "Home Address", DT_STRING},
325 {E_CONTACT_CSV_ADDRESS_HOME_EXT, NOMAP-1, "Home Address2", DT_STRING},
326 {E_CONTACT_CSV_ADDRESS_HOME_CITY, NOMAP-1, "Home Address City", DT_STRING},
327 {E_CONTACT_CSV_ADDRESS_HOME_REGION, NOMAP-1, "Home Address State", DT_STRING},
328 {E_CONTACT_CSV_ADDRESS_HOME_POSTCODE, NOMAP-1, "Home Address PostCode", DT_STRING},
329 {E_CONTACT_CSV_ADDRESS_HOME_COUNTRY, NOMAP-1, "Home Address Country", DT_STRING},
330 {E_CONTACT_CSV_PHONE_MOBILE, E_CONTACT_PHONE_MOBILE, "", DT_STRING},
331 {E_CONTACT_CSV_PHONE_CAR, E_CONTACT_PHONE_CAR, "", DT_STRING},
332 {E_CONTACT_CSV_PHONE_BUSINESS_FAX, E_CONTACT_PHONE_BUSINESS_FAX, "", DT_STRING},
333 {E_CONTACT_CSV_PHONE_HOME_FAX, E_CONTACT_PHONE_HOME_FAX, "", DT_STRING},
334 {E_CONTACT_CSV_PHONE_BUSINESS_2, E_CONTACT_PHONE_BUSINESS_2, "", DT_STRING},
335 {E_CONTACT_CSV_PHONE_HOME_2, E_CONTACT_PHONE_HOME_2, "", DT_STRING},
336 {E_CONTACT_CSV_PHONE_ISDN, E_CONTACT_PHONE_ISDN, "", DT_STRING},
337 {E_CONTACT_CSV_PHONE_OTHER, E_CONTACT_PHONE_OTHER, "", DT_STRING},
338 {E_CONTACT_CSV_PHONE_OTHER_FAX, E_CONTACT_PHONE_OTHER_FAX, "", DT_STRING},
339 {E_CONTACT_CSV_PHONE_PAGER, E_CONTACT_PHONE_PAGER, "", DT_STRING},
340 {E_CONTACT_CSV_PHONE_RADIO, E_CONTACT_PHONE_RADIO, "", DT_STRING},
341 {E_CONTACT_CSV_PHONE_TELEX, E_CONTACT_PHONE_TELEX, "", DT_STRING},
342 {E_CONTACT_CSV_PHONE_TTYTDD, E_CONTACT_PHONE_TTYTDD, "", DT_STRING},
343 /*E_CONTACT_CSV_ADDRESS_OTHER, */
344 {E_CONTACT_CSV_ADDRESS_OTHER_STREET, NOMAP-1, "Other Address", DT_STRING},
345 {E_CONTACT_CSV_ADDRESS_OTHER_EXT, NOMAP-1, "Other Address2", DT_STRING},
346 {E_CONTACT_CSV_ADDRESS_OTHER_CITY, NOMAP-1, "Other Address City", DT_STRING},
347 {E_CONTACT_CSV_ADDRESS_OTHER_REGION, NOMAP-1, "Other Address State", DT_STRING},
348 {E_CONTACT_CSV_ADDRESS_OTHER_POSTCODE, NOMAP-1, "Other Address PostCode", DT_STRING},
349 {E_CONTACT_CSV_ADDRESS_OTHER_COUNTRY, NOMAP-1, "Other Address Country", DT_STRING},
350 {E_CONTACT_CSV_HOMEPAGE_URL, E_CONTACT_HOMEPAGE_URL, "", DT_STRING},
351 {E_CONTACT_CSV_ORG_UNIT, E_CONTACT_ORG_UNIT, "", DT_STRING},
352 {E_CONTACT_CSV_OFFICE, E_CONTACT_OFFICE, "", DT_STRING},
353 {E_CONTACT_CSV_TITLE, E_CONTACT_TITLE, "", DT_STRING},
354 {E_CONTACT_CSV_ROLE, E_CONTACT_ROLE, "", DT_STRING},
355 {E_CONTACT_CSV_MANAGER, E_CONTACT_MANAGER, "", DT_STRING},
356 {E_CONTACT_CSV_ASSISTANT, E_CONTACT_ASSISTANT, "", DT_STRING},
357 {E_CONTACT_CSV_NICKNAME, E_CONTACT_NICKNAME, "", DT_STRING},
358 {E_CONTACT_CSV_SPOUSE, E_CONTACT_SPOUSE, "", DT_STRING},
359 {E_CONTACT_CSV_NOTE, E_CONTACT_NOTE, "", DT_STRING},
360 {E_CONTACT_CSV_CALENDAR_URI, E_CONTACT_CALENDAR_URI, "", DT_STRING},
361 {E_CONTACT_CSV_FREEBUSY_URL, E_CONTACT_FREEBUSY_URL, "", DT_STRING},
362 /*E_CONTACT_ANNIVERSARY, */
363 {E_CONTACT_CSV_ANNIVERSARY_YEAR, NOMAP-1, "Anniversary Year", DT_STRING},
364 {E_CONTACT_CSV_ANNIVERSARY_MONTH, NOMAP-1, "Anniversary Month", DT_STRING},
365 {E_CONTACT_CSV_ANNIVERSARY_DAY, NOMAP-1, "Anniversary Day", DT_STRING},
366 /*E_CONTACT_BIRTH_DATE, */
367 {E_CONTACT_CSV_BIRTH_DATE_YEAR, NOMAP-1, "Birth Year", DT_STRING},
368 {E_CONTACT_CSV_BIRTH_DATE_MONTH, NOMAP-1, "Birth Month", DT_STRING},
369 {E_CONTACT_CSV_BIRTH_DATE_DAY, NOMAP-1, "Birth Day", DT_STRING},
370 {E_CONTACT_CSV_MAILER, E_CONTACT_MAILER, "", DT_STRING},
371 {E_CONTACT_CSV_NAME_OR_ORG, E_CONTACT_NAME_OR_ORG, "", DT_STRING},
372 {E_CONTACT_CSV_CATEGORIES, E_CONTACT_CATEGORIES, "", DT_STRING},
373 {E_CONTACT_CSV_FAMILY_NAME, E_CONTACT_FAMILY_NAME, "", DT_STRING},
374 {E_CONTACT_CSV_GIVEN_NAME, E_CONTACT_GIVEN_NAME, "", DT_STRING},
375 {E_CONTACT_CSV_WANTS_HTML, E_CONTACT_WANTS_HTML, "", DT_BOOLEAN},
376 {E_CONTACT_CSV_IS_LIST, E_CONTACT_IS_LIST, "", DT_BOOLEAN},
377 {E_CONTACT_CSV_MIDDLE_NAME, NOMAP-1, "middle_name", DT_STRING},
378 {E_CONTACT_CSV_NAME_TITLE, NOMAP-1, "name_title", DT_STRING},
379 {E_CONTACT_CSV_NAME_SUFFIX, NOMAP-1, "name_suffix", DT_STRING},
380 {E_CONTACT_CSV_LAST, NOMAP-1, "", DT_STRING}
381
382};
383
384static gchar *
385escape_string (gchar *orig)
386{
387 const guchar *p;
388 gchar *dest;
389 gchar *q;
390
391 if (orig == NULL((void*)0))
392 return g_strdup ("\"\"")g_strdup_inline ("\"\"");
393
394 p = (guchar *) orig;
395 /* Each source byte needs maximally two destination chars (\n), and the extra 2 is for the leading and trailing '"' */
396 q = dest = g_malloc (strlen (orig) * 2 + 1 + 2);
397
398 *q++ = '\"';
399 while (*p)
400 {
401 switch (*p)
402 {
403 case '\n':
404 *q++ = '\\';
405 *q++ = 'n';
406 break;
407 case '\r':
408 *q++ = '\\';
409 *q++ = 'r';
410 break;
411 case '\\':
412 *q++ = '\\';
413 *q++ = '\\';
414 break;
415 case '"':
416 *q++ = '"';
417 *q++ = '"';
418 break;
419 default:
420 *q++ = *p;
421 }
422 p++;
423 }
424
425 *q++ = '\"';
426 *q = 0;
427
428 return dest;
429}
430
431static gchar *
432check_null_pointer (gchar *orig)
433{
434 gchar *result;
435 if (orig == NULL((void*)0))
436 result = g_strdup ("")g_strdup_inline ("");
437 else
438 result = g_strdup (orig)g_strdup_inline (orig);
439 return result;
440}
441
442static gchar *
443delivery_address_get_sub_field (const EContactAddress *address,
444 DeliveryAddressField sub_field)
445{
446 gchar *sub_field_value;
447 gchar *str_temp, *str_temp_a;
448 if (address != NULL((void*)0)) {
449 switch (sub_field) {
450 case DELIVERY_ADDRESS_STREET:
451 str_temp_a = check_null_pointer (address->po);
452 str_temp = check_null_pointer (address->street);
453 sub_field_value = g_strdup_printf ("%s %s", str_temp_a, str_temp);
454 g_free (str_temp);
455 g_free (str_temp_a);
456 break;
457 case DELIVERY_ADDRESS_EXT:
458 sub_field_value = check_null_pointer (address->ext);
459 break;
460 case DELIVERY_ADDRESS_LOCALITY:
461 sub_field_value = check_null_pointer (address->locality);
462 break;
463 case DELIVERY_ADDRESS_REGION:
464 sub_field_value = check_null_pointer (address->region);
465 break;
466 case DELIVERY_ADDRESS_CODE:
467 sub_field_value = check_null_pointer (address->code);
468 break;
469 case DELIVERY_ADDRESS_COUNTRY:
470 sub_field_value = check_null_pointer (address->country);
471 break;
472 default:
473 sub_field_value = g_strdup ("")g_strdup_inline ("");
474 }
475 } else {
476 sub_field_value = g_strdup ("")g_strdup_inline ("");
477 }
478 return sub_field_value;
479}
480
481static gint
482e_contact_csv_get_contact_field (EContactFieldCSV csv_field)
483{
484 return csv_field_data[csv_field].contact_field;
485}
486
487static EContactCSVDataType
488e_contact_csv_get_data_type (EContactFieldCSV csv_field)
489{
490 return csv_field_data[csv_field].data_type;
491}
492
493static gchar *
494e_contact_csv_get_name (EContactFieldCSV csv_field)
495{
496 gint contact_field;
497 gchar *name;
498 gchar *quoted_name;
499
500 contact_field = e_contact_csv_get_contact_field (csv_field);
501
502 if (contact_field != NOMAP-1) {
503 name = g_strdup (e_contact_field_name (contact_field))g_strdup_inline (e_contact_field_name (contact_field));
504 } else {
505 name = g_strdup (csv_field_data[csv_field].csv_name)g_strdup_inline (csv_field_data[csv_field].csv_name);
506 }
507 quoted_name = escape_string (name);
508 g_free (name);
509 return quoted_name;
510}
511
512static gchar *
513e_contact_csv_get (EContact *contact,
514 EContactFieldCSV csv_field)
515{
516 gint contact_field;
517 gchar *field_value = NULL((void*)0);
518 gchar *quoted_field_value;
519
520 EContactAddress *delivery_address = NULL((void*)0);
521 EContactDate *date;
522 EContactName *name;
523
524 contact_field = e_contact_csv_get_contact_field (csv_field);
525
526 if (contact_field != NOMAP-1) {
527 field_value = e_contact_get (contact, contact_field);
528 if (e_contact_csv_get_data_type (csv_field) == DT_BOOLEAN) {
529 field_value = g_strdup ((GPOINTER_TO_INT (field_value)) ? "TRUE" : "FALSE")g_strdup_inline ((((gint) (glong) (field_value))) ? "TRUE" : "FALSE"
)
;
530 }
531 } else {
532 switch (csv_field) {
533 case E_CONTACT_CSV_ADDRESS_HOME_STREET:
534 delivery_address = e_contact_get (contact, E_CONTACT_ADDRESS_HOME);
535 field_value = delivery_address_get_sub_field (delivery_address, DELIVERY_ADDRESS_STREET);
536 break;
537 case E_CONTACT_CSV_ADDRESS_HOME_EXT:
538 delivery_address = e_contact_get (contact, E_CONTACT_ADDRESS_HOME);
539 field_value = delivery_address_get_sub_field (delivery_address, DELIVERY_ADDRESS_EXT);
540 break;
541 case E_CONTACT_CSV_ADDRESS_HOME_CITY:
542 delivery_address = e_contact_get (contact, E_CONTACT_ADDRESS_HOME);
543 field_value = delivery_address_get_sub_field (delivery_address, DELIVERY_ADDRESS_LOCALITY);
544 break;
545 case E_CONTACT_CSV_ADDRESS_HOME_REGION:
546 delivery_address = e_contact_get (contact, E_CONTACT_ADDRESS_HOME);
547 field_value = delivery_address_get_sub_field (delivery_address, DELIVERY_ADDRESS_REGION);
548 break;
549 case E_CONTACT_CSV_ADDRESS_HOME_POSTCODE:
550 delivery_address = e_contact_get (contact, E_CONTACT_ADDRESS_HOME);
551 field_value = delivery_address_get_sub_field (delivery_address, DELIVERY_ADDRESS_CODE);
552 break;
553 case E_CONTACT_CSV_ADDRESS_HOME_COUNTRY:
554 delivery_address = e_contact_get (contact, E_CONTACT_ADDRESS_HOME);
555 field_value = delivery_address_get_sub_field (delivery_address, DELIVERY_ADDRESS_COUNTRY);
556 break;
557 case E_CONTACT_CSV_ADDRESS_BUSINESS_STREET:
558 delivery_address = e_contact_get (contact, E_CONTACT_ADDRESS_WORK);
559 field_value = delivery_address_get_sub_field (delivery_address, DELIVERY_ADDRESS_STREET);
560 break;
561 case E_CONTACT_CSV_ADDRESS_BUSINESS_EXT:
562 delivery_address = e_contact_get (contact, E_CONTACT_ADDRESS_WORK);
563 field_value = delivery_address_get_sub_field (delivery_address, DELIVERY_ADDRESS_EXT);
564 break;
565 case E_CONTACT_CSV_ADDRESS_BUSINESS_CITY:
566 delivery_address = e_contact_get (contact, E_CONTACT_ADDRESS_WORK);
567 field_value = delivery_address_get_sub_field (delivery_address, DELIVERY_ADDRESS_LOCALITY);
568 break;
569 case E_CONTACT_CSV_ADDRESS_BUSINESS_REGION:
570 delivery_address = e_contact_get (contact, E_CONTACT_ADDRESS_WORK);
571 field_value = delivery_address_get_sub_field (delivery_address, DELIVERY_ADDRESS_REGION);
572 break;
573 case E_CONTACT_CSV_ADDRESS_BUSINESS_POSTCODE:
574 delivery_address = e_contact_get (contact, E_CONTACT_ADDRESS_WORK);
575 field_value = delivery_address_get_sub_field (delivery_address, DELIVERY_ADDRESS_CODE);
576 break;
577 case E_CONTACT_CSV_ADDRESS_BUSINESS_COUNTRY:
578 delivery_address = e_contact_get (contact, E_CONTACT_ADDRESS_WORK);
579 field_value = delivery_address_get_sub_field (delivery_address, DELIVERY_ADDRESS_COUNTRY);
580 break;
581 case E_CONTACT_CSV_BIRTH_DATE_YEAR:
582 date = e_contact_get (contact, E_CONTACT_BIRTH_DATE);
583 if (date) {
584 field_value = g_strdup_printf ("%04d", date->year);
585 e_contact_date_free (date);
586 }
587 break;
588
589 case E_CONTACT_CSV_BIRTH_DATE_MONTH:
590 date = e_contact_get (contact, E_CONTACT_BIRTH_DATE);
591 if (date) {
592 field_value = g_strdup_printf ("%04d", date->month);
593 e_contact_date_free (date);
594 }
595 break;
596
597 case E_CONTACT_CSV_BIRTH_DATE_DAY:
598 date = e_contact_get (contact, E_CONTACT_BIRTH_DATE);
599 if (date) {
600 field_value = g_strdup_printf ("%04d", date->day);
601 e_contact_date_free (date);
602 }
603 break;
604 case E_CONTACT_CSV_NAME_TITLE:
605 case E_CONTACT_CSV_MIDDLE_NAME:
606 case E_CONTACT_CSV_NAME_SUFFIX:
607 field_value = NULL((void*)0);
608 name = e_contact_get (contact, E_CONTACT_NAME);
609 if (name) {
610 if (csv_field == E_CONTACT_CSV_NAME_TITLE)
611 field_value = g_strdup (name->prefixes)g_strdup_inline (name->prefixes);
612 else if (csv_field == E_CONTACT_CSV_MIDDLE_NAME)
613 field_value = g_strdup (name->additional)g_strdup_inline (name->additional);
614 else if (csv_field == E_CONTACT_CSV_NAME_SUFFIX)
615 field_value = g_strdup (name->suffixes)g_strdup_inline (name->suffixes);
616
617 e_contact_name_free (name);
618 }
619 break;
620
621 default:
622 break;
623 }
624 }
625
626 /* checking to avoid the NULL pointer */
627 if (field_value == NULL((void*)0))
628 field_value = g_strdup ("")g_strdup_inline ("");
629
630 quoted_field_value = escape_string (field_value);
631 g_free (field_value);
632
633 if (delivery_address)
634 e_contact_address_free (delivery_address);
635
636 return quoted_field_value;
637}
638
639static gchar *
640e_contact_csv_get_header_line (const EContactFieldCSV *csv_all_fields)
641{
642 GPtrArray *field_names;
643 gchar *header_line;
644 gint csv_field;
645 guint ii;
646
647 field_names = g_ptr_array_new_with_free_func (g_free);
648 for (ii = 0; csv_all_fields[ii] != E_CONTACT_CSV_LAST; ii++) {
649 csv_field = csv_all_fields[ii];
650 g_ptr_array_add (field_names, e_contact_csv_get_name (csv_field));
651 }
652
653 g_ptr_array_add (field_names, NULL((void*)0));
654
655 header_line = g_strjoinv (COMMA_SEPARATOR",", (gchar **) field_names->pdata);
656
657 g_ptr_array_unref (field_names);
658
659 return header_line;
660}
661
662static gchar *
663e_contact_to_csv (EContact *contact,
664 const EContactFieldCSV *csv_all_fields)
665{
666 GPtrArray *field_values;
667 gchar *aline;
668 gint csv_field;
669 guint ii;
670
671 field_values = g_ptr_array_new_with_free_func (g_free);
672
673 for (ii = 0; csv_all_fields[ii] != E_CONTACT_CSV_LAST; ii++) {
674 csv_field = csv_all_fields[ii];
675 g_ptr_array_add (field_values, e_contact_csv_get (contact, csv_field));
676 }
677
678 g_ptr_array_add (field_values, NULL((void*)0));
679
680 aline = g_strjoinv (COMMA_SEPARATOR",", (gchar **) field_values->pdata);
681
682 g_ptr_array_unref (field_values);
683
684 return aline;
685}
686
687static gchar *
688e_contact_get_csv (EContact *contact,
689 const EContactFieldCSV *csv_all_fields)
690{
691 GList *emails;
692 guint n_emails;
693 gchar *full_name;
694
695 emails = e_vcard_get_attributes_by_name (E_VCARD (contact)((((EVCard*) (void *) ((contact))))), EVC_EMAIL"EMAIL");
696 n_emails = g_list_length (emails);
697 full_name = e_contact_get (contact, E_CONTACT_FULL_NAME);
698 if (n_emails > 4)
699 g_warning ("%s: only 4 out of %i emails have been exported", full_name, n_emails);
700 g_free (full_name);
701 g_list_free (emails);
702
703 return e_contact_to_csv (contact, csv_all_fields);
704}
705
706static gint
707output_n_cards_file (FILE *outputfile,
708 GSList *contacts,
709 gint size,
710 gint begin_no,
711 CARD_FORMAT format)
712{
713 gint i;
714 if (format == CARD_FORMAT_VCARD) {
715 for (i = begin_no; i < size + begin_no; i++) {
716 EContact *contact = g_slist_nth_data (contacts, i);
717 gchar *vcard = e_vcard_to_string (E_VCARD (contact)((((EVCard*) (void *) ((contact))))));
718 fprintf (outputfile, "%s\n", vcard);
719 g_free (vcard);
720 }
721 } else if (format == CARD_FORMAT_CSV) {
722 const EContactFieldCSV csv_all_fields[] = {
723 E_CONTACT_CSV_NAME_TITLE,
724 E_CONTACT_CSV_GIVEN_NAME,
725 E_CONTACT_CSV_MIDDLE_NAME,
726 E_CONTACT_CSV_FAMILY_NAME,
727 E_CONTACT_CSV_NAME_SUFFIX,
728 E_CONTACT_CSV_FULL_NAME,
729 E_CONTACT_CSV_NICKNAME,
730 E_CONTACT_CSV_EMAIL_1,
731 E_CONTACT_CSV_EMAIL_2,
732 E_CONTACT_CSV_EMAIL_3,
733 E_CONTACT_CSV_EMAIL_4,
734 E_CONTACT_CSV_WANTS_HTML,
735 E_CONTACT_CSV_PHONE_BUSINESS,
736 E_CONTACT_CSV_PHONE_HOME,
737 E_CONTACT_CSV_PHONE_BUSINESS_FAX,
738 E_CONTACT_CSV_PHONE_PAGER,
739 E_CONTACT_CSV_PHONE_MOBILE,
740 E_CONTACT_CSV_ADDRESS_HOME_STREET,
741 E_CONTACT_CSV_ADDRESS_HOME_EXT,
742 E_CONTACT_CSV_ADDRESS_HOME_CITY,
743 E_CONTACT_CSV_ADDRESS_HOME_REGION,
744 E_CONTACT_CSV_ADDRESS_HOME_POSTCODE,
745 E_CONTACT_CSV_ADDRESS_HOME_COUNTRY,
746 E_CONTACT_CSV_ADDRESS_BUSINESS_STREET,
747 E_CONTACT_CSV_ADDRESS_BUSINESS_EXT,
748 E_CONTACT_CSV_ADDRESS_BUSINESS_CITY,
749 E_CONTACT_CSV_ADDRESS_BUSINESS_REGION,
750 E_CONTACT_CSV_ADDRESS_BUSINESS_POSTCODE,
751 E_CONTACT_CSV_ADDRESS_BUSINESS_COUNTRY,
752 E_CONTACT_CSV_TITLE,
753 E_CONTACT_CSV_OFFICE,
754 E_CONTACT_CSV_ORG,
755 E_CONTACT_CSV_HOMEPAGE_URL,
756 E_CONTACT_CSV_CALENDAR_URI,
757 E_CONTACT_CSV_BIRTH_DATE_YEAR,
758 E_CONTACT_CSV_BIRTH_DATE_MONTH,
759 E_CONTACT_CSV_BIRTH_DATE_DAY,
760 E_CONTACT_CSV_NOTE,
761 E_CONTACT_CSV_LAST
762 };
763 gchar *csv_fields_name;
764
765 csv_fields_name = e_contact_csv_get_header_line (csv_all_fields);
766 fprintf (outputfile, "%s\n", csv_fields_name);
767 g_free (csv_fields_name);
768
769 for (i = begin_no; i < size + begin_no; i++) {
770 EContact *contact = g_slist_nth_data (contacts, i);
771 gchar *csv = e_contact_get_csv (contact, csv_all_fields);
772 fprintf (outputfile, "%s\n", csv);
773 g_free (csv);
774 }
775 }
776
777 return SUCCESS0;
778
779}
780
781static void
782action_export (GSList *contacts,
783 ActionContext *p_actctx)
784{
785 FILE *outputfile;
786 long length;
787 CARD_FORMAT format;
788
789 length = g_slist_length (contacts);
790
791 if (length <= 0) {
792 g_warning ("Couldn't load addressbook correctly!!!! %s####", p_actctx->addressbook_source_uid ?
793 p_actctx->addressbook_source_uid : "NULL");
794 exit (-1);
795 }
796
797 if (p_actctx->output_file == NULL((void*)0)) {
798 outputfile = stdoutstdout;
799 } else {
800 /* fopen output file */
801 if (!(outputfile = g_fopenfopen (p_actctx->output_file, "w"))) {
802 g_warning (_("Can not open file")dcgettext (((void*)0), "Can not open file", 5));
803 exit (-1);
804 }
805 }
806
807 if (p_actctx->IsVCard == TRUE(!(0)))
808 format = CARD_FORMAT_VCARD;
809 else
810 format = CARD_FORMAT_CSV;
811
812 output_n_cards_file (outputfile, contacts, length, 0, format);
813
814 if (p_actctx->output_file != NULL((void*)0)) {
815 fclose (outputfile);
816 }
817}
818
819static void
820action_export_init (ActionContext *p_actctx)
821{
822 ESourceRegistry *registry;
823 EClient *client;
824 EBookClient *book_client;
825 ESource *source;
826 GSList *contacts = NULL((void*)0);
827 const gchar *uid;
828 GError *error = NULL((void*)0);
829
830 registry = p_actctx->registry;
831 uid = p_actctx->addressbook_source_uid;
832
833 if (uid != NULL((void*)0))
834 source = e_source_registry_ref_source (registry, uid);
835 else
836 source = e_source_registry_ref_default_address_book (registry);
837
838 if (!source) {
839 g_warning (
840 "Couldn't load addressbook %s: Addressbook doesn't exist",
841 p_actctx->addressbook_source_uid ?
842 p_actctx->addressbook_source_uid :
843 "'default'");
844 exit (-1);
845 }
846
847 client = e_book_client_connect_sync (source, 30, NULL((void*)0), &error);
848
849 g_object_unref (source);
850
851 /* Sanity check. */
852 g_return_if_fail (do { if ((__builtin_expect (__extension__ ({ int _g_boolean_var_15
= 0; if (((client != ((void*)0)) && (error == ((void
*)0))) || ((client == ((void*)0)) && (error != ((void
*)0)))) _g_boolean_var_15 = 1; _g_boolean_var_15; }), 1))) { }
else { g_return_if_fail_warning ("addressbook-export", ((const
char*) (__func__)), "((client != NULL) && (error == NULL)) || ((client == NULL) && (error != NULL))"
); return; } } while (0)
853 ((client != NULL) && (error == NULL)) ||do { if ((__builtin_expect (__extension__ ({ int _g_boolean_var_15
= 0; if (((client != ((void*)0)) && (error == ((void
*)0))) || ((client == ((void*)0)) && (error != ((void
*)0)))) _g_boolean_var_15 = 1; _g_boolean_var_15; }), 1))) { }
else { g_return_if_fail_warning ("addressbook-export", ((const
char*) (__func__)), "((client != NULL) && (error == NULL)) || ((client == NULL) && (error != NULL))"
); return; } } while (0)
854 ((client == NULL) && (error != NULL)))do { if ((__builtin_expect (__extension__ ({ int _g_boolean_var_15
= 0; if (((client != ((void*)0)) && (error == ((void
*)0))) || ((client == ((void*)0)) && (error != ((void
*)0)))) _g_boolean_var_15 = 1; _g_boolean_var_15; }), 1))) { }
else { g_return_if_fail_warning ("addressbook-export", ((const
char*) (__func__)), "((client != NULL) && (error == NULL)) || ((client == NULL) && (error != NULL))"
); return; } } while (0)
;
855
856 if (error != NULL((void*)0)) {
857 g_warning (
858 "Couldn't load addressbook %s: %s",
859 p_actctx->addressbook_source_uid ?
860 p_actctx->addressbook_source_uid :
861 "'default'", error->message);
862 g_error_free (error);
863 exit (-1);
864 }
865
866 book_client = E_BOOK_CLIENT (client)((((EBookClient*) (void *) ((client)))));
867
868 if (e_book_client_get_contacts_sync (book_client, "#t", &contacts, NULL((void*)0), &error)) {
869 action_export (contacts, p_actctx);
870 g_slist_free_full (contacts, g_object_unref);
871 }
872
873 g_object_unref (book_client);
874
875 if (error != NULL((void*)0)) {
876 g_warning ("Failed to get contacts: %s", error->message);
877 g_error_free (error);
878 }
879}
880
881static gboolean
882call_main_loop_quit_idle_cb (gpointer user_data)
883{
884 g_main_loop_quit (user_data);
885
886 return FALSE(0);
887}
888
889static gpointer
890addressbook_export_thread (gpointer user_data)
891{
892 ActionContext *actctx = user_data;
893
894 g_return_val_if_fail (actctx != NULL, NULL)do { if ((__builtin_expect (__extension__ ({ int _g_boolean_var_16
= 0; if (actctx != ((void*)0)) _g_boolean_var_16 = 1; _g_boolean_var_16
; }), 1))) { } else { g_return_if_fail_warning ("addressbook-export"
, ((const char*) (__func__)), "actctx != NULL"); return (((void
*)0)); } } while (0)
;
1
Assuming 'actctx' is not equal to null
2
Taking true branch
3
Taking true branch
895
896 /* do actions */
897 if (actctx->action_type == ACTION_LIST || actctx->action_type == ACTION_LIST_WITH_COUNT) {
4
Loop condition is false. Exiting loop
5
Assuming field 'action_type' is equal to ACTION_LIST
898 action_list_init (actctx, actctx->action_type == ACTION_LIST_WITH_COUNT);
6
Calling 'action_list_init'
899
900 } else if (actctx->action_type == ACTION_EXPORT) {
901 action_export_init (actctx);
902
903 } else {
904 g_warning (_("Unhandled error")dcgettext (((void*)0), "Unhandled error", 5));
905 exit (-1);
906 }
907
908 g_idle_add (call_main_loop_quit_idle_cb, actctx->main_loop);
909
910 return NULL((void*)0);
911}
912
913static gboolean
914addressbook_export_start_idle (gpointer user_data)
915{
916 ActionContext *actctx = user_data;
917 GThread *thread;
918
919 g_return_val_if_fail (actctx != NULL, FALSE)do { if ((__builtin_expect (__extension__ ({ int _g_boolean_var_17
= 0; if (actctx != ((void*)0)) _g_boolean_var_17 = 1; _g_boolean_var_17
; }), 1))) { } else { g_return_if_fail_warning ("addressbook-export"
, ((const char*) (__func__)), "actctx != NULL"); return ((0))
; } } while (0)
;
920
921 thread = g_thread_new (NULL((void*)0), addressbook_export_thread, actctx);
922 g_thread_unref (thread);
923
924 return FALSE(0);
925}
926
927/* Command-Line Options */
928static gchar *opt_output_file = NULL((void*)0);
929static gboolean opt_list = FALSE(0);
930static gboolean opt_list_with_count = FALSE(0);
931static gchar *opt_output_format = NULL((void*)0);
932static gchar *opt_addressbook_source_uid = NULL((void*)0);
933static gchar **opt_remaining = NULL((void*)0);
934
935static GOptionEntry entries[] = {
936 { "output", '\0', 0,
937 G_OPTION_ARG_STRING, &opt_output_file,
938 N_("Specify the output file instead of standard output")("Specify the output file instead of standard output"),
939 N_("OUTPUTFILE")("OUTPUTFILE") },
940 { "list", 'l', 0,
941 G_OPTION_ARG_NONE, &opt_list,
942 N_("List available address books")("List available address books") },
943 { "list-with-count", 'L', 0,
944 G_OPTION_ARG_NONE, &opt_list_with_count,
945 N_("List available address books and show how many contacts they have")("List available address books and show how many contacts they have"
)
},
946 { "format", '\0', 0,
947 G_OPTION_ARG_STRING, &opt_output_format,
948 N_("Show cards as vcard or csv file")("Show cards as vcard or csv file"),
949 /* Do not translate it, the supported values are these, not any translated variants */
950 "[vcard|csv]" },
951 { G_OPTION_REMAINING"", '\0', 0,
952 G_OPTION_ARG_STRING_ARRAY, &opt_remaining },
953 { NULL((void*)0) }
954};
955
956gint
957main (gint argc,
958 gchar **argv)
959{
960 ActionContext actctx;
961 GOptionContext *context;
962 GError *error = NULL((void*)0);
963 gint IsCSV = FALSE(0);
964 gint IsVCard = FALSE(0);
965
966#ifdef G_OS_WIN32
967 e_util_win32_initialize ();
968#endif
969
970 setlocale (LC_ALL6, "");
971 bindtextdomain (GETTEXT_PACKAGE"evolution-data-server", LOCALEDIR"/home/user/_prefix/share/locale");
972 bind_textdomain_codeset (GETTEXT_PACKAGE"evolution-data-server", "UTF-8");
973 textdomain (GETTEXT_PACKAGE"evolution-data-server");
974
975 context = g_option_context_new (NULL((void*)0));
976 g_option_context_add_main_entries (context, entries, GETTEXT_PACKAGE"evolution-data-server");
977 if (!g_option_context_parse (context, &argc, &argv, &error)) {
978 g_printerr ("%s\n", error->message);
979 g_error_free (error);
980 exit (-1);
981 }
982
983 g_clear_pointer (&context, g_option_context_free)do { _Static_assert (sizeof *(&context) == sizeof (gpointer
), "Expression evaluates to false"); __typeof__ ((&context
)) _pp = (&context); __typeof__ (*(&context)) _ptr = *
_pp; *_pp = ((void*)0); if (_ptr) (g_option_context_free) (_ptr
); } while (0)
;
984
985 actctx.action_type = ACTION_NOTHING;
986 actctx.registry = e_source_registry_new_sync (NULL((void*)0), &error);
987 if (error != NULL((void*)0)) {
988 g_printerr ("%s\n", error->message);
989 g_error_free (error);
990 exit (-1);
991 }
992
993 /* Parsing Parameter */
994 if (opt_remaining && g_strv_length (opt_remaining) > 0)
995 opt_addressbook_source_uid = g_strdup (opt_remaining[0])g_strdup_inline (opt_remaining[0]);
996
997 if (opt_list || opt_list_with_count) {
998 actctx.action_type = opt_list ? ACTION_LIST : ACTION_LIST_WITH_COUNT;
999 if (opt_list && opt_list_with_count) {
1000 g_warning (_("Cannot use --list and --list-with-count together.")dcgettext (((void*)0), "Cannot use --list and --list-with-count together."
, 5)
);
1001 exit (-1);
1002 }
1003 if (opt_addressbook_source_uid != NULL((void*)0) || opt_output_format != NULL((void*)0)) {
1004 g_warning (_("Command line arguments error, please use --help option to see the usage.")dcgettext (((void*)0), "Command line arguments error, please use --help option to see the usage."
, 5)
);
1005 exit (-1);
1006 }
1007 } else {
1008
1009 actctx.action_type = ACTION_EXPORT;
1010
1011 /* check the output format */
1012 if (opt_output_format == NULL((void*)0)) {
1013 IsVCard = TRUE(!(0));
1014 } else {
1015 IsCSV = !strcmp (opt_output_format, "csv");
1016 IsVCard = !strcmp (opt_output_format, "vcard");
1017 if (IsCSV == FALSE(0) && IsVCard == FALSE(0)) {
1018 g_warning (_("Only supports csv or vcard format.")dcgettext (((void*)0), "Only supports csv or vcard format.", 5
)
);
1019 exit (-1);
1020 }
1021 }
1022 }
1023
1024 actctx.output_file = opt_output_file;
1025 actctx.IsCSV = IsCSV;
1026 actctx.IsVCard = IsVCard;
1027 actctx.addressbook_source_uid = opt_addressbook_source_uid;
1028
1029 g_idle_add (addressbook_export_start_idle, &actctx);
1030
1031 actctx.main_loop = g_main_loop_new (NULL((void*)0), FALSE(0));
1032
1033 g_main_loop_run (actctx.main_loop);
1034
1035 g_object_unref (actctx.registry);
1036 g_main_loop_unref (actctx.main_loop);
1037
1038 return 0;
1039}