Botan  1.11.15
src/lib/utils/fs.cpp
Go to the documentation of this file.
00001 /*
00002 * (C) 2015 Jack Lloyd
00003 *
00004 * Botan is released under the Simplified BSD License (see license.txt)
00005 */
00006 
00007 #include <botan/fs.h>
00008 #include <algorithm>
00009 #include <deque>
00010 
00011 #if defined(BOTAN_HAS_BOOST_FILESYSTEM)
00012   #include <boost/filesystem.hpp>
00013 
00014 #elif defined(BOTAN_TARGET_OS_HAS_READDIR)
00015   #include <sys/types.h>
00016   #include <sys/stat.h>
00017   #include <dirent.h>
00018 #endif
00019 
00020 namespace Botan {
00021 
00022 std::vector<std::string>
00023 list_all_readable_files_in_or_under(const std::string& dir_path)
00024    {
00025    std::vector<std::string> paths;
00026 
00027 #if defined(BOTAN_HAS_BOOST_FILESYSTEM)
00028    namespace fs = boost::filesystem;
00029 
00030    fs::recursive_directory_iterator end;
00031    for(fs::recursive_directory_iterator dir(dir_path); dir != end; ++dir)
00032       {
00033       if(fs::is_regular_file(dir->path()))
00034          paths.push_back(dir->path().string());
00035       }
00036 
00037 #elif defined(BOTAN_TARGET_OS_HAS_READDIR)
00038 
00039    std::deque<std::string> dir_list;
00040    dir_list.push_back(dir_path);
00041 
00042    while(!dir_list.empty())
00043       {
00044       const std::string cur_path = dir_list[0];
00045       dir_list.pop_front();
00046 
00047       std::unique_ptr<DIR, std::function<int (DIR*)>> dir(::opendir(cur_path.c_str()), ::closedir);
00048 
00049       if(dir)
00050          {
00051          while(struct dirent* dirent = ::readdir(dir.get()))
00052             {
00053             const std::string filename = dirent->d_name;
00054             if(filename == "." || filename == "..")
00055                continue;
00056             const std::string full_path = cur_path + '/' + filename;
00057 
00058             struct stat stat_buf;
00059 
00060             if(::lstat(full_path.c_str(), &stat_buf) == -1)
00061                continue;
00062 
00063             if(S_ISDIR(stat_buf.st_mode))
00064                dir_list.push_back(full_path);
00065             else if(S_ISREG(stat_buf.st_mode))
00066                paths.push_back(full_path);
00067             }
00068          }
00069       }
00070 #else
00071   #warning "No filesystem access enabled"
00072 #endif
00073 
00074    std::sort(paths.begin(), paths.end());
00075 
00076    return paths;
00077    }
00078 
00079 }
00080