1 // SPDX-License-Identifier: GPL-2.0+
3 * stale_handle.c - attempt to create a stale handle and open it
4 * Copyright (C) 2010 Red Hat, Inc. All Rights reserved.
15 #include <sys/types.h>
18 #include <xfs/handle.h>
21 int main(int argc, char **argv)
27 char fname[MAXPATHLEN];
29 void *handle[NUMFILES];
30 size_t hlen[NUMFILES];
37 fprintf(stderr, "usage: stale_handle test_dir\n");
42 if (stat(test_dir, &st) != 0) {
47 ret = path_to_fshandle(test_dir, (void **)fshandle, &fshlen);
49 perror("path_to_fshandle");
54 * create a large number of files to force allocation of new inode
57 for (i=0; i < NUMFILES; i++) {
58 sprintf(fname, "%s/file%06d", test_dir, i);
59 fd = open(fname, O_RDWR | O_CREAT | O_TRUNC, 0644);
61 printf("Warning (%s,%d), open(%s) failed.\n", __FILE__, __LINE__, fname);
68 /* sync to get the new inodes to hit the disk */
71 /* create the handles */
72 for (i=0; i < NUMFILES; i++) {
73 sprintf(fname, "%s/file%06d", test_dir, i);
74 ret = path_to_handle(fname, &handle[i], &hlen[i]);
76 perror("path_to_handle");
81 /* unlink the files */
82 for (i=0; i < NUMFILES; i++) {
83 sprintf(fname, "%s/file%06d", test_dir, i);
91 /* sync to get log forced for unlink transactions to hit the disk */
94 /* sync once more FTW */
98 * now drop the caches so that unlinked inodes are reclaimed and
99 * buftarg page cache is emptied so that the inode cluster has to be
100 * fetched from disk again for the open_by_handle() call.
102 system("echo 3 > /proc/sys/vm/drop_caches");
105 * now try to open the files by the stored handles. Expecting ENOENT
108 for (i=0; i < NUMFILES; i++) {
110 fd = open_by_handle(handle[i], hlen[i], O_RDWR);
111 if (fd < 0 && (errno == ENOENT || errno == ESTALE)) {
112 free_handle(handle[i], hlen[i]);
116 printf("open_by_handle(%d) opened an unlinked file!\n", i);
119 printf("open_by_handle(%d) returned %d incorrectly on an unlinked file!\n", i, errno);
120 free_handle(handle[i], hlen[i]);