1234567891011121314151617181920212223242526272829303132333435363738394041424344454647484950515253545556575859606162636465666768697071727374757677787980818283848586 |
- --- src/spam.c.orig 2011-01-20 19:29:51.179597017 +0300
- +++ src/spam.c 2011-02-21 21:17:15.051230555 +0300
- @@ -21,6 +21,9 @@
- int spam_ok = 0;
- int spam_rc = 0;
-
- +/* push formatted line into vector */
- +static int push_line(struct iovec *iov, int i, const char *fmt, ...);
- +
- int spam(uschar **listptr) {
- int sep = 0;
- uschar *list = *listptr;
- @@ -211,14 +214,26 @@
- }
-
- /* now we are connected to spamd on spamd_sock */
- - (void)string_format(spamd_buffer,
- - sizeof(spamd_buffer),
- - "REPORT SPAMC/1.2\r\nUser: %s\r\nContent-length: %ld\r\n\r\n",
- - user_name,
- - mbox_size);
- + int r, request_p = 0;
- + const char *helo;
- + struct iovec request_v[64];
- +
- + r = 0;
- + r += push_line(request_v, request_p++, "REPORT SPAMC/1.2\r\n");
- + r += push_line(request_v, request_p++, "Content-length: %lu\r\n", mbox_size);
- + r += push_line(request_v, request_p++, "Queue-Id: %s\r\n", message_id);
- + r += push_line(request_v, request_p++, "From: <%s>\r\n", sender_address);
- + r += push_line(request_v, request_p++, "Recipient-Number: %d\r\n", recipients_count);
- + for (i = 0; i < recipients_count; i ++)
- + r += push_line(request_v, request_p++, "Rcpt: <%s>\r\n", recipients_list[i].address);
- + if ((helo = expand_string(US"$sender_helo_name")) != NULL && *helo != '\0')
- + r += push_line(request_v, request_p++, "Helo: %s\r\n", helo);
- + if (sender_host_address != NULL)
- + r += push_line(request_v, request_p++, "IP: %s\r\n", sender_host_address);
- + r += push_line(request_v, request_p++, "\r\n");
-
- /* send our request */
- - if (send(spamd_sock, spamd_buffer, Ustrlen(spamd_buffer), 0) < 0) {
- + if (writev(spamd_sock, request_v, request_p) < 0) {
- (void)close(spamd_sock);
- log_write(0, LOG_MAIN|LOG_PANIC,
- "spam acl condition: spamd send failed: %s", strerror(errno));
- @@ -329,7 +344,7 @@
- (void)close(spamd_sock);
-
- /* dig in the spamd output and put the report in a multiline header, if requested */
- - if( sscanf(CS spamd_buffer,"SPAMD/%7s 0 EX_OK\r\nContent-length: %*u\r\n\r\n%lf/%lf\r\n%n",
- + if( sscanf(CS spamd_buffer,"SPAMD/%7s 0 EX_OK\r\n\r\nSpam: %*s ; %lf / %lf\r\nContent-length: %*u\r\n\r\n%n",
- spamd_version,&spamd_score,&spamd_threshold,&spamd_report_offset) != 3 ) {
-
- /* try to fall back to pre-2.50 spamd output */
- @@ -420,4 +435,31 @@
- };
- }
-
- +static int
- +push_line(struct iovec *iov, const int i, const char *fmt, ...)
- +{
- + va_list ap;
- + size_t len;
- + char buf[512];
- +
- + if (i >= 64) {
- + log_write(0, LOG_MAIN, "rspam: %s: index out of bounds", __FUNCTION__);
- + return (-1);
- + }
- +
- + va_start(ap, fmt);
- + len = vsnprintf(buf, sizeof(buf), fmt, ap);
- + va_end(ap);
- +
- + iov[i].iov_base = string_copy(US buf);
- + iov[i].iov_len = len;
- +
- + if (len >= sizeof(buf)) {
- + log_write(0, LOG_MAIN, "rspam: %s: error, string was longer than %d", __FUNCTION__, sizeof(buf));
- + return (-1);
- + }
- +
- + return 0;
- +}
- +
- #endif
|