重新排序块设备上的扇区?

重新排序块设备上的扇区?

我正在考虑将一些数据备份到 DVD/BD 中。(我知道 DVDisaster。)我读到过 DVD 的外扇区比内扇区更容易磨损。这表明随着时间的推移,图像后半部分的块比前半部分的块更容易损坏。所以我的问题是,有没有办法将相同的数据写入 2 个 DVD 图像,这样

  1. 可以安装任意一张 DVD,可能分两步(例如安装存储在 DVD 上的 iso 文件),但无需先将所有内容复制到 HD 并对其进行操作
  2. 主要数据应以明显不同的顺序写入 2 张 DVD

如果我没有表达清楚,以下是一个可能的解决方案。

假设存在一个可以反向安装 iso 映像的 linux 驱动程序。因此,我给它一个 iso 文件,当它需要第一个扇区时,它会反向读取文件的最后 2048 个字节,而不是按正常顺序读取前 2048 个字节。我不知道是否存在这样的驱动程序,但如果存在,它将是我的问题的一个解决方案,因为我可以这样做:将我的数据放入 iso 映像中;将第二个映像计算为第一个映像;将每个映像封装到只有一个文件的简单 UDF 文件系统中;将两个 UDF 文件系统写入不同的 DVD。现在,当我插入任一 DVD 时,我只需安装单个 iso 文件即可恢复我的数据。此外,数据将以不同的方式写入 2 张 DVD,因此如果两张 DVD 都丢失了最后 1/3 个扇区,我仍然可以恢复所有内容(手动,但这是可能的)。

其他可能的解决方案是使用通用驱动程序对任意块设备中的任意大小的块进行置换/旋转/重新排序。或者,有没有办法使用特定的扇区顺序将文件存储在 UDF 文件系统中?鉴于 UDF 是一个成熟的文件系统,这绝对是可能的,但有工具可以做到这一点吗?

谢谢!!

编辑:正如我在第一条回复下所解释的那样,我并不是要取代 DVDisaster,而是要对其进行补充。考虑两种备份 4G 数据的策略。策略 A:使用 2 张相同的 DVD,每张 DVDisaster 的 ecc 为 15%。策略 B:使用 2 张 DVD,每张 DVD 的 ecc 为 15%,但要加上我上面提到的额外排列(在 2 张 DVD 中的 1 张上)。我认为,由于 DVD 的磨损模式(具体来说,是错误的相关性),经过一段时间后,从 B 完全恢复的概率明显大于从 A 完全恢复的概率(其他所有条件相同)。

編輯2:为了证实我的主张,即 DVDisaster 并非万能药,这里有一个脚本,演示了具有 33% ECC 数据的 DVDisaster 如何遭受数据丢失,而损坏率仅为 1.3%。明显的矛盾是 33% 仅适用于“最佳情况”损坏,而不适用于“任何”损坏。仅供参考,我正在创建一个跨越整个文件系统的文件test.1.udf,在 中仅将文件中的最后一个扇区更改为零test.2.udf,计算两者的 ecc 数据,并比较扇区,包括 ecc 数据。关键是,如果test.1.udf是您的数据,并且您丢失了不同的扇区,并且只有这些扇区,那么您不可能恢复,test.1.udf因为test.2.udf还有另一种可能性。

n_blocks=8192
tdir=$(mktemp -d)
mkudffs -b 2048 test.1.udf $n_blocks
sudo mount test.1.udf $tdir -o bs=2048
sudo chown $USER.$USER $tdir
n=$(df -B 2K $tdir | tail -n 1 | awk '{print $4}')
let n-=1
dd if=/dev/urandom of=$tdir/file bs=2K count=$n 2>/dev/null
last=$(od <$tdir/file -Ad -t x1 | tail -n 2 | head -n 1 | cut -d ' ' -f 2-)
sudo umount $tdir
start_of_last_block=$(od <test.1.udf -Ad -t x1 | grep -A 1 "$last" | tail -n 1 | awk '{print $1}')
last_block=$(($start_of_last_block / 2048))
dd if=test.1.udf bs=2K count=$(($last_block - 1)) >test.2.udf 2>/dev/null
dd if=/dev/zero bs=2K count=1 >>test.2.udf 2>/dev/null
dd if=test.1.udf bs=2K skip=$last_block count=$(($n_blocks - $last_block)) >>test.2.udf 2>/dev/null
n_blocks_with_ecc=$(echo "$n_blocks * 133 / 100" | bc)
echo "add dvdisaster ecc data, using in total $n_blocks_with_ecc"
#run dvdisaster on the 2 files, then...
n_blocks_different=$(for i in $(seq 0 $(($n_blocks_with_ecc - 1))); do
  if [ $((($i / 100) * 100)) -eq $i ]; then
    echo "$i..." >&2
  fi
  diff -q <(dd if=test.1.udf bs=2K skip=$i count=1 2>/dev/null) \
      <(dd if=test.2.udf bs=2K skip=$i count=1 2>/dev/null) >/dev/null || echo $i
done | wc -l)
echo "number of blocks different: $n_blocks_different / $n_blocks_with_ecc ($(echo "scale=6; $n_blocks_different / $n_blocks_with_ecc * 100" | bc)%)"

输出:

number of blocks different: 145 / 10895 (1.330800%)

答案1

您描述的问题已经有了更优雅、更有效的解决方案:Reed-Solomon 错误修正。其工作原理是在磁盘末尾插入纠错码,这样你就可以丢失一定数量的数据随意的单个磁盘上的位置并恢复整个文件。

这是可能的,因为RS解码器不区分用户数据和纠错数据。从 RS 解码器的角度来看,每个块都是 100 个字节的序列,可以从中恢复 20 个字节的任意子集。

虽然磁盘的某些部分可能更容易丢失数据,但任何位置都可能发生数据丢失。在描述的双磁盘方法中,如果任何两个故障扇区重叠,则将丢失数据。在数据丢失程度较高的情况下,这种情况相当常见。相比之下,Reed-Solomon 错误更正可让您轻松恢复丢失 14.3%(正常模式)或 33.5%(高模式)的磁盘。

DVD灾难就是为此而设计的,完全能够满足您的需求。如果您特别谨慎,可以将冗余度设置为“高”(或自定义),这样仍然比使用两个磁盘占用更少的空间,并且可靠性更高。

祝您备份愉快!

在此处输入图片描述

相关内容