summaryrefslogtreecommitdiff
path: root/libmailutils
diff options
context:
space:
mode:
authorSergey Poznyakoff <gray@gnu.org>2020-08-06 21:13:17 +0300
committerSergey Poznyakoff <gray@gnu.org>2020-08-06 21:23:26 +0300
commit6b4df0a20f5a18a4be266fade0a4979a4decf23b (patch)
treed11b72596c97a77e5c1f4b5171496c254f30100d /libmailutils
parentad04463ee93ebd10a65fe9e128919a2dd735a534 (diff)
downloadmailutils-6b4df0a20f5a18a4be266fade0a4979a4decf23b.tar.gz
mailutils-6b4df0a20f5a18a4be266fade0a4979a4decf23b.tar.bz2
decodemail: make sure each message has the final newline on its own
* include/mailutils/stream.h (mu_stream_copy_wcb) (mu_stream_copy_nl): New protos. * libmailutils/stream/streamcpy.c (mu_stream_copy_wcb) (mu_stream_copy_nl): New functions. * libproto/mbox/mbox.c (append_message_to_stream): Use mu_stream_copy_nl. * decodemail/decodemail.c (hdr_print, body_print): Remove. (message_store_stdout): Use message stream instead of piping header and body separately. Use mu_stream_copy_nl to ensure the message has a final newline.
Diffstat (limited to 'libmailutils')
-rw-r--r--libmailutils/stream/streamcpy.c71
1 files changed, 59 insertions, 12 deletions
diff --git a/libmailutils/stream/streamcpy.c b/libmailutils/stream/streamcpy.c
index d375d6941..884b997d2 100644
--- a/libmailutils/stream/streamcpy.c
+++ b/libmailutils/stream/streamcpy.c
@@ -29,10 +29,16 @@
#define STREAMCPY_MAX_BUF_SIZE 16384
/* Copy SIZE bytes from SRC to DST. If SIZE is 0, copy everything up to
- EOF. */
+ EOF.
+ If the callback function CBF is not NULL, it will be called for
+ each buffer-full of data read with the following arguments: pointer to
+ the buffer, length of the data portion in buffer, pointer to the user-
+ supplied callback data (CBD).
+*/
int
-mu_stream_copy (mu_stream_t dst, mu_stream_t src, mu_off_t size,
- mu_off_t *pcsz)
+mu_stream_copy_wcb (mu_stream_t dst, mu_stream_t src, mu_off_t size,
+ void (*cbf) (char *, size_t, void *), void *cbd,
+ mu_off_t *pcsz)
{
int status;
size_t bufsize, n;
@@ -100,6 +106,8 @@ mu_stream_copy (mu_stream_t dst, mu_stream_t src, mu_off_t size,
break;
if (n == 0)
break;
+ if (cbf)
+ cbf (buf, n, cbd);
status = mu_stream_write (dst, buf, n, NULL);
if (status)
break;
@@ -111,15 +119,19 @@ mu_stream_copy (mu_stream_t dst, mu_stream_t src, mu_off_t size,
status = EIO;
}
else
- while ((status = mu_stream_read (src, buf, bufsize, &n)) == 0
- && n > 0)
- {
- status = mu_stream_write (dst, buf, n, NULL);
- if (status)
- break;
- total += n;
- }
-
+ {
+ while ((status = mu_stream_read (src, buf, bufsize, &n)) == 0
+ && n > 0)
+ {
+ if (cbf)
+ cbf (buf, n, cbd);
+ status = mu_stream_write (dst, buf, n, NULL);
+ if (status)
+ break;
+ total += n;
+ }
+ }
+
if (pcsz)
*pcsz = total;
/* FIXME: When EOF error code is implemented:
@@ -129,3 +141,38 @@ mu_stream_copy (mu_stream_t dst, mu_stream_t src, mu_off_t size,
free (buf);
return status;
}
+
+/* Copy SIZE bytes from SRC to DST. If SIZE is 0, copy everything up to
+ EOF. */
+int
+mu_stream_copy (mu_stream_t dst, mu_stream_t src, mu_off_t size,
+ mu_off_t *pcsz)
+{
+ return mu_stream_copy_wcb (dst, src, size, NULL, NULL, pcsz);
+}
+
+static void
+capture_last_char (char *buf, size_t size, void *data)
+{
+ *(char*)data = buf[size-1];
+}
+
+/* Same as mu_stream_copy, but also ensures that the copied data end with
+ a '\n' character. */
+int
+mu_stream_copy_nl (mu_stream_t dst, mu_stream_t src, mu_off_t size,
+ mu_off_t *pcsz)
+{
+ char lc;
+ int status = mu_stream_copy_wcb (dst, src, size, capture_last_char, &lc,
+ pcsz);
+ if (status == 0 && lc != '\n')
+ {
+ status = mu_stream_write (dst, "\n", 1, NULL);
+ if (status == 0 && pcsz)
+ ++ *pcsz;
+ }
+ return status;
+}
+
+

Return to:

Send suggestions and report system problems to the System administrator.