From 844aeed6432ce1cb5b2ce660a68fe7a4edad53d6 Mon Sep 17 00:00:00 2001 From: Pierre Pronchery Date: Sat, 7 Jan 2012 00:27:07 +0000 Subject: [PATCH] Reworked the accounts plug-ins (configuration changes probably crash now) --- include/Mailer/account.h | 14 +- po/fr.po | 12 +- src/account.c | 59 +++---- src/account/imap4.c | 339 +++++++++++++++++++-------------------- src/account/mbox.c | 103 +++++++----- src/account/nntp.c | 8 +- src/account/pop3.c | 266 +++++++++++++++--------------- src/account/rss.c | 8 +- src/mailer.c | 6 +- 9 files changed, 409 insertions(+), 406 deletions(-) diff --git a/include/Mailer/account.h b/include/Mailer/account.h index 53efcdd..ff9918b 100644 --- a/include/Mailer/account.h +++ b/include/Mailer/account.h @@ -1,5 +1,5 @@ /* $Id$ */ -/* Copyright (c) 2011 Pierre Pronchery */ +/* Copyright (c) 2011-2012 Pierre Pronchery */ /* This file is part of DeforaOS Desktop Mailer */ /* This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -86,20 +86,20 @@ typedef struct _AccountPluginHelper typedef struct _AccountPlugin AccountPlugin; -struct _AccountPlugin +typedef const struct _AccountPluginDefinition { - AccountPluginHelper * helper; char const * type; char const * name; char const * icon; - AccountConfig * config; - int (*init)(AccountPlugin * plugin); + char const * description; + AccountConfig const * config; + AccountPlugin * (*init)(AccountPluginHelper * helper); int (*destroy)(AccountPlugin * plugin); + AccountConfig * (*get_config)(AccountPlugin * plugin); char * (*get_source)(AccountPlugin * plugin, AccountFolder * folder, AccountMessage * message); int (*refresh)(AccountPlugin * plugin, AccountFolder * folder, AccountMessage * message); - void * priv; -}; +} AccountPluginDefinition; #endif /* !DESKTOP_MAILER_ACCOUNT_H */ diff --git a/po/fr.po b/po/fr.po index b82f932..c846b05 100644 --- a/po/fr.po +++ b/po/fr.po @@ -7,7 +7,7 @@ msgid "" msgstr "" "Project-Id-Version: Mailer 0.0.0\n" "Report-Msgid-Bugs-To: \n" -"POT-Creation-Date: 2012-01-05 19:24+0100\n" +"POT-Creation-Date: 2012-01-07 01:19+0100\n" "PO-Revision-Date: 2010-10-02 23:25+0200\n" "Last-Translator: Pierre Pronchery \n" "Language-Team: French\n" @@ -478,24 +478,24 @@ msgstr "Paramètres" msgid "An error occured while saving preferences" msgstr "Une erreur est survenue pendant la sauvegarde des préférences" -#: ../src/mailer.c:3000 ../src/mailer.c:3004 +#: ../src/mailer.c:3004 ../src/mailer.c:3008 msgid "Question" msgstr "Question" -#: ../src/mailer.c:3073 +#: ../src/mailer.c:3077 #, c-format msgid "%s/%s: %d %s" msgstr "%s/%s: %d %s" -#: ../src/mailer.c:3076 +#: ../src/mailer.c:3080 msgid "messages" msgstr "messages" -#: ../src/mailer.c:3076 +#: ../src/mailer.c:3080 msgid "message" msgstr "message" -#: ../src/mailer.c:3079 +#: ../src/mailer.c:3083 msgid "Ready" msgstr "Prêt" diff --git a/src/account.c b/src/account.c index e43c6ae..47d6afb 100644 --- a/src/account.c +++ b/src/account.c @@ -1,5 +1,5 @@ /* $Id$ */ -/* Copyright (c) 2011 Pierre Pronchery */ +/* Copyright (c) 2006-2012 Pierre Pronchery */ /* This file is part of DeforaOS Desktop Mailer */ /* This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -52,6 +52,7 @@ struct _Account GtkTreeStore * store; GtkTreeRowReference * row; Plugin * plugin; + AccountPluginDefinition * definition; AccountPlugin * account; int enabled; @@ -115,9 +116,8 @@ Account * account_new(Mailer * mailer, char const * type, char const * title, #ifdef DEBUG fprintf(stderr, "DEBUG: account_new(%p, \"%s\", \"%s\", %p)\n", - (void*)mailer, type, title, (void*)store); + (void *)mailer, type, title, (void *)store); #endif - /* FIXME copy the AccountConfig structure */ if(type == NULL) return NULL; if((account = object_new(sizeof(*account))) == NULL) @@ -129,12 +129,16 @@ Account * account_new(Mailer * mailer, char const * type, char const * title, account->title = string_new(title); account->store = store; account->plugin = plugin_new(LIBDIR, PACKAGE, "account", type); - account->account = (account->plugin != NULL) + account->definition = (account->plugin != NULL) ? plugin_lookup(account->plugin, "account_plugin") : NULL; if(account->type == NULL || account->plugin == NULL - || account->account == NULL) + || account->definition == NULL + || account->definition->init == NULL + || account->definition->destroy == NULL + || account->definition->get_config == NULL) { account_delete(account); + error_set_code(1, "%s%s", "Invalid plug-in ", type); return NULL; } if(store != NULL) @@ -153,7 +157,6 @@ Account * account_new(Mailer * mailer, char const * type, char const * title, memcpy(&account->helper, &_account_plugin_helper, sizeof(account->helper)); account->helper.account = account; - account->account->helper = &account->helper; account->enabled = 1; account->identity = NULL; return account; @@ -163,26 +166,13 @@ Account * account_new(Mailer * mailer, char const * type, char const * title, /* account_delete */ void account_delete(Account * account) { - AccountConfig * p; - if(account->row != NULL) gtk_tree_row_reference_free(account->row); - if(account->plugin != NULL) + if(account->definition != NULL) { - if(account->account->destroy != NULL) - account->account->destroy(account->account); - if(account->account->config != NULL) - for(p = account->account->config; p->name != NULL; p++) - switch(p->type) - { - case ACT_STRING: - case ACT_PASSWORD: - case ACT_FILE: - free(p->value); - break; - default: - break; - } + if(account->definition->destroy != NULL + && account->account != NULL) + account->definition->destroy(account->account); } string_delete(account->title); string_delete(account->type); @@ -196,7 +186,7 @@ void account_delete(Account * account) /* account_get_config */ AccountConfig * account_get_config(Account * account) { - return account->account->config; + return account->definition->get_config(account->account); } @@ -217,7 +207,7 @@ GtkTreeStore * account_get_folders(Account * account) /* account_get_name */ char const * account_get_name(Account * account) { - return account->account->name; + return account->definition->name; } @@ -257,7 +247,7 @@ int account_set_title(Account * account, char const * title) /* account_config_load */ int account_config_load(Account * account, Config * config) { - AccountConfig * p = account->account->config; + AccountConfig * p = account_get_config(account); char const * value; char * q; long l; @@ -303,7 +293,7 @@ int account_config_load(Account * account, Config * config) /* account_config_save */ int account_config_save(Account * account, Config * config) { - AccountConfig * p = account->account->config; + AccountConfig * p = account_get_config(account); uint16_t u16; char buf[6]; @@ -354,9 +344,8 @@ int account_init(Account * account) #ifdef DEBUG fprintf(stderr, "DEBUG: %s(%p)\n", __func__, (void*)account); #endif - if(account->account->init == NULL) - return 0; - return account->account->init(account->account); + return (account->account = account->definition->init(&account->helper)) + != NULL ? 0 : -1; } @@ -376,9 +365,9 @@ GtkTextBuffer * account_select(Account * account, Folder * folder, return NULL; if(message != NULL && (am = message_get_data(message)) == NULL) return NULL; - if(account->account->refresh != NULL - && account->account->refresh(account->account, af, am) - != 0) + if(account->definition->refresh != NULL + && account->definition->refresh(account->account, af, + am) != 0) return NULL; return (message != NULL) ? message_get_body(message) : NULL; } @@ -395,10 +384,10 @@ GtkTextBuffer * account_select_source(Account * account, Folder * folder, fprintf(stderr, "DEBUG: %s(\"%s\", %p)\n", __func__, folder_get_name(folder), (void*)message); #endif - if(account->account->get_source == NULL) + if(account->definition->get_source == NULL) return NULL; ret = gtk_text_buffer_new(NULL); - if((p = account->account->get_source(account->account, + if((p = account->definition->get_source(account->account, folder_get_data(folder), message_get_data(message))) != NULL) { diff --git a/src/account/imap4.c b/src/account/imap4.c index 269dfa1..ea769f7 100644 --- a/src/account/imap4.c +++ b/src/account/imap4.c @@ -1,5 +1,5 @@ /* $Id$ */ -/* Copyright (c) 2011 Pierre Pronchery */ +/* Copyright (c) 2011-2012 Pierre Pronchery */ /* This file is part of DeforaOS Desktop Mailer */ /* This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -135,8 +135,12 @@ typedef struct _IMAP4Command } data; } IMAP4Command; -typedef struct _IMAP4 +typedef struct _AccountPlugin { + AccountPluginHelper * helper; + + AccountConfig * config; + int fd; SSL * ssl; guint source; @@ -159,7 +163,7 @@ typedef struct _IMAP4 static char const _imap4_type[] = "IMAP4"; static char const _imap4_name[] = "IMAP4 server"; -AccountConfig _imap4_config[I4CV_COUNT + 1] = +AccountConfig const _imap4_config[I4CV_COUNT + 1] = { { "username", "Username", ACT_STRING, NULL }, { "password", "Password", ACT_PASSWORD, NULL }, @@ -178,29 +182,30 @@ AccountConfig _imap4_config[I4CV_COUNT + 1] = /* prototypes */ /* plug-in */ -static int _imap4_init(AccountPlugin * plugin); -static int _imap4_destroy(AccountPlugin * plugin); -static int _imap4_refresh(AccountPlugin * plugin, AccountFolder * folder, +static IMAP4 * _imap4_init(AccountPluginHelper * helper); +static int _imap4_destroy(IMAP4 * imap4); +static AccountConfig * _imap4_get_config(IMAP4 * imap4); +static int _imap4_refresh(IMAP4 * imap4, AccountFolder * folder, AccountMessage * message); /* useful */ -static IMAP4Command * _imap4_command(AccountPlugin * plugin, - IMAP4Context context, char const * command); -static int _imap4_parse(AccountPlugin * plugin); -static void _imap4_reset(AccountPlugin * plugin); +static IMAP4Command * _imap4_command(IMAP4 * imap4, IMAP4Context context, + char const * command); +static int _imap4_parse(IMAP4 * imap4); +static void _imap4_reset(IMAP4 * imap4); -static AccountFolder * _imap4_folder_new(AccountPlugin * plugin, - AccountFolder * parent, char const * name); -static void _imap4_folder_delete(AccountPlugin * plugin, +static AccountFolder * _imap4_folder_new(IMAP4 * imap4, AccountFolder * parent, + char const * name); +static void _imap4_folder_delete(IMAP4 * imap4, AccountFolder * folder); -static AccountFolder * _imap4_folder_get_folder(AccountPlugin * plugin, +static AccountFolder * _imap4_folder_get_folder(IMAP4 * imap4, AccountFolder * folder, char const * name); -static AccountMessage * _imap4_folder_get_message(AccountPlugin * plugin, +static AccountMessage * _imap4_folder_get_message(IMAP4 * imap4, AccountFolder * folder, unsigned int id); -static AccountMessage * _imap4_message_new(AccountPlugin * plugin, +static AccountMessage * _imap4_message_new(IMAP4 * imap4, AccountFolder * folder, unsigned int id); -static void _imap4_message_delete(AccountPlugin * plugin, +static void _imap4_message_delete(IMAP4 * imap4, AccountMessage * message); /* callbacks */ @@ -223,58 +228,69 @@ static gboolean _on_watch_can_write_ssl(GIOChannel * source, /* public */ /* variables */ -AccountPlugin account_plugin = +AccountPluginDefinition account_plugin = { - NULL, _imap4_type, _imap4_name, NULL, + NULL, _imap4_config, _imap4_init, _imap4_destroy, + _imap4_get_config, NULL, - _imap4_refresh, - NULL + _imap4_refresh }; /* private */ /* imap4_init */ -static int _imap4_init(AccountPlugin * plugin) +static IMAP4 * _imap4_init(AccountPluginHelper * helper) { IMAP4 * imap4; if((imap4 = malloc(sizeof(*imap4))) == NULL) - return -1; + return NULL; memset(imap4, 0, sizeof(*imap4)); - plugin->priv = imap4; + imap4->helper = helper; + if((imap4->config = malloc(sizeof(_imap4_config))) == NULL) + { + free(imap4); + return NULL; + } + memcpy(imap4->config, &_imap4_config, sizeof(_imap4_config)); imap4->fd = -1; - imap4->source = g_idle_add(_on_connect, plugin); - return 0; + imap4->source = g_idle_add(_on_connect, imap4); + return imap4; } /* imap4_destroy */ -static int _imap4_destroy(AccountPlugin * plugin) +static int _imap4_destroy(IMAP4 * imap4) { - IMAP4 * imap4 = plugin->priv; - #ifdef DEBUG fprintf(stderr, "DEBUG: %s()\n", __func__); #endif if(imap4 == NULL) /* XXX _imap4_destroy() may be called uninitialized */ return 0; - _imap4_reset(plugin); + _imap4_reset(imap4); #if 0 /* XXX do not free() */ - _imap4_folder_delete(plugin, &imap4->folders); + _imap4_folder_delete(imap4, &imap4->folders); #endif free(imap4); return 0; } +/* imap4_get_config */ +static AccountConfig * _imap4_get_config(IMAP4 * imap4) +{ + return imap4->config; +} + + /* imap4_refresh */ -static int _imap4_refresh(AccountPlugin * plugin, AccountFolder * folder, +static int _imap4_refresh(IMAP4 * imap4, AccountFolder * folder, AccountMessage * message) { IMAP4Command * cmd; @@ -289,7 +305,7 @@ static int _imap4_refresh(AccountPlugin * plugin, AccountFolder * folder, || (buf = malloc(++len)) == NULL) return -1; snprintf(buf, len, "EXAMINE \"%s\"", folder->name); - cmd = _imap4_command(plugin, I4C_SELECT, buf); + cmd = _imap4_command(imap4, I4C_SELECT, buf); free(buf); if(cmd == NULL) return -1; @@ -301,10 +317,9 @@ static int _imap4_refresh(AccountPlugin * plugin, AccountFolder * folder, /* useful */ /* imap4_command */ -static IMAP4Command * _imap4_command(AccountPlugin * plugin, - IMAP4Context context, char const * command) +static IMAP4Command * _imap4_command(IMAP4 * imap4, IMAP4Context context, + char const * command) { - IMAP4 * imap4 = plugin->priv; IMAP4Command * p; size_t len; @@ -341,25 +356,24 @@ static IMAP4Command * _imap4_command(AccountPlugin * plugin, } imap4->wr_source = g_io_add_watch(imap4->channel, G_IO_OUT, (imap4->ssl != NULL) ? _on_watch_can_write_ssl - : _on_watch_can_write, plugin); + : _on_watch_can_write, imap4); } return p; } /* imap4_parse */ -static int _parse_context(AccountPlugin * plugin, char const * answer); -static int _context_fetch(AccountPlugin * plugin, char const * answer); -static int _context_init(AccountPlugin * plugin); -static int _context_list(AccountPlugin * plugin, char const * answer); -static int _context_login(AccountPlugin * plugin, char const * answer); -static int _context_select(AccountPlugin * plugin); -static int _context_status(AccountPlugin * plugin, char const * answer); +static int _parse_context(IMAP4 * imap4, char const * answer); +static int _context_fetch(IMAP4 * imap4, char const * answer); +static int _context_init(IMAP4 * imap4); +static int _context_list(IMAP4 * imap4, char const * answer); +static int _context_login(IMAP4 * imap4, char const * answer); +static int _context_select(IMAP4 * imap4); +static int _context_status(IMAP4 * imap4, char const * answer); -static int _imap4_parse(AccountPlugin * plugin) +static int _imap4_parse(IMAP4 * imap4) { - AccountPluginHelper * helper = plugin->helper; - IMAP4 * imap4 = plugin->priv; + AccountPluginHelper * helper = imap4->helper; size_t i; size_t j; IMAP4Command * cmd; @@ -399,7 +413,7 @@ static int _imap4_parse(AccountPlugin * plugin) 1); } } - if(_parse_context(plugin, &imap4->rd_buf[j]) != 0) + if(_parse_context(imap4, &imap4->rd_buf[j]) != 0) cmd->status = I4CS_ERROR; } if(j != 0) @@ -412,10 +426,9 @@ static int _imap4_parse(AccountPlugin * plugin) return (imap4->queue[0].status != I4CS_ERROR) ? 0 : -1; } -static int _parse_context(AccountPlugin * plugin, char const * answer) +static int _parse_context(IMAP4 * imap4, char const * answer) { int ret = -1; - IMAP4 * imap4 = plugin->priv; IMAP4Command * cmd = &imap4->queue[0]; #ifdef DEBUG @@ -425,30 +438,29 @@ static int _parse_context(AccountPlugin * plugin, char const * answer) switch(cmd->context) { case I4C_FETCH: - return _context_fetch(plugin, answer); + return _context_fetch(imap4, answer); case I4C_INIT: - return _context_init(plugin); + return _context_init(imap4); case I4C_LIST: - return _context_list(plugin, answer); + return _context_list(imap4, answer); case I4C_LOGIN: - return _context_login(plugin, answer); + return _context_login(imap4, answer); case I4C_NOOP: if(cmd->status != I4CS_PARSING) return 0; cmd->status = I4CS_OK; return 0; case I4C_SELECT: - return _context_select(plugin); + return _context_select(imap4); case I4C_STATUS: - return _context_status(plugin, answer); + return _context_status(imap4, answer); } return ret; } -static int _context_fetch(AccountPlugin * plugin, char const * answer) +static int _context_fetch(IMAP4 * imap4, char const * answer) { - AccountPluginHelper * helper = plugin->helper; - IMAP4 * imap4 = plugin->priv; + AccountPluginHelper * helper = imap4->helper; IMAP4Command * cmd = &imap4->queue[0]; AccountFolder * folder = cmd->data.fetch.folder; AccountMessage * message = cmd->data.fetch.message; @@ -491,7 +503,7 @@ static int _context_fetch(AccountPlugin * plugin, char const * answer) answer = p; if(strncmp(answer, " FETCH ", 7) != 0) return 0; - if((message = _imap4_folder_get_message(plugin, folder, + if((message = _imap4_folder_get_message(imap4, folder, id)) != NULL) { cmd->data.fetch.status = I4FS_HEADERS; @@ -513,28 +525,26 @@ static int _context_fetch(AccountPlugin * plugin, char const * answer) return -1; } -static int _context_init(AccountPlugin * plugin) +static int _context_init(IMAP4 * imap4) { - IMAP4 * imap4 = plugin->priv; IMAP4Command * cmd = &imap4->queue[0]; char const * p; char const * q; gchar * r; cmd->status = I4CS_OK; - if((p = plugin->config[I4CV_USERNAME].value) == NULL || *p == '\0') + if((p = imap4->config[I4CV_USERNAME].value) == NULL || *p == '\0') return -1; - if((q = plugin->config[I4CV_PASSWORD].value) == NULL || *q == '\0') + if((q = imap4->config[I4CV_PASSWORD].value) == NULL || *q == '\0') return -1; r = g_strdup_printf("%s %s %s", "LOGIN", p, q); - cmd = _imap4_command(plugin, I4C_LOGIN, r); + cmd = _imap4_command(imap4, I4C_LOGIN, r); g_free(r); return (cmd != NULL) ? 0 : -1; } -static int _context_list(AccountPlugin * plugin, char const * answer) +static int _context_list(IMAP4 * imap4, char const * answer) { - IMAP4 * imap4 = plugin->priv; IMAP4Command * cmd = &imap4->queue[0]; AccountFolder * folder; AccountFolder * parent = cmd->data.list.parent; @@ -585,20 +595,20 @@ static int _context_list(AccountPlugin * plugin, char const * answer) else sscanf(p, "%63s", buf); buf[63] = '\0'; - if(buf[0] != '\0' && (folder = _imap4_folder_get_folder(plugin, parent, + if(buf[0] != '\0' && (folder = _imap4_folder_get_folder(imap4, parent, buf)) != NULL) { /* FIXME escape the mailbox name (double quotes...) */ q = g_strdup_printf("%s \"%s\" (%s)", "STATUS", buf, "MESSAGES RECENT UNSEEN"); - if((cmd = _imap4_command(plugin, I4C_STATUS, q)) != NULL) + if((cmd = _imap4_command(imap4, I4C_STATUS, q)) != NULL) cmd->data.status.folder = folder; g_free(q); if(cmd != NULL && recurse == 1 && reference != '\0') { q = g_strdup_printf("%s \"\" \"%s%c%%\"", "LIST", buf, reference); - if((cmd = _imap4_command(plugin, I4C_LIST, q)) != NULL) + if((cmd = _imap4_command(imap4, I4C_LIST, q)) != NULL) cmd->data.list.parent = folder; g_free(q); } @@ -606,12 +616,11 @@ static int _context_list(AccountPlugin * plugin, char const * answer) return (cmd != NULL) ? 0 : -1; } -static int _context_login(AccountPlugin * plugin, char const * answer) +static int _context_login(IMAP4 * imap4, char const * answer) { - AccountPluginHelper * helper = plugin->helper; - IMAP4 * imap4 = plugin->priv; + AccountPluginHelper * helper = imap4->helper; IMAP4Command * cmd = &imap4->queue[0]; - char const * prefix = plugin->config[I4CV_PREFIX].value; + char const * prefix = imap4->config[I4CV_PREFIX].value; gchar * q; if(cmd->status != I4CS_PARSING) @@ -623,7 +632,7 @@ static int _context_login(AccountPlugin * plugin, char const * answer) if((q = g_strdup_printf("%s \"\" \"%s%%\"", "LIST", (prefix != NULL) ? prefix : "")) == NULL) return -1; - cmd = _imap4_command(plugin, I4C_LIST, q); + cmd = _imap4_command(imap4, I4C_LIST, q); g_free(q); if(cmd == NULL) return -1; @@ -631,9 +640,8 @@ static int _context_login(AccountPlugin * plugin, char const * answer) return 0; } -static int _context_select(AccountPlugin * plugin) +static int _context_select(IMAP4 * imap4) { - IMAP4 * imap4 = plugin->priv; IMAP4Command * cmd = &imap4->queue[0]; AccountFolder * folder; AccountMessage * message; @@ -651,7 +659,7 @@ static int _context_select(AccountPlugin * plugin) else snprintf(buf, sizeof(buf), "%s %u %s", "FETCH", message->id, "BODY.PEEK[]"); - if((cmd = _imap4_command(plugin, I4C_FETCH, buf)) == NULL) + if((cmd = _imap4_command(imap4, I4C_FETCH, buf)) == NULL) return -1; cmd->data.fetch.folder = folder; cmd->data.fetch.message = message; @@ -660,9 +668,8 @@ static int _context_select(AccountPlugin * plugin) return 0; } -static int _context_status(AccountPlugin * plugin, char const * answer) +static int _context_status(IMAP4 * imap4, char const * answer) { - IMAP4 * imap4 = plugin->priv; IMAP4Command * cmd = &imap4->queue[0]; char const * p; char const messages[] = "MESSAGES"; @@ -719,9 +726,8 @@ static int _context_status(AccountPlugin * plugin, char const * answer) /* imap4_reset */ -static void _imap4_reset(AccountPlugin * plugin) +static void _imap4_reset(IMAP4 * imap4) { - IMAP4 * imap4 = plugin->priv; size_t i; if(imap4->rd_source != 0) @@ -752,13 +758,12 @@ static void _imap4_reset(AccountPlugin * plugin) /* imap4_folder_new */ -static AccountFolder * _imap4_folder_new(AccountPlugin * plugin, - AccountFolder * parent, char const * name) +static AccountFolder * _imap4_folder_new(IMAP4 * imap4, AccountFolder * parent, + char const * name) { - AccountPluginHelper * helper = plugin->helper; + AccountPluginHelper * helper = imap4->helper; AccountFolder * folder; AccountFolder ** p; - IMAP4 * imap4 = plugin->priv; FolderType type = FT_FOLDER; struct { @@ -801,7 +806,7 @@ static AccountFolder * _imap4_folder_new(AccountPlugin * plugin, folder->folders_cnt = 0; if(folder->folder == NULL || folder->name == NULL) { - _imap4_folder_delete(plugin, folder); + _imap4_folder_delete(imap4, folder); return NULL; } parent->folders[parent->folders_cnt++] = folder; @@ -810,25 +815,25 @@ static AccountFolder * _imap4_folder_new(AccountPlugin * plugin, /* imap4_folder_delete */ -static void _imap4_folder_delete(AccountPlugin * plugin, AccountFolder * folder) +static void _imap4_folder_delete(IMAP4 * imap4, AccountFolder * folder) { size_t i; if(folder->folder != NULL) - plugin->helper->folder_delete(folder->folder); + imap4->helper->folder_delete(folder->folder); free(folder->name); for(i = 0; i < folder->messages_cnt; i++) - _imap4_message_delete(plugin, folder->messages[i]); + _imap4_message_delete(imap4, folder->messages[i]); free(folder->messages); for(i = 0; i < folder->folders_cnt; i++) - _imap4_folder_delete(plugin, folder->folders[i]); + _imap4_folder_delete(imap4, folder->folders[i]); free(folder->folders); object_delete(folder); } /* imap4_folder_get_folder */ -static AccountFolder * _imap4_folder_get_folder(AccountPlugin * plugin, +static AccountFolder * _imap4_folder_get_folder(IMAP4 * imap4, AccountFolder * folder, char const * name) { size_t i; @@ -840,12 +845,12 @@ static AccountFolder * _imap4_folder_get_folder(AccountPlugin * plugin, for(i = 0; i < folder->folders_cnt; i++) if(strcmp(folder->folders[i]->name, name) == 0) return folder->folders[i]; - return _imap4_folder_new(plugin, folder, name); + return _imap4_folder_new(imap4, folder, name); } /* imap4_folder_get_message */ -static AccountMessage * _imap4_folder_get_message(AccountPlugin * plugin, +static AccountMessage * _imap4_folder_get_message(IMAP4 * imap4, AccountFolder * folder, unsigned int id) { size_t i; @@ -856,15 +861,15 @@ static AccountMessage * _imap4_folder_get_message(AccountPlugin * plugin, for(i = 0; i < folder->messages_cnt; i++) if(folder->messages[i]->id == id) return folder->messages[i]; - return _imap4_message_new(plugin, folder, id); + return _imap4_message_new(imap4, folder, id); } /* imap4_message_new */ -static AccountMessage * _imap4_message_new(AccountPlugin * plugin, +static AccountMessage * _imap4_message_new(IMAP4 * imap4, AccountFolder * folder, unsigned int id) { - AccountPluginHelper * helper = plugin->helper; + AccountPluginHelper * helper = imap4->helper; AccountMessage * message; AccountMessage ** p; @@ -878,7 +883,7 @@ static AccountMessage * _imap4_message_new(AccountPlugin * plugin, if((message->message = helper->message_new(helper->account, folder->folder, message)) == NULL) { - _imap4_message_delete(plugin, message); + _imap4_message_delete(imap4, message); return NULL; } folder->messages[folder->messages_cnt++] = message; @@ -887,37 +892,35 @@ static AccountMessage * _imap4_message_new(AccountPlugin * plugin, /* imap4_message_delete */ -static void _imap4_message_delete(AccountPlugin * plugin, +static void _imap4_message_delete(IMAP4 * imap4, AccountMessage * message) { if(message->message != NULL) - plugin->helper->message_delete(message->message); + imap4->helper->message_delete(message->message); object_delete(message); } /* callbacks */ /* on_idle */ -static int _connect_channel(AccountPlugin * plugin); +static int _connect_channel(IMAP4 * imap4); static gboolean _on_connect(gpointer data) { - AccountPlugin * plugin = data; - AccountPluginHelper * helper = plugin->helper; - IMAP4 * imap4 = plugin->priv; + IMAP4 * imap4 = data; + AccountPluginHelper * helper = imap4->helper; char const * hostname; char const * p; struct hostent * he; unsigned short port; struct sockaddr_in sa; int res; - char buf[128]; #ifdef DEBUG fprintf(stderr, "DEBUG: %s()\n", __func__); #endif imap4->source = 0; - if((hostname = plugin->config[I4CV_HOSTNAME].value) == NULL) + if((hostname = imap4->config[I4CV_HOSTNAME].value) == NULL) { helper->error(NULL, "No hostname set", 1); return FALSE; @@ -925,15 +928,15 @@ static gboolean _on_connect(gpointer data) if((he = gethostbyname(hostname)) == NULL) { helper->error(NULL, hstrerror(h_errno), 1); - return _on_reset(plugin); + return _on_reset(imap4); } - if((p = plugin->config[I4CV_PORT].value) == NULL) + if((p = imap4->config[I4CV_PORT].value) == NULL) return FALSE; port = (unsigned long)p; if((imap4->fd = socket(AF_INET, SOCK_STREAM, 0)) == -1) { helper->error(NULL, strerror(errno), 1); - return _on_reset(plugin); + return _on_reset(imap4); } if((res = fcntl(imap4->fd, F_GETFL)) >= 0 && fcntl(imap4->fd, F_SETFL, res | O_NONBLOCK) == -1) @@ -946,20 +949,19 @@ static gboolean _on_connect(gpointer data) inet_ntoa(sa.sin_addr), port); if((connect(imap4->fd, (struct sockaddr *)&sa, sizeof(sa)) != 0 && errno != EINPROGRESS) - || _connect_channel(plugin) != 0) + || _connect_channel(imap4) != 0) { helper->error(NULL, strerror(errno), 1); - return _on_reset(plugin); + return _on_reset(imap4); } imap4->wr_source = g_io_add_watch(imap4->channel, G_IO_OUT, - _on_watch_can_connect, plugin); + _on_watch_can_connect, imap4); return FALSE; } -static int _connect_channel(AccountPlugin * plugin) +static int _connect_channel(IMAP4 * imap4) { - AccountPluginHelper * helper = plugin->helper; - IMAP4 * imap4 = plugin->priv; + AccountPluginHelper * helper = imap4->helper; GError * error = NULL; #ifdef DEBUG @@ -986,10 +988,9 @@ static int _connect_channel(AccountPlugin * plugin) /* on_noop */ static gboolean _on_noop(gpointer data) { - AccountPlugin * plugin = data; - IMAP4 * imap4 = plugin->priv; + IMAP4 * imap4 = data; - _imap4_command(plugin, I4C_NOOP, "NOOP"); + _imap4_command(imap4, I4C_NOOP, "NOOP"); imap4->source = 0; return FALSE; } @@ -998,11 +999,10 @@ static gboolean _on_noop(gpointer data) /* on_reset */ static gboolean _on_reset(gpointer data) { - AccountPlugin * plugin = data; - IMAP4 * imap4 = plugin->priv; + IMAP4 * imap4 = data; - _imap4_reset(plugin); - imap4->source = g_timeout_add(3000, _on_connect, plugin); + _imap4_reset(imap4); + imap4->source = g_timeout_add(3000, _on_connect, imap4); return FALSE; } @@ -1011,9 +1011,8 @@ static gboolean _on_reset(gpointer data) static gboolean _on_watch_can_connect(GIOChannel * source, GIOCondition condition, gpointer data) { - AccountPlugin * plugin = data; - AccountPluginHelper * helper = plugin->helper; - IMAP4 * imap4 = plugin->priv; + IMAP4 * imap4 = data; + AccountPluginHelper * helper = imap4->helper; SSL_CTX * ssl_ctx; char buf[128]; @@ -1024,7 +1023,7 @@ static gboolean _on_watch_can_connect(GIOChannel * source, #endif imap4->wr_source = 0; /* setup SSL */ - if(plugin->config[I4CV_SSL].value != NULL) + if(imap4->config[I4CV_SSL].value != NULL) { if((ssl_ctx = helper->get_ssl_context(helper->account)) == NULL) /* FIXME report error */ @@ -1040,25 +1039,24 @@ static gboolean _on_watch_can_connect(GIOChannel * source, SSL_set_connect_state(imap4->ssl); /* perform initial handshake */ imap4->wr_source = g_io_add_watch(imap4->channel, G_IO_OUT, - _on_watch_can_handshake, plugin); + _on_watch_can_handshake, imap4); return FALSE; } /* wait for the server's banner */ imap4->rd_source = g_io_add_watch(imap4->channel, G_IO_IN, - _on_watch_can_read, plugin); + _on_watch_can_read, imap4); return FALSE; } /* on_watch_can_handshake */ -static int _handshake_verify(AccountPlugin * plugin); +static int _handshake_verify(IMAP4 * imap4); static gboolean _on_watch_can_handshake(GIOChannel * source, GIOCondition condition, gpointer data) { - AccountPlugin * plugin = data; - AccountPluginHelper * helper = plugin->helper; - IMAP4 * imap4 = plugin->priv; + IMAP4 * imap4 = data; + AccountPluginHelper * helper = imap4->helper; int res; int err; char buf[128]; @@ -1073,11 +1071,11 @@ static gboolean _on_watch_can_handshake(GIOChannel * source, imap4->rd_source = 0; if((res = SSL_do_handshake(imap4->ssl)) == 1) { - if(_handshake_verify(plugin) != 0) - return _on_reset(plugin); + if(_handshake_verify(imap4) != 0) + return _on_reset(imap4); /* wait for the server's banner */ imap4->rd_source = g_io_add_watch(imap4->channel, G_IO_IN, - _on_watch_can_read_ssl, plugin); + _on_watch_can_read_ssl, imap4); return FALSE; } err = SSL_get_error(imap4->ssl, res); @@ -1085,26 +1083,25 @@ static gboolean _on_watch_can_handshake(GIOChannel * source, if(res == 0) { helper->error(helper->account, buf, 1); - return _on_reset(plugin); + return _on_reset(imap4); } if(err == SSL_ERROR_WANT_WRITE) imap4->wr_source = g_io_add_watch(imap4->channel, G_IO_OUT, - _on_watch_can_handshake, plugin); + _on_watch_can_handshake, imap4); else if(err == SSL_ERROR_WANT_READ) imap4->rd_source = g_io_add_watch(imap4->channel, G_IO_IN, - _on_watch_can_handshake, plugin); + _on_watch_can_handshake, imap4); else { helper->error(helper->account, buf, 1); - return _on_reset(plugin); + return _on_reset(imap4); } return FALSE; } -static int _handshake_verify(AccountPlugin * plugin) +static int _handshake_verify(IMAP4 * imap4) { - AccountPluginHelper * helper = plugin->helper; - IMAP4 * imap4 = plugin->priv; + AccountPluginHelper * helper = imap4->helper; X509 * x509; char buf[256] = ""; @@ -1114,7 +1111,7 @@ static int _handshake_verify(AccountPlugin * plugin) x509 = SSL_get_peer_certificate(imap4->ssl); X509_NAME_get_text_by_NID(X509_get_subject_name(x509), NID_commonName, buf, sizeof(buf)); - if(strcasecmp(buf, plugin->config[I4CV_HOSTNAME].value) != 0) + if(strcasecmp(buf, imap4->config[I4CV_HOSTNAME].value) != 0) return helper->confirm(helper->account, "The certificate could" " not be matched.\nConnect anyway?"); return 0; @@ -1125,8 +1122,7 @@ static int _handshake_verify(AccountPlugin * plugin) static gboolean _on_watch_can_read(GIOChannel * source, GIOCondition condition, gpointer data) { - AccountPlugin * plugin = data; - IMAP4 * imap4 = plugin->priv; + IMAP4 * imap4 = data; char * p; gsize cnt = 0; GError * error = NULL; @@ -1150,15 +1146,15 @@ static gboolean _on_watch_can_read(GIOChannel * source, GIOCondition condition, case G_IO_STATUS_NORMAL: break; case G_IO_STATUS_ERROR: - plugin->helper->error(NULL, error->message, 1); + imap4->helper->error(NULL, error->message, 1); case G_IO_STATUS_EOF: default: - imap4->rd_source = g_idle_add(_on_reset, plugin); + imap4->rd_source = g_idle_add(_on_reset, imap4); return FALSE; } - if(_imap4_parse(plugin) != 0) + if(_imap4_parse(imap4) != 0) { - imap4->rd_source = g_idle_add(_on_reset, plugin); + imap4->rd_source = g_idle_add(_on_reset, imap4); return FALSE; } if(imap4->queue_cnt == 0) @@ -1177,10 +1173,10 @@ static gboolean _on_watch_can_read(GIOChannel * source, GIOCondition condition, } imap4->rd_source = 0; if(imap4->queue_cnt == 0) - imap4->source = g_timeout_add(30000, _on_noop, plugin); + imap4->source = g_timeout_add(30000, _on_noop, imap4); else imap4->wr_source = g_io_add_watch(imap4->channel, G_IO_OUT, - _on_watch_can_write, plugin); + _on_watch_can_write, imap4); return FALSE; } @@ -1189,8 +1185,7 @@ static gboolean _on_watch_can_read(GIOChannel * source, GIOCondition condition, static gboolean _on_watch_can_read_ssl(GIOChannel * source, GIOCondition condition, gpointer data) { - AccountPlugin * plugin = data; - IMAP4 * imap4 = plugin->priv; + IMAP4 * imap4 = data; char * p; int cnt; IMAP4Command * cmd; @@ -1213,7 +1208,7 @@ static gboolean _on_watch_can_read_ssl(GIOChannel * source, { imap4->rd_source = g_io_add_watch(imap4->channel, G_IO_OUT, _on_watch_can_read_ssl, - plugin); + imap4); return FALSE; } else if(cnt < 0 && SSL_get_error(imap4->ssl, cnt) @@ -1221,12 +1216,12 @@ static gboolean _on_watch_can_read_ssl(GIOChannel * source, { imap4->rd_source = g_io_add_watch(imap4->channel, G_IO_IN, _on_watch_can_read_ssl, - plugin); + imap4); return FALSE; } ERR_error_string(SSL_get_error(imap4->ssl, cnt), buf); - plugin->helper->error(NULL, buf, 1); - imap4->rd_source = g_idle_add(_on_reset, plugin); + imap4->helper->error(NULL, buf, 1); + imap4->rd_source = g_idle_add(_on_reset, imap4); return FALSE; } #ifdef DEBUG @@ -1234,9 +1229,9 @@ static gboolean _on_watch_can_read_ssl(GIOChannel * source, fwrite(&imap4->rd_buf[imap4->rd_buf_cnt], sizeof(*p), cnt, stderr); #endif imap4->rd_buf_cnt += cnt; - if(_imap4_parse(plugin) != 0) + if(_imap4_parse(imap4) != 0) { - imap4->rd_source = g_idle_add(_on_reset, plugin); + imap4->rd_source = g_idle_add(_on_reset, imap4); return FALSE; } if(imap4->queue_cnt == 0) @@ -1255,10 +1250,10 @@ static gboolean _on_watch_can_read_ssl(GIOChannel * source, } imap4->rd_source = 0; if(imap4->queue_cnt == 0) - imap4->source = g_timeout_add(30000, _on_noop, plugin); + imap4->source = g_timeout_add(30000, _on_noop, imap4); else imap4->wr_source = g_io_add_watch(imap4->channel, G_IO_OUT, - _on_watch_can_write_ssl, plugin); + _on_watch_can_write_ssl, imap4); return FALSE; } @@ -1267,8 +1262,7 @@ static gboolean _on_watch_can_read_ssl(GIOChannel * source, static gboolean _on_watch_can_write(GIOChannel * source, GIOCondition condition, gpointer data) { - AccountPlugin * plugin = data; - IMAP4 * imap4 = plugin->priv; + IMAP4 * imap4 = data; IMAP4Command * cmd = &imap4->queue[0]; gsize cnt = 0; GError * error = NULL; @@ -1301,10 +1295,10 @@ static gboolean _on_watch_can_write(GIOChannel * source, GIOCondition condition, case G_IO_STATUS_NORMAL: break; case G_IO_STATUS_ERROR: - plugin->helper->error(NULL, error->message, 1); + imap4->helper->error(NULL, error->message, 1); case G_IO_STATUS_EOF: default: - imap4->wr_source = g_idle_add(_on_reset, plugin); + imap4->wr_source = g_idle_add(_on_reset, imap4); return FALSE; } if(cmd->buf_cnt > 0) @@ -1313,7 +1307,7 @@ static gboolean _on_watch_can_write(GIOChannel * source, GIOCondition condition, imap4->wr_source = 0; if(imap4->rd_source == 0) imap4->rd_source = g_io_add_watch(imap4->channel, G_IO_IN, - _on_watch_can_read, plugin); + _on_watch_can_read, imap4); return FALSE; } @@ -1322,8 +1316,7 @@ static gboolean _on_watch_can_write(GIOChannel * source, GIOCondition condition, static gboolean _on_watch_can_write_ssl(GIOChannel * source, GIOCondition condition, gpointer data) { - AccountPlugin * plugin = data; - IMAP4 * imap4 = plugin->priv; + IMAP4 * imap4 = data; IMAP4Command * cmd = &imap4->queue[0]; int cnt; char * p; @@ -1342,7 +1335,7 @@ static gboolean _on_watch_can_write_ssl(GIOChannel * source, { imap4->wr_source = g_io_add_watch(imap4->channel, G_IO_IN, _on_watch_can_write_ssl, - plugin); + imap4); return FALSE; } else if(cnt < 0 && SSL_get_error(imap4->ssl, cnt) @@ -1350,12 +1343,12 @@ static gboolean _on_watch_can_write_ssl(GIOChannel * source, { imap4->wr_source = g_io_add_watch(imap4->channel, G_IO_OUT, _on_watch_can_write_ssl, - plugin); + imap4); return FALSE; } ERR_error_string(SSL_get_error(imap4->ssl, cnt), buf); - plugin->helper->error(NULL, buf, 1); - imap4->wr_source = g_idle_add(_on_reset, plugin); + imap4->helper->error(NULL, buf, 1); + imap4->wr_source = g_idle_add(_on_reset, imap4); return FALSE; } #ifdef DEBUG @@ -1374,6 +1367,6 @@ static gboolean _on_watch_can_write_ssl(GIOChannel * source, imap4->wr_source = 0; if(imap4->rd_source == 0) imap4->rd_source = g_io_add_watch(imap4->channel, G_IO_IN, - _on_watch_can_read_ssl, plugin); + _on_watch_can_read_ssl, imap4); return FALSE; } diff --git a/src/account/mbox.c b/src/account/mbox.c index 4bbeb79..f6fe097 100644 --- a/src/account/mbox.c +++ b/src/account/mbox.c @@ -1,5 +1,5 @@ /* $Id$ */ -/* Copyright (c) 2011 Pierre Pronchery */ +/* Copyright (c) 2011-2012 Pierre Pronchery */ /* This file is part of DeforaOS Desktop Mailer */ /* This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -43,10 +43,12 @@ typedef enum _ParserContext PC_GARBAGE /* inside crap */ } ParserContext; -typedef struct _Mbox Mbox; +typedef struct _AccountPlugin Mbox; struct _AccountMessage { + AccountPluginHelper * helper; + Message * message; /* Mbox */ @@ -81,9 +83,11 @@ struct _AccountFolder char * pixbuf; }; -struct _Mbox +struct _AccountPlugin { - AccountPlugin * plugin; + AccountPluginHelper * helper; + + AccountConfig * config; AccountFolder folders[_FOLDER_CNT]; @@ -95,7 +99,7 @@ struct _Mbox /* constants */ #define MBOX_REFRESH_TIMEOUT 5000 -static AccountConfig _mbox_config[] = +static AccountConfig const _mbox_config[] = { { "mbox", "Inbox file", ACT_FILE, NULL }, { "spool", "Spool file", ACT_FILE, NULL }, @@ -121,25 +125,26 @@ static const struct /* plug-in */ -static int _mbox_init(AccountPlugin * plugin); -static int _mbox_destroy(AccountPlugin * plugin); -static char * _mbox_get_source(AccountPlugin * plugin, AccountFolder * folder, +static Mbox * _mbox_init(AccountPluginHelper * helper); +static int _mbox_destroy(Mbox * mbox); +static AccountConfig * _mbox_get_config(Mbox * mbox); +static char * _mbox_get_source(Mbox * mbox, AccountFolder * folder, AccountMessage * message); -static int _mbox_refresh(AccountPlugin * plugin, AccountFolder * folder, +static int _mbox_refresh(Mbox * mbox, AccountFolder * folder, AccountMessage * message); -AccountPlugin account_plugin = +AccountPluginDefinition account_plugin = { - NULL, "MBOX", "Local folders", NULL, + NULL, _mbox_config, _mbox_init, _mbox_destroy, + _mbox_get_config, _mbox_get_source, - _mbox_refresh, - NULL + _mbox_refresh }; @@ -153,7 +158,8 @@ static gboolean _folder_watch(GIOChannel * source, GIOCondition condition, /* AccountMessage */ /* private */ /* prototypes */ -static AccountMessage * _message_new(Folder * folder, off_t offset); +static AccountMessage * _message_new(AccountPluginHelper * helper, + Folder * folder, off_t offset); static void _message_delete(AccountMessage * message); static int _message_set_body(AccountMessage * message, off_t offset, @@ -164,7 +170,7 @@ static int _message_set_header(AccountMessage * message, char const * header); /* Mbox */ /* functions */ /* mbox_init */ -static int _mbox_init(AccountPlugin * plugin) +static Mbox * _mbox_init(AccountPluginHelper * helper) { Mbox * mbox; size_t i; @@ -174,30 +180,34 @@ static int _mbox_init(AccountPlugin * plugin) fprintf(stderr, "DEBUG: %s()\n", __func__); #endif if((mbox = calloc(1, sizeof(*mbox))) == NULL) - return -1; - plugin->priv = mbox; - mbox->plugin = plugin; + return NULL; + mbox->helper = helper; mbox->timeout = MBOX_REFRESH_TIMEOUT; + if((mbox->config = malloc(sizeof(_mbox_config))) == NULL) + { + free(mbox); + return NULL; + } + memcpy(mbox->config, &_mbox_config, sizeof(_mbox_config)); for(i = 0; i < _FOLDER_CNT; i++) { af = &mbox->folders[i]; af->config = &_mbox_config[_mbox_folder_defaults[i].config]; if(af->config->value == NULL) continue; - af->folder = plugin->helper->folder_new(plugin->helper->account, - af, NULL, _mbox_folder_defaults[i].type, + af->folder = helper->folder_new(helper->account, af, NULL, + _mbox_folder_defaults[i].type, _mbox_folder_defaults[i].name); af->mbox = mbox; af->source = g_idle_add(_folder_idle, af); } - return 0; + return mbox; } /* mbox_destroy */ -static int _mbox_destroy(AccountPlugin * plugin) +static int _mbox_destroy(Mbox * mbox) { - Mbox * mbox = plugin->priv; size_t i; AccountFolder * mf; size_t j; @@ -221,8 +231,15 @@ static int _mbox_destroy(AccountPlugin * plugin) } +/* mbox_get_config */ +static AccountConfig * _mbox_get_config(Mbox * mbox) +{ + return mbox->config; +} + + /* mbox_get_source */ -static char * _mbox_get_source(AccountPlugin * plugin, AccountFolder * folder, +static char * _mbox_get_source(Mbox * mbox, AccountFolder * folder, AccountMessage * message) { char * ret = NULL; @@ -234,7 +251,7 @@ static char * _mbox_get_source(AccountPlugin * plugin, AccountFolder * folder, return NULL; if((fp = fopen(filename, "r")) == NULL) { - plugin->helper->error(plugin->helper->account, filename, 1); + mbox->helper->error(mbox->helper->account, filename, 1); return NULL; } len = message->body_offset - message->offset + message->body_length; @@ -246,7 +263,7 @@ static char * _mbox_get_source(AccountPlugin * plugin, AccountFolder * folder, free(ret); if(fclose(fp) != 0) { - plugin->helper->error(plugin->helper->account, filename, 1); + mbox->helper->error(mbox->helper->account, filename, 1); free(ret); ret = NULL; } @@ -255,7 +272,7 @@ static char * _mbox_get_source(AccountPlugin * plugin, AccountFolder * folder, /* mbox_refresh */ -static int _mbox_refresh(AccountPlugin * plugin, AccountFolder * folder, +static int _mbox_refresh(Mbox * mbox, AccountFolder * folder, AccountMessage * message) { char const * filename = folder->config->value; @@ -264,21 +281,21 @@ static int _mbox_refresh(AccountPlugin * plugin, AccountFolder * folder, size_t size; #ifdef DEBUG - fprintf(stderr, "DEBUG: %s(%p, %p)\n", __func__, (void*)folder, - (void*)message); + fprintf(stderr, "DEBUG: %s(%p, %p)\n", __func__, (void *)folder, + (void *)message); #endif if(message == NULL) return 0; - plugin->helper->message_set_body(message->message, NULL, 0, 0); + mbox->helper->message_set_body(message->message, NULL, 0, 0); /* XXX we may still be reading the file... */ if((fp = fopen(filename, "r")) == NULL) - return -plugin->helper->error(NULL, strerror(errno), 1); + return -mbox->helper->error(NULL, strerror(errno), 1); if(message->body_offset != 0 && message->body_length > 0 && fseek(fp, message->body_offset, SEEK_SET) == 0 && (buf = malloc(message->body_length)) != NULL) { if((size = fread(buf, 1, message->body_length, fp)) > 0) - plugin->helper->message_set_body(message->message, buf, + mbox->helper->message_set_body(message->message, buf, size, 1); free(buf); } @@ -290,7 +307,8 @@ static int _mbox_refresh(AccountPlugin * plugin, AccountFolder * folder, /* AccountMessage */ /* functions */ /* message_new */ -static AccountMessage * _message_new(Folder * folder, off_t offset) +static AccountMessage * _message_new(AccountPluginHelper * helper, + Folder * folder, off_t offset) { AccountMessage * message; @@ -299,8 +317,9 @@ static AccountMessage * _message_new(Folder * folder, off_t offset) /* FIXME catch error */ return NULL; } - message->message = account_plugin.helper->message_new( - account_plugin.helper->account, folder, message); + message->helper = helper; + message->message = helper->message_new(helper->account, folder, + message); message->offset = offset; message->body_offset = 0; message->body_length = 0; @@ -316,7 +335,7 @@ static AccountMessage * _message_new(Folder * folder, off_t offset) /* message_delete */ static void _message_delete(AccountMessage * message) { - account_plugin.helper->message_delete(message->message); + message->helper->message_delete(message->message); free(message); } @@ -338,8 +357,7 @@ static int _message_set_body(AccountMessage * message, off_t offset, /* message_set_header */ static int _message_set_header(AccountMessage * message, char const * header) { - return account_plugin.helper->message_set_header(message->message, - header); + return message->helper->message_set_header(message->message, header); } @@ -361,7 +379,7 @@ static gboolean _folder_idle(gpointer data) return FALSE; if(stat(filename, &st) != 0) { - mbox->plugin->helper->error(NULL, strerror(errno), 1); + mbox->helper->error(NULL, strerror(errno), 1); folder->source = g_timeout_add(mbox->timeout, _folder_idle, folder); return FALSE; @@ -377,7 +395,7 @@ static gboolean _folder_idle(gpointer data) if((folder->channel = g_io_channel_new_file(filename, "r", &error)) == NULL) { - mbox->plugin->helper->error(NULL, error->message, 1); + mbox->helper->error(NULL, error->message, 1); folder->source = g_timeout_add(mbox->timeout, _folder_idle, folder); return FALSE; @@ -424,7 +442,7 @@ static gboolean _folder_watch(GIOChannel * source, GIOCondition condition, switch(status) { case G_IO_STATUS_ERROR: - mbox->plugin->helper->error(NULL, error->message, 1); + mbox->helper->error(NULL, error->message, 1); /* FIXME new timeout 1000 function after invalidating * mtime */ return FALSE; @@ -596,7 +614,8 @@ static AccountMessage * _folder_message_add(AccountFolder * folder, return NULL; } folder->messages = p; - if((message = _message_new(folder->folder, offset)) == NULL) + if((message = _message_new(folder->mbox->helper, folder->folder, + offset)) == NULL) { /* FIXME track error */ return NULL; diff --git a/src/account/nntp.c b/src/account/nntp.c index 78ebb7f..6a56e3e 100644 --- a/src/account/nntp.c +++ b/src/account/nntp.c @@ -1,5 +1,5 @@ /* $Id$ */ -/* Copyright (c) 2011 Pierre Pronchery */ +/* Copyright (c) 2011-2012 Pierre Pronchery */ /* This file is part of DeforaOS Desktop Mailer */ /* This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -23,7 +23,7 @@ static char const _nntp_type[] = "NNTP"; static char const _nntp_name[] = "Newsgroups"; -static AccountConfig _nntp_config[] = +static AccountConfig const _nntp_config[] = { { "username", "Username", ACT_STRING, NULL }, { "password", "Password", ACT_PASSWORD, NULL }, @@ -37,12 +37,12 @@ static AccountConfig _nntp_config[] = /* functions */ -AccountPlugin account_plugin = +AccountPluginDefinition account_plugin = { - NULL, _nntp_type, _nntp_name, NULL, + NULL, _nntp_config, NULL, NULL, diff --git a/src/account/pop3.c b/src/account/pop3.c index 99fd524..8e569a1 100644 --- a/src/account/pop3.c +++ b/src/account/pop3.c @@ -1,5 +1,5 @@ /* $Id$ */ -/* Copyright (c) 2011 Pierre Pronchery */ +/* Copyright (c) 2011-2012 Pierre Pronchery */ /* This file is part of DeforaOS Desktop Mailer */ /* This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -103,8 +103,12 @@ typedef struct _POP3Command } data; } POP3Command; -typedef struct _POP3 +typedef struct _AccountPlugin { + AccountPluginHelper * helper; + + AccountConfig * config; + int fd; SSL * ssl; guint source; @@ -142,22 +146,23 @@ static AccountConfig _pop3_config[P3CV_COUNT + 1] = /* prototypes */ /* plug-in */ -static int _pop3_init(AccountPlugin * plugin); -static int _pop3_destroy(AccountPlugin * plugin); -static int _pop3_refresh(AccountPlugin * plugin, AccountFolder * folder, +static POP3 * _pop3_init(AccountPluginHelper * helper); +static int _pop3_destroy(POP3 * pop3); +static AccountConfig * _pop3_get_config(POP3 * pop3); +static int _pop3_refresh(POP3 * pop3, AccountFolder * folder, AccountMessage * message); /* useful */ -static POP3Command * _pop3_command(AccountPlugin * plugin, POP3Context context, +static POP3Command * _pop3_command(POP3 * pop3, POP3Context context, char const * command); -static int _pop3_parse(AccountPlugin * plugin); -static void _pop3_reset(AccountPlugin * plugin); +static int _pop3_parse(POP3 * pop3); +static void _pop3_reset(POP3 * pop3); -static AccountMessage * _pop3_message_get(AccountPlugin * plugin, +static AccountMessage * _pop3_message_get(POP3 * pop3, AccountFolder * folder, unsigned int id); -static AccountMessage * _pop3_message_new(AccountPlugin * plugin, +static AccountMessage * _pop3_message_new(POP3 * pop3, AccountFolder * folder, unsigned int id); -static void _pop3_message_delete(AccountPlugin * plugin, +static void _pop3_message_delete(POP3 * pop3, AccountMessage * message); /* callbacks */ @@ -180,61 +185,72 @@ static gboolean _on_watch_can_write_ssl(GIOChannel * source, /* public */ /* variables */ -AccountPlugin account_plugin = +AccountPluginDefinition account_plugin = { - NULL, _pop3_type, _pop3_name, NULL, + NULL, _pop3_config, _pop3_init, _pop3_destroy, + _pop3_get_config, NULL, - _pop3_refresh, - NULL + _pop3_refresh }; /* private */ /* functions */ /* pop3_init */ -static int _pop3_init(AccountPlugin * plugin) +static POP3 * _pop3_init(AccountPluginHelper * helper) { POP3 * pop3; if((pop3 = malloc(sizeof(*pop3))) == NULL) - return -1; + return NULL; memset(pop3, 0, sizeof(*pop3)); - plugin->priv = pop3; + pop3->helper = helper; + if((pop3->config = malloc(sizeof(_pop3_config))) == NULL) + { + free(pop3); + return NULL; + } + memcpy(pop3->config, &_pop3_config, sizeof(_pop3_config)); pop3->fd = -1; - pop3->inbox.folder = plugin->helper->folder_new(plugin->helper->account, + pop3->inbox.folder = pop3->helper->folder_new(pop3->helper->account, &pop3->inbox, NULL, FT_INBOX, "Inbox"); - pop3->trash.folder = plugin->helper->folder_new(plugin->helper->account, + pop3->trash.folder = pop3->helper->folder_new(pop3->helper->account, &pop3->trash, NULL, FT_TRASH, "Trash"); - pop3->source = g_idle_add(_on_connect, plugin); - return 0; + pop3->source = g_idle_add(_on_connect, pop3); + return pop3; } /* pop3_destroy */ -static int _pop3_destroy(AccountPlugin * plugin) +static int _pop3_destroy(POP3 * pop3) { - POP3 * pop3 = plugin->priv; - #ifdef DEBUG fprintf(stderr, "DEBUG: %s()\n", __func__); #endif if(pop3 == NULL) /* XXX _pop3_destroy() may be called uninitialized */ return 0; - _pop3_reset(plugin); + _pop3_reset(pop3); free(pop3); return 0; } +/* pop3_get_config */ +static AccountConfig * _pop3_get_config(POP3 * pop3) +{ + return pop3->config; +} + + /* pop3_refresh */ -static int _pop3_refresh(AccountPlugin * plugin, AccountFolder * folder, +static int _pop3_refresh(POP3 * pop3, AccountFolder * folder, AccountMessage * message) { char buf[32]; @@ -243,7 +259,7 @@ static int _pop3_refresh(AccountPlugin * plugin, AccountFolder * folder, if(message == NULL) return 0; snprintf(buf, sizeof(buf), "%s %u", "RETR", message->id); - if((cmd = _pop3_command(plugin, P3C_TRANSACTION_RETR, buf)) == NULL) + if((cmd = _pop3_command(pop3, P3C_TRANSACTION_RETR, buf)) == NULL) return -1; cmd->data.transaction_retr.id = message->id; return 0; @@ -252,10 +268,9 @@ static int _pop3_refresh(AccountPlugin * plugin, AccountFolder * folder, /* useful */ /* pop3_command */ -static POP3Command * _pop3_command(AccountPlugin * plugin, POP3Context context, +static POP3Command * _pop3_command(POP3 * pop3, POP3Context context, char const * command) { - POP3 * pop3 = plugin->priv; POP3Command * p; size_t len; @@ -292,22 +307,21 @@ static POP3Command * _pop3_command(AccountPlugin * plugin, POP3Context context, } pop3->wr_source = g_io_add_watch(pop3->channel, G_IO_OUT, (pop3->ssl != NULL) ? _on_watch_can_write_ssl - : _on_watch_can_write, plugin); + : _on_watch_can_write, pop3); } return p; } /* pop3_parse */ -static int _parse_context(AccountPlugin * plugin, char const * answer); -static int _parse_context_transaction_retr(AccountPlugin * plugin, +static int _parse_context(POP3 * pop3, char const * answer); +static int _parse_context_transaction_retr(POP3 * pop3, char const * answer); -static int _pop3_parse(AccountPlugin * plugin) +static int _pop3_parse(POP3 * pop3) { int ret = 0; - AccountPluginHelper * helper = plugin->helper; - POP3 * pop3 = plugin->priv; + AccountPluginHelper * helper = pop3->helper; size_t i; size_t j; @@ -334,7 +348,7 @@ static int _pop3_parse(AccountPlugin * plugin) else if(pop3->queue[0].status == P3CS_SENT && strncmp("+OK", &pop3->rd_buf[j], 3) == 0) pop3->queue[0].status = P3CS_PARSING; - if(_parse_context(plugin, &pop3->rd_buf[j]) != 0) + if(_parse_context(pop3, &pop3->rd_buf[j]) != 0) { pop3->queue[0].status = P3CS_ERROR; ret = -1; @@ -348,10 +362,9 @@ static int _pop3_parse(AccountPlugin * plugin) return ret; } -static int _parse_context(AccountPlugin * plugin, char const * answer) +static int _parse_context(POP3 * pop3, char const * answer) { int ret = -1; - POP3 * pop3 = plugin->priv; POP3Command * cmd = &pop3->queue[0]; char const * p; char * q; @@ -368,27 +381,27 @@ static int _parse_context(AccountPlugin * plugin, char const * answer) if(cmd->status != P3CS_PARSING) return 0; cmd->status = P3CS_OK; - if((p = plugin->config[0].value) == NULL) + if((p = pop3->config[0].value) == NULL) return -1; q = g_strdup_printf("%s %s", "USER", p); - cmd = _pop3_command(plugin, P3C_AUTHORIZATION_USER, q); + cmd = _pop3_command(pop3, P3C_AUTHORIZATION_USER, q); g_free(q); return (cmd != NULL) ? 0 : -1; case P3C_AUTHORIZATION_USER: if(cmd->status != P3CS_PARSING) return 0; cmd->status = P3CS_OK; - if((p = plugin->config[1].value) == NULL) + if((p = pop3->config[1].value) == NULL) p = ""; /* assumes an empty password */ q = g_strdup_printf("%s %s", "PASS", p); - cmd = _pop3_command(plugin, P3C_AUTHORIZATION_PASS, q); + cmd = _pop3_command(pop3, P3C_AUTHORIZATION_PASS, q); g_free(q); return (cmd != NULL) ? 0 : -1; case P3C_AUTHORIZATION_PASS: if(cmd->status != P3CS_PARSING) return 0; cmd->status = P3CS_OK; - return (_pop3_command(plugin, P3C_TRANSACTION_STAT, + return (_pop3_command(pop3, P3C_TRANSACTION_STAT, "STAT") != NULL) ? 0 : -1; case P3C_NOOP: if(strncmp(answer, "+OK", 3) == 0) @@ -408,30 +421,29 @@ static int _parse_context(AccountPlugin * plugin, char const * answer) return -1; /* FIXME may not be supported by the server */ q = g_strdup_printf("%s %u 0", "TOP", u); - cmd = _pop3_command(plugin, P3C_TRANSACTION_TOP, q); + cmd = _pop3_command(pop3, P3C_TRANSACTION_TOP, q); free(q); cmd->data.transaction_top.id = u; return (cmd != NULL) ? 0 : -1; case P3C_TRANSACTION_RETR: case P3C_TRANSACTION_TOP: /* same as RETR without the body */ - return _parse_context_transaction_retr(plugin, answer); + return _parse_context_transaction_retr(pop3, answer); case P3C_TRANSACTION_STAT: if(cmd->status != P3CS_PARSING) return 0; if(sscanf(answer, "+OK %u %u", &u, &v) != 2) return -1; cmd->status = P3CS_OK; - return (_pop3_command(plugin, P3C_TRANSACTION_LIST, + return (_pop3_command(pop3, P3C_TRANSACTION_LIST, "LIST") != NULL) ? 0 : -1; } return ret; } -static int _parse_context_transaction_retr(AccountPlugin * plugin, +static int _parse_context_transaction_retr(POP3 * pop3, char const * answer) { - AccountPluginHelper * helper = plugin->helper; - POP3 * pop3 = plugin->priv; + AccountPluginHelper * helper = pop3->helper; POP3Command * cmd = &pop3->queue[0]; AccountMessage * message; @@ -441,7 +453,7 @@ static int _parse_context_transaction_retr(AccountPlugin * plugin, && strncmp(answer, "+OK", 3) == 0) { cmd->data.transaction_retr.body = FALSE; - message = _pop3_message_get(plugin, &pop3->inbox, + message = _pop3_message_get(pop3, &pop3->inbox, cmd->data.transaction_retr.id); cmd->data.transaction_retr.message = message; return 0; @@ -470,9 +482,8 @@ static int _parse_context_transaction_retr(AccountPlugin * plugin, /* pop3_reset */ -static void _pop3_reset(AccountPlugin * plugin) +static void _pop3_reset(POP3 * pop3) { - POP3 * pop3 = plugin->priv; size_t i; if(pop3->rd_source != 0) @@ -497,7 +508,7 @@ static void _pop3_reset(AccountPlugin * plugin) /* pop3_message_get */ -static AccountMessage * _pop3_message_get(AccountPlugin * plugin, +static AccountMessage * _pop3_message_get(POP3 * pop3, AccountFolder * folder, unsigned int id) { size_t i; @@ -505,15 +516,15 @@ static AccountMessage * _pop3_message_get(AccountPlugin * plugin, for(i = 0; i < folder->messages_cnt; i++) if(folder->messages[i]->id == id) return folder->messages[i]; - return _pop3_message_new(plugin, folder, id); + return _pop3_message_new(pop3, folder, id); } /* pop3_message_new */ -static AccountMessage * _pop3_message_new(AccountPlugin * plugin, +static AccountMessage * _pop3_message_new(POP3 * pop3, AccountFolder * folder, unsigned int id) { - AccountPluginHelper * helper = plugin->helper; + AccountPluginHelper * helper = pop3->helper; AccountMessage * message; AccountMessage ** p; @@ -527,7 +538,7 @@ static AccountMessage * _pop3_message_new(AccountPlugin * plugin, if((message->message = helper->message_new(helper->account, folder->folder, message)) == NULL) { - _pop3_message_delete(plugin, message); + _pop3_message_delete(pop3, message); return NULL; } folder->messages[folder->messages_cnt++] = message; @@ -536,37 +547,35 @@ static AccountMessage * _pop3_message_new(AccountPlugin * plugin, /* pop3_message_delete */ -static void _pop3_message_delete(AccountPlugin * plugin, +static void _pop3_message_delete(POP3 * pop3, AccountMessage * message) { if(message->message != NULL) - plugin->helper->message_delete(message->message); + pop3->helper->message_delete(message->message); object_delete(message); } /* callbacks */ /* on_idle */ -static int _connect_channel(AccountPlugin * plugin); +static int _connect_channel(POP3 * pop3); static gboolean _on_connect(gpointer data) { - AccountPlugin * plugin = data; - AccountPluginHelper * helper = plugin->helper; - POP3 * pop3 = plugin->priv; + POP3 * pop3 = data; + AccountPluginHelper * helper = pop3->helper; char const * hostname; char const * p; struct hostent * he; unsigned short port; struct sockaddr_in sa; int res; - char buf[128]; #ifdef DEBUG fprintf(stderr, "DEBUG: %s()\n", __func__); #endif pop3->source = 0; - if((hostname = plugin->config[P3CV_HOSTNAME].value) == NULL) + if((hostname = pop3->config[P3CV_HOSTNAME].value) == NULL) { helper->error(NULL, "No hostname set", 1); return FALSE; @@ -574,15 +583,15 @@ static gboolean _on_connect(gpointer data) if((he = gethostbyname(hostname)) == NULL) { helper->error(NULL, hstrerror(h_errno), 1); - return _on_reset(plugin); + return _on_reset(pop3); } - if((p = plugin->config[P3CV_PORT].value) == NULL) + if((p = pop3->config[P3CV_PORT].value) == NULL) return FALSE; port = (unsigned long)p; if((pop3->fd = socket(AF_INET, SOCK_STREAM, 0)) == -1) { helper->error(NULL, strerror(errno), 1); - return _on_reset(plugin); + return _on_reset(pop3); } if((res = fcntl(pop3->fd, F_GETFL)) >= 0 && fcntl(pop3->fd, F_SETFL, res | O_NONBLOCK) == -1) @@ -595,20 +604,19 @@ static gboolean _on_connect(gpointer data) inet_ntoa(sa.sin_addr), port); if((connect(pop3->fd, (struct sockaddr *)&sa, sizeof(sa)) != 0 && errno != EINPROGRESS) - || _connect_channel(plugin) != 0) + || _connect_channel(pop3) != 0) { helper->error(NULL, strerror(errno), 1); - return _on_reset(plugin); + return _on_reset(pop3); } pop3->wr_source = g_io_add_watch(pop3->channel, G_IO_OUT, - _on_watch_can_connect, plugin); + _on_watch_can_connect, pop3); return FALSE; } -static int _connect_channel(AccountPlugin * plugin) +static int _connect_channel(POP3 * pop3) { - AccountPluginHelper * helper = plugin->helper; - POP3 * pop3 = plugin->priv; + AccountPluginHelper * helper = pop3->helper; GError * error = NULL; #ifdef DEBUG @@ -633,10 +641,9 @@ static int _connect_channel(AccountPlugin * plugin) /* on_noop */ static gboolean _on_noop(gpointer data) { - AccountPlugin * plugin = data; - POP3 * pop3 = plugin->priv; + POP3 * pop3 = data; - _pop3_command(plugin, P3C_NOOP, "NOOP"); + _pop3_command(pop3, P3C_NOOP, "NOOP"); pop3->source = 0; return FALSE; } @@ -645,14 +652,13 @@ static gboolean _on_noop(gpointer data) /* on_reset */ static gboolean _on_reset(gpointer data) { - AccountPlugin * plugin = data; - POP3 * pop3 = plugin->priv; + POP3 * pop3 = data; #ifdef DEBUG fprintf(stderr, "DEBUG: %s()\n", __func__); #endif - _pop3_reset(plugin); - pop3->source = g_timeout_add(3000, _on_connect, plugin); + _pop3_reset(pop3); + pop3->source = g_timeout_add(3000, _on_connect, pop3); return FALSE; } @@ -661,9 +667,8 @@ static gboolean _on_reset(gpointer data) static gboolean _on_watch_can_connect(GIOChannel * source, GIOCondition condition, gpointer data) { - AccountPlugin * plugin = data; - AccountPluginHelper * helper = plugin->helper; - POP3 * pop3 = plugin->priv; + POP3 * pop3 = data; + AccountPluginHelper * helper = pop3->helper; SSL_CTX * ssl_ctx; char buf[128]; @@ -674,7 +679,7 @@ static gboolean _on_watch_can_connect(GIOChannel * source, #endif pop3->wr_source = 0; /* setup SSL */ - if(plugin->config[P3CV_SSL].value != NULL) + if(pop3->config[P3CV_SSL].value != NULL) { if((ssl_ctx = helper->get_ssl_context(helper->account)) == NULL) /* FIXME report error */ @@ -690,25 +695,24 @@ static gboolean _on_watch_can_connect(GIOChannel * source, SSL_set_connect_state(pop3->ssl); /* perform initial handshake */ pop3->wr_source = g_io_add_watch(pop3->channel, G_IO_OUT, - _on_watch_can_handshake, plugin); + _on_watch_can_handshake, pop3); return FALSE; } /* wait for the server's banner */ pop3->rd_source = g_io_add_watch(pop3->channel, G_IO_IN, - _on_watch_can_read, plugin); + _on_watch_can_read, pop3); return FALSE; } /* on_watch_can_handshake */ -static int _handshake_verify(AccountPlugin * plugin); +static int _handshake_verify(POP3 * pop3); static gboolean _on_watch_can_handshake(GIOChannel * source, GIOCondition condition, gpointer data) { - AccountPlugin * plugin = data; - AccountPluginHelper * helper = plugin->helper; - POP3 * pop3 = plugin->priv; + POP3 * pop3 = data; + AccountPluginHelper * helper = pop3->helper; int res; int err; char buf[128]; @@ -723,11 +727,11 @@ static gboolean _on_watch_can_handshake(GIOChannel * source, pop3->rd_source = 0; if((res = SSL_do_handshake(pop3->ssl)) == 1) { - if(_handshake_verify(plugin) != 0) - return _on_reset(plugin); + if(_handshake_verify(pop3) != 0) + return _on_reset(pop3); /* wait for the server's banner */ pop3->rd_source = g_io_add_watch(pop3->channel, G_IO_IN, - _on_watch_can_read_ssl, plugin); + _on_watch_can_read_ssl, pop3); return FALSE; } err = SSL_get_error(pop3->ssl, res); @@ -735,26 +739,25 @@ static gboolean _on_watch_can_handshake(GIOChannel * source, if(res == 0) { helper->error(helper->account, buf, 1); - return _on_reset(plugin); + return _on_reset(pop3); } if(err == SSL_ERROR_WANT_WRITE) pop3->wr_source = g_io_add_watch(pop3->channel, G_IO_OUT, - _on_watch_can_handshake, plugin); + _on_watch_can_handshake, pop3); else if(err == SSL_ERROR_WANT_READ) pop3->rd_source = g_io_add_watch(pop3->channel, G_IO_IN, - _on_watch_can_handshake, plugin); + _on_watch_can_handshake, pop3); else { helper->error(helper->account, buf, 1); - return _on_reset(plugin); + return _on_reset(pop3); } return FALSE; } -static int _handshake_verify(AccountPlugin * plugin) +static int _handshake_verify(POP3 * pop3) { - AccountPluginHelper * helper = plugin->helper; - POP3 * pop3 = plugin->priv; + AccountPluginHelper * helper = pop3->helper; X509 * x509; char buf[256] = ""; @@ -764,7 +767,7 @@ static int _handshake_verify(AccountPlugin * plugin) x509 = SSL_get_peer_certificate(pop3->ssl); X509_NAME_get_text_by_NID(X509_get_subject_name(x509), NID_commonName, buf, sizeof(buf)); - if(strcasecmp(buf, plugin->config[P3CV_HOSTNAME].value) != 0) + if(strcasecmp(buf, pop3->config[P3CV_HOSTNAME].value) != 0) return helper->confirm(helper->account, "The certificate could" " not be matched.\nConnect anyway?"); return 0; @@ -775,8 +778,7 @@ static int _handshake_verify(AccountPlugin * plugin) static gboolean _on_watch_can_read(GIOChannel * source, GIOCondition condition, gpointer data) { - AccountPlugin * plugin = data; - POP3 * pop3 = plugin->priv; + POP3 * pop3 = data; char * p; gsize cnt = 0; GError * error = NULL; @@ -800,15 +802,15 @@ static gboolean _on_watch_can_read(GIOChannel * source, GIOCondition condition, case G_IO_STATUS_NORMAL: break; case G_IO_STATUS_ERROR: - plugin->helper->error(NULL, error->message, 1); + pop3->helper->error(NULL, error->message, 1); case G_IO_STATUS_EOF: default: - pop3->rd_source = g_idle_add(_on_reset, plugin); + pop3->rd_source = g_idle_add(_on_reset, pop3); return FALSE; } - if(_pop3_parse(plugin) != 0) + if(_pop3_parse(pop3) != 0) { - pop3->rd_source = g_idle_add(_on_reset, plugin); + pop3->rd_source = g_idle_add(_on_reset, pop3); return FALSE; } if(pop3->queue_cnt == 0) @@ -827,10 +829,10 @@ static gboolean _on_watch_can_read(GIOChannel * source, GIOCondition condition, } pop3->rd_source = 0; if(pop3->queue_cnt == 0) - pop3->source = g_timeout_add(30000, _on_noop, plugin); + pop3->source = g_timeout_add(30000, _on_noop, pop3); else pop3->wr_source = g_io_add_watch(pop3->channel, G_IO_OUT, - _on_watch_can_write, plugin); + _on_watch_can_write, pop3); return FALSE; } @@ -839,8 +841,7 @@ static gboolean _on_watch_can_read(GIOChannel * source, GIOCondition condition, static gboolean _on_watch_can_read_ssl(GIOChannel * source, GIOCondition condition, gpointer data) { - AccountPlugin * plugin = data; - POP3 * pop3 = plugin->priv; + POP3 * pop3 = data; char * p; int cnt; POP3Command * cmd; @@ -862,20 +863,19 @@ static gboolean _on_watch_can_read_ssl(GIOChannel * source, == SSL_ERROR_WANT_WRITE) { pop3->rd_source = g_io_add_watch(pop3->channel, - G_IO_OUT, _on_watch_can_read_ssl, - plugin); + G_IO_OUT, _on_watch_can_read_ssl, pop3); return FALSE; } else if(cnt < 0 && SSL_get_error(pop3->ssl, cnt) == SSL_ERROR_WANT_READ) { pop3->rd_source = g_io_add_watch(pop3->channel, G_IO_IN, - _on_watch_can_read_ssl, plugin); + _on_watch_can_read_ssl, pop3); return FALSE; } ERR_error_string(SSL_get_error(pop3->ssl, cnt), buf); - plugin->helper->error(NULL, buf, 1); - pop3->rd_source = g_idle_add(_on_reset, plugin); + pop3->helper->error(NULL, buf, 1); + pop3->rd_source = g_idle_add(_on_reset, pop3); return FALSE; } #ifdef DEBUG @@ -883,9 +883,9 @@ static gboolean _on_watch_can_read_ssl(GIOChannel * source, fwrite(&pop3->rd_buf[pop3->rd_buf_cnt], sizeof(*p), cnt, stderr); #endif pop3->rd_buf_cnt += cnt; - if(_pop3_parse(plugin) != 0) + if(_pop3_parse(pop3) != 0) { - pop3->rd_source = g_idle_add(_on_reset, plugin); + pop3->rd_source = g_idle_add(_on_reset, pop3); return FALSE; } if(pop3->queue_cnt == 0) @@ -904,10 +904,10 @@ static gboolean _on_watch_can_read_ssl(GIOChannel * source, } pop3->rd_source = 0; if(pop3->queue_cnt == 0) - pop3->source = g_timeout_add(30000, _on_noop, plugin); + pop3->source = g_timeout_add(30000, _on_noop, pop3); else pop3->wr_source = g_io_add_watch(pop3->channel, G_IO_OUT, - _on_watch_can_write_ssl, plugin); + _on_watch_can_write_ssl, pop3); return FALSE; } @@ -916,8 +916,7 @@ static gboolean _on_watch_can_read_ssl(GIOChannel * source, static gboolean _on_watch_can_write(GIOChannel * source, GIOCondition condition, gpointer data) { - AccountPlugin * plugin = data; - POP3 * pop3 = plugin->priv; + POP3 * pop3 = data; POP3Command * cmd = &pop3->queue[0]; gsize cnt = 0; GError * error = NULL; @@ -947,10 +946,10 @@ static gboolean _on_watch_can_write(GIOChannel * source, GIOCondition condition, case G_IO_STATUS_NORMAL: break; case G_IO_STATUS_ERROR: - plugin->helper->error(NULL, error->message, 1); + pop3->helper->error(NULL, error->message, 1); case G_IO_STATUS_EOF: default: - pop3->wr_source = g_idle_add(_on_reset, plugin); + pop3->wr_source = g_idle_add(_on_reset, pop3); return FALSE; } if(cmd->buf_cnt > 0) @@ -959,7 +958,7 @@ static gboolean _on_watch_can_write(GIOChannel * source, GIOCondition condition, pop3->wr_source = 0; if(pop3->rd_source == 0) pop3->rd_source = g_io_add_watch(pop3->channel, G_IO_IN, - _on_watch_can_read, plugin); + _on_watch_can_read, pop3); return FALSE; } @@ -968,8 +967,7 @@ static gboolean _on_watch_can_write(GIOChannel * source, GIOCondition condition, static gboolean _on_watch_can_write_ssl(GIOChannel * source, GIOCondition condition, gpointer data) { - AccountPlugin * plugin = data; - POP3 * pop3 = plugin->priv; + POP3 * pop3 = data; POP3Command * cmd = &pop3->queue[0]; int cnt; char * p; @@ -986,7 +984,7 @@ static gboolean _on_watch_can_write_ssl(GIOChannel * source, == SSL_ERROR_WANT_READ) { pop3->wr_source = g_io_add_watch(pop3->channel, G_IO_IN, - _on_watch_can_write_ssl, plugin); + _on_watch_can_write_ssl, pop3); return FALSE; } else if(cnt < 0 && SSL_get_error(pop3->ssl, cnt) @@ -994,12 +992,12 @@ static gboolean _on_watch_can_write_ssl(GIOChannel * source, { pop3->wr_source = g_io_add_watch(pop3->channel, G_IO_OUT, _on_watch_can_write_ssl, - plugin); + pop3); return FALSE; } ERR_error_string(SSL_get_error(pop3->ssl, cnt), buf); - plugin->helper->error(NULL, buf, 1); - pop3->wr_source = g_idle_add(_on_reset, plugin); + pop3->helper->error(NULL, buf, 1); + pop3->wr_source = g_idle_add(_on_reset, pop3); return FALSE; } #ifdef DEBUG @@ -1018,6 +1016,6 @@ static gboolean _on_watch_can_write_ssl(GIOChannel * source, pop3->wr_source = 0; if(pop3->rd_source == 0) pop3->rd_source = g_io_add_watch(pop3->channel, G_IO_IN, - _on_watch_can_read_ssl, plugin); + _on_watch_can_read_ssl, pop3); return FALSE; } diff --git a/src/account/rss.c b/src/account/rss.c index f2a7a6d..4d9fb46 100644 --- a/src/account/rss.c +++ b/src/account/rss.c @@ -1,5 +1,5 @@ /* $Id$ */ -/* Copyright (c) 2011 Pierre Pronchery */ +/* Copyright (c) 2011-2012 Pierre Pronchery */ /* This file is part of DeforaOS Desktop Mailer */ /* This program is free software: you can redistribute it and/or modify * it under the terms of the GNU General Public License as published by @@ -23,7 +23,7 @@ static char const _rss_type[] = "RSS"; static char const _rss_name[] = "RSS reader"; -static AccountConfig _rss_config[] = +static AccountConfig const _rss_config[] = { { "uri", "Address", ACT_STRING, NULL }, { NULL, NULL, ACT_NONE, NULL } @@ -33,12 +33,12 @@ static AccountConfig _rss_config[] = /* functions */ -AccountPlugin account_plugin = +AccountPluginDefinition account_plugin = { - NULL, _rss_type, _rss_name, NULL, + NULL, _rss_config, NULL, NULL, diff --git a/src/mailer.c b/src/mailer.c index ffd2eba..bcc0b10 100644 --- a/src/mailer.c +++ b/src/mailer.c @@ -2981,8 +2981,12 @@ static int _mailer_config_load_account(Mailer * mailer, char const * name) if((account = account_new(mailer, type, name, mailer->fo_store)) == NULL) return -mailer_error(mailer, error_get(), 1); + if(mailer_account_add(mailer, account) != 0) + { + account_delete(account); + return -1; + } account_config_load(account, mailer->config); - mailer_account_add(mailer, account); return 0; }