Performance

从源码到性能

CopyFile2 内核 API + Rayon 并行迭代器 + 分级缓冲区,每一个参数都来自真实代码。

CopyFile2 API

Windows 内核级复制 大文件自动启用 COPY_FILE_NO_BUFFERING,绕过系统缓存直接 DMA 传输

并行阈值

512 MB / 128 文件 PARALLEL_COPY_MIN_BYTES = 512MB,PARALLEL_COPY_MIN_FILES = 128,满足任一即启用 Rayon 并行

缓冲区分级

1MB → 8MB → 16MB DEFAULT=1MB,LARGE_FILE(≥128MB)=8MB,HUGE(≥1GB)=16MB,按文件大小自适应

NO_BUFFERING

≥ 128 MB 触发 LARGE_FILE_COPY_THRESHOLD = 128MB,超过此阈值启用无缓冲模式,减少内存拷贝

进度上报

200 ms 间隔 PROGRESS_EMIT_INTERVAL = 200ms,独立线程定期快照 AtomicU64 计数器

空间预留

1% (64~512MB) required_target_space = 源大小 + clamp(1%, 64MB, 512MB),防止磁盘满导致失败
Pipeline

迁移流水线

从源码 file_migrator.rs 提取的真实执行流程

1

Scan & Plan

递归遍历源目录,构建 DirectoryCopyPlan。收集所有文件路径 + FileSignature(size + modified_ns),生成 SourceManifest。

build_directory_copy_plan() → DirectoryCopyPlan
2

Prepare Target

按路径深度排序创建目标目录树,确保父目录先于子目录创建。

prepare_directory_copy_plan() → mkdir -p sorted by depth
3

Copy (Serial / Parallel)

小目录串行复制,大目录 Rayon par_iter 并行。每个文件先尝试 CopyFile2,失败降级为缓冲复制。独立线程 200ms 上报进度。

should_parallelize() ? par_iter : iter → copy_file_optimized()
4

Verify

逐文件验证:源文件 FileSignature 未变 + 目标文件存在 + 大小一致。源文件若在迁移期间被修改,立即报错。

verify_copied_file() → size + modified_ns check
5

Backup → Rename → Link

源文件重命名为 .backup_temp,创建 Junction/Symlink 指向目标,验证链接有效性。失败则还原备份。

fs::rename(src, .backup_temp) → create_link() → verify_link()
6

Cleanup

删除 .backup_temp 备份文件,完成迁移。若任一步失败,逆向回滚:删链接 → 还原备份 → 删目标。

cleanup_backup() → MigrationResult { success: true }
Copy Engine

双引擎复制策略

CopyFile2 优先,缓冲复制降级

Primary

CopyFile2

  • COPY_FILE_FAIL_IF_EXISTS防覆盖
  • COPY_FILE_NO_BUFFERING≥128MB DMA 直传
  • Progress CallbackCHUNK_FINISHED 实时回调
  • 保留 ACL / ADSNTFS 安全描述符和交替数据流
Fallback

Buffered Copy

  • FILE_FLAG_SEQUENTIAL_SCAN顺序读取,预读缓存友好
  • 分级缓冲区1MB / 8MB / 16MB 自适应
  • sync_all()写入后强制 fsync 落盘
  • 降级触发CopyFile2 失败自动降级
Performance

每个参数都有据可查

所有阈值均来自 Rust 源码中的常量定义,无魔数。