aboutsummaryrefslogtreecommitdiffstats
diff options
context:
space:
mode:
-rw-r--r--NEWS4
-rw-r--r--src/cut.c32
-rwxr-xr-xtests/misc/write-errors.sh3
3 files changed, 26 insertions, 13 deletions
diff --git a/NEWS b/NEWS
index dc5d21d9b..8d15f2738 100644
--- a/NEWS
+++ b/NEWS
@@ -62,8 +62,8 @@ GNU coreutils NEWS -*- outline -*-
irrespective of which kernel version coreutils is built against,
reinstating that behaviour from coreutils-9.0.
- od and uniq will now exit immediately upon receiving a write error, which is
- significant when reading large / unbounded inputs.
+ cut, od, and uniq will now exit immediately upon receiving a write error,
+ which is significant when reading large / unbounded inputs.
split now uses more tuned access patterns for its potentially large input.
This was seen to improve throughput by 5% when reading from SSD.
diff --git a/src/cut.c b/src/cut.c
index 12dfd2299..476df0943 100644
--- a/src/cut.c
+++ b/src/cut.c
@@ -232,7 +232,8 @@ cut_bytes (FILE *stream)
if (c == line_delim)
{
- putchar (c);
+ if (putchar (c) < 0)
+ write_error ();
byte_idx = 0;
print_delimiter = false;
current_rp = frp;
@@ -252,13 +253,16 @@ cut_bytes (FILE *stream)
{
if (print_delimiter && is_range_start_index (byte_idx))
{
- fwrite (output_delimiter_string, sizeof (char),
- output_delimiter_length, stdout);
+ if (fwrite (output_delimiter_string, sizeof (char),
+ output_delimiter_length, stdout)
+ != output_delimiter_length)
+ write_error ();
}
print_delimiter = true;
}
- putchar (c);
+ if (putchar (c) < 0)
+ write_error ();
}
}
}
@@ -325,7 +329,9 @@ cut_fields (FILE *stream)
}
else
{
- fwrite (field_1_buffer, sizeof (char), n_bytes, stdout);
+ if (fwrite (field_1_buffer, sizeof (char), n_bytes, stdout)
+ != n_bytes)
+ write_error ();
/* Make sure the output line is newline terminated. */
if (field_1_buffer[n_bytes - 1] != line_delim)
putchar (line_delim);
@@ -336,7 +342,9 @@ cut_fields (FILE *stream)
if (print_kth (1))
{
/* Print the field, but not the trailing delimiter. */
- fwrite (field_1_buffer, sizeof (char), n_bytes - 1, stdout);
+ if (fwrite (field_1_buffer, sizeof (char), n_bytes - 1, stdout)
+ != n_bytes - 1)
+ write_error ();
/* With -d$'\n' don't treat the last '\n' as a delimiter. */
if (delim == line_delim)
@@ -360,14 +368,17 @@ cut_fields (FILE *stream)
{
if (found_any_selected_field)
{
- fwrite (output_delimiter_string, sizeof (char),
- output_delimiter_length, stdout);
+ if (fwrite (output_delimiter_string, sizeof (char),
+ output_delimiter_length, stdout)
+ != output_delimiter_length)
+ write_error ();
}
found_any_selected_field = true;
while ((c = getc (stream)) != delim && c != line_delim && c != EOF)
{
- putchar (c);
+ if (putchar (c) < 0)
+ write_error ();
prev_c = c;
}
}
@@ -398,7 +409,8 @@ cut_fields (FILE *stream)
{
if (c == line_delim || prev_c != line_delim
|| delim == line_delim)
- putchar (line_delim);
+ if (putchar (line_delim) < 0)
+ write_error ();
}
if (c == EOF)
break;
diff --git a/tests/misc/write-errors.sh b/tests/misc/write-errors.sh
index 20942e068..e217c5512 100755
--- a/tests/misc/write-errors.sh
+++ b/tests/misc/write-errors.sh
@@ -28,7 +28,8 @@ fi
echo "\
cat /dev/zero
# TODO: comm -z /dev/zero /dev/zero
-# TODO: cut -z -c1- /dev/zero
+cut -z -c1- /dev/zero
+cut -z -f1- /dev/zero
dd if=/dev/zero
expand /dev/zero
factor --version; yes 1 | factor