PDF 解析

 主页   资讯   文章   代码   电子书 

第8章 - 加密文档

从PDF版本1.1开始,PDF文档可以使用各种行业标准方 案进行加密,这些方案多年来增加了复杂性和安全性。 此外,PDF标准还提供了封装第三方加密和安全策略的 一般机制。

除少数例外情况外,加密适用于文件中的流和字符串, 但不加密数字或其他PDF数据类型,也不对整个文件 进行加密。因此,文档的对象结构在不需要解密的情 况下对应用程序仍然可见,但是文档的实质内容得到了保护。

更现代的PDF加密方法允许文件的XMP元数据流(第93页的 “XML元数据”)保持未加密状态,因此可能由不知道如何打开加密PDF文件的程序提取和读取,或者密码不知道。

介绍

由于加密文档的复杂性,不可能手动构建示例(正如我们 在其他章节中所做的那样),但我们可以使用pdftk将标准的 hello.pdf文件处理为加密文件,encypted.pdf:

pdftk hello.pdf output encrypted.pdf encrypt_40bit owner_pw fred

这将使用40位RC4方法创建输出文件encrypted.pdf, 其所有者密码为“fred”。所有者密码是该文件的主密码。 拥有它的人可以对文件执行任何操作,包括重新加密或更 改安全设置。用户密码允许用户在文件加密时执行由所 有者定义的某些操作(查看文档,打印文档等)。

在我们的示例中,我们使用的是空白用户密码,这很常见。 这意味着文件立即在PDF查看器中打开,无需输入任何密码。 我们已禁止用户执行除查看文件之外的任何操作(有关权 限和不同加密类型的pdftk语法的详细信息,请参阅第11 3页的“加密和解密”)。

在Adobe Reader中打开文件时,唯一明显的变化是(SECURED) 附加到窗口的标题栏。打开File ... Properties窗口, 然后选择Security选项卡,可以查看安全属性 - 请参见图8-1。 通过单击Show Details ...按钮获得更具技术头脑的显示, 以显示如图8-2所示的窗口。

如果使用可以编辑PDF文件的程序(例如Adobe Acrobat), 则在尝试权限不允许的任何编辑操作时,将提示用户输入所 有者密码,如图8-3所示。

如果文档具有非空用户密码,则在打开文件时会显示类似的对 话框,如图8-4所示。如果密码未知,则无法打开文件,即使 是查看也是如此。

例8-1显示了我们新文件的内容。看看你是否能够发现示例2-2中标准hello.pdf文件的差异。

Example 8-1. An encrypted file
%PDF-1.1
%âãÏÓ
1 0 obj
<< /Kids [2 0 R] /Type /Pages /Count 1 >> 
endobj
3 0 obj
<< /Length 72 >> 
stream
(72 bytes of encrypted data) 
endstream
endobj 
2 0 obj
<<
  /Rotate 0 
  /Parent 1 0 R 
  /Resources
  <<
    /Font 
      <<
        /F0 
          <<
            /BaseFont /Times-Italic 
            /Subtype /Type1
            /Type /Font
          >> 
      >>
  >>
  /MediaBox [0.000000 0.000000 595.275590551 841.88976378] 
  /Type /Page
  /Contents [3 0 R]
>>
endobj
4 0 obj
<< /Pages 1 0 R /Type /Catalog >> 
endobj
5 0 obj The encryption dictionary
<<
  /R 2
  /P -64
  /O (ífff÷ÚÉMo]Òq)È¢ÏoA»fgygy^ÏynÔZ3⁄4gtëÙ) 
  /Filter /Standard
  /V 1
  /U (gdË^Wîg:lÆr({M8®qμG9Tæ$YTscåGùLÂÐþ¬)
>>
endobj xref
0 6
0000000000 65535 f 
0000000015 00000 n 
0000000199 00000 n 
0000000074 00000 n 
0000000427 00000 n 
0000000478 00000 n 
trailer
<<
  /Encrypt 5 0 R Reference to encryption dictionary at object 5
  /Root 4 0 R
  /Size 6
  /ID [<a7d625071f5b223d97922e9e6c3fff23><e546c20487a77c4156083bf56f69bb4d>]
>> 
startxref 
617
%%EOF

加密字典

再看一下例8-1。已包含加密字典(对象5),并由trailer字典中的/Encrypt条目 引用。在这个例子中,此加密字典包含:

  • /R和/V条目一起定义要使用哪些加密算法。
  • /P条目,它是一个位域,表示附加到用户密码使用的权限(视图,打印等)。
  • /O和/U条目分别用于验证所有者和用户密码。
  • /Filter条目是Adobe安全方法的标准。

提供的标准加密方法是: 40-bit RC4 (PDF 1.1) 128-bit RC4 (PDF 1.4) 128-bit AES Encryption (PDF 1.5) 256-bit AES Encryption (PDF 1.7 ExtensionLevel 3)

40位RC4(要引入的第一种方法)的权限位域允许a /P条目允许打印, 修改文档,提取文本和图形以及注释的组合。128位RC4及更高版本的方法允许更多权限选项。

权限在ISO标准的散文中描述,因此不能依赖于不同PDF处理程序的实现的一致性。

读取加密文件

任何加密文件都可以照常读取,并解析为对象图,而不考虑其加密。 然后我们可以通过检查trailer字典中是否存在/Encrypt条目来检查它是否加密。 然后,我们尝试使用空白用户密码解密文件:

  1. 读取加密字典的内容,并确定加密类型。
  2. 用户密码经过身份验证(使用单向算法进行处理,并与加密字典中的/U条目进行比较)。
  3. 使用另一算法,计算加密密钥。
  4. 此密钥用于解密文件中的每个流和字符串。这可以一次完成,或者更有效,仅在实际需要对象时完成。
  5. 读取权限,并在对文件执行的任何进一步操作中强制执行。

每个步骤使用的实际算法取决于使用的加密类型。 如果用户密码非空白,则使用相同的过程,而不是使用用户输入的密码。

要使用所有者密码进行解密,请遵循类似的过程,但不需要应用权限。 如果使用用户密码打开文件,稍后输入所有者密码,则可以放宽权限。

写入加密文档

要将已解析的PDF写入带加密的文件:

  1. /U和/O条目是基于组合所有者和用户密码的单向算法计算的。
  2. 构建加密字典中的其余条目,包括权限,并将加密字典添加到预告字典中。
  3. 使用从加密字典计算的密钥对文件中的每个字符串和流进行加密。
  4. PDF对象图以通常的方式展平为文件。

同样,每个阶段涉及的实际算法随使用的加密方法而变化。

编辑加密文档

如果文件上的权限允许仅使用用户密码进行编辑,我们必须能够编写修改后的文件, 仍然使用相同的所有者和用户密码进行加密。但是,上面给出的算法需要知道 所有者密码才能再次加密文件以进行写入。

要解决此问题,即使必须在解密文件后删除加密字典本身,也会保留文件 原始读取的加密参数。因此可以重建加密字典(包括/O和/U条目)。