static int zlib_mailbox_transaction_commit(struct mailbox_transaction_context *t, struct mail_transaction_commit_changes *changes_r) { union mailbox_module_context *zbox = ZLIB_CONTEXT(t->box); struct zlib_transaction_context *zt = ZLIB_CONTEXT(t); int ret; if (zt->tmp_mail != NULL) mail_free(&zt->tmp_mail); ret = zbox->super.transaction_commit(t, changes_r); i_free(zt); return ret; }
int message_search_msg(struct message_search_context *ctx, struct istream *input, struct message_part *parts, const char **error_r) { char *error; int ret; T_BEGIN { ret = message_search_msg_real(ctx, input, parts, error_r); error = i_strdup(*error_r); } T_END; *error_r = t_strdup(error); i_free(error); return ret; }
static void tcpwrap_client_destroy(struct tcpwrap_client **_client) { struct tcpwrap_client *client = *_client; *_client = NULL; timeout_remove(&client->to); io_remove(&client->io); if (close(client->fd) < 0) i_error("close() failed: %m"); i_free(client); tcpwrap_client = NULL; master_service_client_connection_destroyed(master_service); }
static void index_sort_list_finish_float(struct mail_search_sort_program *program) { ARRAY_TYPE(mail_sort_node_float) *nodes = program->context; /* NOTE: higher relevancy is returned first, unlike with all other number based sort keys, so temporarily reverse the search */ static_node_cmp_context.reverse = !static_node_cmp_context.reverse; array_sort(nodes, sort_node_float_cmp); static_node_cmp_context.reverse = !static_node_cmp_context.reverse; memcpy(&program->seqs, nodes, sizeof(program->seqs)); i_free(nodes); program->context = NULL; }
void client_destroy(struct client *client, const char *prefix, const char *reason) { if (client->destroyed) return; client->destroyed = TRUE; client_disconnect(client, prefix, reason); submission_client_count--; DLLIST_REMOVE(&submission_clients, client); if (client->proxy_conn != NULL) smtp_client_connection_close(&client->proxy_conn); if (client->anvil_sent) { master_service_anvil_send(master_service, t_strconcat( "DISCONNECT\t", my_pid, "\tsubmission/", mail_user_get_anvil_userip_ident(client->user), "\n", NULL)); } if (client->urlauth_ctx != NULL) imap_urlauth_deinit(&client->urlauth_ctx); mail_user_unref(&client->user); mail_storage_service_user_unref(&client->service_user); client_state_reset(client); i_free(client->session_id); i_free(client); master_service_client_connection_destroyed(master_service); submission_refresh_proctitle(); }
void connection_list_deinit(struct connection_list **_list) { struct connection_list *list = *_list; struct connection *conn; *_list = NULL; while (list->connections != NULL) { conn = list->connections; conn->disconnect_reason = CONNECTION_DISCONNECT_DEINIT; list->v.destroy(conn); i_assert(conn != list->connections); } i_free(list); }
static void login_access_lookup_free(struct login_access_lookup *lookup) { if (lookup->io != NULL) io_remove(&lookup->io); if (lookup->access != NULL) access_lookup_destroy(&lookup->access); if (lookup->conn.fd != -1) { if (close(lookup->conn.fd) < 0) i_error("close(client) failed: %m"); master_service_client_connection_destroyed(master_service); } p_strsplit_free(default_pool, lookup->sockets); i_free(lookup); }
void mail_transaction_log_move_to_memory(struct mail_transaction_log *log) { struct mail_transaction_log_file *file; if (!log->index->initial_mapped && log->files != NULL && log->files->hdr.prev_file_seq != 0) { /* we couldn't read dovecot.index and we don't have the first .log file, so just start from scratch */ mail_transaction_log_close(log); } i_free(log->filepath); i_free(log->filepath2); log->filepath = i_strconcat(log->index->filepath, MAIL_TRANSACTION_LOG_SUFFIX, NULL); log->filepath2 = i_strconcat(log->filepath, ".2", NULL); if (log->head != NULL) mail_transaction_log_file_move_to_memory(log->head); else { file = mail_transaction_log_file_alloc_in_memory(log); mail_transaction_log_set_head(log, file); } }
void master_connection_destroy(struct master_connection **_conn) { struct master_connection *conn = *_conn; *_conn = NULL; io_remove(&conn->io); i_stream_destroy(&conn->input); if (close(conn->fd) < 0) i_error("close(master conn) failed: %m"); i_free(conn); master_service_client_connection_destroyed(master_service); }
void sieve_tool_set_homedir(struct sieve_tool *tool, const char *homedir) { if ( tool->homedir != NULL ) { if ( strcmp(homedir, tool->homedir) == 0 ) return; i_free(tool->homedir); } tool->homedir = i_strdup(homedir); if ( tool->mail_user_dovecot != NULL ) mail_user_set_home(tool->mail_user_dovecot, tool->homedir); if ( tool->mail_user != NULL ) mail_user_set_home(tool->mail_user, tool->homedir); }
void mail_index_set_ext_init_data(struct mail_index *index, uint32_t ext_id, const void *data, size_t size) { const struct mail_index_registered_ext *rext; i_assert(index->ext_hdr_init_data == NULL || index->ext_hdr_init_id == ext_id); rext = array_idx(&index->extensions, ext_id); i_assert(rext->hdr_size == size); index->ext_hdr_init_id = ext_id; i_free(index->ext_hdr_init_data); index->ext_hdr_init_data = i_malloc(size); memcpy(index->ext_hdr_init_data, data, size); }
int mail_storage_service_next(struct mail_storage_service_ctx *ctx, struct mail_storage_service_user *user, struct mail_user **mail_user_r) { char *old_log_prefix = i_strdup(i_get_failure_prefix()); int ret; mail_storage_service_set_log_prefix(ctx, user->user_set, user, &user->input, NULL); i_set_failure_prefix("%s", old_log_prefix); ret = mail_storage_service_next_real(ctx, user, mail_user_r); if ((user->flags & MAIL_STORAGE_SERVICE_FLAG_NO_LOG_INIT) != 0) i_set_failure_prefix("%s", old_log_prefix); i_free(old_log_prefix); return ret; }
void replicator_connection_destroy(struct replicator_connection **_conn) { struct replicator_connection *conn = *_conn; unsigned int i; *_conn = NULL; replicator_connection_disconnect(conn); for (i = REPLICATION_PRIORITY_LOW; i <= REPLICATION_PRIORITY_SYNC; i++) buffer_free(&conn->queue[i]); if (conn->to != NULL) timeout_remove(&conn->to); hash_table_destroy(&conn->requests); i_free(conn); }
static void dns_client_destroy(struct dns_client **_client) { struct dns_client *client = *_client; *_client = NULL; io_remove(&client->io); i_stream_destroy(&client->input); o_stream_destroy(&client->output); if (close(client->fd) < 0) i_error("close() failed: %m"); i_free(client); dns_client = NULL; master_service_client_connection_destroyed(master_service); }
static void fts_parser_tika_deinit(struct fts_parser *_parser) { struct tika_fts_parser *parser = (struct tika_fts_parser *)_parser; if (parser->ioloop != NULL) { io_remove(&parser->io); io_loop_destroy(&parser->ioloop); } if (parser->payload != NULL) i_stream_unref(&parser->payload); /* FIXME: kludgy, http_req should be NULL here if we don't want to free it. requires lib-http changes. */ if (parser->http_req != NULL) http_client_request_abort(&parser->http_req); i_free(parser); }
void notify_contexts_mail_transaction_commit(struct mailbox_transaction_context *t, struct mail_transaction_commit_changes *changes) { struct notify_context *ctx; struct notify_mail_txn *mail_txn; for (ctx = ctx_list; ctx != NULL; ctx = ctx->next) { if (ctx->v.mail_transaction_commit == NULL) continue; mail_txn = notify_context_find_mail_txn(ctx, t); if (ctx->v.mail_transaction_commit != NULL) ctx->v.mail_transaction_commit(mail_txn->txn, changes); DLLIST_REMOVE(&ctx->mail_txn_list, mail_txn); i_free(mail_txn); } }
static int imap_client_auth_begin(struct imap_client *imap_client, const char *mech_name, const char *init_resp) { char *prefix; prefix = i_strdup_printf("%d%s", imap_client->client_ignores_capability_resp_code, imap_client->cmd_tag); i_free(imap_client->common.master_data_prefix); imap_client->common.master_data_prefix = (void *)prefix; imap_client->common.master_data_prefix_len = strlen(prefix)+1; return client_auth_begin(&imap_client->common, mech_name, init_resp); }
int index_mailbox_sync_deinit(struct mailbox_sync_context *_ctx, struct mailbox_sync_status *status_r) { struct index_mailbox_sync_context *ctx = (struct index_mailbox_sync_context *)_ctx; struct mailbox_sync_rec sync_rec; bool delayed_expunges = FALSE; int ret = ctx->failed ? -1 : 0; /* finish handling expunges, so we don't break when updating recent flags */ while (index_mailbox_sync_next_expunge(ctx, &sync_rec) > 0) ; /* convert sequences to uids before syncing view */ index_sync_search_results_uidify(ctx); if (ctx->sync_ctx != NULL) { if (mail_index_view_sync_commit(&ctx->sync_ctx, &delayed_expunges) < 0) { mailbox_set_index_error(_ctx->box); ret = -1; } } index_mailbox_expunge_unseen_recent(ctx); if ((_ctx->box->flags & MAILBOX_FLAG_DROP_RECENT) == 0 && _ctx->box->opened) { /* mailbox syncing didn't necessarily update our recent state */ index_sync_update_recent_count(_ctx->box); } if (status_r != NULL) status_r->sync_delayed_expunges = delayed_expunges; /* update search results after private index is updated */ index_sync_search_results_update(ctx); if (array_is_created(&ctx->flag_updates)) array_free(&ctx->flag_updates); if (array_is_created(&ctx->hidden_updates)) array_free(&ctx->hidden_updates); if (array_is_created(&ctx->all_flag_update_uids)) array_free(&ctx->all_flag_update_uids); i_free(ctx); return ret; }
void io_loop_handler_run(struct ioloop *ioloop) { struct ioloop_handler_context *ctx = ioloop->handler_context; struct kevent *events; const struct kevent *event; struct timeval tv; struct timespec ts; struct io_file *io; unsigned int events_count; int ret, i; /* get the time left for next timeout task */ io_loop_get_wait_time(ioloop, &tv); ts.tv_sec = tv.tv_sec; ts.tv_nsec = tv.tv_usec * 1000; /* wait for events */ events = array_get_modifiable(&ctx->events, &events_count); ret = kevent (ctx->kq, NULL, 0, events, events_count, &ts); if (ret < 0 && errno != EINTR) i_fatal("kevent(): %m"); /* reference all IOs */ for (i = 0; i < ret; i++) { io = (void *)events[i].udata; i_assert(io->refcount > 0); io->refcount++; } /* execute timeout handlers */ io_loop_handle_timeouts(ioloop); for (i = 0; i < ret; i++) { /* io_loop_handle_add() may cause events array reallocation, so we have use array_idx() */ event = array_idx(&ctx->events, i); io = (void *)event->udata; /* callback is NULL if io_remove() was already called */ if (io->io.callback != NULL) io_loop_call_io(&io->io); i_assert(io->refcount > 0); if (--io->refcount == 0) i_free(io); } }
static int userdb_sql_iterate_deinit(struct userdb_iterate_context *_ctx) { struct sql_userdb_iterate_context *ctx = (struct sql_userdb_iterate_context *)_ctx; int ret = _ctx->failed ? -1 : 0; auth_request_unref(&_ctx->auth_request); if (ctx->result == NULL) { /* sql query hasn't finished yet */ ctx->freed = TRUE; } else { if (ctx->result != NULL) sql_result_unref(ctx->result); i_free(ctx); } return ret; }
static void stats_transaction_free(struct stats_user *suser, struct stats_transaction_context *strans) { const struct mailbox_transaction_stats *src = &strans->trans->stats; struct mailbox_transaction_stats *dest = &suser->finished_transaction_stats; DLLIST_REMOVE(&suser->transactions, strans); dest->open_lookup_count += src->open_lookup_count; dest->stat_lookup_count += src->stat_lookup_count; dest->fstat_lookup_count += src->fstat_lookup_count; dest->files_read_count += src->files_read_count; dest->files_read_bytes += src->files_read_bytes; dest->cache_hit_count += src->cache_hit_count; i_free(strans); }
static void give_special_items(unit *u, item **items) { item **iter = items; while (*iter) { item *itm = *iter; if (itm->number > 0 && itm->type->flags & ITF_NOTLOST) { i_change(&u->items, itm->type, itm->number); *iter = itm->next; if (iter == items) { *items = *iter; } i_free(itm); } else { iter = &itm->next; } } }
void mail_index_transaction_unref(struct mail_index_transaction **_t) { struct mail_index_transaction *t = *_t; *_t = NULL; if (--t->refcount > 0) return; mail_index_transaction_reset_v(t); array_free(&t->module_contexts); mail_index_view_transaction_unref(t->view); if (t->latest_view != NULL) mail_index_view_close(&t->latest_view); mail_index_view_close(&t->view); i_free(t); }
static void auth_postfix_connection_unref(struct auth_postfix_connection **_conn) { struct auth_postfix_connection *conn = *_conn; *_conn = NULL; i_assert(conn->refcount > 0); if (--conn->refcount > 0) return; if (conn->input != NULL) i_stream_unref(&conn->input); if (conn->output != NULL) o_stream_unref(&conn->output); i_free(conn); }
struct mail_transaction_log_file * mail_transaction_log_file_alloc_in_memory(struct mail_transaction_log *log) { struct mail_transaction_log_file *file; file = mail_transaction_log_file_alloc(log, MEMORY_LOG_NAME); if (mail_transaction_log_init_hdr(log, &file->hdr) < 0) { i_free(file); return NULL; } file->buffer = buffer_create_dynamic(default_pool, 4096); file->buffer_offset = sizeof(file->hdr); mail_transaction_log_file_add_to_list(file); return file; }
int cmd_lhlo(struct client *client, const char *args) { struct rfc822_parser_context parser; string_t *domain = t_str_new(128); const char *p; int ret = 0; if (*args == '\0') { client_send_line(client, "501 Missing hostname"); return 0; } /* domain / address-literal */ rfc822_parser_init(&parser, (const unsigned char *)args, strlen(args), NULL); if (*args != '[') ret = rfc822_parse_dot_atom(&parser, domain); else { for (p = args+1; *p != ']'; p++) { if (*p == '\\' || *p == '[') break; } if (strcmp(p, "]") != 0) ret = -1; } if (ret < 0) { str_truncate(domain, 0); str_append(domain, "invalid"); } client_state_reset(client, "LHLO"); client_send_line(client, "250-%s", client->my_domain); if (master_service_ssl_is_enabled(master_service) && client->ssl_iostream == NULL) client_send_line(client, "250-STARTTLS"); if (client_is_trusted(client)) client_send_line(client, "250-XCLIENT ADDR PORT TTL TIMEOUT"); client_send_line(client, "250-8BITMIME"); client_send_line(client, "250-ENHANCEDSTATUSCODES"); client_send_line(client, "250 PIPELINING"); i_free(client->lhlo); client->lhlo = i_strdup(str_c(domain)); client_state_set(client, "LHLO", ""); return 0; }
void io_loop_notify_remove(struct io *_io) { struct ioloop_notify_handler_context *ctx = _io->ioloop->notify_handler_context; struct io_notify *io = (struct io_notify *)_io; struct kevent ev; MY_EV_SET(&ev, io->fd, EVFILT_VNODE, EV_DELETE, 0, 0, NULL); if (kevent(ctx->kq, &ev, 1, NULL, 0, 0) < 0) i_error("kevent(%d) for notify remove failed: %m", io->fd); if (close(io->fd) < 0) i_error("close(%d) for notify remove failed: %m", io->fd); io->fd = -1; if (--io->refcount == 0) i_free(io); }
static int proxy_input_banner(struct imap_client *client, struct ostream *output, const char *line) { const char *const *capabilities = NULL; string_t *str; int ret; if (!str_begins(line, "* OK ")) { client_log_err(&client->common, t_strdup_printf( "proxy: Remote returned invalid banner: %s", str_sanitize(line, 160))); return -1; } str = t_str_new(128); if (str_begins(line + 5, "[CAPABILITY ")) { capabilities = t_strsplit(t_strcut(line + 5 + 12, ']'), " "); if (str_array_icase_find(capabilities, "SASL-IR")) client->proxy_sasl_ir = TRUE; if (str_array_icase_find(capabilities, "LOGINDISABLED")) client->proxy_logindisabled = TRUE; i_free(client->proxy_backend_capability); client->proxy_backend_capability = i_strdup(t_strcut(line + 5 + 12, ']')); if (str_array_icase_find(capabilities, "ID") && !client->common.proxy_not_trusted) { client->proxy_sent_state |= IMAP_PROXY_SENT_STATE_ID; proxy_write_id(client, str); if (client->common.proxy_nopipelining) { /* write login or starttls after I OK */ o_stream_nsend(output, str_data(str), str_len(str)); return 0; } } } if ((ret = proxy_write_starttls(client, str)) < 0) { return -1; } else if (ret == 0) { if (proxy_write_login(client, str) < 0) return -1; } o_stream_nsend(output, str_data(str), str_len(str)); return 0; }
static int proxy_input_banner(struct imap_client *client, struct ostream *output, const char *line) { enum login_proxy_ssl_flags ssl_flags; const char *const *capabilities = NULL; string_t *str; if (strncmp(line, "* OK ", 5) != 0) { client_log_err(&client->common, t_strdup_printf( "proxy: Remote returned invalid banner: %s", str_sanitize(line, 160))); return -1; } str = t_str_new(128); if (strncmp(line + 5, "[CAPABILITY ", 12) == 0) { capabilities = t_strsplit(t_strcut(line + 5 + 12, ']'), " "); if (str_array_icase_find(capabilities, "ID")) proxy_write_id(client, str); if (str_array_icase_find(capabilities, "SASL-IR")) client->proxy_sasl_ir = TRUE; if (str_array_icase_find(capabilities, "LOGINDISABLED")) client->proxy_logindisabled = TRUE; i_free(client->proxy_backend_capability); client->proxy_backend_capability = i_strdup(t_strcut(line + 5 + 12, ']')); } ssl_flags = login_proxy_get_ssl_flags(client->common.login_proxy); if ((ssl_flags & PROXY_SSL_FLAG_STARTTLS) != 0) { if (capabilities != NULL && !str_array_icase_find(capabilities, "STARTTLS")) { client_log_err(&client->common, "proxy: Remote doesn't support STARTTLS"); return -1; } str_append(str, "S STARTTLS\r\n"); } else { if (proxy_write_login(client, str) < 0) return -1; } o_stream_nsend(output, str_data(str), str_len(str)); return 0; }
static int userdb_dict_iterate_deinit(struct userdb_iterate_context *_ctx) { struct dict_userdb_iterate_context *ctx = (struct dict_userdb_iterate_context *)_ctx; const char *error; int ret = _ctx->failed ? -1 : 0; if (ctx->iter != NULL) { if (dict_iterate_deinit(&ctx->iter, &error) < 0) { i_error("dict_iterate(%s) failed: %s", ctx->key_prefix, error); ret = -1; } } auth_request_unref(&ctx->ctx.auth_request); i_free(ctx); return ret; }