/* whatnowsbr.c - the WhatNow shell */
static char ident
[] = "@(#)$Id: whatnowsbr.c,v 1.21 1992/12/15 00:20:22 jromine Exp $";
static int editfile(), copyf(), sendfile(), sendit(), whomfile();
static struct swit whatnowswitches
[] = {
"draftfolder +folder", 0,
static struct swit aleqs
[] = {
"display [<switches>]", 0,
"edit [<editor> <switches>]", 0,
"refile [<switches>] +folder", 0,
static char *myprompt
= "\nWhat now? ";
invo_name
= r1bindex (argv
[0], '/');
if ((cp
= m_find (invo_name
)) != NULL
) {
ap
= brkstring (cp
= getcpy (cp
), " ", "\n");
ap
= copyip (ap
, arguments
);
(void) copyip (argv
+ 1, ap
);
switch (smatch (++cp
, whatnowswitches
)) {
ambigsw (cp
, whatnowswitches
);
adios (NULLCP
, "-%s unknown", cp
);
(void) sprintf (buf
, "%s [switches] [file]", invo_name
);
help (buf
, whatnowswitches
);
adios (NULLCP
, "only one draft folder at a time!");
if (!(cp
= *argp
++) || *cp
== '-')
adios (NULLCP
, "missing argument to %s", argp
[-2]);
dfolder
= path (*cp
== '+' || *cp
== '@' ? cp
+ 1 : cp
,
*cp
!= '@' ? TFOLDER
: TSUBCWF
);
adios (NULLCP
, "only one draft message at a time!");
if (!(dmsg
= *argp
++) || *dmsg
== '-')
adios (NULLCP
, "missing argument to %s", argp
[-2]);
if (!(ed
= *argp
++) || *ed
== '-')
adios (NULLCP
, "missing argument to %s", argp
[-2]);
if (!(myprompt
= *argp
++) || *myprompt
== '-')
adios (NULLCP
, "missing argument to %s", argp
[-2]);
adios (NULLCP
, "only one draft at a time!");
if (drft
== NULL
&& (drft
= getenv ("mhdraft")) == NULL
|| *drft
== 0)
drft
= getcpy (m_draft (dfolder
, dmsg
, 1, &isdf
));
msgnam
= (cp
= getenv ("mhaltmsg")) && *cp
? getcpy (cp
) : NULLCP
;
if (ed
== NULL
&& ((ed
= getenv ("mheditor")) == NULL
|| *ed
== 0))
if ((cp
= getenv ("mhuse")) && *cp
)
&& editfile (&ed
, NULLVP
, drft
, use
, NULLMP
, msgnam
, NULLCP
) < 0)
(void) sprintf (prompt
, myprompt
, invo_name
);
if (!(argp
= getans (prompt
, aleqs
))) {
switch (smatch (*argp
, aleqs
)) {
(void) showfile (++argp
, msgnam
);
advise (NULLCP
, "no alternate message to display");
if (editfile (&ed
, argp
, drft
, NOUSE
, NULLMP
, msgnam
, NULLCP
)
(void) showfile (++argp
, drft
);
(void) whomfile (++argp
, drft
);
if (*++argp
&& (*argp
[0] == 'd' ||
((*argp
)[0] == '-' && (*argp
)[1] == 'd'))) {
if (unlink (drft
) == NOTOK
)
adios (drft
, "unable to unlink");
if (stat (drft
, &st
) != NOTOK
)
advise (NULLCP
, "draft left on %s", drft
);
if (sendfile (++argp
, drft
, 1))
(void) sendfile (++argp
, drft
, 0);
if (refile (++argp
, drft
) == 0)
advise (NULLCP
, "say what?");
static char *edsave
= NULL
;
static int editfile (ed
, arg
, file
, use
, mp
, altmsg
, cwd
)
register struct msgs
*mp
;
int oumask
; /* PJS: for setting permissions on symlinks. */
if (!reedit
) { /* set initial editor */
if (*ed
== NULL
&& (*ed
= m_find ("editor")) == NULL
)
if (!*ed
) { /* no explicit editor */
if ((cp
= r1bindex (*ed
, '/')) == NULL
)
cp
= concat (cp
, "-next", NULLCP
);
if ((cp
= m_find (cp
)) != NULL
)
if (mp
== NULL
|| *altmsg
== '/' || cwd
== NULL
)
(void) strcpy (altpath
, altmsg
);
(void) sprintf (altpath
, "%s/%s", mp
-> foldpath
, altmsg
);
(void) strcpy (linkpath
, LINK
);
(void) sprintf (linkpath
, "%s/%s", cwd
, LINK
);
(void) unlink (linkpath
);
if (link (altpath
, linkpath
) == NOTOK
) {
#ifdef notdef /* I don't think permission on symlinks matters /JLR */
oumask
= umask(0044); /* PJS: else symlinks are world 'r' */
(void) symlink (altpath
, linkpath
);
umask(oumask
); /* PJS: else symlinks are world 'r' */
(void) link (altpath
, linkpath
);
switch (pid
= vfork ()) {
advise ("fork", "unable to");
(void) m_putenv ("mhfolder", mp
-> foldpath
);
(void) m_putenv ("editalt", altpath
);
vec
[vecp
++] = r1bindex (*ed
, '/');
fprintf (stderr
, "unable to exec ");
if (status
= pidwait (pid
, NOTOK
)) {
if ((cp
= r1bindex (*ed
, '/'))
&& strcmp (cp
, "vi") == 0
&& (status
& 0x00ff) == 0)
if (((status
& 0xff00) != 0xff00)
&& (!reedit
|| (status
& 0x00ff)))
if (!use
&& (status
& 0xff00) &&
(rename (file
, cp
= m_backup (file
)) != NOTOK
)) {
advise (NULLCP
, "problems with edit--draft left in %s",
advise (NULLCP
, "problems with edit--%s preserved",
status
= -2; /* maybe "reedit ? -2 : -1"? */
&& (!mp
-> msgflags
& READONLY
)
? lstat (linkpath
, &st
) != NOTOK
&& (st
.st_mode
& S_IFMT
) == S_IFREG
&& copyf (linkpath
, altpath
) == NOTOK
: stat (linkpath
, &st
) != NOTOK
&& (unlink (altpath
) == NOTOK
|| link (linkpath
, altpath
) == NOTOK
)))
advise (linkpath
, "unable to update %s from", altmsg
);
&& (!mp
-> msgflags
& READONLY
)
&& stat (linkpath
, &st
) != NOTOK
&& (unlink (altpath
) == NOTOK
|| link (linkpath
, altpath
) == NOTOK
))
advise (linkpath
, "unable to update %s from", altmsg
);
(void) unlink (linkpath
);
static int copyf (ifile
, ofile
)
if ((in
= open (ifile
, 0)) == NOTOK
)
if ((out
= open (ofile
, 1)) == NOTOK
|| ftruncate (out
, 0) == NOTOK
) {
admonish (ofile
, "unable to truncate");
while ((i
= read (in
, buffer
, sizeof buffer
)) > OK
)
if (write (out
, buffer
, i
) != i
) {
advise (ofile
, "may have damaged");
static sendfile (arg
, file
, pushsw
)
if ((cp
= m_find ("automhnproc"))
&& (i
= editfile (&cp
, NULLVP
, file
, NOUSE
, NULLMP
, NULLCP
,
if (strcmp (sp
= r1bindex (sendproc
, '/'), "send") == 0) {
sendit (invo_name
= sp
, arg
, file
, pushsw
);
for (i
= 0; (child_id
= vfork ()) == NOTOK
&& i
< 5; i
++)
advise (NULLCP
, "unable to fork, so sending directly...");
fprintf (stderr
, "unable to exec ");
if (pidwait (child_id
, OK
) == 0)
static int mhnfile (msgnam
)
if ((fp
= fopen (msgnam
, "r")) == NULL
)
switch (state
= m_getfld (state
, name
, buf
, sizeof buf
, fp
)) {
if (uprf (name
, XXX_FIELD_PRF
)) {
state
= m_getfld (state
, name
, buf
, sizeof buf
, fp
);
for (bp
= buf
; *bp
; bp
++)
if (*bp
!= ' ' && *bp
!= '\t' && *bp
!= '\n') {
state
= m_getfld (state
, name
, buf
, sizeof buf
, fp
);
static struct swit sendswitches
[] = {
"split seconds", MIMEminc(-5),
"draftfolder +folder", -6,
extern int debugsw
; /* from sendsbr.c */
extern char *altmsg
; /* .. */
static sendit (sp
, arg
, file
, pushed
)
(void) copyip (arg
, vec
);
if ((cp
= m_find (sp
)) != NULL
) {
ap
= brkstring (cp
= getcpy (cp
), " ", "\n");
ap
= copyip (ap
, arguments
);
debugsw
= 0, forwsw
= 1, inplace
= 0, unique
= 0;
altmsg
= annotext
= distfile
= NULL
;
vec
[vecp
++] = "-library";
vec
[vecp
++] = getcpy (m_maildir (""));
switch (smatch (++cp
, sendswitches
)) {
ambigsw (cp
, sendswitches
);
advise (NULLCP
, "-%s unknown\n", cp
);
(void) sprintf (buf
, "%s [switches]", sp
);
help (buf
, sendswitches
);
if (!(cp
= *argp
++) || sscanf (cp
, "%d", &splitsw
) != 1) {
advise (NULLCP
, "missing argument to %s", argp
[-2]);
if (!(cp
= *argp
++) || *cp
== '-') {
advise (NULLCP
, "missing argument to %s", argp
[-2]);
if (!(cp
= *argp
++) || *cp
== '-') {
advise (NULLCP
, "missing argument to %s", argp
[-2]);
advise (NULLCP
, "usage: %s [switches]", sp
);
if (cp
= m_find ("Aliasfile")) { /* allow Aliasfile: profile entry */
for (ap
= brkstring(dp
= getcpy(cp
), " ", "\n"); ap
&& *ap
; ap
++) {
if ((cp
= getenv ("KDS")) == NULL
|| *cp
== NULL
)
if ((cp
= m_find ("kdsproc")) && *cp
)
(void) m_putenv ("KDS", cp
);
if ((cp
= getenv ("TMADB")) == NULL
|| *cp
== NULL
)
if ((cp
= m_find ("tmadb")) && *cp
)
(void) m_putenv ("TMADB", m_maildir (cp
));
if ((cp
= getenv ("SIGNATURE")) == NULL
|| *cp
== 0)
if ((cp
= m_find ("signature")) && *cp
)
(void) m_putenv ("SIGNATURE", cp
);
(void) sprintf (buf
, "%s/.signature", mypath
);
if ((fp
= fopen (buf
, "r")) != NULL
&& fgets (buf
, sizeof buf
, fp
) != NULL
) {
if (cp
= index (buf
, '\n'))
(void) m_putenv ("SIGNATURE", buf
);
if ((annotext
= getenv ("mhannotate")) == NULL
|| *annotext
== 0)
if ((altmsg
= getenv ("mhaltmsg")) == NULL
|| *altmsg
== 0)
if (annotext
&& ((cp
= getenv ("mhinplace")) != NULL
&& *cp
!= 0))
if ((cp
= getenv ("mhdist"))
distfile
= getcpy (m_scratch (altmsg
, invo_name
));
if (link (altmsg
, distfile
) == NOTOK
)
adios (distfile
, "unable to link %s to", altmsg
);
if (altmsg
== NULL
|| stat (altmsg
, &st
) == NOTOK
)
st
.st_mtime
= 0, st
.st_dev
= 0, st
.st_ino
= 0;
vec
[0] = r1bindex (postproc
, '/');
if (sendsbr (vec
, vecp
, file
, &st
) == OK
)
static int whomfile (arg
, file
)
switch (pid
= vfork ()) {
advise ("fork", "unable to");
vec
[vecp
++] = r1bindex (whomproc
, '/');
fprintf (stderr
, "unable to exec ");
_exit (-1); /* NOTREACHED */
return (pidwait (pid
, NOTOK
) & 0377 ? 1 : 0);