svn commit: r250469 - head/bin/dd
Eitan Adler
eadler at FreeBSD.org
Fri May 10 18:43:39 UTC 2013
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 at 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;
}
More information about the svn-src-all
mailing list