History

uapi: change the type of struct statx_timestamp.tv_nsec to unsigned

The comment asserting that the value of struct statx_timestamp.tv_nsec must be negative when statx_timestamp.tv_sec is negative, is wrong, as could be seen from the following example: #define _FILE_OFFSET_BITS 64 #include <assert.h> #include <fcntl.h> #include <stdio.h> #include <sys/stat.h> #include <unistd.h> #include <asm/unistd.h> #include <linux/stat.h> int main(void) { static const struct timespec ts[2] = { { .tv_nsec = UTIME_OMIT }, { .tv_sec = -2, .tv_nsec = 42 } }; assert(utimensat(AT_FDCWD, ".", ts, 0) == 0); struct stat st; assert(stat(".", &st) == 0); printf("st_mtim.tv_sec = %lld, st_mtim.tv_nsec = %lu\n", (long long) st.st_mtim.tv_sec, (unsigned long) st.st_mtim.tv_nsec); struct statx stx; assert(syscall(__NR_statx, AT_FDCWD, ".", 0, 0, &stx) == 0); printf("stx_mtime.tv_sec = %lld, stx_mtime.tv_nsec = %lu\n", (long long) stx.stx_mtime.tv_sec, (unsigned long) stx.stx_mtime.tv_nsec); return 0; } It expectedly prints: st_mtim.tv_sec = -2, st_mtim.tv_nsec = 42 stx_mtime.tv_sec = -2, stx_mtime.tv_nsec = 42 The more generic comment asserting that the value of struct statx_timestamp.tv_nsec might be negative is confusing to say the least. It contradicts both the struct stat.st_[acm]time_nsec tradition and struct timespec.tv_nsec requirements in utimensat syscall. If statx syscall ever returns a stx_[acm]time containing a negative tv_nsec that cannot be passed unmodified to utimensat syscall, it will cause an immense confusion. Fix this source of confusion by changing the type of struct statx_timestamp.tv_nsec from __s32 to __u32.

Dmitry V. Levin committed 9 years ago

Commit 17419371 parent 85128b21 file · +2 −6Browse files

Showing the changes to include/uapi/linux (1 of 1 file). Show all

Unified · Split

include/uapi/linux/stat.h+2−6
@@ -48,17 +48,13 @@ · 47 unmodified lines
4848 * tv_sec holds the number of seconds before (negative) or after (positive)
4949 * 00:00:00 1st January 1970 UTC.
5050 *
51− * tv_nsec holds a number of nanoseconds before (0..-999,999,999 if tv_sec is
52− * negative) or after (0..999,999,999 if tv_sec is positive) the tv_sec time.
53− *
54− * Note that if both tv_sec and tv_nsec are non-zero, then the two values must
55− * either be both positive or both negative.
51+ * tv_nsec holds a number of nanoseconds (0..999,999,999) after the tv_sec time.
5652 *
5753 * __reserved is held in case we need a yet finer resolution.
5854 */
5955 struct statx_timestamp {
6056 __s64 tv_sec;
61− __s32 tv_nsec;
57+ __u32 tv_nsec;
6258 __s32 __reserved;
6359 };
6460