du(1)/fts(3) integer overflow
M. Warner Losh
imp at bsdimp.com
Mon Dec 13 12:45:39 PST 2004
In message: <20041213185738.GD79646 at cirb503493.alcatel.com.au>
Peter Jeremy <PeterJeremy at optushome.com.au> writes:
: For 6.x, the ABI isn't fixed so fts_number can be changed to int64_t.
We have to be careful how we deal with these things... You do not
have license to break libc ABI, even in current, without careful
consideration of the consequences to backward compatibility... We're
trying hard not to do this...
: The 5.x ABI is fixed so there's no simple solution there. Possible hacks
: would be:
: - Add a new 'fts_number64' at the end of FTSENT. Since FTSENT is always
: managed by fts(3) and the documentation allows for undocumented fields,
: this should be permitted, though a "new" du(1) with an "old" libc
: would break badly.
: - Move fts_number to the end of FTSENT and leave a 'long' hole where the
: existing fts_number is. This changes the ABI but old programs remain
: compatible with the new fts. (Though new programs break with the
: old fts).
: - <Severe_kludge_alert>Have du(1) treat fts_pointer as an integer that
: it can concatenate to fts_number on 32-bit architectures:
: int64_t x = (int64_t)(ulong)p->fts_parent->fts_number |
: ((int64_t)(ulong)p->fts_parent->fts_pointer) << 32;
: x += p->fts_statp->st_blocks;
: p->fts_parent->fts_number = (long)x;
: p->fts_parent->fts_pointer = (void *)(long)(x >> 32);
: etc. </Severe_kludge_alert>
Wouldn't it be better to keep fts_number where it is, rename it to
fts_number32 (say) and introduce a fts_number at the end? Then you'd
update them both. Let the 32 bit one overflow, who cares: you've not
broken anything. That way old libc.so and new du would work except in
overflow cases.
Warner
More information about the freebsd-hackers
mailing list