summaryrefslogtreecommitdiff
path: root/usr/src/cmd/sendmail/aux/mailcompat.c
diff options
context:
space:
mode:
Diffstat (limited to 'usr/src/cmd/sendmail/aux/mailcompat.c')
-rw-r--r--usr/src/cmd/sendmail/aux/mailcompat.c340
1 files changed, 340 insertions, 0 deletions
diff --git a/usr/src/cmd/sendmail/aux/mailcompat.c b/usr/src/cmd/sendmail/aux/mailcompat.c
new file mode 100644
index 0000000000..8b244b455a
--- /dev/null
+++ b/usr/src/cmd/sendmail/aux/mailcompat.c
@@ -0,0 +1,340 @@
+/*
+ * Copyright 2005 Sun Microsystems, Inc. All rights reserved.
+ * Use is subject to license terms.
+ *
+ * Copyright (c) 1983, 1984, 1986, 1986, 1987, 1988, 1989 AT&T
+ * All Rights Reserved
+ */
+
+/*
+ * Vacation
+ * Copyright (c) 1983 Eric P. Allman
+ * Berkeley, California
+ *
+ * Copyright (c) 1983 Regents of the University of California.
+ * All rights reserved. The Berkeley software License Agreement
+ * specifies the terms and conditions for redistribution.
+ */
+
+#pragma ident "%Z%%M% %I% %E% SMI"
+
+#include <pwd.h>
+#include <stdio.h>
+#include <stdarg.h>
+#include <stdlib.h>
+#include <unistd.h>
+#include <sysexits.h>
+#include <string.h>
+#include <ctype.h>
+#include "conf.h"
+
+/*
+ * MAILCOMPAT -- Deliver mail to a user's mailbox with the "From's" stuffed.
+ */
+
+typedef int bool;
+
+#define FALSE 0
+#define TRUE 1
+
+bool Debug = FALSE;
+char *myname; /* person who is to have their mail filtered */
+char *homedir; /* home directory of said person */
+char *AliasList[MAXLINE]; /* list of aliases to allow */
+char *fromp;
+char *fromuser;
+int AliasCount = 0;
+
+static char *newstr();
+
+int ask(char *);
+int sendmessage(char *);
+void AutoInstall(void);
+void usrerr(const char *, ...);
+
+int
+main(argc, argv)
+ int argc;
+ char **argv;
+{
+ register char *p;
+ struct passwd *pw;
+ extern char *getfrom();
+
+ /* process arguments */
+ while (--argc > 0 && (p = *++argv) != NULL && *p == '-')
+ {
+ switch (*++p)
+ {
+ case 'd': /* debug */
+ Debug = TRUE;
+ break;
+ default:
+ usrerr("Unknown flag -%s", p);
+ exit(EX_USAGE);
+ }
+ }
+
+ /* verify recipient argument */
+ if (argc != 1)
+ {
+ if (argc == 0)
+ AutoInstall();
+ else
+ usrerr("Usage: mailcompat username (or) mailcompat -r");
+ exit(EX_USAGE);
+ }
+
+ myname = p;
+ /* find user's home directory */
+ pw = getpwnam(myname);
+ if (pw == NULL)
+ {
+ usrerr("user: %s look up failed, name services outage ?", myname);
+ exit(EX_TEMPFAIL);
+ }
+ homedir = newstr(pw->pw_dir);
+
+ /* read message from standard input (just from line) */
+ fromuser = getfrom(&fromp);
+ return (sendmessage(fromuser));
+}
+
+/*
+** sendmessage -- read message from standard input do the from stuffing
+** and forward to /bin/mail, Being sure to delete any
+** content-length headers (/bin/mail recalculates them).
+**
+**
+** Parameters:
+** none.
+**
+**
+** Side Effects:
+** Reads first line from standard input.
+*/
+
+#define L_HEADER "Content-Length:"
+#define LL_HEADER 15
+
+int
+sendmessage(from)
+char *from;
+{
+ static char line[MAXLINE];
+ static char command[MAXLINE];
+ bool in_body = FALSE;
+ FILE *mail_fp;
+ static char user_name[L_cuserid];
+
+ if (from == NULL)
+ from = cuserid(user_name);
+
+ snprintf(command, sizeof (command), "/bin/mail -f %s -d %s", from,
+ myname);
+ mail_fp = popen(command, "w");
+
+ /* read the line */
+ while (fgets(line, sizeof line, stdin) != NULL)
+ {
+ if (line[0] == (char)'\n') /* end of mail headers */
+ in_body = TRUE;
+ if (in_body && (strncmp(line, "From ", 5) == 0))
+ fprintf(mail_fp, ">");
+ if (in_body || (strncasecmp(line, L_HEADER, LL_HEADER) != 0))
+ fputs(line, mail_fp);
+ }
+ return (pclose(mail_fp));
+}
+
+char *
+getfrom(shortp)
+char **shortp;
+{
+ static char line[MAXLINE];
+ register char *p, *start, *at, *bang;
+ char saveat;
+
+ /* read the from line */
+ if (fgets(line, sizeof line, stdin) == NULL ||
+ strncmp(line, "From ", 5) != NULL)
+ {
+ usrerr("No initial From line");
+ exit(EX_USAGE);
+ }
+
+ /* find the end of the sender address and terminate it */
+ start = &line[5];
+ p = strchr(start, ' ');
+ if (p == NULL)
+ {
+ usrerr("Funny From line '%s'", line);
+ exit(EX_USAGE);
+ }
+ *p = '\0';
+
+ /*
+ * Strip all but the rightmost UUCP host
+ * to prevent loops due to forwarding.
+ * Start searching leftward from the leftmost '@'.
+ * a!b!c!d yields a short name of c!d
+ * a!b!c!d@e yields a short name of c!d@e
+ * e@a!b!c yields the same short name
+ */
+#ifdef VDEBUG
+printf("start='%s'\n", start);
+#endif /* VDEBUG */
+ *shortp = start; /* assume whole addr */
+ if ((at = strchr(start, '@')) == NULL) /* leftmost '@' */
+ at = p; /* if none, use end of addr */
+ saveat = *at;
+ *at = '\0';
+ if ((bang = strrchr(start, '!')) != NULL) { /* rightmost '!' */
+ char *bang2;
+ *bang = '\0';
+ if ((bang2 = strrchr(start, '!')) != NULL) /* 2nd rightmost '!' */
+ *shortp = bang2 + 1; /* move past ! */
+ *bang = '!';
+ }
+ *at = saveat;
+#ifdef VDEBUG
+printf("place='%s'\n", *shortp);
+#endif /* VDEBUG */
+
+ /* return the sender address */
+ return newstr(start);
+}
+
+/*
+** USRERR -- print user error
+**
+** Parameters:
+** f -- format.
+**
+** Returns:
+** none.
+**
+** Side Effects:
+** none.
+*/
+
+void
+usrerr(const char *f, ...)
+{
+ va_list alist;
+
+ va_start(alist, f);
+ (void) fprintf(stderr, "mailcompat: ");
+ (void) vfprintf(stderr, f, alist);
+ (void) fprintf(stderr, "\n");
+ va_end(alist);
+}
+
+/*
+** NEWSTR -- copy a string
+**
+** Parameters:
+** s -- the string to copy.
+**
+** Returns:
+** A copy of the string.
+**
+** Side Effects:
+** none.
+*/
+
+char *
+newstr(s)
+ char *s;
+{
+ char *p;
+ size_t psize = strlen(s) + 1;
+
+ p = malloc(psize);
+ if (p == NULL)
+ {
+ usrerr("newstr: cannot alloc memory");
+ exit(EX_OSERR);
+ }
+ strlcpy(p, s, psize);
+ return (p);
+}
+
+/*
+ * When invoked with no arguments, we fall into an automatic installation
+ * mode, stepping the user through a default installation.
+ */
+void
+AutoInstall()
+{
+ char forward[MAXLINE];
+ char line[MAXLINE];
+ static char user_name[L_cuserid];
+ FILE *f;
+
+ myname = cuserid(user_name);
+ homedir = getenv("HOME");
+ if (homedir == NULL) {
+ usrerr("Home directory unknown");
+ exit(EX_CONFIG);
+ }
+
+ printf("This program can be used to store your mail in a format\n");
+ printf("that you can read with SunOS 4.X based mail readers\n");
+ (void) strlcpy(forward, homedir, sizeof (forward));
+ (void) strlcat(forward, "/.forward", sizeof (forward));
+ f = fopen(forward, "r");
+ if (f) {
+ printf("You have a .forward file in your home directory");
+ printf(" containing:\n");
+ while (fgets(line, MAXLINE, f))
+ printf(" %s", line);
+ fclose(f);
+ if (!ask("Would you like to remove it and disable the mailcompat feature"))
+ exit(0);
+ if (unlink(forward))
+ perror("Error removing .forward file:");
+ else
+ printf("Back to normal reception of mail.\n");
+ exit(0);
+ }
+
+ printf("To enable the mailcompat feature a \".forward\" ");
+ printf("file is created.\n");
+ if (!ask("Would you like to enable the mailcompat feature")) {
+ printf("OK, mailcompat feature NOT enabled.\n");
+ exit(0);
+ }
+ f = fopen(forward, "w");
+ if (f == NULL) {
+ perror("Error opening .forward file");
+ exit(EX_USAGE);
+ }
+ fprintf(f, "\"|/usr/bin/mailcompat %s\"\n", myname);
+ fclose(f);
+ printf("Mailcompat feature ENABLED.");
+ printf("Run mailcompat with no arguments to remove it\n");
+}
+
+
+/*
+ * Ask the user a question until we get a reasonable answer
+ */
+int
+ask(prompt)
+ char *prompt;
+{
+ char line[MAXLINE];
+
+ for (;;) {
+ printf("%s? ", prompt);
+ fflush(stdout);
+ fgets(line, sizeof (line), stdin);
+ if (line[0] == 'y' || line[0] == 'Y')
+ return (TRUE);
+ if (line[0] == 'n' || line[0] == 'N')
+ return (FALSE);
+ printf("Please reply \"yes\" or \"no\" (\'y\' or \'n\')\n");
+ }
+ /* NOTREACHED */
+}