QPDF Manual

For QPDF Version 10.1.0, January 5, 2021

Jay Berkenbilt


Table of Contents

General Information
1. What is QPDF?
2. Building and Installing QPDF
2.1. System Requirements
2.2. Build Instructions
2.3. Crypto Providers
2.3.1. Build Support For Crypto Providers
2.3.2. Runtime Crypto Provider Selection
2.3.3. Crypto Provider Information for Developers
2.3.4. Crypto Provider Design Notes
2.4. Notes for Packagers
3. Running QPDF
3.1. Basic Invocation
3.1.1. Exit Status
3.2. Shell Completion
3.3. Basic Options
3.4. Encryption Options
3.5. Page Selection Options
3.6. Overlay and Underlay Options
3.7. Advanced Parsing Options
3.8. Advanced Transformation Options
3.9. Testing, Inspection, and Debugging Options
3.10. Unicode Passwords
4. QDF Mode
5. Using the QPDF Library
5.1. Using QPDF from C++
5.2. Using QPDF from other languages
5.3. A Note About Unicode File Names
6. QPDF JSON
6.1. Overview
6.2. JSON Guarantees
6.3. Limitations of JSON Representation
6.4. JSON: Special Considerations
7. Design and Library Notes
7.1. Introduction
7.2. Design Goals
7.3. Helper Classes
7.4. Implementation Notes
7.5. Casting Policy
7.6. Encryption
7.7. Random Number Generation
7.8. Adding and Removing Pages
7.9. Reserving Object Numbers
7.10. Copying Objects From Other PDF Files
7.11. Writing PDF Files
7.12. Filtered Streams
8. Linearization
8.1. Basic Strategy for Linearization
8.2. Preparing For Linearization
8.3. Optimization
8.4. Writing Linearized Files
8.5. Calculating Linearization Data
8.6. Known Issues with Linearization
8.7. Debugging Note
9. Object and Cross-Reference Streams
9.1. Object Streams
9.2. Cross-Reference Streams
9.2.1. Cross-Reference Stream Data
9.3. Implications for Linearized Files
9.4. Implementation Notes
A. Release Notes
B. Upgrading from 2.0 to 2.1
C. Upgrading to 3.0
D. Upgrading to 4.0

General Information

QPDF is a program that does structural, content-preserving transformations on PDF files. QPDF's website is located at http://qpdf.sourceforge.net/. QPDF's source code is hosted on github at https://github.com/qpdf/qpdf.

QPDF is licensed under the Apache License, Version 2.0 (the "License"). Unless required by applicable law or agreed to in writing, software distributed under the License is distributed on an "AS IS" BASIS, WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied. See the License for the specific language governing permissions and limitations under the License.

Versions of qpdf prior to version 7 were released under the terms of the Artistic License, version 2.0. At your option, you may continue to consider qpdf to be licensed under those terms. The Apache License 2.0 permits everything that the Artistic License 2.0 permits but is slightly less restrictive. Allowing the Artistic License to continue being used is primary to help people who may have to get specific approval to use qpdf in their products.

QPDF is intentionally released with a permissive license. However, if there is some reason that the licensing terms don't work for your requirements, please feel free to contact the copyright holder to make other arrangements.

QPDF was originally created in 2001 and modified periodically between 2001 and 2005 during my employment at Apex CoVantage. Upon my departure from Apex, the company graciously allowed me to take ownership of the software and continue maintaining as an open source project, a decision for which I am very grateful. I have made considerable enhancements to it since that time. I feel fortunate to have worked for people who would make such a decision. This work would not have been possible without their support.

Chapter 1. What is QPDF?

QPDF is a program that does structural, content-preserving transformations on PDF files. It could have been called something like pdf-to-pdf. It also provides many useful capabilities to developers of PDF-producing software or for people who just want to look at the innards of a PDF file to learn more about how they work.

With QPDF, it is possible to copy objects from one PDF file into another and to manipulate the list of pages in a PDF file. This makes it possible to merge and split PDF files. The QPDF library also makes it possible for you to create PDF files from scratch. In this mode, you are responsible for supplying all the contents of the file, while the QPDF library takes care off all the syntactical representation of the objects, creation of cross references tables and, if you use them, object streams, encryption, linearization, and other syntactic details. You are still responsible for generating PDF content on your own.

QPDF has been designed with very few external dependencies, and it is intentionally very lightweight. QPDF is not a PDF content creation library, a PDF viewer, or a program capable of converting PDF into other formats. In particular, QPDF knows nothing about the semantics of PDF content streams. If you are looking for something that can do that, you should look elsewhere. However, once you have a valid PDF file, QPDF can be used to transform that file in ways perhaps your original PDF creation can't handle. For example, many programs generate simple PDF files but can't password-protect them, web-optimize them, or perform other transformations of that type.

Chapter 2. Building and Installing QPDF

This chapter describes how to build and install qpdf. Please see also the README.md and INSTALL files in the source distribution.

2.1. System Requirements

The qpdf package has few external dependencies. In order to build qpdf, the following packages are required:

Part of qpdf's test suite does comparisons of the contents PDF files by converting them images and comparing the images. The image comparison tests are disabled by default. Those tests are not required for determining correctness of a qpdf build if you have not modified the code since the test suite also contains expected output files that are compared literally. The image comparison tests provide an extra check to make sure that any content transformations don't break the rendering of pages. Transformations that affect the content streams themselves are off by default and are only provided to help developers look into the contents of PDF files. If you are making deep changes to the library that cause changes in the contents of the files that qpdf generates, then you should enable the image comparison tests. Enable them by running configure with the --enable-test-compare-images flag. If you enable this, the following additional requirements are required by the test suite. Note that in no case are these items required to use qpdf.

If you do not enable this, then you do not need to have tiff and ghostscript.

Pre-built documentation is distributed with qpdf, so you should generally not need to rebuild the documentation. In order to build the documentation from its docbook sources, you need the docbook XML style sheets (http://downloads.sourceforge.net/docbook/). To build the PDF version of the documentation, you need Apache fop (http://xml.apache.org/fop/) version 0.94 or higher.

2.2. Build Instructions

Building qpdf on UNIX is generally just a matter of running

./configure
make

You can also run make check to run the test suite and make install to install. Please run ./configure --help for options on what can be configured. You can also set the value of DESTDIR during installation to install to a temporary location, as is common with many open source packages. Please see also the README.md and INSTALL files in the source distribution.

Building on Windows is a little bit more complicated. For details, please see README-windows.md in the source distribution. You can also download a binary distribution for Windows. There is a port of qpdf to Visual C++ version 6 in the contrib area generously contributed by Jian Ma. This is also discussed in more detail in README-windows.md.

While wchar_t is part of the C++ standard, qpdf uses it in only one place in the public API, and it's just in a helper function. It is possible to build qpdf on a system that doesn't have wchar_t, and it's also possible to compile a program that uses qpdf on a system without wchar_t as long as you don't call that one method. This is a very unusual situation. For a detailed discussion, please see the top-level README.md file in qpdf's source distribution.

There are some other things you can do with the build. Although qpdf uses autoconf, it does not use automake but instead uses a hand-crafted non-recursive Makefile that requires gnu make. If you're really interested, please read the comments in the top-level Makefile.

2.3. Crypto Providers

Starting with qpdf 9.1.0, the qpdf library can be built with multiple implementations of providers of cryptographic functions, which we refer to as “crypto providers.” At the time of writing, a crypto implementation must provide MD5 and SHA2 (256, 384, and 512-bit) hashes and RC4 and AES256 with and without CBC encryption. In the future, if digital signature is added to qpdf, there may be additional requirements beyond this.

Starting with qpdf version 9.1.0, the available implementations are native and gnutls. In qpdf 10.0.0, openssl was added. Additional implementations may be added if needed. It is also possible for a developer to provide their own implementation without modifying the qpdf library.

2.3.1. Build Support For Crypto Providers

When building with qpdf's build system, crypto providers can be enabled at build time using various ./configure options. The default behavior is for ./configure to discover which crypto providers can be supported based on available external libraries, to build all available crypto providers, and to use an external provider as the default over the native one. This behavior can be changed with the following flags to ./configure:

  • --enable-crypto-x (where x is a supported crypto provider): enable the x crypto provider, requiring any external dependencies it needs

  • --disable-crypto-x: disable the x provider, and do not link against its dependencies even if they are available

  • --with-default-crypto=x: make x the default provider even if a higher priority one is available

  • --disable-implicit-crypto: only build crypto providers that are explicitly requested with an --enable-crypto-x option

For example, if you want to guarantee that the gnutls crypto provider is used and that the native provider is not built, you could run ./configure --enable-crypto-gnutls --disable-implicit-crypto.

If you build qpdf using your own build system, in order for qpdf to work at all, you need to enable at least one crypto provider. The file libqpdf/qpdf/qpdf-config.h.in provides macros DEFAULT_CRYPTO, whose value must be a string naming the default crypto provider, and various symbols starting with USE_CRYPTO_, at least one of which has to be enabled. Additionally, you must compile the source files that implement a crypto provider. To get a list of those files, look at libqpdf/build.mk. If you want to omit a particular crypto provider, as long as its USE_CRYPTO_ symbol is undefined, you can completely ignore the source files that belong to a particular crypto provider. Additionally, crypto providers may have their own external dependencies that can be omitted if the crypto provider is not used. For example, if you are building qpdf yourself and are using an environment that does not support gnutls or openssl, you can ensure that USE_CRYPTO_NATIVE is defined, USE_CRYPTO_GNUTLS is not defined, and DEFAULT_CRYPTO is defined to "native". Then you must include the source files used in the native implementation, some of which were added or renamed from earlier versions, to your build, and you can ignore QPDFCrypto_gnutls.cc. Always consult libqpdf/build.mk to get the list of source files you need to build.

2.3.2. Runtime Crypto Provider Selection

You can use the --show-crypto option to qpdf to get a list of available crypto providers. The default provider is always listed first, and the rest are listed in lexical order. Each crypto provider is listed on a line by itself with no other text, enabling the output of this command to be used easily in scripts.

You can override which crypto provider is used by setting the QPDF_CRYPTO_PROVIDER environment variable. There are few reasons to ever do this, but you might want to do it if you were explicitly trying to compare behavior of two different crypto providers while testing performance or reproducing a bug. It could also be useful for people who are implementing their own crypto providers.

2.3.3. Crypto Provider Information for Developers

If you are writing code that uses libqpdf and you want to force a certain crypto provider to be used, you can call the method QPDFCryptoProvider::setDefaultProvider. The argument is the name of a built-in or developer-supplied provider. To add your own crypto provider, you have to create a class derived from QPDFCryptoImpl and register it with QPDFCryptoProvider. For additional information, see comments in include/qpdf/QPDFCryptoImpl.hh.

2.3.4. Crypto Provider Design Notes

This section describes a few bits of rationale for why the crypto provider interface was set up the way it was. You don't need to know any of this information, but it's provided for the record and in case it's interesting.

As a general rule, I want to avoid as much as possible including large blocks of code that are conditionally compiled such that, in most builds, some code is never built. This is dangerous because it makes it very easy for invalid code to creep in unnoticed. As such, I want it to be possible to build qpdf with all available crypto providers, and this is the way I build qpdf for local development. At the same time, if a particular packager feels that it is a security liability for qpdf to use crypto functionality from other than a library that gets considerable scrutiny for this specific purpose (such as gnutls, openssl, or nettle), then I want to give that packager the ability to completely disable qpdf's native implementation. Or if someone wants to avoid adding a dependency on one of the external crypto providers, I don't want the availability of the provider to impose additional external dependencies within that environment. Both of these are situations that I know to be true for some users of qpdf.

I want registration and selection of crypto providers to be thread-safe, and I want it to work deterministically for a developer to provide their own crypto provider and be able to set it up as the default. This was the primary motivation behind requiring C++-11 as doing so enabled me to exploit the guaranteed thread safety of local block static initialization. The QPDFCryptoProvider class uses a singleton pattern with thread-safe initialization to create the singleton instance of QPDFCryptoProvider and exposes only static methods in its public interface. In this way, if a developer wants to call any QPDFCryptoProvider methods, the library guarantees the QPDFCryptoProvider is fully initialized and all built-in crypto providers are registered. Making QPDFCryptoProvider actually know about all the built-in providers may seem a bit sad at first, but this choice makes it extremely clear exactly what the initialization behavior is. There's no question about provider implementations automatically registering themselves in a nondeterministic order. It also means that implementations do not need to know anything about the provider interface, which makes them easier to test in isolation. Another advantage of this approach is that a developer who wants to develop their own crypto provider can do so in complete isolation from the qpdf library and, with just two calls, can make qpdf use their provider in their application. If they decided to contribute their code, plugging it into the qpdf library would require a very small change to qpdf's source code.

The decision to make the crypto provider selectable at runtime was one I struggled with a little, but I decided to do it for various reasons. Allowing an end user to switch crypto providers easily could be very useful for reproducing a potential bug. If a user reports a bug that some cryptographic thing is broken, I can easily ask that person to try with the QPDF_CRYPTO_PROVIDER variable set to different values. The same could apply in the event of a performance problem. This also makes it easier for qpdf's own test suite to exercise code with different providers without having to make every program that links with qpdf aware of the possibility of multiple providers. In qpdf's continuous integration environment, the entire test suite is run for each supported crypto provider. This is made simple by being able to select the provider using an environment variable.

Finally, making crypto providers selectable in this way establish a pattern that I may follow again in the future for stream filter providers. One could imagine a future enhancement where someone could provide their own implementations for basic filters like /FlateDecode or for other filters that qpdf doesn't support. Implementing the registration functions and internal storage of registered providers was also easier using C++-11's functional interfaces, which was another reason to require C++-11 at this time.

2.4. Notes for Packagers

If you are packaging qpdf for an operating system distribution, here are some things you may want to keep in mind:

  • Starting in qpdf version 9.1.1, qpdf no longer has a runtime dependency on perl. This is because fix-qdf was rewritten in C++. However, qpdf still has a build-time dependency on perl.

  • Make sure you are getting the intended behavior with regard to crypto providers. Read Section 2.3.1, “Build Support For Crypto Providers” for details.

  • Passing --enable-show-failed-test-output to ./configure will cause any failed test output to be written to the console. This can be very useful for seeing test failures generated by autobuilders where you can't access qtest.log after the fact.

  • If qpdf's build environment detects the presence of autoconf and related tools, it will check to ensure that automatically generated files are up-to-date with recorded checksums and fail if it detects a discrepancy. This feature is intended to prevent you from accidentally forgetting to regenerate automatic files after modifying their sources. If your packaging environment automatically refreshes automatic files, it can cause this check to fail. Suppress qpdf's checks by passing --disable-check-autofiles to /.configure. This is safe since qpdf's autogen.sh just runs autotools in the normal way.

  • QPDF's make install does not install completion files by default, but as a packager, it's good if you install them wherever your distribution expects such files to go. You can find completion files to install in the completions directory.

  • Packagers are encouraged to install the source files from the examples directory along with qpdf development packages.

Chapter 3. Running QPDF

This chapter describes how to run the qpdf program from the command line.

3.1. Basic Invocation

When running qpdf, the basic invocation is as follows:

qpdf [ options ] infilename [ outfilename ]

This converts PDF file infilename to PDF file outfilename. The output file is functionally identical to the input file but may have been structurally reorganized. Also, orphaned objects will be removed from the file. Many transformations are available as controlled by the options below. In place of infilename, the parameter --empty may be specified. This causes qpdf to use a dummy input file that contains zero pages. The only normal use case for using --empty would be if you were going to add pages from another source, as discussed in Section 3.5, “Page Selection Options”.

If @filename appears anywhere in the command-line, it will be read line by line, and each line will be treated as a command-line argument. The @- option allows arguments to be read from standard input. This allows qpdf to be invoked with an arbitrary number of arbitrarily long arguments. It is also very useful for avoiding having to pass passwords on the command line.

outfilename does not have to be seekable, even when generating linearized files. Specifying “-” as outfilename means to write to standard output. If you want to overwrite the input file with the output, use the option --replace-input and omit the output file name. You can't specify the same file as both the input and the output. If you do this, qpdf will tell you about the --replace-input option.

Most options require an output file, but some testing or inspection commands do not. These are specifically noted.

3.1.1. Exit Status

The exit status of qpdf may be interpreted as follows:

  • 0: no errors or warnings were found. The file may still have problems qpdf can't detect. If --warning-exit-0 was specified, exit status 0 is used even if there are warnings.

  • 2: errors were found. qpdf was not able to fully process the file.

  • 3: qpdf encountered problems that it was able to recover from. In some cases, the resulting file may still be damaged. Note that qpdf still exits with status 3 if it finds warnings even when --no-warn is specified. With --warning-exit-0, warnings without errors exit with status 0 instead of 3.

Note that qpdf never exists with status 1. If you get an exit status of 1, it was something else, like the shell not being able to find or execute qpdf.

3.2. Shell Completion

Starting in qpdf version 8.3.0, qpdf provides its own completion support for zsh and bash. You can enable bash completion with eval $(qpdf --completion-bash) and zsh completion with eval $(qpdf --completion-zsh). If qpdf is not in your path, you should invoke it above with an absolute path. If you invoke it with a relative path, it will warn you, and the completion won't work if you're in a different directory.

qpdf will use argv[0] to figure out where its executable is. This may produce unwanted results in some cases, especially if you are trying to use completion with copy of qpdf that is built from source. You can specify a full path to the qpdf you want to use for completion in the QPDF_EXECUTABLE environment variable.

3.3. Basic Options

The following options are the most common ones and perform commonly needed transformations.

--help

Display command-line invocation help.

--version

Display the current version of qpdf.

--copyright

Show detailed copyright information.

--show-crypto

Show a list of available crypto providers, each on a line by itself. The default provider is always listed first. See Section 2.3, “Crypto Providers” for more information about crypto providers.

--completion-bash

Output a completion command you can eval to enable shell completion from bash.

--completion-zsh

Output a completion command you can eval to enable shell completion from zsh.

--password=password

Specifies a password for accessing encrypted files. Note that you can use @filename or @- as described above to put the password in a file or pass it via standard input so you can avoid specifying it on the command line.

--is-encrypted

Silently exit with status 0 if the file is encrypted or status 2 if the file is not encrypted. This is useful for shell scripts. Other options are ignored if this is given. This option is mutually exclusive with --requires-password. Both this option and --requires-password exit with status 2 for non-encrypted files.

--requires-password

Silently exit with status 0 if a password (other than as supplied) is required. Exit with status 2 if the file is not encrypted. Exit with status 3 if the file is encrypted but requires no password or the correct password has been supplied. This is useful for shell scripts. Note that any supplied password is used when opening the file. When used with a --password option, this option can be used to check the correctness of the password. In that case, an exit status of 3 means the file works with the supplied password. This option is mutually exclusive with --is-encrypted. Both this option and --is-encrypted exit with status 2 for non-encrypted files.

--verbose

Increase verbosity of output. For now, this just prints some indication of any file that it creates.

--progress

Indicate progress while writing files.

--no-warn

Suppress writing of warnings to stderr. If warnings were detected and suppressed, qpdf will still exit with exit code 3. See also --warning-exit-0.

--warning-exit-0

If warnings are found but no errors, exit with exit code 0 instead 3. When combined with --no-warn, the effect is for qpdf to completely ignore warnings.

--linearize

Causes generation of a linearized (web-optimized) output file.

--replace-input

If specified, the output file name should be omitted. This option tells qpdf to replace the input file with the output. It does this by writing to infilename.~qpdf-temp# and, when done, overwriting the input file with the temporary file. If there were any warnings, the original input is saved as infilename.~qpdf-orig.

--copy-encryption=file

Encrypt the file using the same encryption parameters, including user and owner password, as the specified file. Use --encryption-file-password to specify a password if one is needed to open this file. Note that copying the encryption parameters from a file also copies the first half of /ID from the file since this is part of the encryption parameters.

--encryption-file-password=password

If the file specified with --copy-encryption requires a password, specify the password using this option. Note that only one of the user or owner password is required. Both passwords will be preserved since QPDF does not distinguish between the two passwords. It is possible to preserve encryption parameters, including the owner password, from a file even if you don't know the file's owner password.

--encrypt options --

Causes generation an encrypted output file. Please see Section 3.4, “Encryption Options” for details on how to specify encryption parameters.

--decrypt

Removes any encryption on the file. A password must be supplied if the file is password protected.

--password-is-hex-key

Overrides the usual computation/retrieval of the PDF file's encryption key from user/owner password with an explicit specification of the encryption key. When this option is specified, the argument to the --password option is interpreted as a hexadecimal-encoded key value. This only applies to the password used to open the main input file. It does not apply to other files opened by --pages or other options or to files being written.

Most users will never have a need for this option, and no standard viewers support this mode of operation, but it can be useful for forensic or investigatory purposes. For example, if a PDF file is encrypted with an unknown password, a brute-force attack using the key directly is sometimes more efficient than one using the password. Also, if a file is heavily damaged, it may be possible to derive the encryption key and recover parts of the file using it directly. To expose the encryption key used by an encrypted file that you can open normally, use the --show-encryption-key option.

--suppress-password-recovery

Ordinarily, qpdf attempts to automatically compensate for passwords specified in the wrong character encoding. This option suppresses that behavior. Under normal conditions, there are no reasons to use this option. See Section 3.10, “Unicode Passwords” for a discussion

--password-mode=mode

This option can be used to fine-tune how qpdf interprets Unicode (non-ASCII) password strings passed on the command line. With the exception of the hex-bytes mode, these only apply to passwords provided when encrypting files. The hex-bytes mode also applies to passwords specified for reading files. For additional discussion of the supported password modes and when you might want to use them, see Section 3.10, “Unicode Passwords”. The following modes are supported:

  • auto: Automatically determine whether the specified password is a properly encoded Unicode (UTF-8) string, and transcode it as required by the PDF spec based on the type encryption being applied. On Windows starting with version 8.4.0, and on almost all other modern platforms, incoming passwords will be properly encoded in UTF-8, so this is almost always what you want.

  • unicode: Tells qpdf that the incoming password is UTF-8, overriding whatever its automatic detection determines. The only difference between this mode and auto is that qpdf will fail with an error message if the password is not valid UTF-8 instead of falling back to bytes mode with a warning.

  • bytes: Interpret the password as a literal byte string. For non-Windows platforms, this is what versions of qpdf prior to 8.4.0 did. For Windows platforms, there is no way to specify strings of binary data on the command line directly, but you can use the @filename option to do it, in which case this option forces qpdf to respect the string of bytes as provided. This option will allow you to encrypt PDF files with passwords that will not be usable by other readers.

  • hex-bytes: Interpret the password as a hex-encoded string. This provides a way to pass binary data as a password on all platforms including Windows. As with bytes, this option may allow creation of files that can't be opened by other readers. This mode affects qpdf's interpretation of passwords specified for decrypting files as well as for encrypting them. It makes it possible to specify strings that are encoded in some manner other than the system's default encoding.

--rotate=[+|-]angle[:page-range]

Apply rotation to specified pages. The page-range portion of the option value has the same format as page ranges in Section 3.5, “Page Selection Options”. If the page range is omitted, the rotation is applied to all pages. The angle portion of the parameter may be either 90, 180, or 270. If preceded by + or -, the angle is added to or subtracted from the specified pages' original rotations. This is almost always what you want. Otherwise the pages' rotations are set to the exact value, which may cause the appearances of the pages to be inconsistent, especially for scans. For example, the command qpdf in.pdf out.pdf --rotate=+90:2,4,6 --rotate=180:7-8 would rotate pages 2, 4, and 6 90 degrees clockwise from their original rotation and force the rotation of pages 7 through 9 to 180 degrees regardless of their original rotation, and the command qpdf in.pdf out.pdf --rotate=+180 would rotate all pages by 180 degrees.

--keep-files-open=[yn]

This option controls whether qpdf keeps individual files open while merging. Prior to version 8.1.0, qpdf always kept all files open, but this meant that the number of files that could be merged was limited by the operating system's open file limit. Version 8.1.0 opened files as they were referenced and closed them after each read, but this caused a major performance impact. Version 8.2.0 optimized the performance but did so in a way that, for local file systems, there was a small but unavoidable performance hit, but for networked file systems, the performance impact could be very high. Starting with version 8.2.1, the default behavior is that files are kept open if no more than 200 files are specified, but that the behavior can be explicitly overridden with the --keep-files-open flag. If you are merging more than 200 files but less than the operating system's max open files limit, you may want to use --keep-files-open=y, especially if working over a networked file system. If you are using a local file system where the overhead is low and you might sometimes merge more than the OS limit's number of files from a script and are not worried about a few seconds additional processing time, you may want to specify --keep-files-open=n. The threshold for switching may be changed from the default 200 with the --keep-files-open-threshold option.

--keep-files-open-threshold=count

If specified, overrides the default value of 200 used as the threshold for qpdf deciding whether or not to keep files open. See --keep-files-open for details.

--pages options --

Select specific pages from one or more input files. See Section 3.5, “Page Selection Options” for details on how to do page selection (splitting and merging).

--collate

When specified, collate rather than concatenate pages from files specified with --pages. See Section 3.5, “Page Selection Options” for additional details.

--flatten-rotation

For each page that is rotated using the /Rotate key in the page's dictionary, remove the /Rotate key and implement the identical rotation semantics by modifying the page's contents. This option can be useful to prepare files for buggy PDF applications that don't properly handle rotated pages.

--split-pages=[n]

Write each group of n pages to a separate output file. If n is not specified, create single pages. Output file names are generated as follows:

  • If the string %d appears in the output file name, it is replaced with a range of zero-padded page numbers starting from 1.

  • Otherwise, if the output file name ends in .pdf (case insensitive), a zero-padded page range, preceded by a dash, is inserted before the file extension.

  • Otherwise, the file name is appended with a zero-padded page range preceded by a dash.

Page ranges are a single number in the case of single-page groups or two numbers separated by a dash otherwise. For example, if infile.pdf has 12 pages

  • qpdf --split-pages infile.pdf %d-out would generate files 01-out through 12-out

  • qpdf --split-pages=2 infile.pdf outfile.pdf would generate files outfile-01-02.pdf through outfile-11-12.pdf

  • qpdf --split-pages infile.pdf something.else would generate files something.else-01 through something.else-12

Note that outlines, threads, and other global features of the original PDF file are not preserved. For each page of output, this option creates an empty PDF and copies a single page from the output into it. If you require the global data, you will have to run qpdf with the --pages option once for each file. Using --split-pages is much faster if you don't require the global data.

--overlay options --

Overlay pages from another file onto the output pages. See Section 3.6, “Overlay and Underlay Options” for details on overlay/underlay.

--underlay options --

Overlay pages from another file onto the output pages. See Section 3.6, “Overlay and Underlay Options” for details on overlay/underlay.

Password-protected files may be opened by specifying a password. By default, qpdf will preserve any encryption data associated with a file. If --decrypt is specified, qpdf will attempt to remove any encryption information. If --encrypt is specified, qpdf will replace the document's encryption parameters with whatever is specified.

Note that qpdf does not obey encryption restrictions already imposed on the file. Doing so would be meaningless since qpdf can be used to remove encryption from the file entirely. This functionality is not intended to be used for bypassing copyright restrictions or other restrictions placed on files by their producers.

Prior to 8.4.0, in the case of passwords that contain characters that fall outside of 7-bit US-ASCII, qpdf left the burden of supplying properly encoded encryption and decryption passwords to the user. Starting in qpdf 8.4.0, qpdf does this automatically in most cases. For an in-depth discussion, please see Section 3.10, “Unicode Passwords”. Previous versions of this manual described workarounds using the iconv command. Such workarounds are no longer required or recommended with qpdf 8.4.0. However, for backward compatibility, qpdf attempts to detect those workarounds and do the right thing in most cases.

3.4. Encryption Options

To change the encryption parameters of a file, use the --encrypt flag. The syntax is

--encrypt user-password owner-password key-length [ restrictions ] --

Note that “--” terminates parsing of encryption flags and must be present even if no restrictions are present.

Either or both of the user password and the owner password may be empty strings.

The value for key-length may be 40, 128, or 256. The restriction flags are dependent upon key length. When no additional restrictions are given, the default is to be fully permissive.

If key-length is 40, the following restriction options are available:

--print=[yn]

Determines whether or not to allow printing.

--modify=[yn]

Determines whether or not to allow document modification.

--extract=[yn]

Determines whether or not to allow text/image extraction.

--annotate=[yn]

Determines whether or not to allow comments and form fill-in and signing.

If key-length is 128, the following restriction options are available:

--accessibility=[yn]

Determines whether or not to allow accessibility to visually impaired. The qpdf library disregards this field when AES is used or when 256-bit encryption is used. You should really never disable accessibility, but qpdf lets you do it in case you need to configure a file this way for testing purposes. The PDF spec says that conforming readers should disregard this permission and always allow accessibility.

--extract=[yn]

Determines whether or not to allow text/graphic extraction.

--assemble=[yn]

Determines whether document assembly (rotation and reordering of pages) is allowed.

--annotate=[yn]

Determines whether modifying annotations is allowed. This includes adding comments and filling in form fields. Also allows editing of form fields if --modify-other=y is given.

--form=[yn]

Determines whether filling form fields is allowed.

--modify-other=[yn]

Allow all document editing except those controlled separately by the --assemble, --annotate, and --form options.

--print=print-opt

Controls printing access. print-opt may be one of the following:

  • full: allow full printing

  • low: allow low-resolution printing only

  • none: disallow printing

--modify=modify-opt

Controls modify access. This way of controlling modify access has less granularity than new options added in qpdf 8.4. modify-opt may be one of the following:

  • all: allow full document modification

  • annotate: allow comment authoring, form operations, and document assembly

  • form: allow form field fill-in and signing and document assembly

  • assembly: allow document assembly only

  • none: allow no modifications

Using the --modify option does not allow you to create certain combinations of permissions such as allowing form filling but not allowing document assembly. Starting with qpdf 8.4, you can either just use the other options to control fields individually, or you can use something like --modify=form --assembly=n to fine tune.

--cleartext-metadata

If specified, any metadata stream in the document will be left unencrypted even if the rest of the document is encrypted. This also forces the PDF version to be at least 1.5.

--use-aes=[yn]

If --use-aes=y is specified, AES encryption will be used instead of RC4 encryption. This forces the PDF version to be at least 1.6.

--force-V4

Use of this option forces the /V and /R parameters in the document's encryption dictionary to be set to the value 4. As qpdf will automatically do this when required, there is no reason to ever use this option. It exists primarily for use in testing qpdf itself. This option also forces the PDF version to be at least 1.5.

If key-length is 256, the minimum PDF version is 1.7 with extension level 8, and the AES-based encryption format used is the PDF 2.0 encryption method supported by Acrobat X. the same options are available as with 128 bits with the following exceptions:

--use-aes

This option is not available with 256-bit keys. AES is always used with 256-bit encryption keys.

--force-V4

This option is not available with 256 keys.

--force-R5

If specified, qpdf sets the minimum version to 1.7 at extension level 3 and writes the deprecated encryption format used by Acrobat version IX. This option should not be used in practice to generate PDF files that will be in general use, but it can be useful to generate files if you are trying to test proper support in another application for PDF files encrypted in this way.

The default for each permission option is to be fully permissive.

3.5. Page Selection Options

Starting with qpdf 3.0, it is possible to split and merge PDF files by selecting pages from one or more input files. Whatever file is given as the primary input file is used as the starting point, but its pages are replaced with pages as specified.

--pages input-file [ --password=password ] [ page-range ] [ ... ] --

Multiple input files may be specified. Each one is given as the name of the input file, an optional password (if required to open the file), and the range of pages. Note that “--” terminates parsing of page selection flags.

Starting with qpf 8.4, the special input file name “.” can be used shortcut for the primary input filename.

For each file that pages should be taken from, specify the file, a password needed to open the file (if any), and a page range. The password needs to be given only once per file. If any of the input files are the same as the primary input file or the file used to copy encryption parameters (if specified), you do not need to repeat the password here. The same file can be repeated multiple times. If a file that is repeated has a password, the password only has to be given the first time. All non-page data (info, outlines, page numbers, etc.) are taken from the primary input file. To discard these, use --empty as the primary input.

Starting with qpdf 5.0.0, it is possible to omit the page range. If qpdf sees a value in the place where it expects a page range and that value is not a valid range but is a valid file name, qpdf will implicitly use the range 1-z, meaning that it will include all pages in the file. This makes it possible to easily combine all pages in a set of files with a command like qpdf --empty out.pdf --pages *.pdf --.

The page range is a set of numbers separated by commas, ranges of numbers separated dashes, or combinations of those. The character “z” represents the last page. A number preceded by an “r” indicates to count from the end, so r3-r1