[Top][All Lists]
[Date Prev][Date Next][Thread Prev][Thread Next][Date Index][Thread Index]
Re: [PATCH] df: Fix bug when totaling unknown values.
From: |
Paul Eggert |
Subject: |
Re: [PATCH] df: Fix bug when totaling unknown values. |
Date: |
Wed, 25 Mar 2009 21:33:44 -0700 |
User-agent: |
Gnus/5.11 (Gnus v5.11) Emacs/22.3 (gnu/linux) |
Jim Meyering <address@hidden> writes:
> So how about a function like summable (uintmax_t val) to be used
> in place of each of those 5 tests?
Sure thing, though I count 11 tests total, not just the 5 in the
previous patch. I prefer a name like 'known_value' to 'summable', as
it's a bit more specific. Here's that same patch, followed by a further
patch to add known_value, generated by git-format-patch.
=======
>From abc8e21a0b5a55bed938b30adf217a26c1a17bac Mon Sep 17 00:00:00 2001
From: Paul Eggert <address@hidden>
Date: Wed, 25 Mar 2009 14:16:46 -0700
Subject: [PATCH] df: Fix bug when totaling unknown values.
* src/df.c (show_dev): Don't add UINTMAX_MAX to grand totals, as that
value indicates that the true value is unknown; adding it effectively
subtracts 1 from the total, whereas we want to leave the total alone.
---
src/df.c | 19 ++++++++++++-------
1 files changed, 12 insertions(+), 7 deletions(-)
diff --git a/src/df.c b/src/df.c
index 0bb3b1e..bb24934 100644
--- a/src/df.c
+++ b/src/df.c
@@ -393,8 +393,10 @@ show_dev (char const *disk, char const *mount_point,
negate_available = false;
available_to_root = available;
- grand_fsu.fsu_files += total;
- grand_fsu.fsu_ffree += available;
+ if (total != UINTMAX_MAX)
+ grand_fsu.fsu_files += total;
+ if (available != UINTMAX_MAX)
+ grand_fsu.fsu_ffree += available;
}
else
{
@@ -422,11 +424,14 @@ show_dev (char const *disk, char const *mount_point,
& (available != UINTMAX_MAX));
available_to_root = fsu.fsu_bfree;
- grand_fsu.fsu_blocks += input_units * total;
- grand_fsu.fsu_bfree += input_units * available_to_root;
- add_uint_with_neg_flag (&grand_fsu.fsu_bavail,
- &grand_fsu.fsu_bavail_top_bit_set,
- input_units * available, negate_available);
+ if (total != UINTMAX_MAX)
+ grand_fsu.fsu_blocks += input_units * total;
+ if (available_to_root != UINTMAX_MAX)
+ grand_fsu.fsu_bfree += input_units * available_to_root;
+ if (available != UINTMAX_MAX)
+ add_uint_with_neg_flag (&grand_fsu.fsu_bavail,
+ &grand_fsu.fsu_bavail_top_bit_set,
+ input_units * available, negate_available);
}
used = UINTMAX_MAX;
--
1.5.3.2
>From 2c35010ca7651251376f113983141d08b6ecce0a Mon Sep 17 00:00:00 2001
From: Paul Eggert <address@hidden>
Date: Wed, 25 Mar 2009 20:50:17 -0700
Subject: [PATCH] df: Port the known-value fix to AIX as well.
* src/df.c (known_value): New function, which also works on AIX file systems.
(df_readable, show_dev): Use it instead of hardcoding comparison to
UINTMAX_MAX. Suggested by Jim Meyering and Matthew Woehlke.
---
src/df.c | 30 ++++++++++++++++++++----------
1 files changed, 20 insertions(+), 10 deletions(-)
diff --git a/src/df.c b/src/df.c
index bb24934..bbbb47d 100644
--- a/src/df.c
+++ b/src/df.c
@@ -231,18 +231,28 @@ excluded_fstype (const char *fstype)
return false;
}
+/* Return true if N is a known integer value. On many file systems,
+ UINTMAX_MAX represents an unknown value; on AIX, UINTMAX_MAX - 1
+ represents unknown. Use a rule that works on AIX file systems, and
+ that almost-always works on other types. */
+static bool
+known_value (uintmax_t n)
+{
+ return n < UINTMAX_MAX - 1;
+}
+
/* Like human_readable (N, BUF, human_output_opts, INPUT_UNITS, OUTPUT_UNITS),
except:
- If NEGATIVE, then N represents a negative number,
expressed in two's complement.
- - Otherwise, return "-" if N is UINTMAX_MAX. */
+ - Otherwise, return "-" if N is unknown. */
static char const *
df_readable (bool negative, uintmax_t n, char *buf,
uintmax_t input_units, uintmax_t output_units)
{
- if (n == UINTMAX_MAX && !negative)
+ if (! known_value (n) && !negative)
return "-";
else
{
@@ -393,9 +403,9 @@ show_dev (char const *disk, char const *mount_point,
negate_available = false;
available_to_root = available;
- if (total != UINTMAX_MAX)
+ if (known_value (total))
grand_fsu.fsu_files += total;
- if (available != UINTMAX_MAX)
+ if (known_value (available))
grand_fsu.fsu_ffree += available;
}
else
@@ -421,14 +431,14 @@ show_dev (char const *disk, char const *mount_point,
total = fsu.fsu_blocks;
available = fsu.fsu_bavail;
negate_available = (fsu.fsu_bavail_top_bit_set
- & (available != UINTMAX_MAX));
+ & known_value (available));
available_to_root = fsu.fsu_bfree;
- if (total != UINTMAX_MAX)
+ if (known_value (total))
grand_fsu.fsu_blocks += input_units * total;
- if (available_to_root != UINTMAX_MAX)
+ if (known_value (available_to_root))
grand_fsu.fsu_bfree += input_units * available_to_root;
- if (available != UINTMAX_MAX)
+ if (known_value (available))
add_uint_with_neg_flag (&grand_fsu.fsu_bavail,
&grand_fsu.fsu_bavail_top_bit_set,
input_units * available, negate_available);
@@ -436,7 +446,7 @@ show_dev (char const *disk, char const *mount_point,
used = UINTMAX_MAX;
negate_used = false;
- if (total != UINTMAX_MAX && available_to_root != UINTMAX_MAX)
+ if (known_value (total) && known_value (available_to_root))
{
used = total - available_to_root;
negate_used = (total < available_to_root);
@@ -451,7 +461,7 @@ show_dev (char const *disk, char const *mount_point,
width, df_readable (negate_available, available,
buf[2], input_units, output_units));
- if (used == UINTMAX_MAX || available == UINTMAX_MAX)
+ if (! known_value (used) || ! known_value (available))
;
else if (!negate_used
&& used <= TYPE_MAXIMUM (uintmax_t) / 100
--
1.5.3.2
Re: [PATCH] df: Fix bug when totaling unknown values., Matthew Woehlke, 2009/03/25