The unified diff between revisions [c6b7a4e1..] and [2ad2b4ba..] is displayed below. It can also be downloaded as a raw diff.

#
#
# add_file "src/local/ucc_hack.c"
#  content [dff893284a39965bec7cf8dd49b11a4a6902c8b1]
#
# patch "Makefile"
#  from [1e16e4b950f7a65e396923ef96533ff6afa66447]
#    to [899f8f7116bbccb07a1c30de2e3270f493877b4b]
#
# patch "src/global/mail_params.h"
#  from [7ea0531bcf4290bd0f7960a32afc2b5985a2c90b]
#    to [40884dc21a194935413da826f7af533406edb0b9]
#
# patch "src/local/Makefile.in"
#  from [a6813e4c23acb8de28adf63e8ff9682a39ae4634]
#    to [b09ad4112ab43c0f311d25a3010388227e4a53f7]
#
# patch "src/local/local.c"
#  from [2633b724f2a244541bbfd8e72de12a056294dd20]
#    to [49ac05f8caa419117add4bc430696bd8fb1bf89b]
#
# patch "src/local/local.h"
#  from [3599ff9c45facd8f7090f5cd7f2d0fd9a8f38415]
#    to [7bef693fec56c14894ac6c20a7596723238c15b8]
#
# patch "src/local/resolve.c"
#  from [8303327a302edee6f98e153636b25f5aaa3a9e39]
#    to [2d0ce6df0ca07e07ab540dfabef9b7cd55e5ea47]
#
============================================================
--- src/local/ucc_hack.c	dff893284a39965bec7cf8dd49b11a4a6902c8b1
+++ src/local/ucc_hack.c	dff893284a39965bec7cf8dd49b11a4a6902c8b1
@@ -0,0 +1,97 @@
+
+/* System library. */
+
+#include <sys_defs.h>
+#include <unistd.h>
+#include <string.h>
+#include <ctype.h>
+
+/* Utility library. */
+
+#include <msg.h>
+#include <htable.h>
+#include <vstring.h>
+#include <vstream.h>
+#include <vstring_vstream.h>
+#include <stringops.h>
+
+/* Global library. */
+
+#include <record.h>
+#include <rec_type.h>
+#include <is_header.h>
+#include <quote_822_local.h>
+#include <header_opts.h>
+#include <mail_params.h>
+#include <mypwd.h>
+
+/* Application-specific. */
+
+#include "local.h"
+
+static VSTRING *buf;
+
+#define STR vstring_str
+
+/* delivered_init - extract delivered-to information from the message */
+
+/* Returns 1 if relaying is disallowed */
+int ucc_no_relay_check(DELIVER_ATTR attr)
+{
+    if (var_ucc_no_relay_hdr[0] == '\0')
+        return 0;
+
+    if (buf == 0)
+	buf = vstring_alloc(10);
+
+    if (vstream_fseek(attr.fp, attr.offset, SEEK_SET) < 0)
+	msg_fatal("seek queue file %s: %m", VSTREAM_PATH(attr.fp));
+
+    /*
+     * XXX Assume that normal mail systems produce headers that fit in a
+     * REC_TYPE_NORM record. Lowercase the delivered-to addresses for
+     * consistency.
+     */
+    while (rec_get(attr.fp, buf, 0) == REC_TYPE_NORM) {
+        char * hdr = STR(buf);
+        if (strstr(hdr, var_ucc_no_relay_hdr) == hdr)
+        {
+            /* found a no_relay header */
+            return 1;
+	} else if (ISSPACE(STR(buf)[0])) {
+	    continue;
+	} else {
+	    break;
+	}
+    }
+    return 0;
+}
+
+#define NO	0
+#define YES	1
+
+int ucc_deliver_no_relay(LOCAL_STATE state)
+{
+    int status;
+    struct mypasswd *mbox_pwd;
+    USER_ATTR usr_attr;
+    const char* myname = "ucc_deliver_no_relay";
+
+    if (been_here(state.dup_filter, "ucc_no_relay %s", state.msg_attr.local))
+	return (YES);
+
+    mbox_pwd = mypwnam(state.msg_attr.user);
+    if (!mbox_pwd)
+    {
+        mbox_pwd = mypwnam(var_ucc_no_relay_user);
+        if (!mbox_pwd)
+        {
+            return (NO);
+        }
+    }
+
+    SET_USER_ATTR(usr_attr, mbox_pwd, state.level);
+    status = deliver_command(state, usr_attr, var_ucc_no_relay_cmd);
+    mypwfree(mbox_pwd);
+    return status;
+}
============================================================
--- Makefile	1e16e4b950f7a65e396923ef96533ff6afa66447
+++ Makefile	899f8f7116bbccb07a1c30de2e3270f493877b4b
@@ -1,21 +1,95 @@
-# Usage:
-#	make makefiles [CC=compiler] [OPT=compiler-flags] [DEBUG=debug-flags]
-#
-# The defaults are: CC=gcc, OPT=-O, and DEBUG=-g. Examples:
-#
-#	make makefiles
-#	make makefiles CC="purify cc"
-#	make makefiles CC=cc OPT=
-#
+# Do not edit -- this file documents how Postfix was built for your machine.
+SYSTYPE	= MACOSX
+AR	= ar
+ARFL	= rv
+RANLIB	= ranlib
+SYSLIBS	= -L/opt/local/lib -lpcre -flat_namespace
+CC	= cc -DBIND_8_COMPAT -DNO_NETINFO -DHAS_PCRE -I/opt/local/include
+OPT	= -O
+DEBUG	= -g
+AWK	= awk
+STRCASE =
+EXPORT	= AUXLIBS=' -L/opt/local/lib -lpcre' CCARGS=' -DBIND_8_COMPAT -DNO_NETINFO -DHAS_PCRE -I/opt/local/include' OPT='-O' DEBUG='-g'
+WARN	= -W -Wformat -Wimplicit -Wmissing-prototypes \
+	-Wparentheses -Wstrict-prototypes -Wswitch -Wuninitialized \
+	-Wunused
 SHELL	= /bin/sh
+WARN    = -Wmissing-prototypes -Wformat
+OPTS	= 'CC=$(CC)'
+DIRS	= src/util src/global src/dns src/tls src/master src/postfix src/smtpstone \
+	src/sendmail src/error src/pickup src/cleanup src/smtpd src/local \
+	src/lmtp src/trivial-rewrite src/qmgr src/oqmgr src/smtp src/bounce \
+	src/pipe src/showq src/postalias src/postcat src/postconf src/postdrop \
+	src/postkick src/postlock src/postlog src/postmap src/postqueue \
+	src/postsuper src/qmqpd src/spawn src/flush src/verify \
+	src/virtual src/proxymap src/anvil src/scache src/discard src/tlsmgr
+MANDIRS	= proto man html

 default: update

-update depend printfck clean tidy depend_update: Makefiles
-	$(MAKE) MAKELEVEL= $@
+makefiles Makefiles:
+	(echo "# Do not edit -- this file documents how Postfix was built for your machine."; $(SHELL) makedefs) >makedefs.tmp
+	set +e; if cmp makedefs.tmp conf/makedefs.out; then rm makedefs.tmp; \
+	else mv makedefs.tmp conf/makedefs.out; fi >/dev/null 2>/dev/null
+	set -e; for i in $(DIRS); do \
+	 (set -e; echo "[$$i]"; cd $$i; rm -f Makefile; \
+	 $(MAKE) -f Makefile.in Makefile MAKELEVEL=) || exit 1; \
+	done;
+	rm -f Makefile; (cat conf/makedefs.out Makefile.in) >Makefile

-install upgrade:
-	@echo Please review the INSTALL instructions first.
+update printfck tests:
+	set -e; for i in $(DIRS); do \
+	 (set -e; echo "[$$i]"; cd $$i; $(MAKE) $(OPTS) $@ MAKELEVEL=) || exit 1; \
+	done

+manpages:
+	set -e; for i in $(MANDIRS); do \
+	 (set -e; echo "[$$i]"; cd $$i; $(MAKE) -f Makefile.in $(OPTS) MAKELEVEL=) || exit 1; \
+	done
+
+printfck: update
+
+install: update
+	$(SHELL) postfix-install
+
+package: update
+	$(SHELL) postfix-install -package
+
+upgrade: update
+	$(SHELL) postfix-install -non-interactive
+
+non-interactive-package: update
+	$(SHELL) postfix-install -non-interactive -package
+
+depend clean:
+	set -e; for i in $(DIRS); do \
+	 (set -e; echo "[$$i]"; cd $$i; $(MAKE) $@) || exit 1; \
+	done
+
+depend_update:
+	set -e; for i in $(DIRS); do \
+	 (set -e; echo "[$$i]"; cd $$i; $(MAKE) depend && $(MAKE) $(OPTS) update) \
+	    || exit 1; \
+	done
+
+tidy:	clean
+	rm -f Makefile */Makefile src/*/Makefile
+	cp Makefile.init Makefile
+	rm -f bin/[!CRS]* lib/[!CRS]* include/[!CRS]* libexec/[!CRS]* \
+	    junk */junk */*/junk \
+	    *core */*core */*/*core \
+	    .nfs* */.nfs* */*/.nfs* \
+	    .pure */.pure */*/.pure \
+	    *.out */*.out */*/*.out \
+	    *.tmp */*.tmp */*/*.tmp \
+	    *.a */*.a */*/*.a \
+	    *~ */*~ */*/*~ \
+	    *- */*- */*/*- \
+	    *.orig */*.orig */*/*.orig \
+	    *.bak */*.bak */*/*.bak \
+	    make.err */make.err */*/make.err \
+	    *.gmon */*.gmon */*/*.gmon \
+	    conf/main.cf.default
+	find . -type s -print | xargs rm -f
+	find . -type d -print | xargs chmod 755
+	find . -type f -print | xargs chmod a+r
-makefiles Makefiles:
-	$(MAKE) -f Makefile.in MAKELEVEL= Makefiles
============================================================
--- src/global/mail_params.h	7ea0531bcf4290bd0f7960a32afc2b5985a2c90b
+++ src/global/mail_params.h	40884dc21a194935413da826f7af533406edb0b9
@@ -1994,6 +1994,19 @@ extern char *var_anvil_service;
 extern char *var_anvil_service;
 #endif

+/* UCC Hack */
+#define VAR_UCC_NO_RELAY_HDR	"ucc_no_relay_header"
+#define DEF_UCC_NO_RELAY_HDR	""
+extern char *var_ucc_no_relay_hdr;
+
+#define VAR_UCC_NO_RELAY_USER	"ucc_no_relay_user"
+#define DEF_UCC_NO_RELAY_USER	""
+extern char *var_ucc_no_relay_user;
+
+#define VAR_UCC_NO_RELAY_CMD	"ucc_no_relay_command"
+#define DEF_UCC_NO_RELAY_CMD	""
+extern char *var_ucc_no_relay_cmd;
+
 /* LICENSE
 /* .ad
 /* .fi
============================================================
--- src/local/Makefile.in	a6813e4c23acb8de28adf63e8ff9682a39ae4634
+++ src/local/Makefile.in	b09ad4112ab43c0f311d25a3010388227e4a53f7
@@ -2,11 +2,11 @@ SRCS	= alias.c command.c delivered.c dot
 SRCS	= alias.c command.c delivered.c dotforward.c file.c forward.c \
 	include.c indirect.c local.c mailbox.c recipient.c resolve.c token.c \
 	deliver_attr.c maildir.c biff_notify.c unknown.c \
-	local_expand.c
+	local_expand.c ucc_hack.c
 OBJS	= alias.o command.o delivered.o dotforward.o file.o forward.o \
 	include.o indirect.o local.o mailbox.o recipient.o resolve.o token.o \
 	deliver_attr.o maildir.o biff_notify.o unknown.o \
-	local_expand.o
+	local_expand.o ucc_hack.o
 HDRS	= local.h
 TESTSRC	=
 DEFS	= -I. -I$(INC_DIR) -D$(SYSTYPE)
============================================================
--- src/local/local.c	2633b724f2a244541bbfd8e72de12a056294dd20
+++ src/local/local.c	49ac05f8caa419117add4bc430696bd8fb1bf89b
@@ -505,6 +505,9 @@ char   *var_mailbox_cmd_maps;
 char   *var_home_mailbox;
 char   *var_mailbox_command;
 char   *var_mailbox_cmd_maps;
+char   *var_ucc_no_relay_hdr;
+char   *var_ucc_no_relay_user;
+char   *var_ucc_no_relay_cmd;
 char   *var_rcpt_fdelim;
 char   *var_local_cmd_shell;
 char   *var_luser_relay;
@@ -572,6 +575,7 @@ static int local_deliver(DELIVER_REQUEST
     RESET_OWNER_ATTR(state.msg_attr, state.level);
     RESET_USER_ATTR(usr_attr, state.level);
     state.loop_info = delivered_init(state.msg_attr);	/* delivered-to */
+    state.msg_attr.ucc_no_relay = ucc_no_relay_check(state.msg_attr); /* UCC anti-spam-forward */
     state.request = rqst;

     /*
@@ -751,6 +755,9 @@ int     main(int argc, char **argv)
 	VAR_PROP_EXTENSION, DEF_PROP_EXTENSION, &var_prop_extension, 0, 0,
 	VAR_DELIVER_HDR, DEF_DELIVER_HDR, &var_deliver_hdr, 0, 0,
 	VAR_MAILBOX_LOCK, DEF_MAILBOX_LOCK, &var_mailbox_lock, 1, 0,
+        VAR_UCC_NO_RELAY_HDR, DEF_UCC_NO_RELAY_HDR, &var_ucc_no_relay_hdr, 0, 0,
+        VAR_UCC_NO_RELAY_USER, DEF_UCC_NO_RELAY_USER, &var_ucc_no_relay_user, 0, 0,
+        VAR_UCC_NO_RELAY_CMD, DEF_UCC_NO_RELAY_CMD, &var_ucc_no_relay_cmd, 0, 0,
 	0,
     };
     static CONFIG_BOOL_TABLE bool_table[] = {
============================================================
--- src/local/local.h	3599ff9c45facd8f7090f5cd7f2d0fd9a8f38415
+++ src/local/local.h	7bef693fec56c14894ac6c20a7596723238c15b8
@@ -84,6 +84,7 @@ typedef struct DELIVER_ATTR {
     long    arrival_time;		/* arrival time */
     int     exp_type;			/* expansion type. see below */
     char   *exp_from;			/* expanded_from */
+    int    *ucc_no_relay;               /* don't allow this message to be forwarded non-locally */
 } DELIVER_ATTR;

 extern void deliver_attr_init(DELIVER_ATTR *);
@@ -228,6 +229,12 @@ extern MAPS *alias_maps;
   */
 extern MAPS *alias_maps;

+/*
+ * ucc_hack.c
+ */
+extern int ucc_no_relay_check(DELIVER_ATTR attr);
+extern int ucc_deliver_no_relay(LOCAL_STATE state);
+
 /* LICENSE
 /* .ad
 /* .fi
============================================================
--- src/local/resolve.c	8303327a302edee6f98e153636b25f5aaa3a9e39
+++ src/local/resolve.c	2d0ce6df0ca07e07ab540dfabef9b7cd55e5ea47
@@ -155,8 +155,13 @@ int     deliver_resolve_tree(LOCAL_STATE
 	 * too unclean.
 	 */
 	if (strcmp(state.msg_attr.relay, STR(reply.transport)) == 0) {
+            /* UCC Hack */
+            /* UCC: local transport again, is safe.*/
 	    status = deliver_recipient(state, usr_attr);
-	} else {
+	} else if (state.msg_attr.ucc_no_relay) {
+            /* UCC: probably smtp transport. do local stuff. */
+            status = ucc_deliver_no_relay(state);
+        } else {
 	    status = deliver_indirect(state);
 	}
     }