Date: Tue, 4 Jun 2002 11:07:05 +0200 (CEST) From: Alexander Leidinger <netchild@FreeBSD.org> To: audit@freebsd.org Cc: Benjamin Lewis <bhlewis@wossname.net> Subject: [PATCH] making dump EINTR resistant Message-ID: <200206040907.g54975wE003913@Magelan.Leidinger.net>
next in thread | raw e-mail | index | archive | help
--0-1804289383-1023181632=:572 Content-Type: TEXT/plain; charset=us-ascii Hi, Benjamin Lewis <bhlewis@wossname.net> had some problems with dump, have a look at the -current archives (Subject: "Is anyone else having trouble with dump(8) on -current?", around May 15.). I had such a problem on 4.x (perhaps 4.2 or 4.3) once too (I wasn't able to reproduce it, Benjamin is able to reproduce it on -current) and wrote the attached patch to solve the problem. Since I wrote it for 4.x, it runs fine (actually on a 4.4 system which does daily backups to a spare harddisk). Benjamin uses it also on a daily basis on -current. The attached diff is against -current. Comments? Bye, Alexander. -- The computer revolution is over. The computers won. http://www.Leidinger.net Alexander @ Leidinger.net GPG fingerprint = C518 BC70 E67F 143F BE91 3365 79E2 9C60 B006 3FE7 --0-1804289383-1023181632=:572 Content-Type: TEXT/plain; name="dump.diff" Content-Disposition: attachment; filename="dump.diff" Index: dumprmt.c =================================================================== RCS file: /big/FreeBSD-CVS/src/sbin/dump/dumprmt.c,v retrieving revision 1.17 diff -u -r1.17 dumprmt.c --- dumprmt.c 20 Mar 2002 22:49:39 -0000 1.17 +++ dumprmt.c 27 Mar 2002 15:27:54 -0000 @@ -114,10 +114,13 @@ t.tv_sec = 0; t.tv_usec = 0; if (select(errfd + 1, &r, NULL, NULL, &t)) { - int i; + int i = 0; char buf[2048]; - if ((i = read(errfd, buf, sizeof(buf) - 1)) > 0) { + do { + i = read(errfd, buf, sizeof(buf)); + } while ((i == -1) && (errno == EINTR)); + if (i - 1 > 0) { buf[i] = '\0'; msg("on %s: %s%s", rmtpeer, buf, buf[i - 1] == '\n' ? "" : "\n"); @@ -243,7 +246,9 @@ /* rmtcall() properly sets errno for us on errors. */ return (n); for (i = 0; i < n; i += cc) { - cc = read(rmtape, buf+i, n - i); + do { + cc = read(rmtape, buf+i, n - i); + } while ((cc == -1) && (errno == EINTR)); if (cc <= 0) rmtconnaborted(0); } @@ -361,8 +366,12 @@ rmtgetb(void) { char c; + int ret_val; - if (read(rmtape, &c, 1) != 1) + do { + ret_val = read(rmtape, &c, 1); + } while ((ret_val == -1) && (errno == EINTR)); + if (ret_val != 1) rmtconnaborted(0); return (c); } Index: itime.c =================================================================== RCS file: /big/FreeBSD-CVS/src/sbin/dump/itime.c,v retrieving revision 1.11 diff -u -r1.11 itime.c --- itime.c 20 Mar 2002 22:49:39 -0000 1.11 +++ itime.c 27 Mar 2002 14:26:39 -0000 @@ -74,7 +74,10 @@ { FILE *df; - if ((df = fopen(dumpdates, "r")) == NULL) { + do { + df = fopen(dumpdates, "r"); + } while ((df == NULL) && (errno == EINTR)); + if (df == NULL) { if (errno != ENOENT) { msg("WARNING: cannot read %s: %s\n", dumpdates, strerror(errno)); @@ -84,13 +87,19 @@ * Dumpdates does not exist, make an empty one. */ msg("WARNING: no file `%s', making an empty one\n", dumpdates); - if ((df = fopen(dumpdates, "w")) == NULL) { + do { + df = fopen(dumpdates, "w"); + } while ((df == NULL) && (errno == EINTR)); + if (df == NULL) { msg("WARNING: cannot create %s: %s\n", dumpdates, strerror(errno)); return; } (void) fclose(df); - if ((df = fopen(dumpdates, "r")) == NULL) { + do { + df = fopen(dumpdates, "r"); + } while ((df == NULL) && (errno == EINTR)); + if (df == NULL) { quit("cannot read %s even after creating it: %s\n", dumpdates, strerror(errno)); /* NOTREACHED */ @@ -171,7 +180,10 @@ if(uflag == 0) return; - if ((df = fopen(dumpdates, "r+")) == NULL) + do { + df = fopen(dumpdates, "r+"); + } while ((df == NULL) && (errno == EINTR)); + if (df == NULL) quit("cannot rewrite %s: %s\n", dumpdates, strerror(errno)); fd = fileno(df); (void) flock(fd, LOCK_EX); Index: main.c =================================================================== RCS file: /big/FreeBSD-CVS/src/sbin/dump/main.c,v retrieving revision 1.36 diff -u -r1.36 main.c --- main.c 16 May 2002 04:09:56 -0000 1.36 +++ main.c 4 Jun 2002 08:48:51 -0000 @@ -57,6 +57,7 @@ #include <ctype.h> #include <err.h> +#include <errno.h> #include <fcntl.h> #include <fstab.h> #include <signal.h> @@ -335,7 +336,10 @@ else msgtail("to %s\n", tape); - if ((diskfd = open(disk, O_RDONLY)) < 0) + do { + diskfd = open(disk, O_RDONLY); + } while((diskfd < 0) && (errno == EINTR)); + if (diskfd < 0) err(X_STARTUP, "Cannot open %s", disk); if (fstat(diskfd, &sb) != 0) err(X_STARTUP, "%s: stat", disk); Index: optr.c =================================================================== RCS file: /big/FreeBSD-CVS/src/sbin/dump/optr.c,v retrieving revision 1.20 diff -u -r1.20 optr.c --- optr.c 16 May 2002 04:09:56 -0000 1.20 +++ optr.c 4 Jun 2002 08:48:51 -0000 @@ -82,7 +82,10 @@ int back, errcount; FILE *mytty; - if ((mytty = fopen(_PATH_TTY, "r")) == NULL) + do { + mytty = fopen(_PATH_TTY, "r"); + } while ((mytty == NULL) && (errno == EINTR)); + if (mytty == NULL) quit("fopen on %s fails: %s\n", _PATH_TTY, strerror(errno)); attnmessage = question; timeout = 0; Index: tape.c =================================================================== RCS file: /big/FreeBSD-CVS/src/sbin/dump/tape.c,v retrieving revision 1.18 diff -u -r1.18 tape.c --- tape.c 20 Mar 2002 22:49:39 -0000 1.18 +++ tape.c 4 Jun 2002 08:53:44 -0000 @@ -328,7 +328,7 @@ quit("or use no size estimate at all.\n"); } } - (void) close(slaves[f].fd); + while ((close(slaves[f].fd) < 0) && (errno == EINTR)) /* nop */; } while (wait((int *)NULL) >= 0) /* wait for any signals from slaves */ /* void */; @@ -351,10 +351,10 @@ (void)close(tapefd); return; } - (void) close(tapefd); + while ((close(tapefd) < 0) && (errno == EINTR)) /* nop */; while ((f = open(tape, 0)) < 0) sleep (10); - (void) close(f); + while ((close(f) < 0) && (errno == EINTR)) /* nop */; } void @@ -502,6 +502,7 @@ int childpid; int status; int waitpid; + int tmpfd; char *p; sig_t interrupt_save; @@ -590,12 +591,16 @@ nexttape = NULL; msg("Dumping volume %d on %s\n", tapeno, tape); } + + if (0 != pipeout) + do { + tmpfd = open(tape, O_WRONLY|O_CREAT, 0666); + } while ((tmpfd < 0) && (errno == EINTR)); #ifdef RDUMP while ((tapefd = (host ? rmtopen(tape, 2) : - pipeout ? 1 : open(tape, O_WRONLY|O_CREAT, 0666))) < 0) + pipeout ? 1 : tmpfd)) < 0) #else - while ((tapefd = (pipeout ? 1 : - open(tape, O_WRONLY|O_CREAT, 0666))) < 0) + while ((tapefd = (pipeout ? 1 : tmpfd)) < 0) #endif { msg("Cannot open output \"%s\".\n", tape); @@ -696,7 +701,8 @@ slaves[i].sent = 0; if (slaves[i].pid == 0) { /* Slave starts up here */ for (j = 0; j <= i; j++) - (void) close(slaves[j].fd); + while ((close(slaves[j].fd) < 0) + && (errno == EINTR)) /* nop */; signal(SIGINT, SIG_IGN); /* Master handles this */ doslave(cmd[0], i); Exit(X_FINOK); @@ -739,8 +745,11 @@ /* * Need our own seek pointer. */ - (void) close(diskfd); - if ((diskfd = open(disk, O_RDONLY)) < 0) + while ((close(diskfd) < 0) && (errno == EINTR)) /* nop */; + do { + diskfd = open(disk, O_RDONLY); + } while ((diskfd < 0) && (errno == EINTR)); + if (diskfd < 0) quit("slave couldn't reopen disk: %s\n", strerror(errno)); /* @@ -849,7 +858,13 @@ { int got, need = count; - while ((got = (*func)(fd, buf, need)) > 0 && (need -= got) > 0) - buf += got; + do { + do { + got = (*func)(fd, buf, need); + } while ((got == -1) && (errno == EINTR)); + + if ((got > 0) && ((need -= got) > 0)) + buf += got; + } while (got > 0 && need > 0); return (got < 0 ? got : count - need); } --0-1804289383-1023181632=:572-- To Unsubscribe: send mail to majordomo@FreeBSD.org with "unsubscribe freebsd-audit" in the body of the message
Want to link to this message? Use this URL: <https://mail-archive.FreeBSD.org/cgi/mid.cgi?200206040907.g54975wE003913>