Skip site navigation (1)Skip section navigation (2)
Date:      Fri, 10 May 2013 18:43:37 +0000 (UTC)
From:      Eitan Adler <eadler@FreeBSD.org>
To:        src-committers@freebsd.org, svn-src-all@freebsd.org, svn-src-head@freebsd.org
Subject:   svn commit: r250469 - head/bin/dd
Message-ID:  <201305101843.r4AIhbtx000503@svn.freebsd.org>

next in thread | raw e-mail | index | archive | help
Author: eadler
Date: Fri May 10 18:43:36 2013
New Revision: 250469
URL: http://svnweb.freebsd.org/changeset/base/250469

Log:
  Make dd's signal handler async safe.
  
  PR:		bin/75258
  Submitted by:	"Oleg V. Nauman" <oleg@reis.zp.ua>
  Arrival Date:	Sun Dec 19 14:50:21 GMT 2004
  Reviewed by:	mjg, jhb
  Reviewed by:	jilles (earlier version)
  MFC after:	1 week

Modified:
  head/bin/dd/args.c
  head/bin/dd/conv_tab.c
  head/bin/dd/dd.c
  head/bin/dd/extern.h
  head/bin/dd/misc.c
  head/bin/dd/position.c

Modified: head/bin/dd/args.c
==============================================================================
--- head/bin/dd/args.c	Fri May 10 18:41:14 2013	(r250468)
+++ head/bin/dd/args.c	Fri May 10 18:43:36 2013	(r250469)
@@ -45,6 +45,7 @@ __FBSDID("$FreeBSD$");
 #include <errno.h>
 #include <inttypes.h>
 #include <limits.h>
+#include <signal.h>
 #include <stdlib.h>
 #include <string.h>
 

Modified: head/bin/dd/conv_tab.c
==============================================================================
--- head/bin/dd/conv_tab.c	Fri May 10 18:41:14 2013	(r250468)
+++ head/bin/dd/conv_tab.c	Fri May 10 18:43:36 2013	(r250469)
@@ -41,6 +41,7 @@ __FBSDID("$FreeBSD$");
 
 #include <sys/types.h>
 
+#include <signal.h>
 #include <stdint.h>
 
 #include "dd.h"

Modified: head/bin/dd/dd.c
==============================================================================
--- head/bin/dd/dd.c	Fri May 10 18:41:14 2013	(r250468)
+++ head/bin/dd/dd.c	Fri May 10 18:43:36 2013	(r250469)
@@ -81,6 +81,7 @@ size_t	cbsz;			/* conversion block size 
 uintmax_t files_cnt = 1;	/* # of files to copy */
 const	u_char *ctab;		/* conversion table */
 char	fill_char;		/* Character to fill with if defined */
+volatile sig_atomic_t need_summary;
 
 int
 main(int argc __unused, char *argv[])
@@ -89,7 +90,7 @@ main(int argc __unused, char *argv[])
 	jcl(argv);
 	setup();
 
-	(void)signal(SIGINFO, summaryx);
+	(void)signal(SIGINFO, siginfo_handler);
 	(void)signal(SIGINT, terminate);
 
 	atexit(summary);
@@ -375,6 +376,9 @@ dd_in(void)
 
 		in.dbp += in.dbrcnt;
 		(*cfunc)();
+		if (need_summary) {
+			summary();
+		}
 	}
 }
 

Modified: head/bin/dd/extern.h
==============================================================================
--- head/bin/dd/extern.h	Fri May 10 18:41:14 2013	(r250468)
+++ head/bin/dd/extern.h	Fri May 10 18:43:36 2013	(r250469)
@@ -43,7 +43,7 @@ void jcl(char **);
 void pos_in(void);
 void pos_out(void);
 void summary(void);
-void summaryx(int);
+void siginfo_handler(int);
 void terminate(int);
 void unblock(void);
 void unblock_close(void);
@@ -61,3 +61,4 @@ extern const u_char e2a_32V[], e2a_POSIX
 extern const u_char a2ibm_32V[], a2ibm_POSIX[];
 extern u_char casetab[];
 extern char fill_char;
+extern volatile sig_atomic_t need_summary;

Modified: head/bin/dd/misc.c
==============================================================================
--- head/bin/dd/misc.c	Fri May 10 18:41:14 2013	(r250468)
+++ head/bin/dd/misc.c	Fri May 10 18:43:36 2013	(r250469)
@@ -44,6 +44,7 @@ __FBSDID("$FreeBSD$");
 
 #include <errno.h>
 #include <inttypes.h>
+#include <signal.h>
 #include <stdio.h>
 #include <stdlib.h>
 #include <string.h>
@@ -57,41 +58,32 @@ summary(void)
 {
 	struct timeval tv;
 	double secs;
-	char buf[100];
 
 	(void)gettimeofday(&tv, NULL);
 	secs = tv.tv_sec + tv.tv_usec * 1e-6 - st.start;
 	if (secs < 1e-6)
 		secs = 1e-6;
-	/* Use snprintf(3) so that we don't reenter stdio(3). */
-	(void)snprintf(buf, sizeof(buf),
+	(void)fprintf(stderr,
 	    "%ju+%ju records in\n%ju+%ju records out\n",
 	    st.in_full, st.in_part, st.out_full, st.out_part);
-	(void)write(STDERR_FILENO, buf, strlen(buf));
-	if (st.swab) {
-		(void)snprintf(buf, sizeof(buf), "%ju odd length swab %s\n",
+	if (st.swab)
+		(void)fprintf(stderr, "%ju odd length swab %s\n",
 		     st.swab, (st.swab == 1) ? "block" : "blocks");
-		(void)write(STDERR_FILENO, buf, strlen(buf));
-	}
-	if (st.trunc) {
-		(void)snprintf(buf, sizeof(buf), "%ju truncated %s\n",
+	if (st.trunc)
+		(void)fprintf(stderr, "%ju truncated %s\n",
 		     st.trunc, (st.trunc == 1) ? "block" : "blocks");
-		(void)write(STDERR_FILENO, buf, strlen(buf));
-	}
-	(void)snprintf(buf, sizeof(buf),
+	(void)fprintf(stderr,
 	    "%ju bytes transferred in %.6f secs (%.0f bytes/sec)\n",
 	    st.bytes, secs, st.bytes / secs);
-	(void)write(STDERR_FILENO, buf, strlen(buf));
+	need_summary = 0;
 }
 
 /* ARGSUSED */
 void
-summaryx(int notused __unused)
+siginfo_handler(int signo __unused)
 {
-	int save_errno = errno;
 
-	summary();
-	errno = save_errno;
+	need_summary = 1;
 }
 
 /* ARGSUSED */

Modified: head/bin/dd/position.c
==============================================================================
--- head/bin/dd/position.c	Fri May 10 18:41:14 2013	(r250468)
+++ head/bin/dd/position.c	Fri May 10 18:43:36 2013	(r250469)
@@ -45,6 +45,7 @@ __FBSDID("$FreeBSD$");
 #include <err.h>
 #include <errno.h>
 #include <inttypes.h>
+#include <signal.h>
 #include <unistd.h>
 
 #include "dd.h"
@@ -91,6 +92,8 @@ pos_in(void)
 				}
 			} else
 				--cnt;
+			if (need_summary)
+				summary();
 			continue;
 		}
 



Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?201305101843.r4AIhbtx000503>