bin/75258: [patch] dd(1) has not async signal safe interrupt handlers

Oleg V. Nauman oleg at reis.zp.ua
Sun Dec 19 06:50:22 PST 2004


>Number:         75258
>Category:       bin
>Synopsis:       [patch] dd(1) has not async signal safe interrupt handlers
>Confidential:   no
>Severity:       serious
>Priority:       medium
>Responsible:    freebsd-bugs
>State:          open
>Quarter:        
>Keywords:       
>Date-Required:
>Class:          sw-bug
>Submitter-Id:   current-users
>Arrival-Date:   Sun Dec 19 14:50:21 GMT 2004
>Closed-Date:
>Last-Modified:
>Originator:     Oleg V. Nauman
>Release:        FreeBSD 5.3-STABLE i386
>Organization:
ReIS LLC
>Environment:
System: FreeBSD core.zp.ua 5.3-STABLE FreeBSD 5.3-STABLE #16: Fri Dec 17 22:26:44 EET 2004 root at core.zp.ua:/usr/src/sys/i386/compile/core i386

>Description:
	dd(1) uses not safe interrupt handlers, they may leads to strange problems
with dd

>How-To-Repeat:

	man 2 sigaction

>Fix:

diff -u /usr/src/bin/dd/dd.c dd/dd.c
--- /usr/src/bin/dd/dd.c	Fri Oct  1 18:30:06 2004
+++ dd/dd.c	Sun Dec 19 11:31:44 2004
@@ -89,7 +89,7 @@
 	jcl(argv);
 	setup();
 
-	(void)signal(SIGINFO, summaryx);
+	(void)signal(SIGINFO, siginfo_handler);
 	(void)signal(SIGINT, terminate);
 
 	atexit(summary);
@@ -311,6 +311,7 @@
 			if (!(ddflags & C_NOERROR))
 				err(1, "%s", in.name);
 			warn("%s", in.name);
+			need_summary = 0;
 			summary();
 
 			/*
@@ -368,6 +369,10 @@
 
 		in.dbp += in.dbrcnt;
 		(*cfunc)();
+		if (need_summary) {
+			need_summary = 0;
+			summary();
+		}
 	}
 }
 
diff -u /usr/src/bin/dd/extern.h dd/extern.h
--- /usr/src/bin/dd/extern.h	Fri Oct  1 18:30:06 2004
+++ dd/extern.h	Sun Dec 19 11:32:53 2004
@@ -43,7 +43,7 @@
 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,5 @@
 extern const u_char a2ibm_32V[], a2ibm_POSIX[];
 extern u_char casetab[];
 extern char fill_char;
+
+int need_summary;
diff -u /usr/src/bin/dd/misc.c dd/misc.c
--- /usr/src/bin/dd/misc.c	Fri Oct  1 18:30:06 2004
+++ dd/misc.c	Sun Dec 19 11:32:01 2004
@@ -85,13 +85,9 @@
 }
 
 /* ARGSUSED */
-void
-summaryx(int notused __unused)
+void siginfo_handler(int signo __unused)
 {
-	int save_errno = errno;
-
-	summary();
-	errno = save_errno;
+	need_summary = 1;
 }
 
 /* ARGSUSED */
@@ -102,3 +98,4 @@
 	summary();
 	_exit(sig == 0 ? 0 : 1);
 }
+
diff -u /usr/src/bin/dd/position.c dd/position.c
--- /usr/src/bin/dd/position.c	Fri Oct  1 18:30:06 2004
+++ dd/position.c	Sun Dec 19 11:33:19 2004
@@ -91,6 +91,10 @@
 				}
 			} else
 				--cnt;
+			if (need_summary) {
+				need_summary = 0;
+				summary();
+			}
 			continue;
 		}
 
@@ -111,6 +115,7 @@
 			if (!warned) {
 				warn("%s", in.name);
 				warned = 1;
+				need_summary = 0;
 				summary();
 			}
 			continue;


>Release-Note:
>Audit-Trail:
>Unformatted:


More information about the freebsd-bugs mailing list