summaryrefslogtreecommitdiffstats
path: root/base
diff options
context:
space:
mode:
authordbeam@chromium.org <dbeam@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2013-05-08 05:46:20 +0000
committerdbeam@chromium.org <dbeam@chromium.org@0039d316-1c4b-4281-b951-d872f2087c98>2013-05-08 05:46:20 +0000
commit9e66a9b94a40eeeeb52c47c83990b0766e1b7ceb (patch)
tree0818f910c522fb5bda00cab55412201251db32f7 /base
parentad5b14e00b36aab6e2b2d6aba8477a5dd9a11998 (diff)
downloadchromium_src-9e66a9b94a40eeeeb52c47c83990b0766e1b7ceb.zip
chromium_src-9e66a9b94a40eeeeb52c47c83990b0766e1b7ceb.tar.gz
chromium_src-9e66a9b94a40eeeeb52c47c83990b0766e1b7ceb.tar.bz2
Revert 198820 "Move FileEnumerator to its own file, do some refa..."
Broke both windows clobber and official builders' compile with this error: 771>Link: 771> Creating library ..\..\..\build\Release\lib\gcp_portmon64.lib and object ..\..\..\build\Release\lib\gcp_portmon64.exp 771>base.lib(path_service.obj) : fatalerror LNK1112: module machine type 'X86' conflicts with target machine type 'x64' 771> 771>Build FAILED. > Move FileEnumerator to its own file, do some refactoring. > > It creates a class FileInfo to contain the details rather than using a platform-specific typedef. This allows the accessors GetName, GetSize, etc. to be moved directly to this class (previously they were static helpers on the FileEnumerator class) which makes a bunch of code much cleaner. It also gives reasonable getting and initialization which the previous version lacked. > > BUG=175002 > R=rvargas@chromium.org > > Review URL: https://codereview.chromium.org/13165005 TBR=brettw@chromium.org Review URL: https://codereview.chromium.org/14824006 git-svn-id: svn://svn.chromium.org/chrome/trunk/src@198850 0039d316-1c4b-4281-b951-d872f2087c98
Diffstat (limited to 'base')
-rw-r--r--base/base.gypi5
-rw-r--r--base/file_util.cc29
-rw-r--r--base/file_util.h114
-rw-r--r--base/file_util_posix.cc178
-rw-r--r--base/file_util_unittest.cc42
-rw-r--r--base/file_util_win.cc133
-rw-r--r--base/files/file_enumerator.cc21
-rw-r--r--base/files/file_enumerator.h156
-rw-r--r--base/files/file_enumerator_posix.cc160
-rw-r--r--base/files/file_enumerator_win.cc149
-rw-r--r--base/test/test_file_util_posix.cc3
11 files changed, 457 insertions, 533 deletions
diff --git a/base/base.gypi b/base/base.gypi
index be869ce..7194f24 100644
--- a/base/base.gypi
+++ b/base/base.gypi
@@ -159,10 +159,6 @@
'files/dir_reader_fallback.h',
'files/dir_reader_linux.h',
'files/dir_reader_posix.h',
- 'files/file_enumerator.cc',
- 'files/file_enumerator.h',
- 'files/file_enumerator_posix.cc',
- 'files/file_enumerator_win.cc',
'files/file_path.cc',
'files/file_path.h',
'files/file_path_watcher.cc',
@@ -633,7 +629,6 @@
'file_util.cc',
'file_util_posix.cc',
'file_util_proxy.cc',
- 'files/file_enumerator_posix.cc',
'files/file_path_watcher_kqueue.cc',
'memory/shared_memory_posix.cc',
'native_library_posix.cc',
diff --git a/base/file_util.cc b/base/file_util.cc
index 8cdf75b..e76c5c2 100644
--- a/base/file_util.cc
+++ b/base/file_util.cc
@@ -11,7 +11,6 @@
#include <fstream>
-#include "base/files/file_enumerator.h"
#include "base/files/file_path.h"
#include "base/logging.h"
#include "base/string_util.h"
@@ -19,7 +18,6 @@
#include "base/strings/string_piece.h"
#include "base/utf_string_conversions.h"
-using base::FileEnumerator;
using base::FilePath;
namespace {
@@ -167,7 +165,7 @@ bool ReadFileToString(const FilePath& path, std::string* contents) {
bool IsDirectoryEmpty(const FilePath& dir_path) {
FileEnumerator files(dir_path, false,
FileEnumerator::FILES | FileEnumerator::DIRECTORIES);
- if (files.Next().empty())
+ if (files.Next().value().empty())
return true;
return false;
}
@@ -264,9 +262,30 @@ int GetUniquePathNumber(
int64 ComputeDirectorySize(const FilePath& root_path) {
int64 running_size = 0;
FileEnumerator file_iter(root_path, true, FileEnumerator::FILES);
- while (!file_iter.Next().empty())
- running_size += file_iter.GetInfo().GetSize();
+ for (FilePath current = file_iter.Next(); !current.empty();
+ current = file_iter.Next()) {
+ FileEnumerator::FindInfo info;
+ file_iter.GetFindInfo(&info);
+#if defined(OS_WIN)
+ LARGE_INTEGER li = { info.nFileSizeLow, info.nFileSizeHigh };
+ running_size += li.QuadPart;
+#else
+ running_size += info.stat.st_size;
+#endif
+ }
return running_size;
}
+///////////////////////////////////////////////
+// FileEnumerator
+//
+// Note: the main logic is in file_util_<platform>.cc
+
+bool FileEnumerator::ShouldSkip(const FilePath& path) {
+ FilePath::StringType basename = path.BaseName().value();
+ return basename == FILE_PATH_LITERAL(".") ||
+ (basename == FILE_PATH_LITERAL("..") &&
+ !(INCLUDE_DOT_DOT & file_type_));
+}
+
} // namespace
diff --git a/base/file_util.h b/base/file_util.h
index b9bb6eb..4ffd05b 100644
--- a/base/file_util.h
+++ b/base/file_util.h
@@ -20,6 +20,7 @@
#include <stdio.h>
#include <set>
+#include <stack>
#include <string>
#include <vector>
@@ -116,9 +117,9 @@ BASE_EXPORT bool CopyFileUnsafe(const base::FilePath& from_path,
// Copies the given path, and optionally all subdirectories and their contents
// as well.
-//
-// If there are files existing under to_path, always overwrite. Returns true
-// if successful, false otherwise. Wildcards on the names are not supported.
+// If there are files existing under to_path, always overwrite.
+// Returns true if successful, false otherwise.
+// Don't use wildcards on the names, it may stop working without notice.
//
// If you only need to copy a file use CopyFile, it's faster.
BASE_EXPORT bool CopyDirectory(const base::FilePath& from_path,
@@ -421,6 +422,113 @@ class ScopedFDClose {
typedef scoped_ptr_malloc<int, ScopedFDClose> ScopedFD;
#endif // OS_POSIX
+// A class for enumerating the files in a provided path. The order of the
+// results is not guaranteed.
+//
+// DO NOT USE FROM THE MAIN THREAD of your application unless it is a test
+// program where latency does not matter. This class is blocking.
+class BASE_EXPORT FileEnumerator {
+ public:
+#if defined(OS_WIN)
+ typedef WIN32_FIND_DATA FindInfo;
+#elif defined(OS_POSIX)
+ typedef struct {
+ struct stat stat;
+ std::string filename;
+ } FindInfo;
+#endif
+
+ enum FileType {
+ FILES = 1 << 0,
+ DIRECTORIES = 1 << 1,
+ INCLUDE_DOT_DOT = 1 << 2,
+#if defined(OS_POSIX)
+ SHOW_SYM_LINKS = 1 << 4,
+#endif
+ };
+
+ // |root_path| is the starting directory to search for. It may or may not end
+ // in a slash.
+ //
+ // If |recursive| is true, this will enumerate all matches in any
+ // subdirectories matched as well. It does a breadth-first search, so all
+ // files in one directory will be returned before any files in a
+ // subdirectory.
+ //
+ // |file_type|, a bit mask of FileType, specifies whether the enumerator
+ // should match files, directories, or both.
+ //
+ // |pattern| is an optional pattern for which files to match. This
+ // works like shell globbing. For example, "*.txt" or "Foo???.doc".
+ // However, be careful in specifying patterns that aren't cross platform
+ // since the underlying code uses OS-specific matching routines. In general,
+ // Windows matching is less featureful than others, so test there first.
+ // If unspecified, this will match all files.
+ // NOTE: the pattern only matches the contents of root_path, not files in
+ // recursive subdirectories.
+ // TODO(erikkay): Fix the pattern matching to work at all levels.
+ FileEnumerator(const base::FilePath& root_path,
+ bool recursive,
+ int file_type);
+ FileEnumerator(const base::FilePath& root_path,
+ bool recursive,
+ int file_type,
+ const base::FilePath::StringType& pattern);
+ ~FileEnumerator();
+
+ // Returns an empty string if there are no more results.
+ base::FilePath Next();
+
+ // Write the file info into |info|.
+ void GetFindInfo(FindInfo* info);
+
+ // Looks inside a FindInfo and determines if it's a directory.
+ static bool IsDirectory(const FindInfo& info);
+
+ static base::FilePath GetFilename(const FindInfo& find_info);
+ static int64 GetFilesize(const FindInfo& find_info);
+ static base::Time GetLastModifiedTime(const FindInfo& find_info);
+
+ private:
+ // Returns true if the given path should be skipped in enumeration.
+ bool ShouldSkip(const base::FilePath& path);
+
+
+#if defined(OS_WIN)
+ // True when find_data_ is valid.
+ bool has_find_data_;
+ WIN32_FIND_DATA find_data_;
+ HANDLE find_handle_;
+#elif defined(OS_POSIX)
+ struct DirectoryEntryInfo {
+ base::FilePath filename;
+ struct stat stat;
+ };
+
+ // Read the filenames in source into the vector of DirectoryEntryInfo's
+ static bool ReadDirectory(std::vector<DirectoryEntryInfo>* entries,
+ const base::FilePath& source, bool show_links);
+
+ // The files in the current directory
+ std::vector<DirectoryEntryInfo> directory_entries_;
+
+ // The next entry to use from the directory_entries_ vector
+ size_t current_directory_entry_;
+#endif
+
+ base::FilePath root_path_;
+ bool recursive_;
+ int file_type_;
+ base::FilePath::StringType pattern_; // Empty when we want to find
+ // everything.
+
+ // A stack that keeps track of which subdirectories we still need to
+ // enumerate in the breadth-first search.
+ std::stack<base::FilePath> pending_paths_;
+
+ DISALLOW_COPY_AND_ASSIGN(FileEnumerator);
+};
+
#if defined(OS_LINUX)
// Broad categories of file systems as returned by statfs() on Linux.
enum FileSystemType {
diff --git a/base/file_util_posix.cc b/base/file_util_posix.cc
index 68516e4..8b36812 100644
--- a/base/file_util_posix.cc
+++ b/base/file_util_posix.cc
@@ -7,6 +7,7 @@
#include <dirent.h>
#include <errno.h>
#include <fcntl.h>
+#include <fnmatch.h>
#include <libgen.h>
#include <limits.h>
#include <stdio.h>
@@ -31,7 +32,6 @@
#include <fstream>
#include "base/basictypes.h"
-#include "base/files/file_enumerator.h"
#include "base/files/file_path.h"
#include "base/logging.h"
#include "base/memory/scoped_ptr.h"
@@ -58,7 +58,6 @@
#include "base/chromeos/chromeos_version.h"
#endif
-using base::FileEnumerator;
using base::FilePath;
using base::MakeAbsoluteFilePath;
@@ -191,7 +190,10 @@ bool Delete(const FilePath& path, bool recursive) {
FileEnumerator::SHOW_SYM_LINKS);
for (FilePath current = traversal.Next(); success && !current.empty();
current = traversal.Next()) {
- if (traversal.GetInfo().IsDirectory())
+ FileEnumerator::FindInfo info;
+ traversal.GetFindInfo(&info);
+
+ if (S_ISDIR(info.stat.st_mode))
directories.push(current.value());
else
success = (unlink(current.value().c_str()) == 0);
@@ -235,13 +237,14 @@ bool ReplaceFile(const FilePath& from_path, const FilePath& to_path) {
return (rename(from_path.value().c_str(), to_path.value().c_str()) == 0);
}
-bool CopyDirectory(const base::FilePath& from_path,
- const base::FilePath& to_path,
+bool CopyDirectory(const FilePath& from_path,
+ const FilePath& to_path,
bool recursive) {
base::ThreadRestrictions::AssertIOAllowed();
// Some old callers of CopyDirectory want it to support wildcards.
// After some discussion, we decided to fix those callers.
// Break loudly here if anyone tries to do this.
+ // TODO(evanm): remove this once we're sure it's ok.
DCHECK(to_path.value().find('*') == std::string::npos);
DCHECK(from_path.value().find('*') == std::string::npos);
@@ -278,9 +281,9 @@ bool CopyDirectory(const base::FilePath& from_path,
// We have to mimic windows behavior here. |to_path| may not exist yet,
// start the loop with |to_path|.
- struct stat from_stat;
+ FileEnumerator::FindInfo info;
FilePath current = from_path;
- if (stat(from_path.value().c_str(), &from_stat) < 0) {
+ if (stat(from_path.value().c_str(), &info.stat) < 0) {
DLOG(ERROR) << "CopyDirectory() couldn't stat source directory: "
<< from_path.value() << " errno = " << errno;
success = false;
@@ -296,7 +299,7 @@ bool CopyDirectory(const base::FilePath& from_path,
// The Windows version of this function assumes that non-recursive calls
// will always have a directory for from_path.
- DCHECK(recursive || S_ISDIR(from_stat.st_mode));
+ DCHECK(recursive || S_ISDIR(info.stat.st_mode));
while (success && !current.empty()) {
// current is the source path, including from_path, so append
@@ -309,14 +312,14 @@ bool CopyDirectory(const base::FilePath& from_path,
}
}
- if (S_ISDIR(from_stat.st_mode)) {
- if (mkdir(target_path.value().c_str(), from_stat.st_mode & 01777) != 0 &&
+ if (S_ISDIR(info.stat.st_mode)) {
+ if (mkdir(target_path.value().c_str(), info.stat.st_mode & 01777) != 0 &&
errno != EEXIST) {
DLOG(ERROR) << "CopyDirectory() couldn't create directory: "
<< target_path.value() << " errno = " << errno;
success = false;
}
- } else if (S_ISREG(from_stat.st_mode)) {
+ } else if (S_ISREG(info.stat.st_mode)) {
if (!CopyFile(current, target_path)) {
DLOG(ERROR) << "CopyDirectory() couldn't create file: "
<< target_path.value();
@@ -328,8 +331,7 @@ bool CopyDirectory(const base::FilePath& from_path,
}
current = traversal.Next();
- if (!current.empty())
- from_stat = traversal.GetInfo().stat();
+ traversal.GetFindInfo(&info);
}
return success;
@@ -682,6 +684,156 @@ bool SetCurrentDirectory(const FilePath& path) {
return !ret;
}
+///////////////////////////////////////////////
+// FileEnumerator
+
+FileEnumerator::FileEnumerator(const FilePath& root_path,
+ bool recursive,
+ int file_type)
+ : current_directory_entry_(0),
+ root_path_(root_path),
+ recursive_(recursive),
+ file_type_(file_type) {
+ // INCLUDE_DOT_DOT must not be specified if recursive.
+ DCHECK(!(recursive && (INCLUDE_DOT_DOT & file_type_)));
+ pending_paths_.push(root_path);
+}
+
+FileEnumerator::FileEnumerator(const FilePath& root_path,
+ bool recursive,
+ int file_type,
+ const FilePath::StringType& pattern)
+ : current_directory_entry_(0),
+ root_path_(root_path),
+ recursive_(recursive),
+ file_type_(file_type),
+ pattern_(root_path.Append(pattern).value()) {
+ // INCLUDE_DOT_DOT must not be specified if recursive.
+ DCHECK(!(recursive && (INCLUDE_DOT_DOT & file_type_)));
+ // The Windows version of this code appends the pattern to the root_path,
+ // potentially only matching against items in the top-most directory.
+ // Do the same here.
+ if (pattern.empty())
+ pattern_ = FilePath::StringType();
+ pending_paths_.push(root_path);
+}
+
+FileEnumerator::~FileEnumerator() {
+}
+
+FilePath FileEnumerator::Next() {
+ ++current_directory_entry_;
+
+ // While we've exhausted the entries in the current directory, do the next
+ while (current_directory_entry_ >= directory_entries_.size()) {
+ if (pending_paths_.empty())
+ return FilePath();
+
+ root_path_ = pending_paths_.top();
+ root_path_ = root_path_.StripTrailingSeparators();
+ pending_paths_.pop();
+
+ std::vector<DirectoryEntryInfo> entries;
+ if (!ReadDirectory(&entries, root_path_, file_type_ & SHOW_SYM_LINKS))
+ continue;
+
+ directory_entries_.clear();
+ current_directory_entry_ = 0;
+ for (std::vector<DirectoryEntryInfo>::const_iterator
+ i = entries.begin(); i != entries.end(); ++i) {
+ FilePath full_path = root_path_.Append(i->filename);
+ if (ShouldSkip(full_path))
+ continue;
+
+ if (pattern_.size() &&
+ fnmatch(pattern_.c_str(), full_path.value().c_str(), FNM_NOESCAPE))
+ continue;
+
+ if (recursive_ && S_ISDIR(i->stat.st_mode))
+ pending_paths_.push(full_path);
+
+ if ((S_ISDIR(i->stat.st_mode) && (file_type_ & DIRECTORIES)) ||
+ (!S_ISDIR(i->stat.st_mode) && (file_type_ & FILES)))
+ directory_entries_.push_back(*i);
+ }
+ }
+
+ return root_path_.Append(directory_entries_[current_directory_entry_
+ ].filename);
+}
+
+void FileEnumerator::GetFindInfo(FindInfo* info) {
+ DCHECK(info);
+
+ if (current_directory_entry_ >= directory_entries_.size())
+ return;
+
+ DirectoryEntryInfo* cur_entry = &directory_entries_[current_directory_entry_];
+ memcpy(&(info->stat), &(cur_entry->stat), sizeof(info->stat));
+ info->filename.assign(cur_entry->filename.value());
+}
+
+// static
+bool FileEnumerator::IsDirectory(const FindInfo& info) {
+ return S_ISDIR(info.stat.st_mode);
+}
+
+// static
+FilePath FileEnumerator::GetFilename(const FindInfo& find_info) {
+ return FilePath(find_info.filename);
+}
+
+// static
+int64 FileEnumerator::GetFilesize(const FindInfo& find_info) {
+ return find_info.stat.st_size;
+}
+
+// static
+base::Time FileEnumerator::GetLastModifiedTime(const FindInfo& find_info) {
+ return base::Time::FromTimeT(find_info.stat.st_mtime);
+}
+
+bool FileEnumerator::ReadDirectory(std::vector<DirectoryEntryInfo>* entries,
+ const FilePath& source, bool show_links) {
+ base::ThreadRestrictions::AssertIOAllowed();
+ DIR* dir = opendir(source.value().c_str());
+ if (!dir)
+ return false;
+
+#if !defined(OS_LINUX) && !defined(OS_MACOSX) && !defined(OS_BSD) && \
+ !defined(OS_SOLARIS) && !defined(OS_ANDROID)
+ #error Port warning: depending on the definition of struct dirent, \
+ additional space for pathname may be needed
+#endif
+
+ struct dirent dent_buf;
+ struct dirent* dent;
+ while (readdir_r(dir, &dent_buf, &dent) == 0 && dent) {
+ DirectoryEntryInfo info;
+ info.filename = FilePath(dent->d_name);
+
+ FilePath full_name = source.Append(dent->d_name);
+ int ret;
+ if (show_links)
+ ret = lstat(full_name.value().c_str(), &info.stat);
+ else
+ ret = stat(full_name.value().c_str(), &info.stat);
+ if (ret < 0) {
+ // Print the stat() error message unless it was ENOENT and we're
+ // following symlinks.
+ if (!(errno == ENOENT && !show_links)) {
+ DPLOG(ERROR) << "Couldn't stat "
+ << source.Append(dent->d_name).value();
+ }
+ memset(&info.stat, 0, sizeof(info.stat));
+ }
+ entries->push_back(info);
+ }
+
+ closedir(dir);
+ return true;
+}
+
bool NormalizeFilePath(const FilePath& path, FilePath* normalized_path) {
FilePath real_path_result;
if (!RealPath(path, &real_path_result))
diff --git a/base/file_util_unittest.cc b/base/file_util_unittest.cc
index 593ae81..5cfc677 100644
--- a/base/file_util_unittest.cc
+++ b/base/file_util_unittest.cc
@@ -18,7 +18,6 @@
#include "base/base_paths.h"
#include "base/file_util.h"
-#include "base/files/file_enumerator.h"
#include "base/files/file_path.h"
#include "base/files/scoped_temp_dir.h"
#include "base/path_service.h"
@@ -35,7 +34,6 @@
// This macro helps avoid wrapped lines in the test structs.
#define FPL(x) FILE_PATH_LITERAL(x)
-using base::FileEnumerator;
using base::FilePath;
namespace {
@@ -136,7 +134,7 @@ void ChangePosixFilePermissions(const FilePath& path,
const wchar_t bogus_content[] = L"I'm cannon fodder.";
const int FILES_AND_DIRECTORIES =
- FileEnumerator::FILES | FileEnumerator::DIRECTORIES;
+ file_util::FileEnumerator::FILES | file_util::FileEnumerator::DIRECTORIES;
// file_util winds up using autoreleased objects on the Mac, so this needs
// to be a PlatformTest
@@ -154,7 +152,7 @@ class FileUtilTest : public PlatformTest {
// interface to query whether a given file is present.
class FindResultCollector {
public:
- explicit FindResultCollector(FileEnumerator& enumerator) {
+ explicit FindResultCollector(file_util::FileEnumerator& enumerator) {
FilePath cur_file;
while (!(cur_file = enumerator.Next()).value().empty()) {
FilePath::StringType path = cur_file.value();
@@ -919,7 +917,8 @@ TEST_F(FileUtilTest, ChangeDirectoryPermissionsAndEnumerate) {
EXPECT_FALSE(mode & file_util::FILE_PERMISSION_USER_MASK);
// Make sure the file in the directory can't be enumerated.
- FileEnumerator f1(subdir_path, true, FileEnumerator::FILES);
+ file_util::FileEnumerator f1(subdir_path, true,
+ file_util::FileEnumerator::FILES);
EXPECT_TRUE(file_util::PathExists(subdir_path));
FindResultCollector c1(f1);
EXPECT_EQ(c1.size(), 0);
@@ -934,7 +933,8 @@ TEST_F(FileUtilTest, ChangeDirectoryPermissionsAndEnumerate) {
mode & file_util::FILE_PERMISSION_USER_MASK);
// Make sure the file in the directory can be enumerated.
- FileEnumerator f2(subdir_path, true, FileEnumerator::FILES);
+ file_util::FileEnumerator f2(subdir_path, true,
+ file_util::FileEnumerator::FILES);
FindResultCollector c2(f2);
EXPECT_TRUE(c2.HasFile(file_name));
EXPECT_EQ(c2.size(), 1);
@@ -1824,13 +1824,13 @@ TEST_F(FileUtilTest, DetectDirectoryTest) {
TEST_F(FileUtilTest, FileEnumeratorTest) {
// Test an empty directory.
- FileEnumerator f0(temp_dir_.path(), true, FILES_AND_DIRECTORIES);
+ file_util::FileEnumerator f0(temp_dir_.path(), true, FILES_AND_DIRECTORIES);
EXPECT_EQ(f0.Next().value(), FILE_PATH_LITERAL(""));
EXPECT_EQ(f0.Next().value(), FILE_PATH_LITERAL(""));
// Test an empty directory, non-recursively, including "..".
- FileEnumerator f0_dotdot(temp_dir_.path(), false,
- FILES_AND_DIRECTORIES | FileEnumerator::INCLUDE_DOT_DOT);
+ file_util::FileEnumerator f0_dotdot(temp_dir_.path(), false,
+ FILES_AND_DIRECTORIES | file_util::FileEnumerator::INCLUDE_DOT_DOT);
EXPECT_EQ(temp_dir_.path().Append(FILE_PATH_LITERAL("..")).value(),
f0_dotdot.Next().value());
EXPECT_EQ(FILE_PATH_LITERAL(""),
@@ -1857,7 +1857,8 @@ TEST_F(FileUtilTest, FileEnumeratorTest) {
FilePath file2_abs = temp_dir_.path().Append(FILE_PATH_LITERAL("file2.txt"));
// Only enumerate files.
- FileEnumerator f1(temp_dir_.path(), true, FileEnumerator::FILES);
+ file_util::FileEnumerator f1(temp_dir_.path(), true,
+ file_util::FileEnumerator::FILES);
FindResultCollector c1(f1);
EXPECT_TRUE(c1.HasFile(file1));
EXPECT_TRUE(c1.HasFile(file2_abs));
@@ -1866,7 +1867,8 @@ TEST_F(FileUtilTest, FileEnumeratorTest) {
EXPECT_EQ(c1.size(), 4);
// Only enumerate directories.
- FileEnumerator f2(temp_dir_.path(), true, FileEnumerator::DIRECTORIES);
+ file_util::FileEnumerator f2(temp_dir_.path(), true,
+ file_util::FileEnumerator::DIRECTORIES);
FindResultCollector c2(f2);
EXPECT_TRUE(c2.HasFile(dir1));
EXPECT_TRUE(c2.HasFile(dir2));
@@ -1874,17 +1876,17 @@ TEST_F(FileUtilTest, FileEnumeratorTest) {
EXPECT_EQ(c2.size(), 3);
// Only enumerate directories non-recursively.
- FileEnumerator f2_non_recursive(
- temp_dir_.path(), false, FileEnumerator::DIRECTORIES);
+ file_util::FileEnumerator f2_non_recursive(
+ temp_dir_.path(), false, file_util::FileEnumerator::DIRECTORIES);
FindResultCollector c2_non_recursive(f2_non_recursive);
EXPECT_TRUE(c2_non_recursive.HasFile(dir1));
EXPECT_TRUE(c2_non_recursive.HasFile(dir2));
EXPECT_EQ(c2_non_recursive.size(), 2);
// Only enumerate directories, non-recursively, including "..".
- FileEnumerator f2_dotdot(temp_dir_.path(), false,
- FileEnumerator::DIRECTORIES |
- FileEnumerator::INCLUDE_DOT_DOT);
+ file_util::FileEnumerator f2_dotdot(temp_dir_.path(), false,
+ file_util::FileEnumerator::DIRECTORIES |
+ file_util::FileEnumerator::INCLUDE_DOT_DOT);
FindResultCollector c2_dotdot(f2_dotdot);
EXPECT_TRUE(c2_dotdot.HasFile(dir1));
EXPECT_TRUE(c2_dotdot.HasFile(dir2));
@@ -1893,7 +1895,7 @@ TEST_F(FileUtilTest, FileEnumeratorTest) {
EXPECT_EQ(c2_dotdot.size(), 3);
// Enumerate files and directories.
- FileEnumerator f3(temp_dir_.path(), true, FILES_AND_DIRECTORIES);
+ file_util::FileEnumerator f3(temp_dir_.path(), true, FILES_AND_DIRECTORIES);
FindResultCollector c3(f3);
EXPECT_TRUE(c3.HasFile(dir1));
EXPECT_TRUE(c3.HasFile(dir2));
@@ -1905,7 +1907,7 @@ TEST_F(FileUtilTest, FileEnumeratorTest) {
EXPECT_EQ(c3.size(), 7);
// Non-recursive operation.
- FileEnumerator f4(temp_dir_.path(), false, FILES_AND_DIRECTORIES);
+ file_util::FileEnumerator f4(temp_dir_.path(), false, FILES_AND_DIRECTORIES);
FindResultCollector c4(f4);
EXPECT_TRUE(c4.HasFile(dir2));
EXPECT_TRUE(c4.HasFile(dir2));
@@ -1914,7 +1916,7 @@ TEST_F(FileUtilTest, FileEnumeratorTest) {
EXPECT_EQ(c4.size(), 4);
// Enumerate with a pattern.
- FileEnumerator f5(temp_dir_.path(), true, FILES_AND_DIRECTORIES,
+ file_util::FileEnumerator f5(temp_dir_.path(), true, FILES_AND_DIRECTORIES,
FILE_PATH_LITERAL("dir*"));
FindResultCollector c5(f5);
EXPECT_TRUE(c5.HasFile(dir1));
@@ -1926,7 +1928,7 @@ TEST_F(FileUtilTest, FileEnumeratorTest) {
// Make sure the destructor closes the find handle while in the middle of a
// query to allow TearDown to delete the directory.
- FileEnumerator f6(temp_dir_.path(), true, FILES_AND_DIRECTORIES);
+ file_util::FileEnumerator f6(temp_dir_.path(), true, FILES_AND_DIRECTORIES);
EXPECT_FALSE(f6.Next().value().empty()); // Should have found something
// (we don't care what).
}
diff --git a/base/file_util_win.cc b/base/file_util_win.cc
index b166322..964302a 100644
--- a/base/file_util_win.cc
+++ b/base/file_util_win.cc
@@ -595,6 +595,139 @@ bool SetCurrentDirectory(const FilePath& directory) {
return ret != 0;
}
+///////////////////////////////////////////////
+// FileEnumerator
+
+FileEnumerator::FileEnumerator(const FilePath& root_path,
+ bool recursive,
+ int file_type)
+ : recursive_(recursive),
+ file_type_(file_type),
+ has_find_data_(false),
+ find_handle_(INVALID_HANDLE_VALUE) {
+ // INCLUDE_DOT_DOT must not be specified if recursive.
+ DCHECK(!(recursive && (INCLUDE_DOT_DOT & file_type_)));
+ memset(&find_data_, 0, sizeof(find_data_));
+ pending_paths_.push(root_path);
+}
+
+FileEnumerator::FileEnumerator(const FilePath& root_path,
+ bool recursive,
+ int file_type,
+ const FilePath::StringType& pattern)
+ : recursive_(recursive),
+ file_type_(file_type),
+ has_find_data_(false),
+ pattern_(pattern),
+ find_handle_(INVALID_HANDLE_VALUE) {
+ // INCLUDE_DOT_DOT must not be specified if recursive.
+ DCHECK(!(recursive && (INCLUDE_DOT_DOT & file_type_)));
+ memset(&find_data_, 0, sizeof(find_data_));
+ pending_paths_.push(root_path);
+}
+
+FileEnumerator::~FileEnumerator() {
+ if (find_handle_ != INVALID_HANDLE_VALUE)
+ FindClose(find_handle_);
+}
+
+void FileEnumerator::GetFindInfo(FindInfo* info) {
+ DCHECK(info);
+
+ if (!has_find_data_)
+ return;
+
+ memcpy(info, &find_data_, sizeof(*info));
+}
+
+// static
+bool FileEnumerator::IsDirectory(const FindInfo& info) {
+ return (info.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) != 0;
+}
+
+// static
+FilePath FileEnumerator::GetFilename(const FindInfo& find_info) {
+ return FilePath(find_info.cFileName);
+}
+
+// static
+int64 FileEnumerator::GetFilesize(const FindInfo& find_info) {
+ ULARGE_INTEGER size;
+ size.HighPart = find_info.nFileSizeHigh;
+ size.LowPart = find_info.nFileSizeLow;
+ DCHECK_LE(size.QuadPart, std::numeric_limits<int64>::max());
+ return static_cast<int64>(size.QuadPart);
+}
+
+// static
+base::Time FileEnumerator::GetLastModifiedTime(const FindInfo& find_info) {
+ return base::Time::FromFileTime(find_info.ftLastWriteTime);
+}
+
+FilePath FileEnumerator::Next() {
+ base::ThreadRestrictions::AssertIOAllowed();
+
+ while (has_find_data_ || !pending_paths_.empty()) {
+ if (!has_find_data_) {
+ // The last find FindFirstFile operation is done, prepare a new one.
+ root_path_ = pending_paths_.top();
+ pending_paths_.pop();
+
+ // Start a new find operation.
+ FilePath src = root_path_;
+
+ if (pattern_.empty())
+ src = src.Append(L"*"); // No pattern = match everything.
+ else
+ src = src.Append(pattern_);
+
+ find_handle_ = FindFirstFile(src.value().c_str(), &find_data_);
+ has_find_data_ = true;
+ } else {
+ // Search for the next file/directory.
+ if (!FindNextFile(find_handle_, &find_data_)) {
+ FindClose(find_handle_);
+ find_handle_ = INVALID_HANDLE_VALUE;
+ }
+ }
+
+ if (INVALID_HANDLE_VALUE == find_handle_) {
+ has_find_data_ = false;
+
+ // This is reached when we have finished a directory and are advancing to
+ // the next one in the queue. We applied the pattern (if any) to the files
+ // in the root search directory, but for those directories which were
+ // matched, we want to enumerate all files inside them. This will happen
+ // when the handle is empty.
+ pattern_ = FilePath::StringType();
+
+ continue;
+ }
+
+ FilePath cur_file(find_data_.cFileName);
+ if (ShouldSkip(cur_file))
+ continue;
+
+ // Construct the absolute filename.
+ cur_file = root_path_.Append(find_data_.cFileName);
+
+ if (find_data_.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) {
+ if (recursive_) {
+ // If |cur_file| is a directory, and we are doing recursive searching,
+ // add it to pending_paths_ so we scan it after we finish scanning this
+ // directory.
+ pending_paths_.push(cur_file);
+ }
+ if (file_type_ & FileEnumerator::DIRECTORIES)
+ return cur_file;
+ } else if (file_type_ & FileEnumerator::FILES) {
+ return cur_file;
+ }
+ }
+
+ return FilePath();
+}
+
bool NormalizeFilePath(const FilePath& path, FilePath* real_path) {
base::ThreadRestrictions::AssertIOAllowed();
FilePath mapped_file;
diff --git a/base/files/file_enumerator.cc b/base/files/file_enumerator.cc
deleted file mode 100644
index e49f465..0000000
--- a/base/files/file_enumerator.cc
+++ /dev/null
@@ -1,21 +0,0 @@
-// Copyright (c) 2013 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#include "base/files/file_enumerator.h"
-
-#include "base/file_util.h"
-
-namespace base {
-
-FileEnumerator::FileInfo::~FileInfo() {
-}
-
-bool FileEnumerator::ShouldSkip(const FilePath& path) {
- FilePath::StringType basename = path.BaseName().value();
- return basename == FILE_PATH_LITERAL(".") ||
- (basename == FILE_PATH_LITERAL("..") &&
- !(INCLUDE_DOT_DOT & file_type_));
-}
-
-} // namespace base
diff --git a/base/files/file_enumerator.h b/base/files/file_enumerator.h
deleted file mode 100644
index 3834281..0000000
--- a/base/files/file_enumerator.h
+++ /dev/null
@@ -1,156 +0,0 @@
-// Copyright (c) 2012 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#ifndef BASE_FILES_FILE_ENUMERATOR_H_
-#define BASE_FILES_FILE_ENUMERATOR_H_
-
-#include <stack>
-#include <vector>
-
-#include "base/base_export.h"
-#include "base/basictypes.h"
-#include "base/files/file_path.h"
-#include "base/time.h"
-#include "build/build_config.h"
-
-#if defined(OS_WIN)
-#include <windows.h>
-#elif defined(OS_POSIX)
-#include <sys/stat.h>
-#include <unistd.h>
-#endif
-
-namespace base {
-
-// A class for enumerating the files in a provided path. The order of the
-// results is not guaranteed.
-//
-// This is blocking. Do not use on critical threads.
-//
-// Example:
-//
-// base::FileEnumerator enum(my_dir, false, base::FileEnumerator::FILES,
-// FILE_PATH_LITERAL("*.txt"));
-// for (base::FilePath name = enum.Next(); !name.empty(); name = enum.Next())
-// ...
-class BASE_EXPORT FileEnumerator {
- public:
- // Note: copy & assign supported.
- class FileInfo {
- public:
- FileInfo();
- ~FileInfo();
-
- bool IsDirectory() const;
-
- // The name of the file. This will not include any path information. This
- // is in constrast to the value returned by FileEnumerator.Next() which
- // includes the |root_path| passed into the FileEnumerator constructor.
- FilePath GetName() const;
-
- int64 GetSize() const;
- Time GetLastModifiedTime() const;
-
-#if defined(OS_WIN)
- const WIN32_FIND_DATA& find_data() const { return find_data_; }
-#elif defined(OS_POSIX)
- const struct stat& stat() const { return stat_; }
-#endif
-
- private:
- friend class FileEnumerator;
-
-#if defined(OS_WIN)
- WIN32_FIND_DATA find_data_;
-#elif defined(OS_POSIX)
- struct stat stat_;
- FilePath filename_;
-#endif
- };
-
- enum FileType {
- FILES = 1 << 0,
- DIRECTORIES = 1 << 1,
- INCLUDE_DOT_DOT = 1 << 2,
-#if defined(OS_POSIX)
- SHOW_SYM_LINKS = 1 << 4,
-#endif
- };
-
- // |root_path| is the starting directory to search for. It may or may not end
- // in a slash.
- //
- // If |recursive| is true, this will enumerate all matches in any
- // subdirectories matched as well. It does a breadth-first search, so all
- // files in one directory will be returned before any files in a
- // subdirectory.
- //
- // |file_type|, a bit mask of FileType, specifies whether the enumerator
- // should match files, directories, or both.
- //
- // |pattern| is an optional pattern for which files to match. This
- // works like shell globbing. For example, "*.txt" or "Foo???.doc".
- // However, be careful in specifying patterns that aren't cross platform
- // since the underlying code uses OS-specific matching routines. In general,
- // Windows matching is less featureful than others, so test there first.
- // If unspecified, this will match all files.
- // NOTE: the pattern only matches the contents of root_path, not files in
- // recursive subdirectories.
- // TODO(erikkay): Fix the pattern matching to work at all levels.
- FileEnumerator(const FilePath& root_path,
- bool recursive,
- int file_type);
- FileEnumerator(const FilePath& root_path,
- bool recursive,
- int file_type,
- const FilePath::StringType& pattern);
- ~FileEnumerator();
-
- // Returns the next file or an empty string if there are no more results.
- //
- // The returned path will incorporate the |root_path| passed in the
- // constructor: "<root_path>/file_name.txt". If the |root_path| is absolute,
- // then so will be the result of Next().
- FilePath Next();
-
- // Write the file info into |info|.
- FileInfo GetInfo() const;
-
- private:
- // Returns true if the given path should be skipped in enumeration.
- bool ShouldSkip(const FilePath& path);
-
-#if defined(OS_WIN)
- // True when find_data_ is valid.
- bool has_find_data_;
- WIN32_FIND_DATA find_data_;
- HANDLE find_handle_;
-#elif defined(OS_POSIX)
-
- // Read the filenames in source into the vector of DirectoryEntryInfo's
- static bool ReadDirectory(std::vector<FileInfo>* entries,
- const FilePath& source, bool show_links);
-
- // The files in the current directory
- std::vector<FileInfo> directory_entries_;
-
- // The next entry to use from the directory_entries_ vector
- size_t current_directory_entry_;
-#endif
-
- FilePath root_path_;
- bool recursive_;
- int file_type_;
- FilePath::StringType pattern_; // Empty when we want to find everything.
-
- // A stack that keeps track of which subdirectories we still need to
- // enumerate in the breadth-first search.
- std::stack<FilePath> pending_paths_;
-
- DISALLOW_COPY_AND_ASSIGN(FileEnumerator);
-};
-
-} // namespace base
-
-#endif // BASE_FILES_FILE_ENUMERATOR_H_
diff --git a/base/files/file_enumerator_posix.cc b/base/files/file_enumerator_posix.cc
deleted file mode 100644
index 7533a24..0000000
--- a/base/files/file_enumerator_posix.cc
+++ /dev/null
@@ -1,160 +0,0 @@
-// Copyright (c) 2013 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#include "base/files/file_enumerator.h"
-
-#include <dirent.h>
-#include <errno.h>
-#include <fnmatch.h>
-
-#include "base/logging.h"
-#include "base/threading/thread_restrictions.h"
-
-namespace base {
-
-// FileEnumerator::FileInfo ----------------------------------------------------
-
-FileEnumerator::FileInfo::FileInfo() {
- memset(&stat_, 0, sizeof(stat_));
-}
-
-bool FileEnumerator::FileInfo::IsDirectory() const {
- return S_ISDIR(stat_.st_mode);
-}
-
-FilePath FileEnumerator::FileInfo::GetName() const {
- return filename_;
-}
-
-int64 FileEnumerator::FileInfo::GetSize() const {
- return stat_.st_size;
-}
-
-base::Time FileEnumerator::FileInfo::GetLastModifiedTime() const {
- return base::Time::FromTimeT(stat_.st_mtime);
-}
-
-// FileEnumerator --------------------------------------------------------------
-
-FileEnumerator::FileEnumerator(const FilePath& root_path,
- bool recursive,
- int file_type)
- : current_directory_entry_(0),
- root_path_(root_path),
- recursive_(recursive),
- file_type_(file_type) {
- // INCLUDE_DOT_DOT must not be specified if recursive.
- DCHECK(!(recursive && (INCLUDE_DOT_DOT & file_type_)));
- pending_paths_.push(root_path);
-}
-
-FileEnumerator::FileEnumerator(const FilePath& root_path,
- bool recursive,
- int file_type,
- const FilePath::StringType& pattern)
- : current_directory_entry_(0),
- root_path_(root_path),
- recursive_(recursive),
- file_type_(file_type),
- pattern_(root_path.Append(pattern).value()) {
- // INCLUDE_DOT_DOT must not be specified if recursive.
- DCHECK(!(recursive && (INCLUDE_DOT_DOT & file_type_)));
- // The Windows version of this code appends the pattern to the root_path,
- // potentially only matching against items in the top-most directory.
- // Do the same here.
- if (pattern.empty())
- pattern_ = FilePath::StringType();
- pending_paths_.push(root_path);
-}
-
-FileEnumerator::~FileEnumerator() {
-}
-
-FilePath FileEnumerator::Next() {
- ++current_directory_entry_;
-
- // While we've exhausted the entries in the current directory, do the next
- while (current_directory_entry_ >= directory_entries_.size()) {
- if (pending_paths_.empty())
- return FilePath();
-
- root_path_ = pending_paths_.top();
- root_path_ = root_path_.StripTrailingSeparators();
- pending_paths_.pop();
-
- std::vector<FileInfo> entries;
- if (!ReadDirectory(&entries, root_path_, file_type_ & SHOW_SYM_LINKS))
- continue;
-
- directory_entries_.clear();
- current_directory_entry_ = 0;
- for (std::vector<FileInfo>::const_iterator i = entries.begin();
- i != entries.end(); ++i) {
- FilePath full_path = root_path_.Append(i->filename_);
- if (ShouldSkip(full_path))
- continue;
-
- if (pattern_.size() &&
- fnmatch(pattern_.c_str(), full_path.value().c_str(), FNM_NOESCAPE))
- continue;
-
- if (recursive_ && S_ISDIR(i->stat_.st_mode))
- pending_paths_.push(full_path);
-
- if ((S_ISDIR(i->stat_.st_mode) && (file_type_ & DIRECTORIES)) ||
- (!S_ISDIR(i->stat_.st_mode) && (file_type_ & FILES)))
- directory_entries_.push_back(*i);
- }
- }
-
- return root_path_.Append(
- directory_entries_[current_directory_entry_].filename_);
-}
-
-FileEnumerator::FileInfo FileEnumerator::GetInfo() const {
- return directory_entries_[current_directory_entry_];
-}
-
-bool FileEnumerator::ReadDirectory(std::vector<FileInfo>* entries,
- const FilePath& source, bool show_links) {
- base::ThreadRestrictions::AssertIOAllowed();
- DIR* dir = opendir(source.value().c_str());
- if (!dir)
- return false;
-
-#if !defined(OS_LINUX) && !defined(OS_MACOSX) && !defined(OS_BSD) && \
- !defined(OS_SOLARIS) && !defined(OS_ANDROID)
- #error Port warning: depending on the definition of struct dirent, \
- additional space for pathname may be needed
-#endif
-
- struct dirent dent_buf;
- struct dirent* dent;
- while (readdir_r(dir, &dent_buf, &dent) == 0 && dent) {
- FileInfo info;
- info.filename_ = FilePath(dent->d_name);
-
- FilePath full_name = source.Append(dent->d_name);
- int ret;
- if (show_links)
- ret = lstat(full_name.value().c_str(), &info.stat_);
- else
- ret = stat(full_name.value().c_str(), &info.stat_);
- if (ret < 0) {
- // Print the stat() error message unless it was ENOENT and we're
- // following symlinks.
- if (!(errno == ENOENT && !show_links)) {
- DPLOG(ERROR) << "Couldn't stat "
- << source.Append(dent->d_name).value();
- }
- memset(&info.stat_, 0, sizeof(info.stat_));
- }
- entries->push_back(info);
- }
-
- closedir(dir);
- return true;
-}
-
-} // namespace base
diff --git a/base/files/file_enumerator_win.cc b/base/files/file_enumerator_win.cc
deleted file mode 100644
index 64c9845..0000000
--- a/base/files/file_enumerator_win.cc
+++ /dev/null
@@ -1,149 +0,0 @@
-// Copyright (c) 2013 The Chromium Authors. All rights reserved.
-// Use of this source code is governed by a BSD-style license that can be
-// found in the LICENSE file.
-
-#include "base/files/file_enumerator.h"
-
-#include <string.h>
-
-#include "base/logging.h"
-#include "base/threading/thread_restrictions.h"
-
-namespace base {
-
-// FileEnumerator::FileInfo ----------------------------------------------------
-
-FileEnumerator::FileInfo::FileInfo() {
- memset(&find_data_, 0, sizeof(find_data_));
-}
-
-bool FileEnumerator::FileInfo::IsDirectory() const {
- return (find_data_.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) != 0;
-}
-
-FilePath FileEnumerator::FileInfo::GetName() const {
- return FilePath(find_data_.cFileName);
-}
-
-int64 FileEnumerator::FileInfo::GetSize() const {
- ULARGE_INTEGER size;
- size.HighPart = find_data_.nFileSizeHigh;
- size.LowPart = find_data_.nFileSizeLow;
- DCHECK_LE(size.QuadPart, std::numeric_limits<int64>::max());
- return static_cast<int64>(size.QuadPart);
-}
-
-base::Time FileEnumerator::FileInfo::GetLastModifiedTime() const {
- return base::Time::FromFileTime(find_data_.ftLastWriteTime);
-}
-
-// FileEnumerator --------------------------------------------------------------
-
-FileEnumerator::FileEnumerator(const FilePath& root_path,
- bool recursive,
- int file_type)
- : recursive_(recursive),
- file_type_(file_type),
- has_find_data_(false),
- find_handle_(INVALID_HANDLE_VALUE) {
- // INCLUDE_DOT_DOT must not be specified if recursive.
- DCHECK(!(recursive && (INCLUDE_DOT_DOT & file_type_)));
- memset(&find_data_, 0, sizeof(find_data_));
- pending_paths_.push(root_path);
-}
-
-FileEnumerator::FileEnumerator(const FilePath& root_path,
- bool recursive,
- int file_type,
- const FilePath::StringType& pattern)
- : recursive_(recursive),
- file_type_(file_type),
- has_find_data_(false),
- pattern_(pattern),
- find_handle_(INVALID_HANDLE_VALUE) {
- // INCLUDE_DOT_DOT must not be specified if recursive.
- DCHECK(!(recursive && (INCLUDE_DOT_DOT & file_type_)));
- memset(&find_data_, 0, sizeof(find_data_));
- pending_paths_.push(root_path);
-}
-
-FileEnumerator::~FileEnumerator() {
- if (find_handle_ != INVALID_HANDLE_VALUE)
- FindClose(find_handle_);
-}
-
-FileEnumerator::FileInfo FileEnumerator::GetInfo() const {
- if (!has_find_data_) {
- NOTREACHED();
- return FileInfo();
- }
- FileInfo ret;
- memcpy(&ret.find_data_, &find_data_, sizeof(find_data_));
- return ret;
-}
-
-FilePath FileEnumerator::Next() {
- base::ThreadRestrictions::AssertIOAllowed();
-
- while (has_find_data_ || !pending_paths_.empty()) {
- if (!has_find_data_) {
- // The last find FindFirstFile operation is done, prepare a new one.
- root_path_ = pending_paths_.top();
- pending_paths_.pop();
-
- // Start a new find operation.
- FilePath src = root_path_;
-
- if (pattern_.empty())
- src = src.Append(L"*"); // No pattern = match everything.
- else
- src = src.Append(pattern_);
-
- find_handle_ = FindFirstFile(src.value().c_str(), &find_data_);
- has_find_data_ = true;
- } else {
- // Search for the next file/directory.
- if (!FindNextFile(find_handle_, &find_data_)) {
- FindClose(find_handle_);
- find_handle_ = INVALID_HANDLE_VALUE;
- }
- }
-
- if (INVALID_HANDLE_VALUE == find_handle_) {
- has_find_data_ = false;
-
- // This is reached when we have finished a directory and are advancing to
- // the next one in the queue. We applied the pattern (if any) to the files
- // in the root search directory, but for those directories which were
- // matched, we want to enumerate all files inside them. This will happen
- // when the handle is empty.
- pattern_ = FilePath::StringType();
-
- continue;
- }
-
- FilePath cur_file(find_data_.cFileName);
- if (ShouldSkip(cur_file))
- continue;
-
- // Construct the absolute filename.
- cur_file = root_path_.Append(find_data_.cFileName);
-
- if (find_data_.dwFileAttributes & FILE_ATTRIBUTE_DIRECTORY) {
- if (recursive_) {
- // If |cur_file| is a directory, and we are doing recursive searching,
- // add it to pending_paths_ so we scan it after we finish scanning this
- // directory.
- pending_paths_.push(cur_file);
- }
- if (file_type_ & FileEnumerator::DIRECTORIES)
- return cur_file;
- } else if (file_type_ & FileEnumerator::FILES) {
- return cur_file;
- }
- }
-
- return FilePath();
-}
-
-} // namespace base
diff --git a/base/test/test_file_util_posix.cc b/base/test/test_file_util_posix.cc
index d80a954..7c16cb18 100644
--- a/base/test/test_file_util_posix.cc
+++ b/base/test/test_file_util_posix.cc
@@ -12,12 +12,13 @@
#include <string>
#include "base/file_util.h"
-#include "base/files/file_enumerator.h"
#include "base/files/file_path.h"
#include "base/logging.h"
#include "base/string_util.h"
#include "base/utf_string_conversions.h"
+using base::MakeAbsoluteFilePath;
+
namespace file_util {
namespace {