[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
[Nmh-workers] [PATCH] mhbuild: implement #on/#off/#pop, and the -[no]dir
From: |
Paul Fox |
Subject: |
[Nmh-workers] [PATCH] mhbuild: implement #on/#off/#pop, and the -[no]directives switch |
Date: |
Thu, 31 May 2012 14:17:16 -0400 |
ken wrote:
> > > I'm fine with the #on/#off directives; I can see their usefulness.
> > > Send in the code and we'll add it.
> >
> >i'm looking at it. no promises! :-)
>
> One additional thing occurs to me.
>
> We have a few tools right now which put in mhbuild directives in drafts
> for you (forw -mime, the attach WhatNow? command). It occurs to me that
> instead of #on/#off, maybe it should really be something like:
>
> #push on
> <mhbuild directives>
> #pop
>
> #push off would also work. You get the idea ... that way automatically
> inserted directives wouldn't mess up your current process/no process state.
i've implemented this as #on, #off, and #pop. i have no attachment to
the names, or whether there should be a "push" in front of "on" or
"off". it's lightly tested -- there may well be corner cases in
complicated drafts that will get it confused. it works for my simple
usages. comments/suggestions welcome.
paul
---
man/mhbuild.man | 31 +++++++++++++++++--
uip/mhbuild.c | 57 +++++++++++++++++++++--------------
uip/mhbuildsbr.c | 86 ++++++++++++++++++++++++++++++++++++++++++------------
3 files changed, 129 insertions(+), 45 deletions(-)
diff --git a/man/mhbuild.man b/man/mhbuild.man
index cd7e7fd..7ee13a2 100644
--- a/man/mhbuild.man
+++ b/man/mhbuild.man
@@ -12,6 +12,7 @@ mhbuild \- translate MIME composition draft
.RB [ \-list " | " \-nolist ]
.RB [ \-realsize " | " \-norealsize ]
.RB [ \-headers " | " \-noheaders ]
+.RB [ \-directives " | " \-nodirectives ]
.RB [ \-ebcdicsafe " | " \-noebcdicsafe ]
.RB [ \-rfc934mode " | " \-norfc934mode ]
.RB [ \-contentid " | " \-nocontentid ]
@@ -115,12 +116,36 @@ than one line, e.g.,
.fi
.RE
.PP
-There are four kinds of directives: \*(lqtype\*(rq directives, which
+There are five kinds of directives: \*(lqtype\*(rq directives, which
name the type and subtype of the content; \*(lqexternal-type\*(rq
directives, which also name the type and subtype of the content; the
\*(lqmessage\*(rq directive (#forw), which is used to forward one or
-more messages; and, the \*(lqbegin\*(rq directive (#begin), which is
-used to create a multipart content.
+more messages; the \*(lqbegin\*(rq directive (#begin), which is
+used to create a multipart content; and the \*(lqon/off/pop\*(rq
+directives (#on, #off, #pop) which control whether any other
+directives are honored at all.
+.PP
+The
+.B \-directives
+switch allows control over whether mhbuild will honor any of the
+\*(lq#\*(rq-directives. This can also be affected with the #on or
+#off directives, and #pop, which restores the state of processing to
+that preceding the most recent #on or #off. (The #on, #off, and #pop
+directives are always honored, of course.) This allows inclusion of
+plain text which looks like mhbuild directives, without causing
+errors:
+.PP
+.RS 5
+.nf
+#off
+#include <stdio.h>
+
+printf("Hello, World!);
+#pop
+.fi
+.RE
+.PP
+Currently the stack depth for the #on/off/pop directives is 32.
.PP
The \*(lqtype\*(rq directive is used to directly specify the type and
subtype of a content. You may only specify discrete types in this manner
diff --git a/uip/mhbuild.c b/uip/mhbuild.c
index ad674f4..020512d 100644
--- a/uip/mhbuild.c
+++ b/uip/mhbuild.c
@@ -25,43 +25,47 @@ static struct swit switches[] = {
{ "check", 0 },
#define NCHECKSW 1
{ "nocheck", 0 },
-#define EBCDICSW 2
+#define DIRECTIVES 2
+ { "directives", 0 },
+#define NDIRECTIVES 3
+ { "nodirectives", 0 },
+#define EBCDICSW 4
{ "ebcdicsafe", 0 },
-#define NEBCDICSW 3
+#define NEBCDICSW 5
{ "noebcdicsafe", 0 },
-#define HEADSW 4
+#define HEADSW 6
{ "headers", 0 },
-#define NHEADSW 5
+#define NHEADSW 7
{ "noheaders", 0 },
-#define LISTSW 6
+#define LISTSW 8
{ "list", 0 },
-#define NLISTSW 7
+#define NLISTSW 9
{ "nolist", 0 },
-#define SIZESW 8
+#define SIZESW 10
{ "realsize", 0 },
-#define NSIZESW 9
+#define NSIZESW 11
{ "norealsize", 0 },
-#define RFC934SW 10
+#define RFC934SW 12
{ "rfc934mode", 0 },
-#define NRFC934SW 11
+#define NRFC934SW 13
{ "norfc934mode", 0 },
-#define VERBSW 12
+#define VERBSW 14
{ "verbose", 0 },
-#define NVERBSW 13
+#define NVERBSW 15
{ "noverbose", 0 },
-#define RCACHESW 14
+#define RCACHESW 16
{ "rcache policy", 0 },
-#define WCACHESW 15
+#define WCACHESW 17
{ "wcache policy", 0 },
-#define CONTENTIDSW 16
+#define CONTENTIDSW 18
{ "contentid", 0 },
-#define NCONTENTIDSW 17
+#define NCONTENTIDSW 19
{ "nocontentid", 0 },
-#define VERSIONSW 18
+#define VERSIONSW 20
{ "version", 0 },
-#define HELPSW 19
+#define HELPSW 21
{ "help", 0 },
-#define DEBUGSW 20
+#define DEBUGSW 22
{ "debug", -5 },
{ NULL, 0 }
};
@@ -96,7 +100,7 @@ static int unlink_outfile = 0;
static void unlink_done (int) NORETURN;
/* mhbuildsbr.c */
-CT build_mime (char *);
+CT build_mime (char *, int);
int output_message (CT, char *);
int output_message_fp (CT, FILE *, char*);
@@ -110,7 +114,7 @@ void free_content (CT);
int
main (int argc, char **argv)
{
- int sizesw = 1, headsw = 1;
+ int sizesw = 1, headsw = 1, directives = 1;
int *icachesw;
char *cp, buf[BUFSIZ];
char buffer[BUFSIZ], *compfile = NULL;
@@ -198,6 +202,13 @@ main (int argc, char **argv)
headsw = 0;
continue;
+ case DIRECTIVES:
+ directives = 1;
+ continue;
+ case NDIRECTIVES:
+ directives = 0;
+ continue;
+
case LISTSW:
listsw++;
continue;
@@ -306,7 +317,7 @@ main (int argc, char **argv)
unlink_infile = 1;
/* build the content structures for MIME message */
- ct = build_mime (infile);
+ ct = build_mime (infile, directives);
cts[0] = ct;
cts[1] = NULL;
@@ -340,7 +351,7 @@ main (int argc, char **argv)
*/
/* build the content structures for MIME message */
- ct = build_mime (compfile);
+ ct = build_mime (compfile, directives);
cts[0] = ct;
cts[1] = NULL;
diff --git a/uip/mhbuildsbr.c b/uip/mhbuildsbr.c
index fd6a974..8a47dd5 100644
--- a/uip/mhbuildsbr.c
+++ b/uip/mhbuildsbr.c
@@ -72,7 +72,7 @@ void free_encoding (CT, int);
/*
* prototypes
*/
-CT build_mime (char *);
+CT build_mime (char *, int);
/*
* static prototypes
@@ -87,6 +87,38 @@ static int build_headers (CT);
static char *calculate_digest (CT, int);
+static unsigned char directives_stack[32];
+static unsigned int directives_index;
+
+static int do_direct(void)
+{
+ return directives_stack[directives_index];
+}
+
+static void directive_onoff(int onoff)
+{
+ if (directives_index >= sizeof(directives_stack)) {
+ fprintf(stderr, "mhbuild: #on/off overflow, continuing\n");
+ return;
+ }
+ directives_stack[++directives_index] = onoff;
+}
+
+static void directive_init(int onoff)
+{
+ directives_index = 0;
+ directives_stack[0] = onoff;
+}
+
+static void directive_pop(void)
+{
+ if (directives_index > 0)
+ directives_index--;
+ else
+ fprintf(stderr, "mhbuild: #pop underflow, continuing\n");
+
+}
+
/*
* Main routine for translating composition file
* into valid MIME message. It translates the draft
@@ -97,7 +129,7 @@ static char *calculate_digest (CT, int);
*/
CT
-build_mime (char *infile)
+build_mime (char *infile, int directives)
{
int compnum, state;
char buf[BUFSIZ], name[NAMESZ];
@@ -107,6 +139,8 @@ build_mime (char *infile)
CT ct;
FILE *in;
+ directive_init(directives);
+
umask (~m_gmprot ());
/* open the composition draft */
@@ -327,20 +361,34 @@ static char *
fgetstr (char *s, int n, FILE *stream)
{
char *cp, *ep;
+ int o_n = n;
+
+ while(1) {
+ for (ep = (cp = s) + o_n; cp < ep; ) {
+ int i;
- for (ep = (cp = s) + n; cp < ep; ) {
- int i;
+ if (!fgets (cp, n, stream))
+ return (cp != s ? s : NULL);
- if (!fgets (cp, n, stream))
- return (cp != s ? s : NULL);
- if (cp == s && *cp != '#')
- return s;
+ if (cp == s && *cp != '#')
+ return s;
- cp += (i = strlen (cp)) - 1;
- if (i <= 1 || *cp-- != '\n' || *cp != '\\')
+ cp += (i = strlen (cp)) - 1;
+ if (i <= 1 || *cp-- != '\n' || *cp != '\\')
+ break;
+ *cp = '\0';
+ n -= (i - 2);
+ }
+
+ if (strcmp(s, "#on\n") == 0) {
+ directive_onoff(1);
+ } else if (strcmp(s, "#off\n") == 0) {
+ directive_onoff(0);
+ } else if (strcmp(s, "#pop\n") == 0) {
+ directive_pop();
+ } else {
break;
- *cp = '\0';
- n -= (i - 2);
+ }
}
return s;
@@ -367,7 +415,7 @@ user_content (FILE *in, char *file, char *buf, CT *ctp)
CT ct;
CE ce;
- if (buf[0] == '\n' || strcmp (buf, "#\n") == 0) {
+ if (buf[0] == '\n' || (do_direct() && strcmp (buf, "#\n") == 0)) {
*ctp = NULL;
return OK;
}
@@ -392,7 +440,7 @@ user_content (FILE *in, char *file, char *buf, CT *ctp)
* 2) begins with "##" (implicit directive)
* 3) begins with "#<"
*/
- if (buf[0] != '#' || buf[1] == '#' || buf[1] == '<') {
+ if (!do_direct() || buf[0] != '#' || buf[1] == '#' || buf[1] == '<') {
int headers;
int inlineD;
long pos;
@@ -407,7 +455,7 @@ user_content (FILE *in, char *file, char *buf, CT *ctp)
ce->ce_file = add (cp, NULL);
ce->ce_unlink = 1;
- if (buf[0] == '#' && buf[1] == '<') {
+ if (do_direct() && (buf[0] == '#' && buf[1] == '<')) {
strncpy (content, buf + 2, sizeof(content));
inlineD = 1;
goto rock_and_roll;
@@ -418,11 +466,11 @@ user_content (FILE *in, char *file, char *buf, CT *ctp)
/* the directive is implicit */
strncpy (content, "text/plain", sizeof(content));
headers = 0;
- strncpy (buffer, buf[0] != '#' ? buf : buf + 1, sizeof(buffer));
+ strncpy (buffer, (!do_direct() || buf[0] != '#') ? buf : buf + 1,
sizeof(buffer));
for (;;) {
int i;
- if (headers >= 0 && uprf (buffer, DESCR_FIELD)
+ if (headers >= 0 && do_direct() && uprf (buffer, DESCR_FIELD)
&& buffer[i = strlen (DESCR_FIELD)] == ':') {
headers = 1;
@@ -445,7 +493,7 @@ again_descr:
}
}
- if (headers >= 0 && uprf (buffer, DISPO_FIELD)
+ if (headers >= 0 && do_direct() && uprf (buffer, DISPO_FIELD)
&& buffer[i = strlen (DISPO_FIELD)] == ':') {
headers = 1;
@@ -476,7 +524,7 @@ rock_and_roll:
pos = ftell (in);
if ((cp = fgetstr (buffer, sizeof(buffer) - 1, in)) == NULL)
break;
- if (buffer[0] == '#') {
+ if (do_direct() && buffer[0] == '#') {
char *bp;
if (buffer[1] != '#')
--
1.7.4.1
=---------------------
paul fox, address@hidden (arlington, ma, where it's 75.9 degrees)
- Re: [Nmh-workers] UTF-8 message bodies, (continued)
- Re: [Nmh-workers] UTF-8 message bodies, Aleksander Matuszak, 2012/05/28
- Re: [Nmh-workers] UTF-8 message bodies, Ken Hornstein, 2012/05/28
- Re: [Nmh-workers] UTF-8 message bodies, Aleksander Matuszak, 2012/05/30
- Re: [Nmh-workers] UTF-8 message bodies, Ken Hornstein, 2012/05/31
- Re: [Nmh-workers] UTF-8 message bodies, Aleksander Matuszak, 2012/05/31
- Re: [Nmh-workers] UTF-8 message bodies, Ken Hornstein, 2012/05/31
- Re: [Nmh-workers] UTF-8 message bodies, Paul Fox, 2012/05/31
- Re: [Nmh-workers] UTF-8 message bodies, Ken Hornstein, 2012/05/31
- Re: [Nmh-workers] UTF-8 message bodies, Paul Fox, 2012/05/31
- Re: [Nmh-workers] UTF-8 message bodies, Ken Hornstein, 2012/05/31
- [Nmh-workers] [PATCH] mhbuild: implement #on/#off/#pop, and the -[no]directives switch,
Paul Fox <=
- Re: [Nmh-workers] [PATCH] mhbuild: implement #on/#off/#pop, and the -[no]directives switch, Ken Hornstein, 2012/05/31
- Re: [Nmh-workers] [PATCH] mhbuild: implement #on/#off/#pop, and the -[no]directives switch, Ralph Corderoy, 2012/05/31
- Re: [Nmh-workers] [PATCH] mhbuild: implement #on/#off/#pop, and the -[no]directives switch, Paul Fox, 2012/05/31
- Re: [Nmh-workers] UTF-8 message bodies, valdis . kletnieks, 2012/05/31