【发布时间】:2018-11-16 02:36:36
【问题描述】:
我正在处理以下代码:
枚举源目录和目标目录并生成 {
src,dst} 对...每一对都被发送到一个工作线程池
...执行工作,例如“将
src复制到dst”
(所有这些都被简化了很多)。
问题:
当文件被创建时,它还会获得一个短名称,它可以与源目录中的另一个文件相同(名称冲突),这会导致各种效果(取决于操作的顺序)。例如,复制两个文件 my file 和 MYFILE~1 可以在目标中生成 2 或 1 个文件(取决于你的运气),可能包含损坏的内容(在后一种情况下)。
问题:
如何避免此类碰撞产生的问题?如果有一个函数可以创建/打开忽略短名称的文件...
注意事项:
无法假设短名称的生成方式。不同的系统采用不同的方案(见this)
即使您以顺序方式(一个接一个)运行这些作业——它们也需要按顺序执行,这取决于短名称生成逻辑(未知)。另外,这意味着在运行任何作业之前在内存中加载和排序/等整个目录
源和目标都可能非常大(可能是数百万个文件),(如果可能)我想避免将整个目录加载到内存中或多次枚举它
无法关闭目标卷中的短名称生成,并且不能将其作为要求(另外,关闭它并不会删除现有的短名称)
应用仅限于 Win32 API 和 NT API
编辑:在我看来,在一般情况下,即使所有事情都发生在一个线程上,您也无法做到这一点——仅仅是因为无论您选择什么顺序,都会有一个短名称生成方案以及一组保证在处理过程中产生冲突的文件名。
如果这是正确的——系统实用程序如何复制文件?他们是否会在复制完成后假设一些短名称或执行“验证和修复差异”?
【问题讨论】:
-
您确定您的诊断正确吗?我真的怀疑文件系统会创建两个具有相同短名称的文件。
-
不,不会。复制
my file(具有MYFILE~2短名称)将在dst 目录中创建my file(可能带有MYFILE~1短名称)。如果在此之后您复制MYFILE~1(没有短名称)-它将覆盖上一步创建的文件并且(取决于许多事情)可能会损坏它的数据(如果复制并行发生)。 -
你为什么要使用短文件名?使用完整文件名复制文件。在某些文件系统上,您甚至可以关闭短文件名的生成。
-
@Remy 我认为提问者是在使用完整文件名进行复制,但是在目标端生成的短文件名与源端不同,进而干扰后续操作。
-
@C.M.我想知道为什么您使用线程来执行不受 CPU 限制的操作
标签: winapi filesystems ntdll