1 /*
2 *
3 * Copyright (c) International Business Machines Corp., 2002
4 *
5 * This program is free software; you can redistribute it and/or modify
6 * it under the terms of the GNU General Public License as published by
7 * the Free Software Foundation; either version 2 of the License, or
8 * (at your option) any later version.
9 *
10 * This program is distributed in the hope that it will be useful,
11 * but WITHOUT ANY WARRANTY; without even the implied warranty of
12 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See
13 * the GNU General Public License for more details.
14 *
15 * You should have received a copy of the GNU General Public License
16 * along with this program; if not, write to the Free Software
17 * Foundation, Inc., 51 Franklin Street, Fifth Floor, Boston, MA 02110-1301 USA
18 */
19
20 /* 10/31/2002 Port to LTP robbiew@us.ibm.com */
21 /* 06/30/2001 Port to Linux nsharoff@us.ibm.com */
22
23 /*
24 * NAME
25 * test64.c - Test functions for nftw64()
26 */
27
28 #include "nftw64.h"
29
30 extern int callback(const char *path);
31
32 extern pathdata pathdat[];
33 extern struct list mnem[], badlist[];
34 extern char *dirlist[NDIRLISTENTS], *goodlist[];
35 extern int npathdats, ngoods, nbads, nmnem, visit, s2, next_fd[4];
36 extern FILE *temp;
37 /*
38 * void test1A() - tests the assertion:
39 * A call to int nftw64(const char *path, int (*fn)(const char *, const
40 * struct stat *, int, struct FTW *), int depth, int flags) shall
41 * recursively descend the directory hierarchy rooted in path until it
42 * has traversed the whole tree, calling the function fn for each object
43 * in the directory tree, and return 0.
44 */
45
test1A(void)46 void test1A(void)
47 {
48 int i, j, ret;
49 temp = stderr;
50 #ifdef DEBUG
51 fprintf(temp, "TEST: nftw64() succeeds\n");
52 #endif
53
54 visit = 0;
55 if ((ret = nftw64("./tmp/data/dirh", test_func1, MAX_FD, 0)) == -1) {
56 perror("ERROR: nftw64 failed");
57 cleanup_function();
58 fail_exit();
59 }
60
61 if (ret == 999) {
62 cleanup_function();
63 fail_exit();
64 }
65 #ifdef DEBUG
66 fprintf(temp, "TEST: Whole tree traversed\n");
67 #endif
68
69 if (visit != ngoods) {
70 fprintf(temp, "ERROR: Count of objects visited incorrect\n");
71 fprintf(temp, " Expected %d, Received %d\n", ngoods,
72 visit);
73 cleanup_function();
74 fail_exit();
75 }
76
77 for (i = 0; i < visit; i++) {
78 for (j = 0; j < ngoods; j++) {
79 if (strcmp(dirlist[i], goodlist[j]) == 0) {
80 free(dirlist[i]);
81 dirlist[i] = NULL;
82 break;
83 }
84 }
85 }
86
87 for (i = 0; i < visit; i++) {
88 if (dirlist[i] != NULL) {
89 free(dirlist[i]);
90 fprintf(temp, "ERROR: Unexpected visit to %s\n",
91 dirlist[i]);
92 cleanup_function();
93 fail_exit();
94 }
95 }
96 }
97
98 /*
99 * void test2A() - tests the assertion:
100 * A call to int nftw64(const char *path, int (*fn)(const char *, const
101 * struct stat *, int, struct FTW *), int depth, int flags) when flags
102 * contains FTW_PHYS shall not traverse symbolic links.
103 */
104
test2A(void)105 void test2A(void)
106 {
107 int i, ret;
108
109 temp = stderr;
110 #ifdef DEBUG
111 fprintf(temp,
112 "TEST: nftw64 with FTW_PHYS does not follow symbolic links\n");
113 #endif
114
115 visit = 0;
116 if ((ret = nftw64("./tmp/data/dirl", test_func1, MAX_FD, FTW_PHYS))
117 == -1) {
118 perror("nftw64");
119 cleanup_function();
120 fail_exit();
121 }
122
123 if (ret == 999) {
124 cleanup_function();
125 fail_exit();
126 }
127
128 if (visit != NO_LINK_CNT) {
129 fprintf(temp,
130 "ERROR: Expected %d files to be visited. nftw64() visited %d\n",
131 NO_LINK_CNT, visit);
132 cleanup_function();
133 fail_exit();
134 }
135
136 for (i = 0; i < visit; i++) {
137 if (dirlist[i] != NULL)
138 free(dirlist[i]);
139 }
140 }
141
142 /*
143 * void test3A() - tests the assertion:
144 * A call to int nftw64(const char *path, int (*fn)(const char *, const
145 * struct stat *, int, struct FTW *), int depth, int flags) when flags
146 * does not contain FTW_PHYS shall follow links instead of reporting
147 * them and shall not report the same file twice.
148 */
149
test3A(void)150 void test3A(void)
151 {
152 int ret;
153
154 temp = stderr;
155 #ifdef DEBUG
156 fprintf(temp, "TEST: nftw64 without FTW_PHYS follows symbolic links\n");
157 #endif
158
159 visit = 0;
160
161 if ((ret = nftw64("./tmp/data/dirl", test_func3, MAX_FD, 0)) == -1) {
162 perror("nftw64");
163 cleanup_function();
164 fail_exit();
165 }
166 if (ret == 999) {
167 cleanup_function();
168 fail_exit();
169 }
170
171 if (visit != LINK_CNT - 1) {
172 fprintf(temp,
173 "ERROR: Expected %d files to be visited. nftw64() visited %d\n",
174 LINK_CNT - 1, visit);
175 cleanup_function();
176 fail_exit();
177 }
178 }
179
180 /*
181 * void test4A() - tests the assertion:
182 * A call to int nftw64(const char *path, int (*fn)(const char *, const
183 * struct stat *, int, struct FTW *), int depth, int flags) when flags
184 * contains FTW_DEPTH shall report all files in a directory before
185 * reporting the directory.
186 */
187
test4A(void)188 void test4A(void)
189 {
190 char path[] = "./tmp/data/d777";
191 int ret_val;
192
193 temp = stderr;
194 #ifdef DEBUG
195 fprintf(temp, "TEST: Verify traversal with FTW_DEPTH set\n");
196 #endif
197
198 visit = 0;
199 if ((ret_val = nftw64(path, test_func4, MAX_FD, FTW_DEPTH)) == -1) {
200 perror("nftw64");
201 cleanup_function();
202 fail_exit();
203 }
204 if (ret_val != 999) {
205 fprintf(temp, "ERROR: %s never visited\n", path);
206 cleanup_function();
207 fail_exit();
208 }
209
210 if (visit != 2) {
211 fprintf(temp, "ERROR: Visited directory before contents\n");
212 cleanup_function();
213 fail_exit();
214 }
215 }
216
217 /*
218 * void test5A() - tests the assertion:
219 * A call to int nftw64(const char *path, int (*fn)(const char *, const
220 * struct stat *, int, struct FTW *), int depth, int flags) when flags
221 * does not contain FTW_DEPTH shall report a directory before reporting
222 * the files in that directory.
223 */
224
test5A(void)225 void test5A(void)
226 {
227 char path[] = "./tmp/data/d777";
228 int ret_val;
229
230 temp = stderr;
231 #ifdef DEBUG
232 fprintf(temp, "TEST: Verify traversal without FTW_DEPTH set\n");
233 #endif
234
235 visit = 0;
236 if ((ret_val = nftw64(path, test_func4, MAX_FD, 0)) == -1) {
237 perror("nftw64");
238 cleanup_function();
239 fail_exit();
240 }
241 if (ret_val != 999) {
242 fprintf(temp, "ERROR: %s never visited\n", path);
243 cleanup_function();
244 fail_exit();
245 }
246
247 if (visit != 1) {
248 fprintf(temp, "ERROR: Visited contents before directory\n");
249 cleanup_function();
250 fail_exit();
251 }
252 }
253
254 /*
255 * void test6A() - tests the assertion:
256 * A call to int nftw64(const char *path, int (*fn)(const char *, const
257 * struct stat *, int, struct FTW *), int depth, int flags) when flags
258 * contains FTW_CHDIR shall change the current working directory to each
259 * directory as it reports files in that directory.
260 */
261
test6A(void)262 void test6A(void)
263 {
264 char path[PATH_MAX + NAME_MAX];
265 int ret_val;
266
267 if (getcwd(path, sizeof(path)) == NULL) {
268 perror("getcwd");
269 cleanup_function();
270 fail_exit();
271 }
272 (void)strcat(path, "/tmp/data/dirh");
273
274 temp = stderr;
275 #ifdef DEBUG
276 fprintf(temp,
277 "TEST: nftw64 with FTW_CHDIR changes to each dir before reporting files in it\n");
278 #endif
279
280 ret_val = nftw64(path, test_func5, MAX_FD, FTW_CHDIR);
281 if (ret_val == -1) {
282 perror("nftw64");
283 cleanup_function();
284 fail_exit();
285 }
286 if ((ret_val == 998) || (ret_val == 999)) {
287 cleanup_function();
288 fail_exit();
289 }
290 }
291
292 /*
293 * void test7A() - tests the assertion:
294 * A call to int nftw64(const char *path, int (*fn)(const char *, const
295 * struct stat *, int, struct FTW *), int depth, int flags) shall pass
296 * the path-name of the current object as the first argument of the
297 * function fn.
298 */
299
test7A(void)300 void test7A(void)
301 {
302 int ret;
303
304 temp = stderr;
305 #ifdef DEBUG
306 fprintf(temp,
307 "TEST: nftw64 passes pathname as first argument to fn()\n");
308 #endif
309
310 if ((ret = nftw64("./tmp/data/dirg", test_func7, MAX_FD, 0)) == -1) {
311 perror("nftw64");
312 cleanup_function();
313 fail_exit();
314 }
315
316 if (ret == 999) {
317 cleanup_function();
318 fail_exit();
319 }
320 }
321
322 /*
323 * void test8A() - tests the assertion:
324 * A call to int nftw64(const char *path, int (*fn)(const char *, const
325 * struct stat *, int, struct FTW *), int depth, int flags) shall pass a
326 * pointer to a stat structure containing information about the current
327 * object as the second argument to fn.
328 */
329
test8A(void)330 void test8A(void)
331 {
332 int ret;
333
334 temp = stderr;
335 #ifdef DEBUG
336 fprintf(temp,
337 "TEST: nftw64 passes stat struct as second argument to fn()\n");
338 #endif
339
340 if ((ret = nftw64("./tmp/data/dirg", test_func8, MAX_FD, 0)) == -1) {
341 perror("nftw64");
342 cleanup_function();
343 fail_exit();
344 }
345
346 if (ret == 999) {
347 cleanup_function();
348 fail_exit();
349 }
350 }
351
352 /*
353 * void test9A() - tests the assertion:
354 * A call to int nftw64(const char *path, int (*fn)(const char *, const
355 * struct stat *, int, struct FTW *), int depth, int flags) shall pass
356 * FTW_F as the third argument of the function fn when the object is a
357 * file
358 */
359
test9A(void)360 void test9A(void)
361 {
362 int ret;
363
364 temp = stderr;
365 #ifdef DEBUG
366 fprintf(temp,
367 "TEST: nftw64 passes FTW_F as third arg to fn() for files\n");
368 #endif
369
370 if ((ret = nftw64("./tmp/data/dirg", test_func9, MAX_FD, FTW_PHYS))
371 == -1) {
372 perror("nftw64");
373 cleanup_function();
374 fail_exit();
375 }
376
377 if (ret == 999) {
378 cleanup_function();
379 fail_exit();
380 }
381 }
382
383 /*
384 * void test10A() - tests the assertion:
385 * A call to int nftw64(const char *path, int (*fn)(const char *, const
386 * struct stat *, int, struct FTW *), int depth, int flags) shall pass
387 * FTW_D as the third argument of the function fn when the object is a
388 * directory.
389 */
390
test10A(void)391 void test10A(void)
392 {
393 int ret;
394
395 temp = stderr;
396 #ifdef DEBUG
397 fprintf(temp,
398 "TEST: nftw64 passes FTW_D as third arg to fn() when file is directory\n");
399 #endif
400
401 if ((ret = nftw64("./tmp/data/dirg", test_func10, MAX_FD, FTW_PHYS))
402 == -1) {
403 perror("nftw64");
404 cleanup_function();
405 fail_exit();
406 }
407
408 if (ret == 999) {
409 cleanup_function();
410 fail_exit();
411 }
412 }
413
414 /*
415 * void test11A() - tests the assertion:
416 * A call to int nftw64(const char *path, int (*fn)(const char *, const
417 * struct stat *, int, struct FTW *), int depth, int flags) shall pass
418 * FTW_DP as the third argument of the function fn when the object is a
419 * directory and subdirectories have been visited.
420 */
421
test11A(void)422 void test11A(void)
423 {
424 int i, ret;
425
426 for (i = 0; i < nbads; i++)
427 if (badlist[i].i == FTW_D)
428 badlist[i].i = FTW_DP;
429
430 temp = stderr;
431 #ifdef DEBUG
432 fprintf(temp,
433 "TEST: nftw64 passes FTW_DP when file is directory and subdirs already visited\n");
434 #endif
435
436 if ((ret = nftw64("./tmp/data/dirg", test_func11, MAX_FD, FTW_DEPTH |
437 FTW_PHYS)) == -1) {
438 perror("nftw64");
439 cleanup_function();
440 fail_exit();
441 }
442
443 if (ret == 999) {
444 cleanup_function();
445 fail_exit();
446 }
447 }
448
449 /*
450 * void test12A() - tests the assertion:
451 * A call to int nftw64(const char *path, int (*fn)(const char *, const
452 * struct stat *, int, struct FTW *), int depth, int flags) shall pass
453 * FTW_SL as the third argument of the function fn when the object is a
454 * symbolic link.
455 */
456
test12A(void)457 void test12A(void)
458 {
459 int ret;
460
461 temp = stderr;
462 #ifdef DEBUG
463 fprintf(temp,
464 "TEST: nftw64 wth FTW_PHYS passes FTW_SL when file is symlink\n");
465 #endif
466 if ((ret = nftw64("./tmp/data/dirg", test_func12, MAX_FD, FTW_PHYS))
467 == -1) {
468 perror("nftw64");
469 cleanup_function();
470 fail_exit();
471 }
472
473 if (ret == 999) {
474 cleanup_function();
475 fail_exit();
476 }
477 }
478
479 /*
480 * void test13A() - tests the assertion:
481 * A call to int nftw64(const char *path, int (*fn)(const char *, const
482 * struct stat *, int, struct FTW *), int depth, int flags) shall pass
483 * FTW_SLN as the third argument of the function fn when the object is a
484 * symbolic link that does not name an existing file.
485 */
486
test13A(void)487 void test13A(void)
488 {
489 int i, ret;
490
491 if (unlink("./tmp/byebye") == -1) {
492 perror("unlink");
493 cleanup_function();
494 fail_exit();
495 }
496
497 for (i = 0; i < nbads; i++)
498 if (badlist[i].i == FTW_SL)
499 badlist[i].i = FTW_SLN;
500
501 temp = stderr;
502 #ifdef DEBUG
503 fprintf(temp, "TEST: nftw64 with FTW_PHYS passes FTW_SLN when file");
504 fprintf(temp, " is symlink pointing \n to non-existent file\n");
505 #endif
506
507 if ((ret = nftw64("./tmp/data/dirg", test_func13, MAX_FD, FTW_PHYS))
508 == -1) {
509 perror("nftw64");
510 cleanup_function();
511 fail_exit();
512 }
513
514 if (ret == 999) {
515 cleanup_function();
516 fail_exit();
517 }
518 }
519
520 /*
521 * void test14A() - tests the assertion:
522 * A call to int nftw64(const char *path, int (*fn)(const char *, const
523 * struct stat *, int, struct FTW *), int depth, int flags) shall pass
524 * FTW_DNR as the third argument of the function fn when the object is a
525 * directory that cannot be read.
526 */
527
test14A(void)528 void test14A(void)
529 {
530 int ret;
531
532 temp = stderr;
533 #ifdef DEBUG
534 fprintf(temp,
535 "TEST: nftw64 passes FTW_DNR when file is directory that cannot be read\n");
536 #endif
537
538 if ((ret = nftw64("./tmp/data/d333", test_func14, MAX_FD, 0)) == -1) {
539 perror("nftw64");
540 cleanup_function();
541 fail_exit();
542 }
543
544 if (ret == 999) {
545 cleanup_function();
546 fail_exit();
547 }
548 }
549
550 /*
551 * void test15A() - tests the assertion:
552 * A call to int nftw64(const char *path, int (*fn)(const char *, const
553 * struct stat *, int, struct FTW *), int depth, int flags) shall pass
554 * FTW_NS as the third argument of the function fn when stat() failed on
555 * the object because of lack of appropriate permission.
556 */
557
test15A(void)558 void test15A(void)
559 {
560 int ret;
561
562 temp = stderr;
563 #ifdef DEBUG
564 fprintf(temp,
565 "TEST: nftw64(path, fn, depth, FTW_PHYS) passes FTW_NS when dir unsearchable\n");
566 #endif
567
568 if ((ret = nftw64("./tmp/data/d666", test_func15, MAX_FD, FTW_PHYS))
569 == -1) {
570 perror("nftw64");
571 cleanup_function();
572 fail_exit();
573 }
574
575 if (ret == 999) {
576 cleanup_function();
577 fail_exit();
578 }
579 }
580
581 /*
582 * void test16A() - tests the assertion:
583 * A call to int nftw64(const char *path, int (*fn)(const char *, const
584 * struct stat *, int, struct FTW *), int depth, int flags) shall pass a
585 * structure which contains the offset into the pathname of the object
586 * and the depth relative to the root of the walk starting from 0 as the
587 * fourth argument of the function fn.
588 */
589
test16A(void)590 void test16A(void)
591 {
592 char path[PATH_MAX + NAME_MAX];
593 char orig[PATH_MAX + NAME_MAX];
594
595 if (getcwd(orig, sizeof(orig)) == NULL) {
596 perror("getcwd on original wd");
597 cleanup_function();
598 fail_exit();
599 }
600 strcpy(path, orig);
601 (void)strcat(path, "/tmp/data/dirg");
602
603 temp = stderr;
604 #ifdef DEBUG
605 fprintf(temp, "TEST: nftw64 with absolute pathname %s\n", path);
606 #endif
607
608 if ((s2 = nftw64(path, test_func16, MAX_FD, 0)) == -1) {
609 perror("nftw64");
610 cleanup_function();
611 fail_exit();
612 }
613 if (s2 == 999) {
614 cleanup_function();
615 fail_exit();
616 }
617
618 (void)strcpy(path, "./tmp/data/dirg");
619
620 #ifdef DEBUG
621 fprintf(temp, "TEST: nftw64 with relative pathname %s\n", path);
622 #endif
623
624 if ((s2 = nftw64(path, test_func16, MAX_FD, 0)) == -1) {
625 perror("nftw64");
626 cleanup_function();
627 fail_exit();
628 }
629
630 if (s2 == 999) {
631 cleanup_function();
632 fail_exit();
633 }
634 }
635
636 /*
637 * void test17A() - tests the assertion:
638 * A call to int nftw64(const char *path, int (*fn)(const char *, const
639 * struct stat *, int, struct FTW *), int depth, int flags) shall pass
640 * FTW_SL as the third argument to the function fn if and only if the
641 * FTW_PHYS flag is included in flags.
642 */
643
test17A(void)644 void test17A(void)
645 {
646 int ret;
647
648 visit = 0;
649
650 temp = stderr;
651 #ifdef DEBUG
652 fprintf(temp, "TEST: nftw64 with FTW_PHYS passes FTW_SL for symlink\n");
653 #endif
654
655 if ((ret = nftw64("./tmp/data/dirl", test_func17, MAX_FD, FTW_PHYS))
656 == -1) {
657 perror("nftw64");
658 cleanup_function();
659 fail_exit();
660 }
661 if (ret != 999) {
662 fprintf(temp, "ERROR: nftw64() failed to find symbolic link\n");
663 cleanup_function();
664 fail_exit();
665 }
666
667 visit = 0;
668
669 #ifdef DEBUG
670 fprintf(temp,
671 "TEST: nftw64 without FTW_PHYS does not pass FTW_SL for symlink\n");
672 #endif
673
674 if ((ret = nftw64("./tmp/data/dirl", test_func17, MAX_FD, 0)) == -1) {
675 perror("nftw64");
676 cleanup_function();
677 fail_exit();
678 }
679 if (ret == 999) {
680 fprintf(temp, "ERROR: nftw64() found symbolic link\n");
681 cleanup_function();
682 fail_exit();
683 }
684 }
685
686 /*
687 * void test18A() - tests the assertion:
688 * A call to int nftw64(const char *path, int (*fn)(const char *, const
689 * struct stat *, int, struct FTW *), int depth, int flags) shall pass
690 * FTW_SLN as the third argument to the function fn if and only if the
691 * FTW_PHYS flag is not included in flags.
692 */
693
test18A(void)694 void test18A(void)
695 {
696 int ret;
697
698 unlink("./tmp/byebye");
699
700 visit = 0;
701
702 temp = stderr;
703 #ifdef DEBUG
704 fprintf(temp, "TEST: nftw64 with FTW_PHYS does not pass FTW_SLN\n");
705 #endif
706
707 if ((ret = nftw64("./tmp/data/dirg", test_func18, MAX_FD, FTW_PHYS))
708 == -1) {
709 perror("nftw64");
710 cleanup_function();
711 fail_exit();
712 }
713 if (ret == 999) {
714 fprintf(temp, "ERROR: nftw64() passed FTW_SLN\n");
715 cleanup_function();
716 fail_exit();
717 }
718
719 visit = 0;
720
721 #ifdef DEBUG
722 fprintf(temp, "TEST: nftw64 without FTW_PHYS passes FTW_SLN\n");
723 #endif
724
725 if ((ret = nftw64("./tmp/data/dirg", test_func18, MAX_FD, 0)) == -1) {
726 perror("nftw64");
727 cleanup_function();
728 fail_exit();
729 }
730
731 if (visit == 1) {
732 if (ret == 999) {
733 /* Test is passed */
734 return;
735 } else {
736 fprintf(temp, "ERROR: nftw64 passed FTW_SLN but did");
737 fprintf(temp, "not return value returned by fn()\n");
738 cleanup_function();
739 fail_exit();
740 }
741 } else {
742 fprintf(temp, "ERROR: nftw64() did not pass FTW_SLN\n");
743 cleanup_function();
744 fail_exit();
745 }
746 }
747
748 /*
749 * void test19A() - tests the assertion:
750 * On a call to int nftw64(const char *path, int (*fn)(const char *, const
751 * struct stat *, int, struct FTW *), int depth, int flags) when the
752 * third argument passed to the function fn is FTW_DNR then the
753 * descendants of the directory shall not be processed.
754 */
755
test19A(void)756 void test19A(void)
757 {
758 int ret_val;
759
760 temp = stderr;
761 #ifdef DEBUG
762 fprintf(temp,
763 "TEST: Can not traverse directory with no read permission\n");
764 #endif
765
766 visit = 0;
767
768 ret_val = nftw64("./tmp/data/d333", test_func19, MAX_FD, 0);
769 if (ret_val == -1) {
770 perror("nftw64");
771 cleanup_function();
772 fail_exit();
773 }
774
775 if (ret_val == 999) {
776 cleanup_function();
777 fail_exit();
778 }
779 #ifdef DEBUG
780 fprintf(temp, "TEST: fn only be called once\n");
781 #endif
782
783 if (visit != 1) {
784 fprintf(temp, "ERROR: %s",
785 "Directory without read permission allows traversing\n");
786 fprintf(temp, " Visited %d files\n", visit);
787 cleanup_function();
788 fail_exit();
789 }
790 }
791
792 /*
793 * void test20A() - tests the assertion:
794 * A call to int nftw64(const char *path, int (*fn)(const char *, const
795 * struct stat *, int, struct FTW *), int depth, int flags) shall close
796 * any file descriptors or directory streams used to traverse the
797 * directory tree.
798 */
799
test20A(void)800 void test20A(void)
801 {
802 int fd, nfd;
803
804 temp = stderr;
805 #ifdef DEBUG
806 fprintf(temp, "TEST: File descriptors used in traversal are closed\n");
807 #endif
808
809 if ((fd = open("./tmp/data/dirh", O_RDONLY)) == -1) {
810 perror("close");
811 cleanup_function();
812 fail_exit();
813 }
814
815 if (close(fd) == -1) {
816 perror("close");
817 cleanup_function();
818 fail_exit();
819 }
820
821 if (nftw64("./tmp/data/dirh", test_func20, 1, 0) == -1) {
822 perror("nftw64");
823 cleanup_function();
824 fail_exit();
825 }
826
827 if ((nfd = open("./tmp/data/dirh", O_RDONLY)) == -1) {
828 perror("open");
829 cleanup_function();
830 fail_exit();
831 }
832
833 if (nfd != fd) {
834 fprintf(temp, "ERROR: %s,fd == %d ofd = %d",
835 "nftw64 did not close all file descriptors used in traversal\n",
836 nfd, fd);
837 cleanup_function();
838 fail_exit();
839 }
840
841 if (close(nfd) == -1) {
842 perror("close");
843 cleanup_function();
844 fail_exit();
845 }
846 }
847
848 /*
849 * void test21A() - tests the assertion:
850 * On a call to int nftw64(const char *path, int (*fn)(const char *, const
851 * struct stat *, int, struct FTW *), int depth, int flags) shall
852 * be the maximum number of file descriptors used for the search.
853 */
854
test21A(void)855 void test21A(void)
856 {
857 char path[] = "./tmp/data/dirh";
858 int ret_val;
859
860 temp = stderr;
861 #ifdef DEBUG
862 fprintf(temp,
863 "TEST: No more than depth file descriptors used in traversal\n");
864 #endif
865
866 /*this is the fd we expect if 0 are used */
867 if ((next_fd[0] = open(path, O_RDONLY)) == -1) {
868 perror("open next_fd[0]");
869 cleanup_function();
870 fail_exit();
871 }
872
873 /*this is the fd we expect if 1 is used */
874 if ((next_fd[1] = open(path, O_RDONLY)) == -1) {
875 perror("open next_fd[1]");
876 cleanup_function();
877 fail_exit();
878 }
879
880 if (close(next_fd[0]) == -1) {
881 perror("close next_fd[0]");
882 cleanup_function();
883 fail_exit();
884 }
885
886 if (close(next_fd[1]) == -1) {
887 perror("close next_fd[1]");
888 cleanup_function();
889 fail_exit();
890 }
891
892 visit = 0;
893 ret_val = nftw64(path, test_func21, 1, 0);
894 if (ret_val == -1) {
895 perror("nftw64");
896 cleanup_function();
897 fail_exit();
898 }
899
900 if (ret_val == 999) {
901 cleanup_function();
902 fail_exit();
903 }
904 }
905
906 /*
907 * void test22A() - tests the assertion:
908 * A call to int nftw64(const char *path, int (*fn)(const char *, const
909 * struct stat *, int, struct FTW *), int depth, int flags) shall use at
910 * most one file descriptor for each directory level.
911 */
912
test22A(void)913 void test22A(void)
914 {
915 char path[] = "./tmp/data/dirh";
916 int ret_val, i;
917
918 for (i = 0; i < 4; i++) {
919 if ((next_fd[i] = open(path, O_RDONLY)) == -1) {
920 perror("open");
921 cleanup_function();
922 fail_exit();
923 }
924 }
925
926 for (i = 0; i < 4; i++) {
927 if (close(next_fd[i]) == -1) {
928 perror("close");
929 cleanup_function();
930 fail_exit();
931 }
932 }
933
934 visit = 0;
935
936 temp = stderr;
937 #ifdef DEBUG
938 fprintf(temp,
939 "TEST: No more than 1 fd per level is used in traversal\n");
940 #endif
941
942 ret_val = nftw64(path, test_func22, MAX_FD, 0);
943
944 if (ret_val == -1) {
945 perror("nftw64");
946 cleanup_function();
947 fail_exit();
948 }
949
950 if (ret_val == 999) {
951 cleanup_function();
952 fail_exit();
953 }
954 }
955
956 /*
957 * void test23A() - tests the assertion:
958 * A call to int nftw64(const char *path, int (*fn)(const char *, const
959 * struct stat *, int, struct FTW *), int depth, int flags) when the
960 * function fn returns a non-zero value shall stop and return the value
961 * returned by fn.
962 */
963
test23A(void)964 void test23A(void)
965 {
966 int ret;
967
968 visit = 0;
969
970 temp = stderr;
971 #ifdef DEBUG
972 fprintf(temp,
973 "TEST: The function nftw64 should return with value set by fn\n");
974 #endif
975
976 if ((ret = nftw64("./tmp/data/dirh", test_func23, MAX_FD, FTW_PHYS))
977 == -1) {
978 perror("nftw64");
979 cleanup_function();
980 fail_exit();
981 }
982
983 if (ret != 999) {
984 fprintf(temp,
985 "ERROR: nftw64 did not return value returned by fn()\n");
986 cleanup_function();
987 fail_exit();
988 }
989 if (visit != 4) {
990 fprintf(temp,
991 "ERROR: nftw64() did not return immediately on non-zero fn() return\n");
992 cleanup_function();
993 fail_exit();
994 }
995 }
996
997 /*
998 * void test24A() - tests the assertion:
999 * ENAMETOOLONG in errno and return -1 on a call to int nftw64(const char
1000 * *path, int (*fn)(const char *, const struct stat *, int, struct FTW
1001 * *), int depth, int flags) when the length of path exceeds PATH_MAX.
1002 */
1003
test24A(void)1004 void test24A(void)
1005 {
1006 test_ENAMETOOLONG_path("nftw64", callback, -1);
1007 }
1008
1009 /*
1010 * void test25A() - tests the assertion:
1011 * ENAMETOOLONG in errno and return -1 on a call to int nftw64(const char
1012 * *path, int (*fn)(const char *, const struct stat *, int, struct FTW
1013 * *), int depth, int flags) when a component of path exceeds NAME_MAX.
1014 */
1015
test25A(void)1016 void test25A(void)
1017 {
1018 test_ENAMETOOLONG_name("nftw64", callback, -1);
1019 }
1020
1021 /*
1022 * void test26A() - tests the assertion:
1023 * ENOENT in errno and return -1 on a call to int nftw64(const char *path,
1024 * int (*fn)(const char *, const struct stat *, int, struct FTW *), int
1025 * depth, int flags) when path points to a file which does not exist.
1026 */
1027
test26A(void)1028 void test26A(void)
1029 {
1030 temp = stderr;
1031 #ifdef DEBUG
1032 fprintf(temp, "TEST: [ENOENT] && -1 returned by nftw64\n");
1033 #endif
1034
1035 test_ENOENT_nofile("nftw64", callback, -1);
1036 }
1037
1038 /*
1039 * void test27A() - tests the assertion:
1040 * ENOENT in errno and return -1 on a call to int nftw64(const char *path,
1041 * int (*fn)(const char *, const struct stat *, int, struct FTW *), int
1042 * depth, int flags) when path points to an empty string.
1043 */
1044
test27A(void)1045 void test27A(void)
1046 {
1047 temp = stderr;
1048 #ifdef DEBUG
1049 fprintf(temp, "TEST: The function nftw64 should return with a -1\n");
1050 #endif
1051
1052 test_ENOENT_empty("nftw64", callback, -1);
1053 }
1054
1055 /*
1056 * void test28A() - tests the assertion:
1057 * ENOTDIR in errno and return -1 on a call to int nftw64(const char
1058 * *path, int (*fn)(const char *, const struct stat *, int, struct FTW
1059 * *), int depth, int flags) when path is not a directory.
1060 */
1061
test28A(void)1062 void test28A(void)
1063 {
1064 temp = stderr;
1065 #ifdef DEBUG
1066 fprintf(temp, "TEST: [ENOTDIR] && -1 returned by nftw64\n");
1067 #endif
1068
1069 test_ENOTDIR("nftw64", callback, -1);
1070 }
1071
1072 /*
1073 * void test29A() - tests the assertion:
1074 * EACCES in errno and return -1 on a call to int nftw64(const char *path,
1075 * int (*fn)(const char *, const struct stat *, int, struct FTW *), int
1076 * depth, int flags) when search permission is denied for any component
1077 * of path.
1078 */
1079
test29A(void)1080 void test29A(void)
1081 {
1082 if (chmod("./tmp/data/d333", (mode_t) S_IRUSR) == -1) {
1083 perror("chmod");
1084 cleanup_function();
1085 fail_exit();
1086 }
1087
1088 temp = stderr;
1089 #ifdef DEBUG
1090 fprintf(temp, "TEST: [EACCES] && -1 returned by nftw64\n");
1091 #endif
1092
1093 test_ENOTDIR("nftw64", callback, -1);
1094 }
1095
1096 /*
1097 * void test30A() - tests the assertion:
1098 * EACCES in errno and return -1 on a call to int nftw64(const char *path,
1099 * int (*fn)(const char *, const struct stat *, int, struct FTW *), int
1100 * depth, int flags) when read permission is denied for path.
1101 */
1102
test30A(void)1103 void test30A(void)
1104 {
1105 if (chmod("./tmp/data/d333", (mode_t) S_IXUSR) == -1) {
1106 perror("chmod");
1107 cleanup_function();
1108 fail_exit();
1109 }
1110
1111 temp = stderr;
1112 #ifdef DEBUG
1113 fprintf(temp, "TEST: [EACCES] && -1 returned by nftw64\n");
1114 #endif
1115
1116 test_ENOTDIR("nftw64", callback, -1);
1117 }
1118