root/maint/gnulib/tests/test-utime.c

/* [previous][next][first][last][top][bottom][index][help] */

DEFINITIONS

This source file includes following definitions.
  1. test_utime
  2. main

   1 /* Tests of utime.
   2    Copyright (C) 2017-2021 Free Software Foundation, Inc.
   3 
   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 3 of the License, or
   7    (at your option) any later version.
   8 
   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.
  13 
  14    You should have received a copy of the GNU General Public License
  15    along with this program.  If not, see <https://www.gnu.org/licenses/>.  */
  16 
  17 #include <config.h>
  18 
  19 #include <utime.h>
  20 
  21 #include <stdbool.h>
  22 #include <stdio.h>
  23 #include <stdlib.h>
  24 
  25 #include "ignore-value.h"
  26 #include "macros.h"
  27 
  28 #define BASE "test-utime.t"
  29 
  30 #include "test-utimens-common.h"
  31 
  32 /* If PRINT, warn before skipping tests with status 77.  */
  33 static int
  34 test_utime (bool print)
     /* [previous][next][first][last][top][bottom][index][help] */
  35 {
  36   struct stat st1;
  37   struct stat st2;
  38 
  39   ASSERT (close (creat (BASE "file", 0600)) == 0);
  40   ASSERT (stat (BASE "file", &st1) == 0);
  41   nap ();
  42   ASSERT (utime (BASE "file", NULL) == 0);
  43   ASSERT (stat (BASE "file", &st2) == 0);
  44   ASSERT (0 <= utimecmp (BASE "file", &st2, &st1, UTIMECMP_TRUNCATE_SOURCE));
  45   if (check_ctime)
  46     ASSERT (ctime_compare (&st1, &st2) < 0);
  47   {
  48     /* On some NFS systems, the 'now' timestamp of creat or a NULL
  49        utimbuf is determined by the server, but the 'now' timestamp
  50        determined by time() is determined by the client; since the two
  51        machines are not necessarily on the same clock, this is another
  52        case where time can appear to go backwards.  The rest of this
  53        test cares about client time, so manually use time() to set
  54        both times.  */
  55     struct utimbuf ts;
  56     ts.actime = ts.modtime = time (NULL);
  57     ASSERT (utime (BASE "file", &ts) == 0);
  58     ASSERT (stat (BASE "file", &st1) == 0);
  59     nap ();
  60   }
  61 
  62   /* Invalid arguments.  */
  63   errno = 0;
  64   ASSERT (utime ("no_such", NULL) == -1);
  65   ASSERT (errno == ENOENT);
  66   errno = 0;
  67   ASSERT (utime ("no_such/", NULL) == -1);
  68   ASSERT (errno == ENOENT || errno == ENOTDIR);
  69   errno = 0;
  70   ASSERT (utime ("", NULL) == -1);
  71   ASSERT (errno == ENOENT);
  72   {
  73     struct utimbuf ts;
  74     ts.actime = ts.modtime = Y2K;
  75     errno = 0;
  76     ASSERT (utime (BASE "file/", &ts) == -1);
  77     ASSERT (errno == ENOTDIR || errno == EINVAL);
  78   }
  79   ASSERT (stat (BASE "file", &st2) == 0);
  80   ASSERT (st1.st_atime == st2.st_atime);
  81   ASSERT (get_stat_atime_ns (&st1) == get_stat_atime_ns (&st2));
  82   ASSERT (utimecmp (BASE "file", &st1, &st2, 0) == 0);
  83 
  84   /* Set both times.  */
  85   {
  86     struct utimbuf ts;
  87     ts.actime = ts.modtime = Y2K;
  88     ASSERT (utime (BASE "file", &ts) == 0);
  89     ASSERT (stat (BASE "file", &st2) == 0);
  90     ASSERT (st2.st_atime == Y2K);
  91     ASSERT (0 <= get_stat_atime_ns (&st2));
  92     ASSERT (get_stat_atime_ns (&st2) < BILLION / 2);
  93     ASSERT (st2.st_mtime == Y2K);
  94     ASSERT (0 <= get_stat_mtime_ns (&st2));
  95     ASSERT (get_stat_mtime_ns (&st2) < BILLION);
  96     if (check_ctime)
  97       ASSERT (ctime_compare (&st1, &st2) < 0);
  98   }
  99 
 100   /* Make sure this dereferences symlinks.  */
 101   if (symlink (BASE "file", BASE "link"))
 102     {
 103       ASSERT (unlink (BASE "file") == 0);
 104       if (print)
 105         fputs ("skipping test: symlinks not supported on this file system\n",
 106                stderr);
 107       return 77;
 108     }
 109   ASSERT (lstat (BASE "link", &st1) == 0);
 110   ASSERT (st1.st_mtime != Y2K);
 111   errno = 0;
 112   ASSERT (utime (BASE "link/", NULL) == -1);
 113   ASSERT (errno == ENOTDIR);
 114   {
 115     struct utimbuf ts;
 116     ts.actime = ts.modtime = Y2K;
 117     ASSERT (utime (BASE "link", &ts) == 0);
 118     ASSERT (lstat (BASE "link", &st2) == 0);
 119     /* Can't compare atimes, since lstat() changes symlink atime on cygwin.  */
 120     ASSERT (st1.st_mtime == st2.st_mtime);
 121     ASSERT (stat (BASE "link", &st2) == 0);
 122     ASSERT (st2.st_mtime == Y2K);
 123     ASSERT (get_stat_mtime_ns (&st2) == 0);
 124   }
 125 
 126   /* Cleanup.  */
 127   ASSERT (unlink (BASE "link") == 0);
 128   ASSERT (unlink (BASE "file") == 0);
 129   return 0;
 130 }
 131 
 132 int
 133 main (void)
     /* [previous][next][first][last][top][bottom][index][help] */
 134 {
 135   int result1; /* Skip because of no symlink support.  */
 136 
 137   /* Clean up any trash from prior testsuite runs.  */
 138   ignore_value (system ("rm -rf " BASE "*"));
 139 
 140   result1 = test_utime (true);
 141   return result1;
 142 }

/* [previous][next][first][last][top][bottom][index][help] */