vacation.c revision 4c0312813f96388b6ce9453c99f2db7d6a393bd4
2280N/A * Copyright 2006 Sun Microsystems, Inc. All rights reserved. 2280N/A * Use is subject to license terms. 2280N/A * Copyright (c) 1983, 1984, 1985, 1986, 1987, 1988, 1989 AT&T 2280N/A * Copyright (c) 1983 Eric P. Allman 2280N/A * Copyright (c) 1983 Regents of the University of California. 2280N/A * All rights reserved. The Berkeley software License Agreement 2280N/A * specifies the terms and conditions for redistribution. 2280N/A#
pragma ident "%Z%%M% %I% %E% SMI" 2655N/A * VACATION -- return a message to the sender when on vacation. 2280N/A * This program could be invoked as a message receiver 2280N/A * when someone is on vacation. It returns a message 2280N/A * specified by the user to whoever sent the mail, taking 2280N/A * care not to return a message too often to prevent 2280N/A * "I am on vacation" loops. 2280N/A * For best operation, this program should run setuid to 2280N/A * root or uucp or someone else that sendmail will believe 2280N/A * a -f flag from. Otherwise, the user must be careful 2280N/A * to include a header on his .vacation.msg file. 2280N/A * the user to collect the vacation message from. 2280N/A * -I initialize the database. 2280N/A * -tT set the timeout to T. messages arriving more 2280N/A * often than T will be ignored to avoid loops. 2655N/A * A message is sent back to the sender. 2280N/A case 'a':
/* add this to list of acceptable aliases */ 2280N/A case 'e':
/* alternate filter file */ 2280N/A case 'f':
/* alternate database file name base */ 2280N/A case 'j':
/* answer all mail, even if not in To/Cc */ 2280N/A case 'm':
/* alternate message file */ 2280N/A case 's':
/* sender: use this instead of getfrom() */ 2280N/A case 't':
/* set timeout */ /* verify recipient argument */ usrerr(
"Usage: vacation username (or) vacation -I");
/* find user's home directory */ usrerr(
"user %s look up failed, name services outage ?",
for (c =
at +
1; *c; c++)
/* read message from standard input (just from line) */ /* check if junk mail or this person is already informed */ /* mark this person as knowing */ /* send the message back */ continue;
/* drain input */ * GETFROM -- read message from standard input and return sender * pointer to the sender address. * Reads first line from standard input. usrerr(
"No initial From line");
/* find the end of the sender address and terminate it */ * 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 at = p;
/* if none, use end of addr */ for (c =
at +
1; *c; c++)
/* return the sender address */ * JUNKMAIL -- read the header and tell us if this is junk/bulk mail. * from -- the Return-Path of the sender. We assume that * anything from "*-REQUEST@*" is bulk mail. * TRUE -- if this is junk or bulk mail (that is, if the * sender shouldn't receive a response). * FALSE -- if the sender deserves a response. * May read the header from standard input. When this * returns the position on stdin is undefined. /* test for inhuman sender */ #
define Delims " \n\t:,:;()<>@!" /* read the header looking for "interesting" lines */ return (
FALSE);
/* no header found */ }
else /* continuation line? */ /* find the value of this field */ /* see if it is "junk" or "bulk" */ * FILTER_OK -- see if the Return-Path is in the filter file. * Note that a non-existent filter file means everything * is OK, but an empty file means nothing is OK. * from -- the Return-Path of the sender. * TRUE -- if this is in the filter file * (sender should receive a response). * FALSE -- if the sender does not deserve a response. * If the file does not exist, then there is no filter to * apply, so we simply return TRUE. (
void)
printf(
"%s does not exist, filter ok.\n",
/* zero out trailing newline */ (
void)
printf(
"filter match on %s\n",
* Make sure the last part of from is the domain line * and that the character immediately preceding is an * '@' or a '.', otherwise we could get false positives (
void)
printf(
"filter match on %s\n",
(
void)
printf(
"no filter match\n");
* KNOWS -- predicate telling if user has already been informed. * user -- the user who sent this message. * TRUE if 'user' has already been informed that the * recipient is on vacation. * SETKNOWS -- set that this user knows about the vacation. * user -- the user who should be marked. * The dbm file is updated as appropriate. * SENDMESSAGE -- send a message to a particular user. * msgf -- filename containing the message. * user -- user who should receive it. /* find the message to send */ * We used to write directly to the pipe. But now we need to know * what character set to use, and we need to examine the entire * message to determine this. So write to a temp file first. usrerr(
"newstr: cannot alloc memory");
* Check for a line with no ':' character. If it's just \n, * we're at the end of the headers and all is fine. Or if * it starts with white-space, then it's a continuation header. * Otherwise, it's the start of the body, which means the * header/body separator was skipped. So output it. if (p &&
strncmp(p,
"$SUBJECT",
8) == 0) {
* If we haven't seen a funky Subject with Charset, use the default. * If we have and it's us-ascii, 8-bit chars in the message file will * still result in iso-8859-1. * Now read back in from the temp file and write to the pipe. * INITIALIZE -- initialize the database before leaving for vacation * Initializes the files .vacation.{pag,dir} in the * caller's home directory. * USRERR -- print user error * NEWSTR -- copy a string * s -- the string to copy. usrerr(
"newstr: cannot alloc memory");
* SAMEWORD -- return TRUE if the words are the same * a, b -- the words to compare. * TRUE if a & b match exactly (modulo case) }
while (
ca !=
'\0' &&
ca ==
cb);
* When invoked with no arguments, we fall into an automatic installation * mode, stepping the user through a default installation. usrerr(
"Home directory unknown");
printf(
"This program can be used to answer your mail automatically\n");
printf(
"when you go away on vacation.\n");
if (
ask(
"Would you like to see it")) {
if (
ask(
"Would you like to edit it"))
printf(
"You need to create a message file" " in %s first.\n",
file);
fprintf(f,
"Subject: away from my mail\n");
fprintf(f,
"\nI will not be reading my mail" fprintf(f,
"Your mail regarding \"$SUBJECT\" will" " be read when I return.\n");
printf(
"Please use your editor (%s)" " to edit this file.\n",
editor);
printf(
"You have a .forward file" " in your home directory containing:\n");
if (!
ask(
"Would you like to remove it and" " disable the vacation feature"))
perror(
"Error removing .forward file:");
printf(
"Back to normal reception of mail.\n");
printf(
"To enable the vacation feature" " a \".forward\" file is created.\n");
if (!
ask(
"Would you like to enable the vacation feature")) {
printf(
"OK, vacation feature NOT enabled.\n");
perror(
"Error opening .forward file");
printf(
"Vacation feature ENABLED." " Please remember to turn it off when\n");
printf(
"you get back from vacation. Bon voyage.\n");
* Ask the user a question until we get a reasonable answer if (
res[0] ==
'y' ||
res[0] ==
'Y')
if (
res[0] ==
'n' ||
res[0] ==
'N')
printf(
"Please reply \"yes\" or \"no\" (\'y\' or \'n\')\n");