Commit 9eb5982fa334a2db42a278fce853bd7ebd2a61a7
1 parent
0ea70e5d
Avoid modifying trailer when writing
When preparing the trailer for writing to the new file, trim a copy of the trailer instead of the original file's trailer.
Showing
2 changed files
with
16 additions
and
10 deletions
include/qpdf/QPDFWriter.hh
| ... | ... | @@ -322,6 +322,7 @@ class QPDFWriter |
| 322 | 322 | void setDataKey(int objid); |
| 323 | 323 | int openObject(int objid = 0); |
| 324 | 324 | void closeObject(int objid); |
| 325 | + QPDFObjectHandle getTrimmedTrailer(); | |
| 325 | 326 | void prepareFileForWrite(); |
| 326 | 327 | void writeStandard(); |
| 327 | 328 | void writeLinearized(); | ... | ... |
libqpdf/QPDFWriter.cc
| ... | ... | @@ -1057,7 +1057,7 @@ void |
| 1057 | 1057 | QPDFWriter::writeTrailer(trailer_e which, int size, bool xref_stream, |
| 1058 | 1058 | qpdf_offset_t prev) |
| 1059 | 1059 | { |
| 1060 | - QPDFObjectHandle trailer = pdf.getTrailer(); | |
| 1060 | + QPDFObjectHandle trailer = getTrimmedTrailer(); | |
| 1061 | 1061 | if (! xref_stream) |
| 1062 | 1062 | { |
| 1063 | 1063 | writeString("trailer <<"); |
| ... | ... | @@ -1932,20 +1932,19 @@ QPDFWriter::generateObjectStreams() |
| 1932 | 1932 | } |
| 1933 | 1933 | } |
| 1934 | 1934 | |
| 1935 | -void | |
| 1936 | -QPDFWriter::prepareFileForWrite() | |
| 1935 | +QPDFObjectHandle | |
| 1936 | +QPDFWriter::getTrimmedTrailer() | |
| 1937 | 1937 | { |
| 1938 | 1938 | // Remove keys from the trailer that necessarily have to be |
| 1939 | 1939 | // replaced when writing the file. |
| 1940 | 1940 | |
| 1941 | - QPDFObjectHandle trailer = pdf.getTrailer(); | |
| 1941 | + QPDFObjectHandle trailer = pdf.getTrailer().shallowCopy(); | |
| 1942 | 1942 | |
| 1943 | - // Note that removing the encryption dictionary does not interfere | |
| 1944 | - // with reading encrypted files. QPDF loads all the information | |
| 1945 | - // it needs from the encryption dictionary at the beginning and | |
| 1946 | - // never looks at it again. | |
| 1943 | + // Remove encryption keys | |
| 1947 | 1944 | trailer.removeKey("/ID"); |
| 1948 | 1945 | trailer.removeKey("/Encrypt"); |
| 1946 | + | |
| 1947 | + // Remove modification information | |
| 1949 | 1948 | trailer.removeKey("/Prev"); |
| 1950 | 1949 | |
| 1951 | 1950 | // Remove all trailer keys that potentially come from a |
| ... | ... | @@ -1958,6 +1957,12 @@ QPDFWriter::prepareFileForWrite() |
| 1958 | 1957 | trailer.removeKey("/Type"); |
| 1959 | 1958 | trailer.removeKey("/XRefStm"); |
| 1960 | 1959 | |
| 1960 | + return trailer; | |
| 1961 | +} | |
| 1962 | + | |
| 1963 | +void | |
| 1964 | +QPDFWriter::prepareFileForWrite() | |
| 1965 | +{ | |
| 1961 | 1966 | // Do a traversal of the entire PDF file structure replacing all |
| 1962 | 1967 | // indirect objects that QPDFWriter wants to be direct. This |
| 1963 | 1968 | // includes stream lengths, stream filtering parameters, and |
| ... | ... | @@ -1967,7 +1972,7 @@ QPDFWriter::prepareFileForWrite() |
| 1967 | 1972 | // holders. |
| 1968 | 1973 | |
| 1969 | 1974 | std::list<QPDFObjectHandle> queue; |
| 1970 | - queue.push_back(pdf.getTrailer()); | |
| 1975 | + queue.push_back(getTrimmedTrailer()); | |
| 1971 | 1976 | std::set<int> visited; |
| 1972 | 1977 | |
| 1973 | 1978 | while (! queue.empty()) |
| ... | ... | @@ -2861,7 +2866,7 @@ QPDFWriter::writeStandard() |
| 2861 | 2866 | writeString(this->extra_header_text); |
| 2862 | 2867 | |
| 2863 | 2868 | // Put root first on queue. |
| 2864 | - QPDFObjectHandle trailer = pdf.getTrailer(); | |
| 2869 | + QPDFObjectHandle trailer = getTrimmedTrailer(); | |
| 2865 | 2870 | enqueueObject(trailer.getKey("/Root")); |
| 2866 | 2871 | |
| 2867 | 2872 | // Next place any other objects referenced from the trailer | ... | ... |