llvm.org GIT mirror llvm / bea1e20
[Support] Test directory iterators and recursive directory iterators with broken symlinks. This commit adds a unit test to the file system tests to verify the behavior of the directory iterator and recursive directory iterator with broken symlinks. This test is Unix only. git-svn-id: https://llvm.org/svn/llvm-project/llvm/trunk@297669 91177308-0d34-0410-b5e6-96231b3b80d8 Juergen Ributzka 3 years ago
1 changed file(s) with 78 addition(s) and 0 deletion(s). Raw diff Collapse all Expand all
777777 ASSERT_NO_ERROR(fs::remove(Twine(TestDirectory) + "/reclevel"));
778778 }
779779
780 #ifdef LLVM_ON_UNIX
781 TEST_F(FileSystemTest, BrokenSymlinkDirectoryIteration) {
782 // Create a known hierarchy to recurse over.
783 ASSERT_NO_ERROR(fs::create_directories(Twine(TestDirectory) + "/symlink"));
784 ASSERT_NO_ERROR(
785 fs::create_link("no_such_file", Twine(TestDirectory) + "/symlink/a"));
786 ASSERT_NO_ERROR(
787 fs::create_directories(Twine(TestDirectory) + "/symlink/b/bb"));
788 ASSERT_NO_ERROR(
789 fs::create_link("no_such_file", Twine(TestDirectory) + "/symlink/b/ba"));
790 ASSERT_NO_ERROR(
791 fs::create_link("no_such_file", Twine(TestDirectory) + "/symlink/b/bc"));
792 ASSERT_NO_ERROR(
793 fs::create_link("no_such_file", Twine(TestDirectory) + "/symlink/c"));
794 ASSERT_NO_ERROR(
795 fs::create_directories(Twine(TestDirectory) + "/symlink/d/dd/ddd"));
796 ASSERT_NO_ERROR(fs::create_link(Twine(TestDirectory) + "/symlink/d/dd",
797 Twine(TestDirectory) + "/symlink/d/da"));
798 ASSERT_NO_ERROR(
799 fs::create_link("no_such_file", Twine(TestDirectory) + "/symlink/e"));
800
801 typedef std::vector v_t;
802 v_t visited;
803
804 // The directory iterator doesn't stat the file, so we should be able to
805 // iterate over the whole directory.
806 std::error_code ec;
807 for (fs::directory_iterator i(Twine(TestDirectory) + "/symlink", ec), e;
808 i != e; i.increment(ec)) {
809 ASSERT_NO_ERROR(ec);
810 visited.push_back(path::filename(i->path()));
811 }
812 std::sort(visited.begin(), visited.end());
813 v_t expected = {"a", "b", "c", "d", "e"};
814 ASSERT_TRUE(visited.size() == expected.size());
815 ASSERT_TRUE(std::equal(visited.begin(), visited.end(), expected.begin()));
816 visited.clear();
817
818 // The recursive directory iterator has to stat the file, so we need to skip
819 // the broken symlinks.
820 for (fs::recursive_directory_iterator
821 i(Twine(TestDirectory) + "/symlink", ec),
822 e;
823 i != e; i.increment(ec)) {
824 ASSERT_NO_ERROR(ec);
825
826 fs::file_status status;
827 if (i->status(status) == std::errc::no_such_file_or_directory) {
828 i.no_push();
829 continue;
830 }
831
832 visited.push_back(path::filename(i->path()));
833 }
834 std::sort(visited.begin(), visited.end());
835 expected = {"b", "bb", "d", "da", "dd", "ddd", "ddd"};
836 ASSERT_TRUE(visited.size() == expected.size());
837 ASSERT_TRUE(std::equal(visited.begin(), visited.end(), expected.begin()));
838 visited.clear();
839
840 // This recursive directory iterator doesn't follow symlinks, so we don't need
841 // to skip them.
842 for (fs::recursive_directory_iterator
843 i(Twine(TestDirectory) + "/symlink", ec, /*follow_symlinks=*/false),
844 e;
845 i != e; i.increment(ec)) {
846 ASSERT_NO_ERROR(ec);
847 visited.push_back(path::filename(i->path()));
848 }
849
850 expected = {"a", "b", "ba", "bb", "bc", "c", "d", "da", "dd", "ddd", "e"};
851 ASSERT_TRUE(visited.size() == expected.size());
852 ASSERT_TRUE(std::equal(visited.begin(), visited.end(), expected.begin()));
853
854 ASSERT_NO_ERROR(fs::remove_directories(Twine(TestDirectory) + "/symlink"));
855 }
856 #endif
857
780858 TEST_F(FileSystemTest, Remove) {
781859 SmallString<64> BaseDir;
782860 SmallString<64> Paths[4];