Deprecate pointer-width integer aliases · Issue #1400 · rust-lang/libc (original) (raw)

Similar to #1304, we guarantee that usize/isize is layout compatible with C's uintptr_t/intptr_t.

From the Rust documentation on usize:

The size of this primitive is how many bytes it takes to reference any location in memory. For example, on a 32 bit target, this is 4 bytes and on a 64 bit target, this is 8 bytes.

From the C11 standard (N1570) section 7.20.1.4:

7.20.1.4 Integer types capable of holding object pointers

The following type designates an unsigned integer type with the property that any valid pointer to void can be converted to this type, then converted back to pointer to void, and the result will compare equal to the original pointer:
uintptr_t

There is no need to provide type aliases (e.g. libc::uintptr_t) for these, in the same way that we don't provide a libc::c_bool type alias for bool.

What about size_t and ptrdiff_t?

We could potentially deprecate libc::size_t for usize (and libc::ptrdiff_t for isize). This is a more interesting question, as they are defined to be the type returned by a specific operation.

From section 7.19 of the C11 standard:

The types are
ptrdiff_t
which is the signed integer type of the result of subtracting two pointers;
size_t
which is the unsigned integer type of the result of the sizeof operator;

For ptrdiff_t, Rust's pointer methods ptr::offset and ptr::offset_from use isize to represent the "difference between pointers".

For size_t, Rust's core::mem::size_of function returns usize.

@gnzlbg @alexcrichton, I'm not sure what we should do here; I would love to know your thoughts. The argument for deprecation seems stronger for size_t than for ptrdiff_t.

The reason we have size_t/ptrdiff_t and uintptr_t/intptr_t in C is to support segmented addressing, but on every system I could find (including x86 Real Mode) uintptr_t and size_t are the same. Also, Rust already seems to implicitly assume that size_t == usize, this would just make it explicit.

What about ssize_t?

Note that we definitely don't want to deprecate libc::ssize_t because:

  1. Is isn't in the C standard, but in the Open Gorup <sys/types.h> standard
  2. This type is not necessarily isize. In fact, ssize_t only needs to be able to have the range [-1, SSIZE_MAX] and SSIZE_MAX has no relation to size_t's SIZE_MAX.

Also, see #1244 (comment)

What about intmax_t and uintmax_t?

While I did try to address those in #1244 and they are part of the C standard, defining them to either be [u|i]size or [u|i]64 would be wrong, as it would preclude a platform from using a 128-bit integer as it's largest type.