Bug 237426 - RFE: "cut" does not interwork with "tail" (or: "cut" should have an option to flush output). Patch attached
RFE: "cut" does not interwork with "tail" (or: "cut" should have an option to...
Status: CLOSED NOTABUG
Product: Red Hat Enterprise Linux 4
Classification: Red Hat
Component: coreutils (Show other bugs)
4.0
All Linux
medium Severity medium
: ---
: ---
Assigned To: Tim Waugh
:
Depends On:
Blocks:
  Show dependency treegraph
 
Reported: 2007-04-22 16:00 EDT by David Tonhofer
Modified: 2007-11-30 17:07 EST (History)
1 user (show)

See Also:
Fixed In Version:
Doc Type: Bug Fix
Doc Text:
Story Points: ---
Clone Of:
Environment:
Last Closed: 2007-04-22 18:15:31 EDT
Type: ---
Regression: ---
Mount Type: ---
Documentation: ---
CRM:
Verified Versions:
Category: ---
oVirt Team: ---
RHEL 7.3 requirements from Atomic Host:
Cloudforms Team: ---


Attachments (Terms of Use)
Patch for "cut". Contains old cut.c, new cut.c and diff (60.00 KB, application/x-tar)
2007-04-22 16:00 EDT, David Tonhofer
no flags Details

  None (edit)
Description David Tonhofer 2007-04-22 16:00:09 EDT
Description of problem:

When piping output from "tail" into "cut", the output of "cut" to stdout is
buffered. This is unfortunate in case one wants to follow a logfile in realtime.

E.g. "tail -f msgserver.log" 
     ...outputs the lines as they come
     "tail -f msgserver.log | cut --field=6 --delimiter='|'
     ...outputs the lines once the buffer between 'cut' and the
        terminal driver is full (or something)

Version-Release number of selected component:

  coreutils-5.2.1-31.4

How reproducible:

  Always

Patch attached. I have added the option '--push' (with short option 'p')  
to 'cut' (no Red Hat patches have been applied to cut as far as I see)

Why option 'p' instead of 'f'? Because 'f' was already taken. And 'p'/'push'
sounded good.

If the option has been set, 'cut' goes into a mode whereby it issues an
'flush' after every 'fwrite' to stdout.

Note that my C knowledge has become somewhat rusty, but this does seem to 
work.

Patch file created with "diff --unified cut.c new_cut.c"
Comment 1 David Tonhofer 2007-04-22 16:00:10 EDT
Created attachment 153257 [details]
Patch for "cut". Contains old cut.c, new cut.c and diff
Comment 2 David Tonhofer 2007-04-22 16:05:34 EDT
Hmm, there is still a problem whereby the flush mode is always on irrespective
of the whether the flag is given or not? Unfortunately, I have to do some "real
work" now.
Comment 3 Jim Meyering 2007-04-22 16:21:08 EDT
Thanks for the suggestion and patch, but that sort of change is not necessary.
Instead, you can do something like the following, using the small unbuffer
script that comes with expect.  For your reference, here's a copy:

#!/bin/sh
# \
exec expect -- "$0" ${1+"$@"}
# Description: unbuffer stdout of a program
# Author: Don Libes, NIST

if {[string compare [lindex $argv 0] "-p"] == 0} {
    # pipeline
    set stty_init "-echo"
    eval spawn -noecho [lrange $argv 1 end]
    interact
} else {
    set stty_init "-opost"
    eval spawn -noecho $argv
    set timeout -1
    expect
}

The solution is to run "cut" via unbuffer -p.  For example,

   for i in $(seq 10); do echo a $i >> k; sleep 1; done &
   tail -F k | ./unbuffer -p cut -d' ' -f2
Comment 4 David Tonhofer 2007-04-23 07:30:39 EDT
Uh wow.. I have to get my mind around this. Good thing is, it generalizes to all
programs, but somehow it is really, really ugly ;-)

Thanks,

-- David

Note You need to log in before you can comment on or make changes to this bug.