1 /* Test of file timestamp modification functions.
2 Copyright (C) 2009 Free Software Foundation, Inc.
4 This program is free software: you can redistribute it and/or modify
5 it under the terms of the GNU General Public License as published by
6 the Free Software Foundation; either version 2 of the License, or
7 (at your option) any later version.
9 This program is distributed in the hope that it will be useful,
10 but WITHOUT ANY WARRANTY; without even the implied warranty of
11 MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
12 GNU General Public License for more details.
14 You should have received a copy of the GNU General Public License
15 along with this program. If not, see <http://www.gnu.org/licenses/>. */
17 /* This file assumes that BASE and ASSERT are already defined. */
19 #ifndef GL_TEST_UTIMENS
20 # define GL_TEST_UTIMENS
27 #include "stat-time.h"
32 BILLION = 1000 * 1000 * 1000,
34 Y2K = 946684800, /* Jan 1, 2000, in seconds since epoch. */
36 /* Bogus positive and negative tv_nsec values closest to valid
37 range, but without colliding with UTIME_NOW or UTIME_OMIT. */
38 UTIME_BOGUS_POS = BILLION + ((UTIME_NOW == BILLION || UTIME_OMIT == BILLION)
39 ? (1 + (UTIME_NOW == BILLION + 1)
40 + (UTIME_OMIT == BILLION + 1))
42 UTIME_BOGUS_NEG = -1 - ((UTIME_NOW == -1 || UTIME_OMIT == -1)
43 ? (1 + (UTIME_NOW == -2) + (UTIME_OMIT == -2))
47 #endif /* GL_TEST_UTIMENS */
49 /* This function is designed to test both gl_futimens(a,NULL,b) and
50 futimens(a,b). FUNC is the function to test. If PRINT, warn
51 before skipping tests with status 77. */
53 test_futimens (int (*func) (int, struct timespec const *),
56 int fd = creat (BASE "file", 0600);
64 result = func (fd, NULL);
65 if (result == -1 && errno == ENOSYS)
67 ASSERT (close (fd) == 0);
68 ASSERT (unlink (BASE "file") == 0);
70 fputs ("skipping test: "
71 "setting fd time not supported on this file system\n",
76 ASSERT (fstat (fd, &st1) == 0);
78 /* Invalid arguments. */
80 ASSERT (func (AT_FDCWD, NULL) == -1);
81 ASSERT (errno == EBADF);
83 struct timespec ts[2] = { { Y2K, UTIME_BOGUS_POS }, { Y2K, 0 } };
85 ASSERT (func (fd, ts) == -1);
86 ASSERT (errno == EINVAL);
89 struct timespec ts[2] = { { Y2K, 0 }, { Y2K, UTIME_BOGUS_NEG } };
91 ASSERT (func (fd, ts) == -1);
92 ASSERT (errno == EINVAL);
94 ASSERT (fstat (fd, &st2) == 0);
95 ASSERT (st1.st_atime == st2.st_atime);
96 ASSERT (get_stat_atime_ns (&st1) == get_stat_atime_ns (&st2));
97 ASSERT (utimecmp (BASE "file", &st1, &st2, 0) == 0);
101 struct timespec ts[2] = { { Y2K, BILLION / 2 - 1 }, { Y2K, BILLION - 1 } };
102 ASSERT (func (fd, ts) == 0);
103 ASSERT (fstat (fd, &st2) == 0);
104 ASSERT (st2.st_atime == Y2K);
105 ASSERT (0 <= get_stat_atime_ns (&st2));
106 ASSERT (get_stat_atime_ns (&st2) < BILLION / 2);
107 ASSERT (st2.st_mtime == Y2K);
108 ASSERT (0 <= get_stat_mtime_ns (&st2));
109 ASSERT (get_stat_mtime_ns (&st2) < BILLION);
112 /* Play with UTIME_OMIT, UTIME_NOW. */
114 struct timespec ts[2] = { { BILLION, UTIME_OMIT }, { 0, UTIME_NOW } };
115 ASSERT (func (fd, ts) == 0);
116 ASSERT (fstat (fd, &st2) == 0);
117 ASSERT (st2.st_atime == Y2K);
118 ASSERT (0 <= get_stat_atime_ns (&st2));
119 ASSERT (get_stat_atime_ns (&st2) <= BILLION / 2);
120 ASSERT (utimecmp (BASE "file", &st1, &st2, 0) <= 0);
124 ASSERT (close (fd) == 0);
125 ASSERT (unlink (BASE "file") == 0);