]>
diplodocus.org Git - mdeliver/blob - processor.c
66652d77865fc2a1c63021d9bf3bf2c104fbcd96
1 static char ident
[] = "$Id$";
4 #define T_TYPE TRANSPORT_LOCALHOST
5 #define T_SOCK NULL /* for TRANSPORT_UNIX */
6 #define T_HOST NULL /* for TRANSPORT_TCP */
7 #define T_PORT 7783 /* for TRANSPORT_{LOCALHOST,TCP} */
8 #define M_TIME 30 /* call it ham if no answer in 30 seconds */
10 #include <sys/types.h>
27 static int flags
= SPAMC_CHECK_ONLY
| SPAMC_RAW_MODE
;
29 #define err(n, ...) _err(n, true, __FILE__, __LINE__, __VA_ARGS__)
30 #define errx(n, ...) _err(n, false, __FILE__, __LINE__, __VA_ARGS__)
31 #define warn(...) _err(-1, true, __FILE__, __LINE__, __VA_ARGS__)
32 #define warnx(...) _err(-1, false, __FILE__, __LINE__, __VA_ARGS__)
35 _err(int exitcode
, bool want_strerror
, char *fn
, int lineno
, char *format
, ...)
40 /* If anything fails in here, we're fucked, so just exit. If
41 * exitcode is greather than 0 (i.e. the caller is trying to exit
42 * with a failure code), use that, else use EX_IOERR. */
44 if ((fp
= fopen(errfn
, "a")) == NULL
) {
45 exit(exitcode
> 0 ? exitcode
: EX_IOERR
);
48 if (fprintf(fp
, ".mdeliver-processor:%s:%d:", fn
, lineno
) < 0) {
49 exit(exitcode
> 0 ? exitcode
: EX_IOERR
);
53 if (vfprintf(fp
, format
, ap
) < 0) {
54 exit(exitcode
> 0 ? exitcode
: EX_IOERR
);
59 if (fputs(": ", fp
) == EOF
) {
60 exit(exitcode
> 0 ? exitcode
: EX_IOERR
);
62 if (fputs(strerror(errno
), fp
) == EOF
) {
63 exit(exitcode
> 0 ? exitcode
: EX_IOERR
);
66 if (fputs("\n", fp
) == EOF
) {
67 exit(exitcode
> 0 ? exitcode
: EX_IOERR
);
70 if (fclose(fp
) == EOF
) {
71 exit(exitcode
> 0 ? exitcode
: EX_IOERR
);
85 if ((logname
= getenv("LOGNAME")) != NULL
) {
90 if ((p
= getpwuid(getuid())) == NULL
) {
92 err(EX_OSERR
, "getpwuid(getuid())");
94 errx(EX_NOUSER
, "Who are you? What do you want? Why are you here? Where are you going?");
101 get_transport(struct transport
*t
)
107 t
->socketpath
= T_SOCK
;
108 t
->hostname
= T_HOST
;
110 /* In 3.1.3, these were the hard-coded settings. */
111 t
->connect_retries
= 3;
114 if ((status
= transport_setup(t
, 0)) != EX_OK
) {
115 warnx("non-fatal: transport_setup");
123 get_message(char *fn
, struct message
*m
)
129 /* message_filter stupidly allocates a buffer a little bigger than
130 * max_len for reading the processed message back from spamd even
131 * when told not to. It never uses the buffer. */
134 if ((fd
= open(fn
, O_RDONLY
)) == -1) {
135 err(EX_IOERR
, "open(%s)", fn
);
138 if ((status
= message_read(fd
, flags
, m
)) != EX_OK
) {
139 warnx("non-fatal: message_read");
147 is_spam(char *message
)
153 if (!get_transport(&t
)) {
156 if (!get_message(message
, &m
)) {
160 if ((status
= message_filter(&t
, logname(), flags
, &m
)) != EX_OK
) {
161 warnx("non-fatal: message_filter");
165 if (m
.is_spam
== EX_ISSPAM
) {
167 } else if (m
.is_spam
== EX_NOTSPAM
) {
171 warnx("non-fatal: message_filter returned %d", m
.is_spam
);
178 size_t len
= strlen(tmp
);
179 errfn
= malloc(len
+ 1);
180 /* 5 for spam/ and 1 for terminating null */
181 char *new = malloc(len
+ 5 + 1);
183 /* Nothing to do about a malloc failure but dump core. */
184 strcpy(errfn
, "err");
185 strcat(errfn
, tmp
+ 3);
189 strcpy(new, "spam/");
192 strcat(new, tmp
+ 3);
194 if (rename(tmp
, new) == -1) {
195 err(EX_OSERR
, "rename(%s, %s)", tmp
, new);
203 main(int argc
, char *argv
[])
209 if (argv
[1][0] == '-' && argv
[1][1] == 'v') {
214 return process(argv
[1]);