masqmail-0.2

view src/queue.c @ 91:3e7136221104

correct masqmail path in rmail script; remove docs on uninstall on install the correct path to the masqmail executable gets inserted into the rmail script now. now documentation, examples, and the templates are removed on uninstall. Empty directories are the only thing that may remain if one installs masqmail into an unusual path.
author meillo@marmaro.de
date Mon, 21 Jun 2010 09:40:16 +0200
parents ac0233b5f6f8
children a80ebfa16cd5
line source
1 /* MasqMail
2 Copyright (C) 1999-2001 Oliver Kurth
4 This program is free software; you can redistribute it and/or modify
5 it under the terms of the GNU General Public License as published by
6 the Free Software Foundation; either version 2 of the License, or
7 (at your option) any later version.
9 This program is distributed in the hope that it will be useful,
10 but WITHOUT ANY WARRANTY; without even the implied warranty of
11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 GNU General Public License for more details.
14 You should have received a copy of the GNU General Public License
15 along with this program; if not, write to the Free Software
16 Foundation, Inc., 59 Temple Place - Suite 330, Boston, MA 02111-1307, USA.
17 */
19 #include <sys/stat.h>
20 #include <glob.h>
22 #include "masqmail.h"
24 static void
25 mix_arr(int *buf, int len)
26 {
27 int i;
29 for (i = 0; i < len; i++)
30 buf[i] = i;
31 for (i = 0; i < len - 1; i++) {
32 int j = (int) ((float) (len - i) * ((float) rand()) / (RAND_MAX + 1.0));
33 int tmp;
35 if (i != j) {
36 tmp = buf[i];
37 buf[i] = buf[j];
38 buf[j] = tmp;
39 }
40 }
41 }
43 GList*
44 read_queue(gboolean do_readdata)
45 {
46 GList *msg_list = NULL;
47 glob_t gl;
48 gchar *pattern;
49 int i, *idx_arr;
51 /* Escaping the question marks prevents them from being
52 interpreted as trigraphs */
53 pattern = g_strdup_printf("%s/input/?????\?-??\?-?\?-H", conf.spool_dir);
54 gl.gl_offs = 0;
55 glob(pattern, 0, NULL, &gl);
57 g_free(pattern);
59 DEBUG(4) {
60 int i;
61 for (i = 0; i < gl.gl_pathc; i++) {
62 debugf("spoolfile: %s\n", gl.gl_pathv[i]);
63 }
64 }
66 idx_arr = g_malloc(sizeof(int) * gl.gl_pathc);
67 mix_arr(idx_arr, gl.gl_pathc);
69 for (i = 0; i < gl.gl_pathc; i++) {
70 gchar *uid;
72 /* copy 13 chars, offset spooldir path + 7 chars for /input/ */
73 /* uid length = 6 chars + '-' + 3 chars + '-' + 2 = 13 chars */
74 uid = g_strndup(&(gl.gl_pathv[idx_arr[i]][strlen(conf.spool_dir) + 7]), 13);
76 DEBUG(5) debugf("uid: %s\n", uid);
78 msg_list = g_list_append(msg_list, msg_spool_read(uid, do_readdata));
80 DEBUG(5) debugf("after read spool file for %s\n", uid);
82 g_free(uid);
83 }
84 return msg_list;
85 }
87 gboolean
88 queue_run()
89 {
90 GList *msg_list;
91 gboolean ok = TRUE;
93 logwrite(LOG_NOTICE, "Starting queue run.\n");
95 msg_list = read_queue(FALSE);
97 if (msg_list != NULL) {
98 ok = deliver_msg_list(msg_list, DLVR_ALL);
99 destroy_msg_list(msg_list);
100 }
101 logwrite(LOG_NOTICE, "Finished queue run.\n");
103 return ok;
104 }
106 gboolean
107 queue_run_online()
108 {
109 GList *msg_list = read_queue(FALSE);
110 gboolean ok = TRUE;
112 logwrite(LOG_NOTICE, "Starting online queue run.\n");
113 if (msg_list != NULL) {
114 ok = deliver_msg_list(msg_list, DLVR_ONLINE);
115 destroy_msg_list(msg_list);
116 }
117 logwrite(LOG_NOTICE, "Finished online queue run.\n");
119 return ok;
120 }
122 static gchar*
123 format_difftime(double secs)
124 {
125 if (secs > 86400)
126 return g_strdup_printf("%.1fd", secs / 86400);
127 else if (secs > 3600)
128 return g_strdup_printf("%.1fh", secs / 3600);
129 else if (secs > 60)
130 return g_strdup_printf("%.1fm", secs / 60);
131 else
132 return g_strdup_printf("%.0fs", secs);
133 }
135 void
136 queue_list()
137 {
138 GList *msg_list;
139 GList *msg_node;
141 msg_list = read_queue(FALSE);
143 if (msg_list == NULL) {
144 printf("mail queue is empty.\n");
145 return;
146 }
148 foreach(msg_list, msg_node) {
149 message *msg = (message *) (msg_node->data);
150 GList *rcpt_node;
151 gchar *size_str = NULL;
152 gchar *time_str = NULL;
153 gchar *host_str = NULL;
154 gchar *ident_str = NULL;
156 if (msg->data_size >= 0)
157 size_str = g_strdup_printf(" size=%d", msg->data_size);
158 if (msg->received_time > 0) {
159 gchar *tmp_str;
160 time_str = g_strdup_printf(" age=%s", tmp_str = format_difftime(difftime(time(NULL), msg->received_time)));
161 g_free(tmp_str);
162 }
163 if (msg->received_host != NULL)
164 host_str = g_strdup_printf(" host=%s", msg->received_host);
165 if (msg->ident != NULL)
166 ident_str = g_strdup_printf(" ident=%s", msg->ident);
168 printf("%s <= %s%s%s%s%s\n", msg->uid, addr_string(msg->return_path), size_str ? size_str : "",
169 time_str ? time_str : "", host_str ? host_str : "", ident_str ? ident_str : "");
171 if (size_str)
172 g_free(size_str);
173 if (time_str)
174 g_free(time_str);
175 if (host_str)
176 g_free(host_str);
177 if (ident_str)
178 g_free(ident_str);
180 foreach(msg->rcpt_list, rcpt_node) {
181 address *rcpt = (address *) (rcpt_node->data);
183 printf(" %s %s\n", addr_is_delivered(rcpt) ? "=>" : (addr_is_failed(rcpt) ? "!=" : "=="), addr_string(rcpt));
184 }
185 g_free(msg);
186 }
187 }
189 gboolean
190 queue_delete(gchar * uid)
191 {
192 gboolean hdr_ok = TRUE;
193 gboolean dat_ok = TRUE;
194 gchar *hdr_name = g_strdup_printf("%s/input/%s-H", conf.spool_dir, uid);
195 gchar *dat_name = g_strdup_printf("%s/input/%s-D", conf.spool_dir, uid);
196 struct stat stat_buf;
198 if (!spool_lock(uid)) {
199 fprintf(stderr, "message %s is locked.\n", uid);
200 return FALSE;
201 }
203 if (stat(hdr_name, &stat_buf) == 0) {
204 if (unlink(hdr_name) != 0) {
205 fprintf(stderr, "could not unlink %s: %s\n", hdr_name, strerror(errno));
206 hdr_ok = FALSE;
207 }
208 } else {
209 fprintf(stderr, "could not stat file %s: %s\n", hdr_name, strerror(errno));
210 hdr_ok = FALSE;
211 }
212 if (stat(dat_name, &stat_buf) == 0) {
213 if (unlink(dat_name) != 0) {
214 fprintf(stderr, "could not unlink %s: %s\n", dat_name, strerror(errno));
215 dat_ok = FALSE;
216 }
217 } else {
218 fprintf(stderr, "could not stat file %s: %s\n", dat_name, strerror(errno));
219 dat_ok = FALSE;
220 }
221 printf("message %s deleted\n", uid);
223 spool_unlock(uid);
225 return (dat_ok && hdr_ok);
226 }