我有一个由 std::filesystem::path
表示的根路径.我想向该路径添加一些用户提供的文件名,并确保生成的路径不在根目录之外。
例如:
std::filesystem::path root = "/foo/bar";
std::filesystem::path userFile = "ham/spam";
std::filesystem::path finalPath = root / userFile;
最终路径没问题,在
/foo/bar
里面.但是如果我给
../ham/spam
到userFile
变量,这将导致定义之外的文件 rootPath
.如何检查生成的文件是否保持在其允许的边界内?
最佳答案
首先,您需要normalize the final path .这将删除所有 .
和 ..
s 在路径中。然后,您需要检查它是否在其目录迭代器范围内有任何不匹配,相对于 root
.还有一个 standard library algorithm为了那个原因。
总的来说,代码如下所示:
std::optional<fs::path> MakeAbsolute(const fs::path &root, const fs::path &userPath)
{
auto finalPath = (root / userPath).lexically_normal();
auto[rootEnd, nothing] = std::mismatch(root.begin(), root.end(), finalPath.begin());
if(rootEnd != root.end())
return std::nullopt;
return finalPath;
}
请注意,这仅在理论上有效;用户可能在根目录中使用了符号链接(symbolic link)恶作剧来突破您的根目录。您需要 use
canonical
而不是 lexically_normal
以确保不会发生这种情况。但是,canonical
要求路径存在,所以如果这是需要创建的文件/目录的路径,它将不起作用。
关于c++ - 检查 std::filesystem::path 是否在目录中,我们在Stack Overflow上找到一个类似的问题: https://stackoverflow.com/questions/61123627/