bin/57414: /usr/bin/script fails silently if stdin is not a terminal
Jonathan Lennox
lennox at cs.columbia.edu
Tue Sep 30 11:20:22 PDT 2003
>Number: 57414
>Category: bin
>Synopsis: /usr/bin/script fails silently if stdin is not a terminal
>Confidential: no
>Severity: serious
>Priority: medium
>Responsible: freebsd-bugs
>State: open
>Quarter:
>Keywords:
>Date-Required:
>Class: sw-bug
>Submitter-Id: current-users
>Arrival-Date: Tue Sep 30 11:20:17 PDT 2003
>Closed-Date:
>Last-Modified:
>Originator: Jonathan Lennox
>Release: FreeBSD 5.1-RELEASE-p7 i386
>Organization:
Columbia University
>Environment:
System: FreeBSD cnr.cs.columbia.edu 5.1-RELEASE-p7 FreeBSD 5.1-RELEASE-p7 #7: Wed Sep 24 18:19:12 EDT 2003 lennox at cnr.cs.columbia.edu:/usr/obj/usr/src/sys/CNR i386
>Description:
The /usr/bin/script utility fails silently if its standard input is not a
terminal. It does nothing, and does not execute its argument, but exits
with a successful output status.
This is not such a big deal if the user is using 'script' directly -- it's
pretty easy to figure out what happened. However, this can be *extremely*
surprising -- and dangerous -- if 'script' is called by some other program
which doesn't document this limitation.
In particular, the 'portupgrade' utility wraps its calls to 'make' and 'make
install' of upgraded ports in 'script'. As a result, if portupgrade is run
with its standard input redirected, out-of-date ports will be deleted and
then not reinstalled, with no warning or indication of any problem.
>How-To-Repeat:
$ script /var/tmp/foo cat /etc/passwd < /dev/null
outputs only
Script started, output file is /var/tmp/foo
Script done, output file is /var/tmp/foo
and /var/tmp/foo is empty.
# BATCH=yes portupgrade -arRv < /dev/null > /var/tmp/portupgrade.log 2>&1 &
(which seems like a perfectly reasonable way of upgrading all one's ports,
without having to stay logged in to watch it happen)
deletes all out-of-date ports from your system, without replacing them with
up-to-date versions.
>Fix:
The following patch causes /usr/bin/script to error quickly with a non-zero
exit status if tcgetattr or ioctl fail, as they will if stdin is not a tty.
--- usr.bin/script/script.1.orig Tue Sep 30 14:02:29 2003
+++ usr.bin/script/script.1 Tue Sep 30 14:06:29 2003
@@ -155,3 +155,7 @@
mode, echo cancelling is far from ideal. The slave terminal mode is checked
for ECHO mode to check when to avoid manual echo logging. This does not
work when in a raw mode where the program being run is doing manual echo.
+.Pp
+The
+.Nm
+utility fails if the standard input is not a terminal.
--- usr.bin/script/script.c.orig Tue Sep 30 14:01:46 2003
+++ usr.bin/script/script.c Tue Sep 30 14:04:48 2003
@@ -126,8 +126,10 @@
if ((fscript = fopen(fname, aflg ? "a" : "w")) == NULL)
err(1, "%s", fname);
- (void)tcgetattr(STDIN_FILENO, &tt);
- (void)ioctl(STDIN_FILENO, TIOCGWINSZ, &win);
+ if (tcgetattr(STDIN_FILENO, &tt) == -1)
+ err(1, "tcgetattr");
+ if (ioctl(STDIN_FILENO, TIOCGWINSZ, &win) == -1)
+ err(1, "ioctl");
if (openpty(&master, &slave, NULL, &tt, &win) == -1)
err(1, "openpty");
>Release-Note:
>Audit-Trail:
>Unformatted:
More information about the freebsd-bugs
mailing list