Semnodime
Semnodime

Reputation: 2003

truncate does not support creating files with sizes greater than 2^63-1

Apparently, gnu truncate on my x86_64 system does not support creating files with sizes of size >= 8EiB (= 2^63 Bytes = 9223372036854775808 Bytes).

/usr/bin/truncate: ELF 64-bit LSB pie executable, x86-64, version 1 (SYSV), dynamically linked, interpreter /lib64/ld-linux-x86-64.so.2, BuildID[sha1]=c45930b128536914bf8134c0f11745cbd115d34b, for GNU/Linux 3.2.0, stripped

truncate -s 9223372036854775807 file
truncate -s 8E file
truncate: Invalid number: ‘8E’: Value too large for defined data type

I assumed file sizes up to 16EiB = 2^64 Bytes to be valid, or at least 2^64 - 1 Bytes.

Why is my intuition regarding the implementation of truncate flawed?

Upvotes: 0

Views: 83

Answers (1)

Semnodime
Semnodime

Reputation: 2003

The GNU C Library Reference Manual defines this error message when encounting an overflow error:

[Macro]
int EOVERFLOW
“Value too large for defined data type.”

The source code of gnu truncate contains this definition:

static bool do_ftruncate (int fd, char const *fname, off_t ssize, off_t rel_mode_t rel_mode)

which uses type off_t from #include <sys/types.h> for file sizes.

As it is built using gcc/glibc with _FILE_OFFSET_BITS set to 64, off_t is refering to off64_t, which is "able to address files up to 2^63 bytes" according to the The GNU C Library Reference Manual, because it is a signed integer:

[Data Type]
off_t
This is a signed integer type used to represent file sizes. In the GNU C Library, this type is no narrower than int.
If the source is compiled with _FILE_OFFSET_BITS == 64 this type is transparently replaced by off64_t.

[Data Type]
off64_t
This type is used similar to off_t. The difference is that even on 32 bit machines, where the off_t type would have 32 bits, off64_t has 64 bits and so is able to address files up to 2^63 bytes in length.
When compiling with _FILE_OFFSET_BITS == 64 this type is available under the name off_t.

Upvotes: 0

Related Questions