changeset 20:40748b097655

add output.
author David A. Holland
date Mon, 20 Dec 2010 04:03:35 -0500
parents f9792a9ec704
children e3fab8f1b52c
files Makefile mode.h output.c utils.c
diffstat 4 files changed, 77 insertions(+), 1 deletions(-) [+]
line wrap: on
line diff
--- a/Makefile	Mon Dec 20 03:55:19 2010 -0500
+++ b/Makefile	Mon Dec 20 04:03:35 2010 -0500
@@ -1,7 +1,10 @@
 #	$NetBSD$
 
 PROG=	tradcpp
-SRCS=	main.c files.c directive.c eval.c macro.c place.c array.c utils.c
+SRCS=	main.c \
+	files.c directive.c eval.c macro.c output.c \
+	place.c array.c utils.c
+NOMAN=	1
 WARNS=	5
 
 .include <bsd.prog.mk>
--- a/mode.h	Mon Dec 20 03:55:19 2010 -0500
+++ b/mode.h	Mon Dec 20 04:03:35 2010 -0500
@@ -1,3 +1,5 @@
+#include <stdbool.h>
+
 struct mode {
 	bool werror;
 	bool input_allow_dollars;
--- /dev/null	Thu Jan 01 00:00:00 1970 +0000
+++ b/output.c	Mon Dec 20 04:03:35 2010 -0500
@@ -0,0 +1,60 @@
+#include <unistd.h>
+#include <fcntl.h>
+#include <err.h>
+
+#include "utils.h"
+#include "mode.h"
+#include "output.h"
+
+static int outputfd = -1;
+
+static
+void
+output_open(void)
+{
+	outputfd = open(mode.output_file, O_WRONLY|O_CREAT|O_TRUNC, 0664);
+	if (outputfd < 0) {
+		warn("%s", mode.output_file);
+		die();
+	}
+}
+
+void
+output(const char *buf, size_t len)
+{
+	size_t done;
+	ssize_t result;
+	static unsigned write_errors = 0;
+
+	if (outputfd < 0) {
+		output_open();
+	}
+
+	/* XXX this will often come by ones and twos, should buffer */
+
+	done = 0;
+	while (done < len) {
+		result = write(outputfd, buf+done, len-done);
+		if (result == -1) {
+			warn("%s: write", mode.output_file);
+			complain_failed();
+			write_errors++;
+			if (write_errors > 5) {
+				warnx("%s: giving up", mode.output_file);
+				die();
+			}
+			/* XXX is this really a good idea? */
+			sleep(1);
+		}
+		done += (size_t)result;
+	}
+}
+
+void
+output_eof(void)
+{
+	if (outputfd >= 0) {
+		close(outputfd);
+	}
+	outputfd = -1;
+}
--- a/utils.c	Mon Dec 20 03:55:19 2010 -0500
+++ b/utils.c	Mon Dec 20 04:03:35 2010 -0500
@@ -108,6 +108,17 @@
 	return ret;
 }
 
+char *
+dostrndup(const char *s, size_t len)
+{
+	char *ret;
+
+	ret = domalloc(len+1);
+	memcpy(ret, s, len);
+	ret[len] = '\0';
+	return ret;
+}
+
 size_t
 notrailingws(char *buf, size_t len)
 {