文件格式为什么需要魔数?

6
例如,可移植可执行文件有几个魔数,包括著名的“MZ”开头,以及PE头部开头的“PE\0\0”。RAR文件格式在开头有“Rar!”标头,其他一些文件也有类似的“魔法值”。
这些魔法值有什么作用?
5个回答

9
因为用户可能会更改文件扩展名,或其他程序会窃取文件扩展名,所以应用程序可以取消处理未知格式的文件,而不是尝试最好却最终失败。

如果它无论如何都会失败,那么为什么需要检测错误的幻数呢?假设文件的其他部分如果是不同的文件格式,那么它们也将毫无意义。 - Billy ONeal
3
对于一些文件格式,你不能确定其中的数据是否“有问题”。例如,如果没有魔数(magic number),很难通过程序判断一个文件是否为位图。 - Seth
1
那么你将无法区分已知格式中的损坏文件和未知格式中的(可能)有效文件。 - Fabio Ceconello
Billy:完全不是这样。我曾经编写过自动检测和加载某些特定科学数据的7或8种文件类型的代码。那些没有魔数的格式几乎是不可能的,因为许多格式足够灵活,以至于格式X中的某些内容实际上也是有效的格式Y。最终,我在两个格式中都加载了它,并查看了实际数据集,以确定哪个更有意义。(例如,如果在格式X中,数据类型标记指示“与前一次相比的%变化”,而所有读数都高于1000%,那么它可能是其他格式。)但总的来说,这是不可能的。 - Ken
@Billy:在失败发生之前的处理可能会非常昂贵。你提到了rar,这是一种归档格式。让我们想想其他归档格式,比如gzip。它们都是流式的,所以你不能在第一遍扫描文件时查看所有内容是否合理,你必须在第一遍输出。输出可能是硬盘(甚至更慢的存储介质),在故障之前,你可能会写入多个千兆字节的“解压缩”输出。唯一可以防止这种情况的方法是进行某种内部一致性检查。最好的方法可能是使用用魔数初始化的CRC。 - Ben Voigt
我认为应该提到“冗余”这个词。从我所读的内容来看,文件的魔数与其文件类型是冗余的。当某些东西很重要时,冗余是一个常见的主题。此外,我认为可能的魔数范围远大于漂亮的文件扩展名的范围。 - JoseOrtiz3

7
魔数的概念可以追溯到Unix,早于文件扩展名的使用。原始的shell想法是所有“可执行”文件看起来都一样 - 文件是如何创建的或应该用什么程序来评估它并不重要。 shell将查看文件的内容并确定适当的文件类型。然后微软采取了不同的方法,文件扩展名的时代就诞生了。然后为了让用户更方便,微软选择“隐藏”这些扩展名,于是类似木马文件的时代就诞生了,这些文件看起来像是某种类型,但实际上有不同的扩展名,并由不同的文件处理。

2
如果两个应用程序以不同的方式存储数据,但是构造得使一个文件可能也是另一个文件的有效文件(但是没有意义),那么会发生非常糟糕的事情。程序可能会认为它已经成功加载了文件(不知道数据是没有意义的),然后写回一个对它来说语义上相同但不再有意义可读性的文件,而写它的应用程序(或任何其他东西)将无法读取。

使用魔数不能完全防止这种情况,但至少可以在一定程度上帮助。

顺便说一下,尝试猜测数据格式通常非常危险。例如,假设有一个可能是 nn-nn-nn 格式的日期列表。如果不知道日期的格式是什么,可能有足够的信息来猜测格式(例如,如果其中一个记录是 12-31-99,则在缺乏相反信息的情况下,日期可能是 mm-dd-yy),但如果所有日期都在一个月的前 12 天内,则数据很容易被误解。不过,假设数据之前有一些内容说“MM-DD-YY”。那么误解风险就可以减小。


1

为了快速识别文件类型或其中的位置。


1

你的问题不应该是“为什么文件格式有魔数”,而应该是“文件格式具有魔数的优势是什么”!

建议:

  • 通过读取磁盘空闲空间来恢复文件的程序可以识别文件类型
  • 你的UNIX知道可执行文件是要解释还是二进制
  • 当你失去扩展名时,像file这样的程序可以检测你的文件类型
  • 文件格式的设计者认为,当应用程序可以轻松确保它们正在读取正确格式的文件时,这总是更安全的。
  • 由于你有一个头部,将其放在头部开头并不会花费太多成本。

网页内容由stack overflow 提供, 点击上面的
可以查看英文原文,
原文链接