将 std::filesystem 与 linux 一起使用是错误的还是无法访问文件系统树?

Is using std::filesystem with linux bad or the file system tree unreachable?

我正在尝试打印我的系统目录树,但是在使用根目录或其附近的某个位置时,程序会抛出异常,如下所示

terminate called after throwing an instance of 'std::filesystem::__cxx11::filesystem_error'
  what():  filesystem error: status: Too many levels of symbolic links [/home/asmmo/.local/share/webkitgtk/databases/indexeddb/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0]

并且在使用 root 本身时,程序抛出

terminate called after throwing an instance of 'std::filesystem::__cxx11::filesystem_error'
  what():  filesystem error: status: Too many levels of symbolic links [/sys/kernel/software_nodes/node2/dw-apb-uart.2/firmware_node/physical_node1/firmware_node/physical_node1/firmware_node/physical_node1/firmware_node/physical_node1/firmware_node/physical_node1/firmware_node/physical_node1/firmware_node/physical_node1/firmware_node/physical_node1/firmware_node/physical_node1/firmware_node/physical_node1/firmware_node/physical_node1/firmware_node/physical_node1/firmware_node/physical_node1/firmware_node/physical_node1/firmware_node/physical_node1/firmware_node/physical_node1/firmware_node/physical_node1/firmware_node/physical_node1/firmware_node/physical_node1/firmware_node/physical_node1]

我使用的代码是:

#include<iostream>
#include<filesystem>
#include<fstream>


void processPth(const std::filesystem::path&, std::ostream& = std::cout, const size_t& =0);

int main() {

    std::filesystem::path p{LR"(/home/asmmo)"};//or p{LR"(/)"} for the root
    std::ofstream myFile{"tree.txt"};
    processPth(p, myFile);

}




void processPth(const std::filesystem::path & p, std::ostream& ostream , const size_t& level ){
    if(!std::filesystem::exists(p)) return;//base case

    if(std::filesystem::is_regular_file(p))
        ostream<<std::string(2*level, ' ')<<"File: "<< p.filename()<<"\tSize: "<<std::filesystem::directory_entry(p).file_size()<<"\n";
    else if(std::filesystem::is_directory(p))
    {
        ostream<<std::string(2*level, ' ')<<"Directory: "<< p.filename()<<"\n";
        for(const auto& it : std::filesystem::directory_iterator(p))
            processPth( it, ostream, level+1);
    }


}

我尝试使用终端联系那些 v0,结果如下

asmmo@asmmo:~/.local/share/webkitgtk/databases/indexeddb$ cd v0
asmmo@asmmo:~/.local/share/webkitgtk/databases/indexeddb/v0$ cd v0
asmmo@asmmo:~/.local/share/webkitgtk/databases/indexeddb/v0/v0$ cd v0
asmmo@asmmo:~/.local/share/webkitgtk/databases/indexeddb/v0/v0/v0$ cd v0
asmmo@asmmo:~/.local/share/webkitgtk/databases/indexeddb/v0/v0/v0/v0$ cd v0
asmmo@asmmo:~/.local/share/webkitgtk/databases/indexeddb/v0/v0/v0/v0/v0$ cd v0
asmmo@asmmo:~/.local/share/webkitgtk/databases/indexeddb/v0/v0/v0/v0/v0/v0$ cd v0
asmmo@asmmo:~/.local/share/webkitgtk/databases/indexeddb/v0/v0/v0/v0/v0/v0/v0$ cd v0
asmmo@asmmo:~/.local/share/webkitgtk/databases/indexeddb/v0/v0/v0/v0/v0/v0/v0/v0$ cd v0
asmmo@asmmo:~/.local/share/webkitgtk/databases/indexeddb/v0/v0/v0/v0/v0/v0/v0/v0/v0$ cd v0
asmmo@asmmo:~/.local/share/webkitgtk/databases/indexeddb/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0$ cd v0
asmmo@asmmo:~/.local/share/webkitgtk/databases/indexeddb/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0$ cd v0
asmmo@asmmo:~/.local/share/webkitgtk/databases/indexeddb/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0$ cd v0
asmmo@asmmo:~/.local/share/webkitgtk/databases/indexeddb/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0$ cd v0
asmmo@asmmo:~/.local/share/webkitgtk/databases/indexeddb/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0$ cd v0
asmmo@asmmo:~/.local/share/webkitgtk/databases/indexeddb/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0$ cd v0
asmmo@asmmo:~/.local/share/webkitgtk/databases/indexeddb/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0$ cd v0
asmmo@asmmo:~/.local/share/webkitgtk/databases/indexeddb/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0$ cd v0
asmmo@asmmo:~/.local/share/webkitgtk/databases/indexeddb/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0$ cd v0
asmmo@asmmo:~/.local/share/webkitgtk/databases/indexeddb/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0$ cd v0
asmmo@asmmo:~/.local/share/webkitgtk/databases/indexeddb/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0$ cd v0
asmmo@asmmo:~/.local/share/webkitgtk/databases/indexeddb/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0$ cd v0
asmmo@asmmo:~/.local/share/webkitgtk/databases/indexeddb/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0$ cd v0
asmmo@asmmo:~/.local/share/webkitgtk/databases/indexeddb/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0$ cd v0
asmmo@asmmo:~/.local/share/webkitgtk/databases/indexeddb/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0$ cd v0
asmmo@asmmo:~/.local/share/webkitgtk/databases/indexeddb/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0$ cd v0
asmmo@asmmo:~/.local/share/webkitgtk/databases/indexeddb/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0$ cd v0
asmmo@asmmo:~/.local/share/webkitgtk/databases/indexeddb/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0$ cd v0
asmmo@asmmo:~/.local/share/webkitgtk/databases/indexeddb/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0$ cd v0
asmmo@asmmo:~/.local/share/webkitgtk/databases/indexeddb/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0$ cd v0
asmmo@asmmo:~/.local/share/webkitgtk/databases/indexeddb/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0$ cd v0
asmmo@asmmo:~/.local/share/webkitgtk/databases/indexeddb/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0$ cd v0
asmmo@asmmo:~/.local/share/webkitgtk/databases/indexeddb/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0$ cd v0
asmmo@asmmo:~/.local/share/webkitgtk/databases/indexeddb/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0/v0$ cd v0
asmmo@asmmo:~/.local/share/webkitgtk/databases/indexeddb/v0/v0/v0/v0/v0/v0/v0/v0

当我尝试为附近的目录打印树时(如以下代码),它工作正常。

int main() {

    std::filesystem::path p {std::filesystem::current_path()};
    std::ofstream myFile{"tree.txt"};
    processPth(p, myFile);

}

如果您的文件系统有一个链接回其父目录之一的符号链接,则递归搜索该目录将以无限递归结束,因为符号链接会不断将您带回父目录。

系统只允许这么多次递归,returns如果递归太深会出错。

递归遍历这样的目录时,您可能应该忽略符号链接。您可以使用 std::filesystem::is_symlink 来测试路径是否是符号链接。