Commit 5696a507b6dacf34d066810a3f2fca3525eb02f5
Committed by
GitHub
Merge pull request #731 from m-holger/og_unparse
Tidy QPDFObjGen related code
Showing
22 changed files
with
291 additions
and
390 deletions
examples/pdf-create.cc
| @@ -29,8 +29,7 @@ class ImageProvider: public QPDFObjectHandle::StreamDataProvider | @@ -29,8 +29,7 @@ class ImageProvider: public QPDFObjectHandle::StreamDataProvider | ||
| 29 | public: | 29 | public: |
| 30 | ImageProvider(std::string const& color_space, std::string const& filter); | 30 | ImageProvider(std::string const& color_space, std::string const& filter); |
| 31 | virtual ~ImageProvider() = default; | 31 | virtual ~ImageProvider() = default; |
| 32 | - virtual void | ||
| 33 | - provideStreamData(int objid, int generation, Pipeline* pipeline); | 32 | + virtual void provideStreamData(QPDFObjGen const&, Pipeline* pipeline); |
| 34 | size_t getWidth() const; | 33 | size_t getWidth() const; |
| 35 | size_t getHeight() const; | 34 | size_t getHeight() const; |
| 36 | 35 | ||
| @@ -93,7 +92,7 @@ ImageProvider::getHeight() const | @@ -93,7 +92,7 @@ ImageProvider::getHeight() const | ||
| 93 | } | 92 | } |
| 94 | 93 | ||
| 95 | void | 94 | void |
| 96 | -ImageProvider::provideStreamData(int objid, int generation, Pipeline* pipeline) | 95 | +ImageProvider::provideStreamData(QPDFObjGen const&, Pipeline* pipeline) |
| 97 | { | 96 | { |
| 98 | std::vector<std::shared_ptr<Pipeline>> to_delete; | 97 | std::vector<std::shared_ptr<Pipeline>> to_delete; |
| 99 | Pipeline* p = pipeline; | 98 | Pipeline* p = pipeline; |
| @@ -292,7 +291,7 @@ check( | @@ -292,7 +291,7 @@ check( | ||
| 292 | ImageProvider* p = new ImageProvider(desired_color_space, "null"); | 291 | ImageProvider* p = new ImageProvider(desired_color_space, "null"); |
| 293 | std::shared_ptr<QPDFObjectHandle::StreamDataProvider> provider(p); | 292 | std::shared_ptr<QPDFObjectHandle::StreamDataProvider> provider(p); |
| 294 | Pl_Buffer b_p("get image data"); | 293 | Pl_Buffer b_p("get image data"); |
| 295 | - provider->provideStreamData(0, 0, &b_p); | 294 | + provider->provideStreamData(QPDFObjGen(), &b_p); |
| 296 | std::shared_ptr<Buffer> desired_data(b_p.getBuffer()); | 295 | std::shared_ptr<Buffer> desired_data(b_p.getBuffer()); |
| 297 | 296 | ||
| 298 | if (desired_data->getSize() != actual_data->getSize()) { | 297 | if (desired_data->getSize() != actual_data->getSize()) { |
examples/pdf-custom-filter.cc
| @@ -201,7 +201,7 @@ class StreamReplacer: public QPDFObjectHandle::StreamDataProvider | @@ -201,7 +201,7 @@ class StreamReplacer: public QPDFObjectHandle::StreamDataProvider | ||
| 201 | StreamReplacer(QPDF* pdf); | 201 | StreamReplacer(QPDF* pdf); |
| 202 | virtual ~StreamReplacer() = default; | 202 | virtual ~StreamReplacer() = default; |
| 203 | virtual void | 203 | virtual void |
| 204 | - provideStreamData(int objid, int generation, Pipeline* pipeline) override; | 204 | + provideStreamData(QPDFObjGen const& og, Pipeline* pipeline) override; |
| 205 | 205 | ||
| 206 | void registerStream( | 206 | void registerStream( |
| 207 | QPDFObjectHandle stream, | 207 | QPDFObjectHandle stream, |
| @@ -384,9 +384,8 @@ StreamReplacer::registerStream( | @@ -384,9 +384,8 @@ StreamReplacer::registerStream( | ||
| 384 | } | 384 | } |
| 385 | 385 | ||
| 386 | void | 386 | void |
| 387 | -StreamReplacer::provideStreamData(int objid, int generation, Pipeline* pipeline) | 387 | +StreamReplacer::provideStreamData(QPDFObjGen const& og, Pipeline* pipeline) |
| 388 | { | 388 | { |
| 389 | - QPDFObjGen og(objid, generation); | ||
| 390 | QPDFObjectHandle orig = this->copied_streams[og]; | 389 | QPDFObjectHandle orig = this->copied_streams[og]; |
| 391 | // call maybeReplace again, this time with the pipeline and no | 390 | // call maybeReplace again, this time with the pipeline and no |
| 392 | // dict_updates. In this mode, maybeReplace doesn't make any | 391 | // dict_updates. In this mode, maybeReplace doesn't make any |
examples/pdf-invert-images.cc
| @@ -35,7 +35,7 @@ class ImageInverter: public QPDFObjectHandle::StreamDataProvider | @@ -35,7 +35,7 @@ class ImageInverter: public QPDFObjectHandle::StreamDataProvider | ||
| 35 | public: | 35 | public: |
| 36 | virtual ~ImageInverter() = default; | 36 | virtual ~ImageInverter() = default; |
| 37 | virtual void | 37 | virtual void |
| 38 | - provideStreamData(int objid, int generation, Pipeline* pipeline) override; | 38 | + provideStreamData(QPDFObjGen const& og, Pipeline* pipeline) override; |
| 39 | 39 | ||
| 40 | void registerImage( | 40 | void registerImage( |
| 41 | QPDFObjectHandle image, | 41 | QPDFObjectHandle image, |
| @@ -82,12 +82,11 @@ ImageInverter::registerImage( | @@ -82,12 +82,11 @@ ImageInverter::registerImage( | ||
| 82 | } | 82 | } |
| 83 | 83 | ||
| 84 | void | 84 | void |
| 85 | -ImageInverter::provideStreamData(int objid, int generation, Pipeline* pipeline) | 85 | +ImageInverter::provideStreamData(QPDFObjGen const& og, Pipeline* pipeline) |
| 86 | { | 86 | { |
| 87 | // Use the object and generation number supplied to look up the | 87 | // Use the object and generation number supplied to look up the |
| 88 | // image data. Then invert the image data and write the inverted | 88 | // image data. Then invert the image data and write the inverted |
| 89 | // data to the pipeline. | 89 | // data to the pipeline. |
| 90 | - QPDFObjGen og(objid, generation); | ||
| 91 | std::shared_ptr<Buffer> data = | 90 | std::shared_ptr<Buffer> data = |
| 92 | this->copied_images[og].getStreamData(qpdf_dl_all); | 91 | this->copied_images[og].getStreamData(qpdf_dl_all); |
| 93 | size_t size = data->getSize(); | 92 | size_t size = data->getSize(); |
include/qpdf/QPDF.hh
| @@ -815,9 +815,9 @@ class QPDF | @@ -815,9 +815,9 @@ class QPDF | ||
| 815 | 815 | ||
| 816 | private: | 816 | private: |
| 817 | static std::shared_ptr<QPDFObject> | 817 | static std::shared_ptr<QPDFObject> |
| 818 | - resolve(QPDF* qpdf, int objid, int generation) | 818 | + resolve(QPDF* qpdf, QPDFObjGen const& og) |
| 819 | { | 819 | { |
| 820 | - return qpdf->resolve(objid, generation); | 820 | + return qpdf->resolve(og); |
| 821 | } | 821 | } |
| 822 | static bool | 822 | static bool |
| 823 | objectChanged( | 823 | objectChanged( |
| @@ -879,8 +879,7 @@ class QPDF | @@ -879,8 +879,7 @@ class QPDF | ||
| 879 | static bool | 879 | static bool |
| 880 | pipeStreamData( | 880 | pipeStreamData( |
| 881 | QPDF* qpdf, | 881 | QPDF* qpdf, |
| 882 | - int objid, | ||
| 883 | - int generation, | 882 | + QPDFObjGen const& og, |
| 884 | qpdf_offset_t offset, | 883 | qpdf_offset_t offset, |
| 885 | size_t length, | 884 | size_t length, |
| 886 | QPDFObjectHandle dict, | 885 | QPDFObjectHandle dict, |
| @@ -889,8 +888,7 @@ class QPDF | @@ -889,8 +888,7 @@ class QPDF | ||
| 889 | bool will_retry) | 888 | bool will_retry) |
| 890 | { | 889 | { |
| 891 | return qpdf->pipeStreamData( | 890 | return qpdf->pipeStreamData( |
| 892 | - objid, | ||
| 893 | - generation, | 891 | + og, |
| 894 | offset, | 892 | offset, |
| 895 | length, | 893 | length, |
| 896 | dict, | 894 | dict, |
| @@ -959,8 +957,7 @@ class QPDF | @@ -959,8 +957,7 @@ class QPDF | ||
| 959 | std::string user_password; | 957 | std::string user_password; |
| 960 | std::string encryption_key; | 958 | std::string encryption_key; |
| 961 | std::string cached_object_encryption_key; | 959 | std::string cached_object_encryption_key; |
| 962 | - int cached_key_objid; | ||
| 963 | - int cached_key_generation; | 960 | + QPDFObjGen cached_key_og; |
| 964 | bool user_password_matched; | 961 | bool user_password_matched; |
| 965 | bool owner_password_matched; | 962 | bool owner_password_matched; |
| 966 | }; | 963 | }; |
| @@ -973,8 +970,7 @@ class QPDF | @@ -973,8 +970,7 @@ class QPDF | ||
| 973 | ForeignStreamData( | 970 | ForeignStreamData( |
| 974 | std::shared_ptr<EncryptionParameters> encp, | 971 | std::shared_ptr<EncryptionParameters> encp, |
| 975 | std::shared_ptr<InputSource> file, | 972 | std::shared_ptr<InputSource> file, |
| 976 | - int foreign_objid, | ||
| 977 | - int foreign_generation, | 973 | + QPDFObjGen const& foreign_og, |
| 978 | qpdf_offset_t offset, | 974 | qpdf_offset_t offset, |
| 979 | size_t length, | 975 | size_t length, |
| 980 | QPDFObjectHandle local_dict); | 976 | QPDFObjectHandle local_dict); |
| @@ -982,8 +978,7 @@ class QPDF | @@ -982,8 +978,7 @@ class QPDF | ||
| 982 | private: | 978 | private: |
| 983 | std::shared_ptr<EncryptionParameters> encp; | 979 | std::shared_ptr<EncryptionParameters> encp; |
| 984 | std::shared_ptr<InputSource> file; | 980 | std::shared_ptr<InputSource> file; |
| 985 | - int foreign_objid; | ||
| 986 | - int foreign_generation; | 981 | + QPDFObjGen foreign_og; |
| 987 | qpdf_offset_t offset; | 982 | qpdf_offset_t offset; |
| 988 | size_t length; | 983 | size_t length; |
| 989 | QPDFObjectHandle local_dict; | 984 | QPDFObjectHandle local_dict; |
| @@ -995,8 +990,7 @@ class QPDF | @@ -995,8 +990,7 @@ class QPDF | ||
| 995 | CopiedStreamDataProvider(QPDF& destination_qpdf); | 990 | CopiedStreamDataProvider(QPDF& destination_qpdf); |
| 996 | virtual ~CopiedStreamDataProvider() = default; | 991 | virtual ~CopiedStreamDataProvider() = default; |
| 997 | virtual bool provideStreamData( | 992 | virtual bool provideStreamData( |
| 998 | - int objid, | ||
| 999 | - int generation, | 993 | + QPDFObjGen const& og, |
| 1000 | Pipeline* pipeline, | 994 | Pipeline* pipeline, |
| 1001 | bool suppress_warnings, | 995 | bool suppress_warnings, |
| 1002 | bool will_retry) override; | 996 | bool will_retry) override; |
| @@ -1017,14 +1011,13 @@ class QPDF | @@ -1017,14 +1011,13 @@ class QPDF | ||
| 1017 | friend class QPDF; | 1011 | friend class QPDF; |
| 1018 | 1012 | ||
| 1019 | public: | 1013 | public: |
| 1020 | - StringDecrypter(QPDF* qpdf, int objid, int gen); | 1014 | + StringDecrypter(QPDF* qpdf, QPDFObjGen const& og); |
| 1021 | virtual ~StringDecrypter() = default; | 1015 | virtual ~StringDecrypter() = default; |
| 1022 | virtual void decryptString(std::string& val); | 1016 | virtual void decryptString(std::string& val); |
| 1023 | 1017 | ||
| 1024 | private: | 1018 | private: |
| 1025 | QPDF* qpdf; | 1019 | QPDF* qpdf; |
| 1026 | - int objid; | ||
| 1027 | - int gen; | 1020 | + QPDFObjGen og; |
| 1028 | }; | 1021 | }; |
| 1029 | 1022 | ||
| 1030 | class ResolveRecorder | 1023 | class ResolveRecorder |
| @@ -1127,17 +1120,15 @@ class QPDF | @@ -1127,17 +1120,15 @@ class QPDF | ||
| 1127 | void insertXrefEntry( | 1120 | void insertXrefEntry( |
| 1128 | int obj, int f0, qpdf_offset_t f1, int f2, bool overwrite = false); | 1121 | int obj, int f0, qpdf_offset_t f1, int f2, bool overwrite = false); |
| 1129 | void setLastObjectDescription( | 1122 | void setLastObjectDescription( |
| 1130 | - std::string const& description, int objid, int generation); | 1123 | + std::string const& description, QPDFObjGen const& og); |
| 1131 | QPDFObjectHandle readObject( | 1124 | QPDFObjectHandle readObject( |
| 1132 | std::shared_ptr<InputSource>, | 1125 | std::shared_ptr<InputSource>, |
| 1133 | std::string const& description, | 1126 | std::string const& description, |
| 1134 | - int objid, | ||
| 1135 | - int generation, | 1127 | + QPDFObjGen const& og, |
| 1136 | bool in_object_stream); | 1128 | bool in_object_stream); |
| 1137 | size_t recoverStreamLength( | 1129 | size_t recoverStreamLength( |
| 1138 | std::shared_ptr<InputSource> input, | 1130 | std::shared_ptr<InputSource> input, |
| 1139 | - int objid, | ||
| 1140 | - int generation, | 1131 | + QPDFObjGen const& og, |
| 1141 | qpdf_offset_t stream_offset); | 1132 | qpdf_offset_t stream_offset); |
| 1142 | QPDFTokenizer::Token | 1133 | QPDFTokenizer::Token |
| 1143 | readToken(std::shared_ptr<InputSource>, size_t max_len = 0); | 1134 | readToken(std::shared_ptr<InputSource>, size_t max_len = 0); |
| @@ -1146,21 +1137,18 @@ class QPDF | @@ -1146,21 +1137,18 @@ class QPDF | ||
| 1146 | bool attempt_recovery, | 1137 | bool attempt_recovery, |
| 1147 | qpdf_offset_t offset, | 1138 | qpdf_offset_t offset, |
| 1148 | std::string const& description, | 1139 | std::string const& description, |
| 1149 | - int exp_objid, | ||
| 1150 | - int exp_generation, | ||
| 1151 | - int& act_objid, | ||
| 1152 | - int& act_generation); | 1140 | + QPDFObjGen const& exp_og, |
| 1141 | + QPDFObjGen& og); | ||
| 1153 | bool objectChanged(QPDFObjGen const& og, std::shared_ptr<QPDFObject>& oph); | 1142 | bool objectChanged(QPDFObjGen const& og, std::shared_ptr<QPDFObject>& oph); |
| 1154 | - std::shared_ptr<QPDFObject> resolve(int objid, int generation); | 1143 | + std::shared_ptr<QPDFObject> resolve(QPDFObjGen const& og); |
| 1155 | void resolveObjectsInStream(int obj_stream_number); | 1144 | void resolveObjectsInStream(int obj_stream_number); |
| 1156 | void stopOnError(std::string const& message); | 1145 | void stopOnError(std::string const& message); |
| 1157 | - QPDFObjectHandle reserveObjectIfNotExists(int objid, int gen); | ||
| 1158 | - QPDFObjectHandle reserveStream(int objid, int gen); | 1146 | + QPDFObjectHandle reserveObjectIfNotExists(QPDFObjGen const& og); |
| 1147 | + QPDFObjectHandle reserveStream(QPDFObjGen const& og); | ||
| 1159 | 1148 | ||
| 1160 | // Calls finish() on the pipeline when done but does not delete it | 1149 | // Calls finish() on the pipeline when done but does not delete it |
| 1161 | bool pipeStreamData( | 1150 | bool pipeStreamData( |
| 1162 | - int objid, | ||
| 1163 | - int generation, | 1151 | + QPDFObjGen const& og, |
| 1164 | qpdf_offset_t offset, | 1152 | qpdf_offset_t offset, |
| 1165 | size_t length, | 1153 | size_t length, |
| 1166 | QPDFObjectHandle dict, | 1154 | QPDFObjectHandle dict, |
| @@ -1176,8 +1164,7 @@ class QPDF | @@ -1176,8 +1164,7 @@ class QPDF | ||
| 1176 | std::shared_ptr<QPDF::EncryptionParameters> encp, | 1164 | std::shared_ptr<QPDF::EncryptionParameters> encp, |
| 1177 | std::shared_ptr<InputSource> file, | 1165 | std::shared_ptr<InputSource> file, |
| 1178 | QPDF& qpdf_for_warning, | 1166 | QPDF& qpdf_for_warning, |
| 1179 | - int objid, | ||
| 1180 | - int generation, | 1167 | + QPDFObjGen const& og, |
| 1181 | qpdf_offset_t offset, | 1168 | qpdf_offset_t offset, |
| 1182 | size_t length, | 1169 | size_t length, |
| 1183 | QPDFObjectHandle dict, | 1170 | QPDFObjectHandle dict, |
| @@ -1230,10 +1217,9 @@ class QPDF | @@ -1230,10 +1217,9 @@ class QPDF | ||
| 1230 | void initializeEncryption(); | 1217 | void initializeEncryption(); |
| 1231 | static std::string getKeyForObject( | 1218 | static std::string getKeyForObject( |
| 1232 | std::shared_ptr<EncryptionParameters> encp, | 1219 | std::shared_ptr<EncryptionParameters> encp, |
| 1233 | - int objid, | ||
| 1234 | - int generation, | 1220 | + QPDFObjGen const& og, |
| 1235 | bool use_aes); | 1221 | bool use_aes); |
| 1236 | - void decryptString(std::string&, int objid, int generation); | 1222 | + void decryptString(std::string&, QPDFObjGen const& og); |
| 1237 | static std::string compute_encryption_key_from_password( | 1223 | static std::string compute_encryption_key_from_password( |
| 1238 | std::string const& password, EncryptionData const& data); | 1224 | std::string const& password, EncryptionData const& data); |
| 1239 | static std::string recover_encryption_key_with_password( | 1225 | static std::string recover_encryption_key_with_password( |
| @@ -1247,8 +1233,7 @@ class QPDF | @@ -1247,8 +1233,7 @@ class QPDF | ||
| 1247 | std::shared_ptr<InputSource> file, | 1233 | std::shared_ptr<InputSource> file, |
| 1248 | QPDF& qpdf_for_warning, | 1234 | QPDF& qpdf_for_warning, |
| 1249 | Pipeline*& pipeline, | 1235 | Pipeline*& pipeline, |
| 1250 | - int objid, | ||
| 1251 | - int generation, | 1236 | + QPDFObjGen const& og, |
| 1252 | QPDFObjectHandle& stream_dict, | 1237 | QPDFObjectHandle& stream_dict, |
| 1253 | std::vector<std::shared_ptr<Pipeline>>& heap); | 1238 | std::vector<std::shared_ptr<Pipeline>>& heap); |
| 1254 | 1239 | ||
| @@ -1571,7 +1556,6 @@ class QPDF | @@ -1571,7 +1556,6 @@ class QPDF | ||
| 1571 | void dumpHSharedObject(); | 1556 | void dumpHSharedObject(); |
| 1572 | void dumpHGeneric(HGeneric&); | 1557 | void dumpHGeneric(HGeneric&); |
| 1573 | qpdf_offset_t adjusted_offset(qpdf_offset_t offset); | 1558 | qpdf_offset_t adjusted_offset(qpdf_offset_t offset); |
| 1574 | - QPDFObjectHandle objGenToIndirect(QPDFObjGen const&); | ||
| 1575 | void | 1559 | void |
| 1576 | calculateLinearizationData(std::map<int, int> const& object_stream_data); | 1560 | calculateLinearizationData(std::map<int, int> const& object_stream_data); |
| 1577 | void pushOutlinesToPart( | 1561 | void pushOutlinesToPart( |
include/qpdf/QPDFObjGen.hh
| @@ -23,7 +23,6 @@ | @@ -23,7 +23,6 @@ | ||
| 23 | #define QPDFOBJGEN_HH | 23 | #define QPDFOBJGEN_HH |
| 24 | 24 | ||
| 25 | #include <qpdf/DLL.h> | 25 | #include <qpdf/DLL.h> |
| 26 | -#include <qpdf/QUtil.hh> | ||
| 27 | #include <iostream> | 26 | #include <iostream> |
| 28 | 27 | ||
| 29 | // This class represents an object ID and generation pair. It is | 28 | // This class represents an object ID and generation pair. It is |
| @@ -39,7 +38,7 @@ class QPDFObjGen | @@ -39,7 +38,7 @@ class QPDFObjGen | ||
| 39 | { | 38 | { |
| 40 | } | 39 | } |
| 41 | QPDF_DLL | 40 | QPDF_DLL |
| 42 | - QPDFObjGen(int obj, int gen) : | 41 | + explicit QPDFObjGen(int obj, int gen) : |
| 43 | obj(obj), | 42 | obj(obj), |
| 44 | gen(gen) | 43 | gen(gen) |
| 45 | { | 44 | { |
| @@ -48,13 +47,19 @@ class QPDFObjGen | @@ -48,13 +47,19 @@ class QPDFObjGen | ||
| 48 | bool | 47 | bool |
| 49 | operator<(QPDFObjGen const& rhs) const | 48 | operator<(QPDFObjGen const& rhs) const |
| 50 | { | 49 | { |
| 51 | - return ((obj < rhs.obj) || ((obj == rhs.obj) && (gen < rhs.gen))); | 50 | + return (obj < rhs.obj) || ((obj == rhs.obj) && (gen < rhs.gen)); |
| 52 | } | 51 | } |
| 53 | QPDF_DLL | 52 | QPDF_DLL |
| 54 | bool | 53 | bool |
| 55 | operator==(QPDFObjGen const& rhs) const | 54 | operator==(QPDFObjGen const& rhs) const |
| 56 | { | 55 | { |
| 57 | - return ((obj == rhs.obj) && (gen == rhs.gen)); | 56 | + return (obj == rhs.obj) && (gen == rhs.gen); |
| 57 | + } | ||
| 58 | + QPDF_DLL | ||
| 59 | + bool | ||
| 60 | + operator!=(QPDFObjGen const& rhs) const | ||
| 61 | + { | ||
| 62 | + return (obj != rhs.obj) || (gen != rhs.gen); | ||
| 58 | } | 63 | } |
| 59 | QPDF_DLL | 64 | QPDF_DLL |
| 60 | int | 65 | int |
| @@ -69,18 +74,15 @@ class QPDFObjGen | @@ -69,18 +74,15 @@ class QPDFObjGen | ||
| 69 | return gen; | 74 | return gen; |
| 70 | } | 75 | } |
| 71 | QPDF_DLL | 76 | QPDF_DLL |
| 72 | - std::string | ||
| 73 | - unparse() const | 77 | + bool |
| 78 | + isIndirect() const | ||
| 74 | { | 79 | { |
| 75 | - return QUtil::int_to_string(obj) + "," + QUtil::int_to_string(gen); | 80 | + return obj != 0; |
| 76 | } | 81 | } |
| 77 | QPDF_DLL | 82 | QPDF_DLL |
| 78 | - friend std::ostream& | ||
| 79 | - operator<<(std::ostream& os, const QPDFObjGen& og) | ||
| 80 | - { | ||
| 81 | - os << og.obj << "," << og.gen; | ||
| 82 | - return os; | ||
| 83 | - } | 83 | + std::string unparse(char separator = ',') const; |
| 84 | + QPDF_DLL | ||
| 85 | + friend std::ostream& operator<<(std::ostream& os, const QPDFObjGen& og); | ||
| 84 | 86 | ||
| 85 | private: | 87 | private: |
| 86 | // This class does not use the Members pattern to avoid a memory | 88 | // This class does not use the Members pattern to avoid a memory |
include/qpdf/QPDFObjectHandle.hh
| @@ -116,9 +116,16 @@ class QPDFObjectHandle | @@ -116,9 +116,16 @@ class QPDFObjectHandle | ||
| 116 | // indicating whether it ran without errors. | 116 | // indicating whether it ran without errors. |
| 117 | QPDF_DLL | 117 | QPDF_DLL |
| 118 | virtual void | 118 | virtual void |
| 119 | - provideStreamData(int objid, int generation, Pipeline* pipeline); | 119 | + provideStreamData(QPDFObjGen const& og, Pipeline* pipeline); |
| 120 | QPDF_DLL | 120 | QPDF_DLL |
| 121 | virtual bool provideStreamData( | 121 | virtual bool provideStreamData( |
| 122 | + QPDFObjGen const& og, | ||
| 123 | + Pipeline* pipeline, | ||
| 124 | + bool suppress_warnings, | ||
| 125 | + bool will_retry); | ||
| 126 | + QPDF_DLL virtual void | ||
| 127 | + provideStreamData(int objid, int generation, Pipeline* pipeline); | ||
| 128 | + QPDF_DLL virtual bool provideStreamData( | ||
| 122 | int objid, | 129 | int objid, |
| 123 | int generation, | 130 | int generation, |
| 124 | Pipeline* pipeline, | 131 | Pipeline* pipeline, |
| @@ -1429,21 +1436,20 @@ class QPDFObjectHandle | @@ -1429,21 +1436,20 @@ class QPDFObjectHandle | ||
| 1429 | 1436 | ||
| 1430 | private: | 1437 | private: |
| 1431 | static QPDFObjectHandle | 1438 | static QPDFObjectHandle |
| 1432 | - newIndirect(QPDF* qpdf, int objid, int generation) | 1439 | + newIndirect(QPDF* qpdf, QPDFObjGen const& og) |
| 1433 | { | 1440 | { |
| 1434 | - return QPDFObjectHandle::newIndirect(qpdf, objid, generation); | 1441 | + return QPDFObjectHandle::newIndirect(qpdf, og); |
| 1435 | } | 1442 | } |
| 1436 | static QPDFObjectHandle | 1443 | static QPDFObjectHandle |
| 1437 | newStream( | 1444 | newStream( |
| 1438 | QPDF* qpdf, | 1445 | QPDF* qpdf, |
| 1439 | - int objid, | ||
| 1440 | - int generation, | 1446 | + QPDFObjGen const& og, |
| 1441 | QPDFObjectHandle stream_dict, | 1447 | QPDFObjectHandle stream_dict, |
| 1442 | qpdf_offset_t offset, | 1448 | qpdf_offset_t offset, |
| 1443 | size_t length) | 1449 | size_t length) |
| 1444 | { | 1450 | { |
| 1445 | return QPDFObjectHandle::newStream( | 1451 | return QPDFObjectHandle::newStream( |
| 1446 | - qpdf, objid, generation, stream_dict, offset, length); | 1452 | + qpdf, og, stream_dict, offset, length); |
| 1447 | } | 1453 | } |
| 1448 | // Reserve an object with a specific ID | 1454 | // Reserve an object with a specific ID |
| 1449 | static QPDFObjectHandle | 1455 | static QPDFObjectHandle |
| @@ -1550,7 +1556,7 @@ class QPDFObjectHandle | @@ -1550,7 +1556,7 @@ class QPDFObjectHandle | ||
| 1550 | bool isImage(bool exclude_imagemask = true); | 1556 | bool isImage(bool exclude_imagemask = true); |
| 1551 | 1557 | ||
| 1552 | private: | 1558 | private: |
| 1553 | - QPDFObjectHandle(QPDF*, int objid, int generation); | 1559 | + QPDFObjectHandle(QPDF*, QPDFObjGen const& og); |
| 1554 | QPDFObjectHandle(std::shared_ptr<QPDFObject> const&); | 1560 | QPDFObjectHandle(std::shared_ptr<QPDFObject> const&); |
| 1555 | 1561 | ||
| 1556 | enum parser_state_e { | 1562 | enum parser_state_e { |
| @@ -1563,11 +1569,10 @@ class QPDFObjectHandle | @@ -1563,11 +1569,10 @@ class QPDFObjectHandle | ||
| 1563 | }; | 1569 | }; |
| 1564 | 1570 | ||
| 1565 | // Private object factory methods | 1571 | // Private object factory methods |
| 1566 | - static QPDFObjectHandle newIndirect(QPDF*, int objid, int generation); | 1572 | + static QPDFObjectHandle newIndirect(QPDF*, QPDFObjGen const& og); |
| 1567 | static QPDFObjectHandle newStream( | 1573 | static QPDFObjectHandle newStream( |
| 1568 | QPDF* qpdf, | 1574 | QPDF* qpdf, |
| 1569 | - int objid, | ||
| 1570 | - int generation, | 1575 | + QPDFObjGen const& og, |
| 1571 | QPDFObjectHandle stream_dict, | 1576 | QPDFObjectHandle stream_dict, |
| 1572 | qpdf_offset_t offset, | 1577 | qpdf_offset_t offset, |
| 1573 | size_t length); | 1578 | size_t length); |
| @@ -1584,7 +1589,6 @@ class QPDFObjectHandle | @@ -1584,7 +1589,6 @@ class QPDFObjectHandle | ||
| 1584 | bool stop_at_streams); | 1589 | bool stop_at_streams); |
| 1585 | void shallowCopyInternal(QPDFObjectHandle& oh, bool first_level_only); | 1590 | void shallowCopyInternal(QPDFObjectHandle& oh, bool first_level_only); |
| 1586 | void releaseResolved(); | 1591 | void releaseResolved(); |
| 1587 | - std::string getObjGenAsStr() const; | ||
| 1588 | static void setObjectDescriptionFromInput( | 1592 | static void setObjectDescriptionFromInput( |
| 1589 | QPDFObjectHandle, | 1593 | QPDFObjectHandle, |
| 1590 | QPDF*, | 1594 | QPDF*, |
| @@ -1618,8 +1622,7 @@ class QPDFObjectHandle | @@ -1618,8 +1622,7 @@ class QPDFObjectHandle | ||
| 1618 | // a substantial performance penalty since QPDFObjectHandle | 1622 | // a substantial performance penalty since QPDFObjectHandle |
| 1619 | // objects are copied around so frequently. | 1623 | // objects are copied around so frequently. |
| 1620 | QPDF* qpdf; | 1624 | QPDF* qpdf; |
| 1621 | - int objid; // 0 for direct object | ||
| 1622 | - int generation; | 1625 | + QPDFObjGen og; |
| 1623 | std::shared_ptr<QPDFObject> obj; | 1626 | std::shared_ptr<QPDFObject> obj; |
| 1624 | bool reserved; | 1627 | bool reserved; |
| 1625 | }; | 1628 | }; |
libqpdf/CMakeLists.txt
| @@ -74,6 +74,7 @@ set(libqpdf_SOURCES | @@ -74,6 +74,7 @@ set(libqpdf_SOURCES | ||
| 74 | QPDFNumberTreeObjectHelper.cc | 74 | QPDFNumberTreeObjectHelper.cc |
| 75 | QPDFObject.cc | 75 | QPDFObject.cc |
| 76 | QPDFObjectHandle.cc | 76 | QPDFObjectHandle.cc |
| 77 | + QPDFObjGen.cc | ||
| 77 | QPDFOutlineDocumentHelper.cc | 78 | QPDFOutlineDocumentHelper.cc |
| 78 | QPDFOutlineObjectHelper.cc | 79 | QPDFOutlineObjectHelper.cc |
| 79 | QPDFPageDocumentHelper.cc | 80 | QPDFPageDocumentHelper.cc |
libqpdf/QPDF.cc
| @@ -113,15 +113,13 @@ namespace | @@ -113,15 +113,13 @@ namespace | ||
| 113 | QPDF::ForeignStreamData::ForeignStreamData( | 113 | QPDF::ForeignStreamData::ForeignStreamData( |
| 114 | std::shared_ptr<EncryptionParameters> encp, | 114 | std::shared_ptr<EncryptionParameters> encp, |
| 115 | std::shared_ptr<InputSource> file, | 115 | std::shared_ptr<InputSource> file, |
| 116 | - int foreign_objid, | ||
| 117 | - int foreign_generation, | 116 | + QPDFObjGen const& foreign_og, |
| 118 | qpdf_offset_t offset, | 117 | qpdf_offset_t offset, |
| 119 | size_t length, | 118 | size_t length, |
| 120 | QPDFObjectHandle local_dict) : | 119 | QPDFObjectHandle local_dict) : |
| 121 | encp(encp), | 120 | encp(encp), |
| 122 | file(file), | 121 | file(file), |
| 123 | - foreign_objid(foreign_objid), | ||
| 124 | - foreign_generation(foreign_generation), | 122 | + foreign_og(foreign_og), |
| 125 | offset(offset), | 123 | offset(offset), |
| 126 | length(length), | 124 | length(length), |
| 127 | local_dict(local_dict) | 125 | local_dict(local_dict) |
| @@ -137,22 +135,19 @@ QPDF::CopiedStreamDataProvider::CopiedStreamDataProvider( | @@ -137,22 +135,19 @@ QPDF::CopiedStreamDataProvider::CopiedStreamDataProvider( | ||
| 137 | 135 | ||
| 138 | bool | 136 | bool |
| 139 | QPDF::CopiedStreamDataProvider::provideStreamData( | 137 | QPDF::CopiedStreamDataProvider::provideStreamData( |
| 140 | - int objid, | ||
| 141 | - int generation, | 138 | + QPDFObjGen const& og, |
| 142 | Pipeline* pipeline, | 139 | Pipeline* pipeline, |
| 143 | bool suppress_warnings, | 140 | bool suppress_warnings, |
| 144 | bool will_retry) | 141 | bool will_retry) |
| 145 | { | 142 | { |
| 146 | - std::shared_ptr<ForeignStreamData> foreign_data = | ||
| 147 | - this->foreign_stream_data[QPDFObjGen(objid, generation)]; | 143 | + std::shared_ptr<ForeignStreamData> foreign_data = foreign_stream_data[og]; |
| 148 | bool result = false; | 144 | bool result = false; |
| 149 | if (foreign_data.get()) { | 145 | if (foreign_data.get()) { |
| 150 | result = destination_qpdf.pipeForeignStreamData( | 146 | result = destination_qpdf.pipeForeignStreamData( |
| 151 | foreign_data, pipeline, suppress_warnings, will_retry); | 147 | foreign_data, pipeline, suppress_warnings, will_retry); |
| 152 | QTC::TC("qpdf", "QPDF copy foreign with data", result ? 0 : 1); | 148 | QTC::TC("qpdf", "QPDF copy foreign with data", result ? 0 : 1); |
| 153 | } else { | 149 | } else { |
| 154 | - QPDFObjectHandle foreign_stream = | ||
| 155 | - this->foreign_streams[QPDFObjGen(objid, generation)]; | 150 | + auto foreign_stream = foreign_streams[og]; |
| 156 | result = foreign_stream.pipeStreamData( | 151 | result = foreign_stream.pipeStreamData( |
| 157 | pipeline, nullptr, 0, qpdf_dl_none, suppress_warnings, will_retry); | 152 | pipeline, nullptr, 0, qpdf_dl_none, suppress_warnings, will_retry); |
| 158 | QTC::TC( | 153 | QTC::TC( |
| @@ -176,17 +171,16 @@ QPDF::CopiedStreamDataProvider::registerForeignStream( | @@ -176,17 +171,16 @@ QPDF::CopiedStreamDataProvider::registerForeignStream( | ||
| 176 | this->foreign_stream_data[local_og] = foreign_stream; | 171 | this->foreign_stream_data[local_og] = foreign_stream; |
| 177 | } | 172 | } |
| 178 | 173 | ||
| 179 | -QPDF::StringDecrypter::StringDecrypter(QPDF* qpdf, int objid, int gen) : | 174 | +QPDF::StringDecrypter::StringDecrypter(QPDF* qpdf, QPDFObjGen const& og) : |
| 180 | qpdf(qpdf), | 175 | qpdf(qpdf), |
| 181 | - objid(objid), | ||
| 182 | - gen(gen) | 176 | + og(og) |
| 183 | { | 177 | { |
| 184 | } | 178 | } |
| 185 | 179 | ||
| 186 | void | 180 | void |
| 187 | QPDF::StringDecrypter::decryptString(std::string& val) | 181 | QPDF::StringDecrypter::decryptString(std::string& val) |
| 188 | { | 182 | { |
| 189 | - qpdf->decryptString(val, objid, gen); | 183 | + qpdf->decryptString(val, og); |
| 190 | } | 184 | } |
| 191 | 185 | ||
| 192 | std::string const& | 186 | std::string const& |
| @@ -205,8 +199,6 @@ QPDF::EncryptionParameters::EncryptionParameters() : | @@ -205,8 +199,6 @@ QPDF::EncryptionParameters::EncryptionParameters() : | ||
| 205 | cf_stream(e_none), | 199 | cf_stream(e_none), |
| 206 | cf_string(e_none), | 200 | cf_string(e_none), |
| 207 | cf_file(e_none), | 201 | cf_file(e_none), |
| 208 | - cached_key_objid(0), | ||
| 209 | - cached_key_generation(0), | ||
| 210 | user_password_matched(false), | 202 | user_password_matched(false), |
| 211 | owner_password_matched(false) | 203 | owner_password_matched(false) |
| 212 | { | 204 | { |
| @@ -631,7 +623,7 @@ QPDF::reconstruct_xref(QPDFExc& e) | @@ -631,7 +623,7 @@ QPDF::reconstruct_xref(QPDFExc& e) | ||
| 631 | (!this->m->trailer.isInitialized()) && | 623 | (!this->m->trailer.isInitialized()) && |
| 632 | (t1 == QPDFTokenizer::Token(QPDFTokenizer::tt_word, "trailer"))) { | 624 | (t1 == QPDFTokenizer::Token(QPDFTokenizer::tt_word, "trailer"))) { |
| 633 | QPDFObjectHandle t = | 625 | QPDFObjectHandle t = |
| 634 | - readObject(this->m->file, "trailer", 0, 0, false); | 626 | + readObject(this->m->file, "trailer", QPDFObjGen(), false); |
| 635 | if (!t.isDictionary()) { | 627 | if (!t.isDictionary()) { |
| 636 | // Oh well. It was worth a try. | 628 | // Oh well. It was worth a try. |
| 637 | } else { | 629 | } else { |
| @@ -969,7 +961,7 @@ QPDF::read_xrefTable(qpdf_offset_t xref_offset) | @@ -969,7 +961,7 @@ QPDF::read_xrefTable(qpdf_offset_t xref_offset) | ||
| 969 | 961 | ||
| 970 | // Set offset to previous xref table if any | 962 | // Set offset to previous xref table if any |
| 971 | QPDFObjectHandle cur_trailer = | 963 | QPDFObjectHandle cur_trailer = |
| 972 | - readObject(this->m->file, "trailer", 0, 0, false); | 964 | + readObject(this->m->file, "trailer", QPDFObjGen(), false); |
| 973 | if (!cur_trailer.isDictionary()) { | 965 | if (!cur_trailer.isDictionary()) { |
| 974 | QTC::TC("qpdf", "QPDF missing trailer"); | 966 | QTC::TC("qpdf", "QPDF missing trailer"); |
| 975 | throw QPDFExc( | 967 | throw QPDFExc( |
| @@ -1055,12 +1047,11 @@ QPDF::read_xrefStream(qpdf_offset_t xref_offset) | @@ -1055,12 +1047,11 @@ QPDF::read_xrefStream(qpdf_offset_t xref_offset) | ||
| 1055 | { | 1047 | { |
| 1056 | bool found = false; | 1048 | bool found = false; |
| 1057 | if (!this->m->ignore_xref_streams) { | 1049 | if (!this->m->ignore_xref_streams) { |
| 1058 | - int xobj; | ||
| 1059 | - int xgen; | 1050 | + QPDFObjGen x_og; |
| 1060 | QPDFObjectHandle xref_obj; | 1051 | QPDFObjectHandle xref_obj; |
| 1061 | try { | 1052 | try { |
| 1062 | xref_obj = readObjectAtOffset( | 1053 | xref_obj = readObjectAtOffset( |
| 1063 | - false, xref_offset, "xref stream", 0, 0, xobj, xgen); | 1054 | + false, xref_offset, "xref stream", QPDFObjGen(0, 0), x_og); |
| 1064 | } catch (QPDFExc&) { | 1055 | } catch (QPDFExc&) { |
| 1065 | // ignore -- report error below | 1056 | // ignore -- report error below |
| 1066 | } | 1057 | } |
| @@ -1363,7 +1354,7 @@ QPDF::showXRefTable() | @@ -1363,7 +1354,7 @@ QPDF::showXRefTable() | ||
| 1363 | for (auto const& iter: this->m->xref_table) { | 1354 | for (auto const& iter: this->m->xref_table) { |
| 1364 | QPDFObjGen const& og = iter.first; | 1355 | QPDFObjGen const& og = iter.first; |
| 1365 | QPDFXRefEntry const& entry = iter.second; | 1356 | QPDFXRefEntry const& entry = iter.second; |
| 1366 | - cout << og.getObj() << "/" << og.getGen() << ": "; | 1357 | + cout << og.unparse('/') << ": "; |
| 1367 | switch (entry.getType()) { | 1358 | switch (entry.getType()) { |
| 1368 | case 1: | 1359 | case 1: |
| 1369 | cout << "uncompressed; offset = " << entry.getOffset(); | 1360 | cout << "uncompressed; offset = " << entry.getOffset(); |
| @@ -1405,9 +1396,8 @@ QPDF::fixDanglingReferences(bool force) | @@ -1405,9 +1396,8 @@ QPDF::fixDanglingReferences(bool force) | ||
| 1405 | // For each non-scalar item to process, put it in the queue. | 1396 | // For each non-scalar item to process, put it in the queue. |
| 1406 | std::list<QPDFObjectHandle> queue; | 1397 | std::list<QPDFObjectHandle> queue; |
| 1407 | queue.push_back(this->m->trailer); | 1398 | queue.push_back(this->m->trailer); |
| 1408 | - for (auto const& iter: to_process) { | ||
| 1409 | - QPDFObjectHandle obj = QPDFObjectHandle::Factory::newIndirect( | ||
| 1410 | - this, iter.getObj(), iter.getGen()); | 1399 | + for (auto const& og: to_process) { |
| 1400 | + QPDFObjectHandle obj = QPDFObjectHandle::Factory::newIndirect(this, og); | ||
| 1411 | if (obj.isDictionary() || obj.isArray()) { | 1401 | if (obj.isDictionary() || obj.isArray()) { |
| 1412 | queue.push_back(obj); | 1402 | queue.push_back(obj); |
| 1413 | } else if (obj.isStream()) { | 1403 | } else if (obj.isStream()) { |
| @@ -1473,29 +1463,24 @@ QPDF::getAllObjects() | @@ -1473,29 +1463,24 @@ QPDF::getAllObjects() | ||
| 1473 | std::vector<QPDFObjectHandle> result; | 1463 | std::vector<QPDFObjectHandle> result; |
| 1474 | for (auto const& iter: this->m->obj_cache) { | 1464 | for (auto const& iter: this->m->obj_cache) { |
| 1475 | QPDFObjGen const& og = iter.first; | 1465 | QPDFObjGen const& og = iter.first; |
| 1476 | - result.push_back( | ||
| 1477 | - // line-break | ||
| 1478 | - QPDFObjectHandle::Factory::newIndirect( | ||
| 1479 | - this, og.getObj(), og.getGen())); | 1466 | + result.push_back(QPDFObjectHandle::Factory::newIndirect(this, og)); |
| 1480 | } | 1467 | } |
| 1481 | return result; | 1468 | return result; |
| 1482 | } | 1469 | } |
| 1483 | 1470 | ||
| 1484 | void | 1471 | void |
| 1485 | QPDF::setLastObjectDescription( | 1472 | QPDF::setLastObjectDescription( |
| 1486 | - std::string const& description, int objid, int generation) | 1473 | + std::string const& description, QPDFObjGen const& og) |
| 1487 | { | 1474 | { |
| 1488 | this->m->last_object_description.clear(); | 1475 | this->m->last_object_description.clear(); |
| 1489 | if (!description.empty()) { | 1476 | if (!description.empty()) { |
| 1490 | this->m->last_object_description += description; | 1477 | this->m->last_object_description += description; |
| 1491 | - if (objid > 0) { | 1478 | + if (og.isIndirect()) { |
| 1492 | this->m->last_object_description += ": "; | 1479 | this->m->last_object_description += ": "; |
| 1493 | } | 1480 | } |
| 1494 | } | 1481 | } |
| 1495 | - if (objid > 0) { | ||
| 1496 | - this->m->last_object_description += "object " + | ||
| 1497 | - QUtil::int_to_string(objid) + " " + | ||
| 1498 | - QUtil::int_to_string(generation); | 1482 | + if (og.isIndirect()) { |
| 1483 | + this->m->last_object_description += "object " + og.unparse(' '); | ||
| 1499 | } | 1484 | } |
| 1500 | } | 1485 | } |
| 1501 | 1486 | ||
| @@ -1503,19 +1488,17 @@ QPDFObjectHandle | @@ -1503,19 +1488,17 @@ QPDFObjectHandle | ||
| 1503 | QPDF::readObject( | 1488 | QPDF::readObject( |
| 1504 | std::shared_ptr<InputSource> input, | 1489 | std::shared_ptr<InputSource> input, |
| 1505 | std::string const& description, | 1490 | std::string const& description, |
| 1506 | - int objid, | ||
| 1507 | - int generation, | 1491 | + QPDFObjGen const& og, |
| 1508 | bool in_object_stream) | 1492 | bool in_object_stream) |
| 1509 | { | 1493 | { |
| 1510 | - setLastObjectDescription(description, objid, generation); | 1494 | + setLastObjectDescription(description, og); |
| 1511 | qpdf_offset_t offset = input->tell(); | 1495 | qpdf_offset_t offset = input->tell(); |
| 1512 | 1496 | ||
| 1513 | bool empty = false; | 1497 | bool empty = false; |
| 1514 | std::shared_ptr<StringDecrypter> decrypter_ph; | 1498 | std::shared_ptr<StringDecrypter> decrypter_ph; |
| 1515 | StringDecrypter* decrypter = 0; | 1499 | StringDecrypter* decrypter = 0; |
| 1516 | if (this->m->encp->encrypted && (!in_object_stream)) { | 1500 | if (this->m->encp->encrypted && (!in_object_stream)) { |
| 1517 | - decrypter_ph = | ||
| 1518 | - std::make_shared<StringDecrypter>(this, objid, generation); | 1501 | + decrypter_ph = std::make_shared<StringDecrypter>(this, og); |
| 1519 | decrypter = decrypter_ph.get(); | 1502 | decrypter = decrypter_ph.get(); |
| 1520 | } | 1503 | } |
| 1521 | QPDFObjectHandle object = QPDFObjectHandle::parse( | 1504 | QPDFObjectHandle object = QPDFObjectHandle::parse( |
| @@ -1657,14 +1640,13 @@ QPDF::readObject( | @@ -1657,14 +1640,13 @@ QPDF::readObject( | ||
| 1657 | } catch (QPDFExc& e) { | 1640 | } catch (QPDFExc& e) { |
| 1658 | if (this->m->attempt_recovery) { | 1641 | if (this->m->attempt_recovery) { |
| 1659 | warn(e); | 1642 | warn(e); |
| 1660 | - length = recoverStreamLength( | ||
| 1661 | - input, objid, generation, stream_offset); | 1643 | + length = recoverStreamLength(input, og, stream_offset); |
| 1662 | } else { | 1644 | } else { |
| 1663 | throw e; | 1645 | throw e; |
| 1664 | } | 1646 | } |
| 1665 | } | 1647 | } |
| 1666 | object = QPDFObjectHandle::Factory::newStream( | 1648 | object = QPDFObjectHandle::Factory::newStream( |
| 1667 | - this, objid, generation, object, stream_offset, length); | 1649 | + this, og, object, stream_offset, length); |
| 1668 | } else { | 1650 | } else { |
| 1669 | input->seek(cur_offset, SEEK_SET); | 1651 | input->seek(cur_offset, SEEK_SET); |
| 1670 | } | 1652 | } |
| @@ -1692,8 +1674,7 @@ QPDF::findEndstream() | @@ -1692,8 +1674,7 @@ QPDF::findEndstream() | ||
| 1692 | size_t | 1674 | size_t |
| 1693 | QPDF::recoverStreamLength( | 1675 | QPDF::recoverStreamLength( |
| 1694 | std::shared_ptr<InputSource> input, | 1676 | std::shared_ptr<InputSource> input, |
| 1695 | - int objid, | ||
| 1696 | - int generation, | 1677 | + QPDFObjGen const& og, |
| 1697 | qpdf_offset_t stream_offset) | 1678 | qpdf_offset_t stream_offset) |
| 1698 | { | 1679 | { |
| 1699 | // Try to reconstruct stream length by looking for | 1680 | // Try to reconstruct stream length by looking for |
| @@ -1718,11 +1699,10 @@ QPDF::recoverStreamLength( | @@ -1718,11 +1699,10 @@ QPDF::recoverStreamLength( | ||
| 1718 | 1699 | ||
| 1719 | if (length) { | 1700 | if (length) { |
| 1720 | qpdf_offset_t this_obj_offset = 0; | 1701 | qpdf_offset_t this_obj_offset = 0; |
| 1721 | - QPDFObjGen this_obj(0, 0); | 1702 | + QPDFObjGen this_og; |
| 1722 | 1703 | ||
| 1723 | // Make sure this is inside this object | 1704 | // Make sure this is inside this object |
| 1724 | for (auto const& iter: this->m->xref_table) { | 1705 | for (auto const& iter: this->m->xref_table) { |
| 1725 | - QPDFObjGen const& og = iter.first; | ||
| 1726 | QPDFXRefEntry const& entry = iter.second; | 1706 | QPDFXRefEntry const& entry = iter.second; |
| 1727 | if (entry.getType() == 1) { | 1707 | if (entry.getType() == 1) { |
| 1728 | qpdf_offset_t obj_offset = entry.getOffset(); | 1708 | qpdf_offset_t obj_offset = entry.getOffset(); |
| @@ -1730,12 +1710,11 @@ QPDF::recoverStreamLength( | @@ -1730,12 +1710,11 @@ QPDF::recoverStreamLength( | ||
| 1730 | ((this_obj_offset == 0) || | 1710 | ((this_obj_offset == 0) || |
| 1731 | (this_obj_offset > obj_offset))) { | 1711 | (this_obj_offset > obj_offset))) { |
| 1732 | this_obj_offset = obj_offset; | 1712 | this_obj_offset = obj_offset; |
| 1733 | - this_obj = og; | 1713 | + this_og = iter.first; |
| 1734 | } | 1714 | } |
| 1735 | } | 1715 | } |
| 1736 | } | 1716 | } |
| 1737 | - if (this_obj_offset && (this_obj.getObj() == objid) && | ||
| 1738 | - (this_obj.getGen() == generation)) { | 1717 | + if (this_obj_offset && (this_og == og)) { |
| 1739 | // Well, we found endstream\nendobj within the space | 1718 | // Well, we found endstream\nendobj within the space |
| 1740 | // allowed for this object, so we're probably in good | 1719 | // allowed for this object, so we're probably in good |
| 1741 | // shape. | 1720 | // shape. |
| @@ -1777,13 +1756,11 @@ QPDF::readObjectAtOffset( | @@ -1777,13 +1756,11 @@ QPDF::readObjectAtOffset( | ||
| 1777 | bool try_recovery, | 1756 | bool try_recovery, |
| 1778 | qpdf_offset_t offset, | 1757 | qpdf_offset_t offset, |
| 1779 | std::string const& description, | 1758 | std::string const& description, |
| 1780 | - int exp_objid, | ||
| 1781 | - int exp_generation, | ||
| 1782 | - int& objid, | ||
| 1783 | - int& generation) | 1759 | + QPDFObjGen const& exp_og, |
| 1760 | + QPDFObjGen& og) | ||
| 1784 | { | 1761 | { |
| 1785 | bool check_og = true; | 1762 | bool check_og = true; |
| 1786 | - if (exp_objid == 0) { | 1763 | + if (exp_og.getObj() == 0) { |
| 1787 | // This method uses an expect object ID of 0 to indicate that | 1764 | // This method uses an expect object ID of 0 to indicate that |
| 1788 | // we don't know or don't care what the actual object ID is at | 1765 | // we don't know or don't care what the actual object ID is at |
| 1789 | // this offset. This is true when we read the xref stream and | 1766 | // this offset. This is true when we read the xref stream and |
| @@ -1795,7 +1772,7 @@ QPDF::readObjectAtOffset( | @@ -1795,7 +1772,7 @@ QPDF::readObjectAtOffset( | ||
| 1795 | check_og = false; | 1772 | check_og = false; |
| 1796 | try_recovery = false; | 1773 | try_recovery = false; |
| 1797 | } else { | 1774 | } else { |
| 1798 | - setLastObjectDescription(description, exp_objid, exp_generation); | 1775 | + setLastObjectDescription(description, exp_og); |
| 1799 | } | 1776 | } |
| 1800 | 1777 | ||
| 1801 | if (!this->m->attempt_recovery) { | 1778 | if (!this->m->attempt_recovery) { |
| @@ -1841,9 +1818,9 @@ QPDF::readObjectAtOffset( | @@ -1841,9 +1818,9 @@ QPDF::readObjectAtOffset( | ||
| 1841 | offset, | 1818 | offset, |
| 1842 | "expected n n obj"); | 1819 | "expected n n obj"); |
| 1843 | } | 1820 | } |
| 1844 | - objid = QUtil::string_to_int(tobjid.getValue().c_str()); | ||
| 1845 | - generation = QUtil::string_to_int(tgen.getValue().c_str()); | ||
| 1846 | - | 1821 | + int objid = QUtil::string_to_int(tobjid.getValue().c_str()); |
| 1822 | + int generation = QUtil::string_to_int(tgen.getValue().c_str()); | ||
| 1823 | + og = QPDFObjGen(objid, generation); | ||
| 1847 | if (objid == 0) { | 1824 | if (objid == 0) { |
| 1848 | QTC::TC("qpdf", "QPDF object id 0"); | 1825 | QTC::TC("qpdf", "QPDF object id 0"); |
| 1849 | throw QPDFExc( | 1826 | throw QPDFExc( |
| @@ -1853,17 +1830,14 @@ QPDF::readObjectAtOffset( | @@ -1853,17 +1830,14 @@ QPDF::readObjectAtOffset( | ||
| 1853 | offset, | 1830 | offset, |
| 1854 | "object with ID 0"); | 1831 | "object with ID 0"); |
| 1855 | } | 1832 | } |
| 1856 | - | ||
| 1857 | - if (check_og && | ||
| 1858 | - (!((objid == exp_objid) && (generation == exp_generation)))) { | 1833 | + if (check_og && (exp_og != og)) { |
| 1859 | QTC::TC("qpdf", "QPDF err wrong objid/generation"); | 1834 | QTC::TC("qpdf", "QPDF err wrong objid/generation"); |
| 1860 | QPDFExc e( | 1835 | QPDFExc e( |
| 1861 | qpdf_e_damaged_pdf, | 1836 | qpdf_e_damaged_pdf, |
| 1862 | this->m->file->getName(), | 1837 | this->m->file->getName(), |
| 1863 | this->m->last_object_description, | 1838 | this->m->last_object_description, |
| 1864 | offset, | 1839 | offset, |
| 1865 | - (std::string("expected ") + QUtil::int_to_string(exp_objid) + | ||
| 1866 | - " " + QUtil::int_to_string(exp_generation) + " obj")); | 1840 | + (std::string("expected ") + exp_og.unparse(' ') + " obj")); |
| 1867 | if (try_recovery) { | 1841 | if (try_recovery) { |
| 1868 | // Will be retried below | 1842 | // Will be retried below |
| 1869 | throw e; | 1843 | throw e; |
| @@ -1877,18 +1851,12 @@ QPDF::readObjectAtOffset( | @@ -1877,18 +1851,12 @@ QPDF::readObjectAtOffset( | ||
| 1877 | if (try_recovery) { | 1851 | if (try_recovery) { |
| 1878 | // Try again after reconstructing xref table | 1852 | // Try again after reconstructing xref table |
| 1879 | reconstruct_xref(e); | 1853 | reconstruct_xref(e); |
| 1880 | - QPDFObjGen og(exp_objid, exp_generation); | ||
| 1881 | - if (this->m->xref_table.count(og) && | ||
| 1882 | - (this->m->xref_table[og].getType() == 1)) { | ||
| 1883 | - qpdf_offset_t new_offset = this->m->xref_table[og].getOffset(); | 1854 | + if (this->m->xref_table.count(exp_og) && |
| 1855 | + (this->m->xref_table[exp_og].getType() == 1)) { | ||
| 1856 | + qpdf_offset_t new_offset = | ||
| 1857 | + this->m->xref_table[exp_og].getOffset(); | ||
| 1884 | QPDFObjectHandle result = readObjectAtOffset( | 1858 | QPDFObjectHandle result = readObjectAtOffset( |
| 1885 | - false, | ||
| 1886 | - new_offset, | ||
| 1887 | - description, | ||
| 1888 | - exp_objid, | ||
| 1889 | - exp_generation, | ||
| 1890 | - objid, | ||
| 1891 | - generation); | 1859 | + false, new_offset, description, exp_og, og); |
| 1892 | QTC::TC("qpdf", "QPDF recovered in readObjectAtOffset"); | 1860 | QTC::TC("qpdf", "QPDF recovered in readObjectAtOffset"); |
| 1893 | return result; | 1861 | return result; |
| 1894 | } else { | 1862 | } else { |
| @@ -1898,8 +1866,7 @@ QPDF::readObjectAtOffset( | @@ -1898,8 +1866,7 @@ QPDF::readObjectAtOffset( | ||
| 1898 | "", | 1866 | "", |
| 1899 | 0, | 1867 | 0, |
| 1900 | std::string( | 1868 | std::string( |
| 1901 | - "object " + QUtil::int_to_string(exp_objid) + " " + | ||
| 1902 | - QUtil::int_to_string(exp_generation) + | 1869 | + "object " + exp_og.unparse(' ') + |
| 1903 | " not found in file after regenerating" | 1870 | " not found in file after regenerating" |
| 1904 | " cross reference table")); | 1871 | " cross reference table")); |
| 1905 | return QPDFObjectHandle::newNull(); | 1872 | return QPDFObjectHandle::newNull(); |
| @@ -1909,8 +1876,7 @@ QPDF::readObjectAtOffset( | @@ -1909,8 +1876,7 @@ QPDF::readObjectAtOffset( | ||
| 1909 | } | 1876 | } |
| 1910 | } | 1877 | } |
| 1911 | 1878 | ||
| 1912 | - QPDFObjectHandle oh = | ||
| 1913 | - readObject(this->m->file, description, objid, generation, false); | 1879 | + QPDFObjectHandle oh = readObject(this->m->file, description, og, false); |
| 1914 | 1880 | ||
| 1915 | if (!(readToken(this->m->file) == | 1881 | if (!(readToken(this->m->file) == |
| 1916 | QPDFTokenizer::Token(QPDFTokenizer::tt_word, "endobj"))) { | 1882 | QPDFTokenizer::Token(QPDFTokenizer::tt_word, "endobj"))) { |
| @@ -1922,7 +1888,6 @@ QPDF::readObjectAtOffset( | @@ -1922,7 +1888,6 @@ QPDF::readObjectAtOffset( | ||
| 1922 | "expected endobj"); | 1888 | "expected endobj"); |
| 1923 | } | 1889 | } |
| 1924 | 1890 | ||
| 1925 | - QPDFObjGen og(objid, generation); | ||
| 1926 | if (!this->m->obj_cache.count(og)) { | 1891 | if (!this->m->obj_cache.count(og)) { |
| 1927 | // Store the object in the cache here so it gets cached | 1892 | // Store the object in the cache here so it gets cached |
| 1928 | // whether we first know the offset or whether we first know | 1893 | // whether we first know the offset or whether we first know |
| @@ -1987,12 +1952,11 @@ QPDF::objectChanged(QPDFObjGen const& og, std::shared_ptr<QPDFObject>& oph) | @@ -1987,12 +1952,11 @@ QPDF::objectChanged(QPDFObjGen const& og, std::shared_ptr<QPDFObject>& oph) | ||
| 1987 | } | 1952 | } |
| 1988 | 1953 | ||
| 1989 | std::shared_ptr<QPDFObject> | 1954 | std::shared_ptr<QPDFObject> |
| 1990 | -QPDF::resolve(int objid, int generation) | 1955 | +QPDF::resolve(QPDFObjGen const& og) |
| 1991 | { | 1956 | { |
| 1992 | // Check object cache before checking xref table. This allows us | 1957 | // Check object cache before checking xref table. This allows us |
| 1993 | // to insert things into the object cache that don't actually | 1958 | // to insert things into the object cache that don't actually |
| 1994 | // exist in the file. | 1959 | // exist in the file. |
| 1995 | - QPDFObjGen og(objid, generation); | ||
| 1996 | if (this->m->resolving.count(og)) { | 1960 | if (this->m->resolving.count(og)) { |
| 1997 | // This can happen if an object references itself directly or | 1961 | // This can happen if an object references itself directly or |
| 1998 | // indirectly in some key that has to be resolved during | 1962 | // indirectly in some key that has to be resolved during |
| @@ -2002,8 +1966,7 @@ QPDF::resolve(int objid, int generation) | @@ -2002,8 +1966,7 @@ QPDF::resolve(int objid, int generation) | ||
| 2002 | qpdf_e_damaged_pdf, | 1966 | qpdf_e_damaged_pdf, |
| 2003 | "", | 1967 | "", |
| 2004 | this->m->file->getLastOffset(), | 1968 | this->m->file->getLastOffset(), |
| 2005 | - ("loop detected resolving object " + QUtil::int_to_string(objid) + | ||
| 2006 | - " " + QUtil::int_to_string(generation))); | 1969 | + ("loop detected resolving object " + og.unparse(' '))); |
| 2007 | return QPDF_Null::create(); | 1970 | return QPDF_Null::create(); |
| 2008 | } | 1971 | } |
| 2009 | ResolveRecorder rr(this, og); | 1972 | ResolveRecorder rr(this, og); |
| @@ -2016,16 +1979,9 @@ QPDF::resolve(int objid, int generation) | @@ -2016,16 +1979,9 @@ QPDF::resolve(int objid, int generation) | ||
| 2016 | { | 1979 | { |
| 2017 | qpdf_offset_t offset = entry.getOffset(); | 1980 | qpdf_offset_t offset = entry.getOffset(); |
| 2018 | // Object stored in cache by readObjectAtOffset | 1981 | // Object stored in cache by readObjectAtOffset |
| 2019 | - int aobjid; | ||
| 2020 | - int ageneration; | ||
| 2021 | - QPDFObjectHandle oh = readObjectAtOffset( | ||
| 2022 | - true, | ||
| 2023 | - offset, | ||
| 2024 | - "", | ||
| 2025 | - objid, | ||
| 2026 | - generation, | ||
| 2027 | - aobjid, | ||
| 2028 | - ageneration); | 1982 | + QPDFObjGen a_og; |
| 1983 | + QPDFObjectHandle oh = | ||
| 1984 | + readObjectAtOffset(true, offset, "", og, a_og); | ||
| 2029 | } | 1985 | } |
| 2030 | break; | 1986 | break; |
| 2031 | 1987 | ||
| @@ -2039,8 +1995,7 @@ QPDF::resolve(int objid, int generation) | @@ -2039,8 +1995,7 @@ QPDF::resolve(int objid, int generation) | ||
| 2039 | this->m->file->getName(), | 1995 | this->m->file->getName(), |
| 2040 | "", | 1996 | "", |
| 2041 | 0, | 1997 | 0, |
| 2042 | - ("object " + QUtil::int_to_string(objid) + "/" + | ||
| 2043 | - QUtil::int_to_string(generation) + | 1998 | + ("object " + og.unparse('/') + |
| 2044 | " has unexpected xref entry type")); | 1999 | " has unexpected xref entry type")); |
| 2045 | } | 2000 | } |
| 2046 | } catch (QPDFExc& e) { | 2001 | } catch (QPDFExc& e) { |
| @@ -2050,8 +2005,7 @@ QPDF::resolve(int objid, int generation) | @@ -2050,8 +2005,7 @@ QPDF::resolve(int objid, int generation) | ||
| 2050 | qpdf_e_damaged_pdf, | 2005 | qpdf_e_damaged_pdf, |
| 2051 | "", | 2006 | "", |
| 2052 | 0, | 2007 | 0, |
| 2053 | - ("object " + QUtil::int_to_string(objid) + "/" + | ||
| 2054 | - QUtil::int_to_string(generation) + | 2008 | + ("object " + og.unparse('/') + |
| 2055 | ": error reading object: " + e.what())); | 2009 | ": error reading object: " + e.what())); |
| 2056 | } | 2010 | } |
| 2057 | } | 2011 | } |
| @@ -2065,10 +2019,7 @@ QPDF::resolve(int objid, int generation) | @@ -2065,10 +2019,7 @@ QPDF::resolve(int objid, int generation) | ||
| 2065 | 2019 | ||
| 2066 | std::shared_ptr<QPDFObject> result(this->m->obj_cache[og].object); | 2020 | std::shared_ptr<QPDFObject> result(this->m->obj_cache[og].object); |
| 2067 | if (!result->hasDescription()) { | 2021 | if (!result->hasDescription()) { |
| 2068 | - result->setDescription( | ||
| 2069 | - this, | ||
| 2070 | - ("object " + QUtil::int_to_string(objid) + " " + | ||
| 2071 | - QUtil::int_to_string(generation))); | 2022 | + result->setDescription(this, ("object " + og.unparse(' '))); |
| 2072 | } | 2023 | } |
| 2073 | return result; | 2024 | return result; |
| 2074 | } | 2025 | } |
| @@ -2165,7 +2116,7 @@ QPDF::resolveObjectsInStream(int obj_stream_number) | @@ -2165,7 +2116,7 @@ QPDF::resolveObjectsInStream(int obj_stream_number) | ||
| 2165 | (entry.getObjStreamNumber() == obj_stream_number)) { | 2116 | (entry.getObjStreamNumber() == obj_stream_number)) { |
| 2166 | int offset = iter.second; | 2117 | int offset = iter.second; |
| 2167 | input->seek(offset, SEEK_SET); | 2118 | input->seek(offset, SEEK_SET); |
| 2168 | - QPDFObjectHandle oh = readObject(input, "", obj, 0, true); | 2119 | + QPDFObjectHandle oh = readObject(input, "", og, true); |
| 2169 | this->m->obj_cache[og] = ObjCache( | 2120 | this->m->obj_cache[og] = ObjCache( |
| 2170 | QPDFObjectHandle::ObjAccessor::getObject(oh), | 2121 | QPDFObjectHandle::ObjAccessor::getObject(oh), |
| 2171 | end_before_space, | 2122 | end_before_space, |
| @@ -2187,48 +2138,46 @@ QPDF::makeIndirectObject(QPDFObjectHandle oh) | @@ -2187,48 +2138,46 @@ QPDF::makeIndirectObject(QPDFObjectHandle oh) | ||
| 2187 | QPDFObjGen next(max_objid + 1, 0); | 2138 | QPDFObjGen next(max_objid + 1, 0); |
| 2188 | this->m->obj_cache[next] = | 2139 | this->m->obj_cache[next] = |
| 2189 | ObjCache(QPDFObjectHandle::ObjAccessor::getObject(oh), -1, -1); | 2140 | ObjCache(QPDFObjectHandle::ObjAccessor::getObject(oh), -1, -1); |
| 2190 | - return QPDFObjectHandle::Factory::newIndirect( | ||
| 2191 | - this, next.getObj(), next.getGen()); | 2141 | + return QPDFObjectHandle::Factory::newIndirect(this, next); |
| 2192 | } | 2142 | } |
| 2193 | 2143 | ||
| 2194 | QPDFObjectHandle | 2144 | QPDFObjectHandle |
| 2195 | -QPDF::reserveObjectIfNotExists(int objid, int gen) | 2145 | +QPDF::reserveObjectIfNotExists(QPDFObjGen const& og) |
| 2196 | { | 2146 | { |
| 2197 | - QPDFObjGen og(objid, gen); | ||
| 2198 | if ((!this->m->obj_cache.count(og)) && (!this->m->xref_table.count(og))) { | 2147 | if ((!this->m->obj_cache.count(og)) && (!this->m->xref_table.count(og))) { |
| 2199 | - resolve(objid, gen); | ||
| 2200 | - replaceObject(objid, gen, QPDFObjectHandle::Factory::makeReserved()); | 2148 | + resolve(og); |
| 2149 | + replaceObject(og, QPDFObjectHandle::Factory::makeReserved()); | ||
| 2201 | } | 2150 | } |
| 2202 | - return getObjectByID(objid, gen); | 2151 | + return getObjectByObjGen(og); |
| 2203 | } | 2152 | } |
| 2204 | 2153 | ||
| 2205 | QPDFObjectHandle | 2154 | QPDFObjectHandle |
| 2206 | -QPDF::reserveStream(int objid, int gen) | 2155 | +QPDF::reserveStream(QPDFObjGen const& og) |
| 2207 | { | 2156 | { |
| 2208 | return QPDFObjectHandle::Factory::newStream( | 2157 | return QPDFObjectHandle::Factory::newStream( |
| 2209 | - this, objid, gen, QPDFObjectHandle::newDictionary(), 0, 0); | 2158 | + this, og, QPDFObjectHandle::newDictionary(), 0, 0); |
| 2210 | } | 2159 | } |
| 2211 | 2160 | ||
| 2212 | QPDFObjectHandle | 2161 | QPDFObjectHandle |
| 2213 | QPDF::getObjectByObjGen(QPDFObjGen const& og) | 2162 | QPDF::getObjectByObjGen(QPDFObjGen const& og) |
| 2214 | { | 2163 | { |
| 2215 | - return getObjectByID(og.getObj(), og.getGen()); | 2164 | + return QPDFObjectHandle::Factory::newIndirect(this, og); |
| 2216 | } | 2165 | } |
| 2217 | 2166 | ||
| 2218 | QPDFObjectHandle | 2167 | QPDFObjectHandle |
| 2219 | QPDF::getObjectByID(int objid, int generation) | 2168 | QPDF::getObjectByID(int objid, int generation) |
| 2220 | { | 2169 | { |
| 2221 | - return QPDFObjectHandle::Factory::newIndirect(this, objid, generation); | 2170 | + return getObjectByObjGen(QPDFObjGen(objid, generation)); |
| 2222 | } | 2171 | } |
| 2223 | 2172 | ||
| 2224 | void | 2173 | void |
| 2225 | -QPDF::replaceObject(QPDFObjGen const& og, QPDFObjectHandle oh) | 2174 | +QPDF::replaceObject(int objid, int generation, QPDFObjectHandle oh) |
| 2226 | { | 2175 | { |
| 2227 | - replaceObject(og.getObj(), og.getGen(), oh); | 2176 | + replaceObject(QPDFObjGen(objid, generation), oh); |
| 2228 | } | 2177 | } |
| 2229 | 2178 | ||
| 2230 | void | 2179 | void |
| 2231 | -QPDF::replaceObject(int objid, int generation, QPDFObjectHandle oh) | 2180 | +QPDF::replaceObject(QPDFObjGen const& og, QPDFObjectHandle oh) |
| 2232 | { | 2181 | { |
| 2233 | if (oh.isIndirect()) { | 2182 | if (oh.isIndirect()) { |
| 2234 | QTC::TC("qpdf", "QPDF replaceObject called with indirect object"); | 2183 | QTC::TC("qpdf", "QPDF replaceObject called with indirect object"); |
| @@ -2237,10 +2186,9 @@ QPDF::replaceObject(int objid, int generation, QPDFObjectHandle oh) | @@ -2237,10 +2186,9 @@ QPDF::replaceObject(int objid, int generation, QPDFObjectHandle oh) | ||
| 2237 | } | 2186 | } |
| 2238 | 2187 | ||
| 2239 | // Force new object to appear in the cache | 2188 | // Force new object to appear in the cache |
| 2240 | - resolve(objid, generation); | 2189 | + resolve(og); |
| 2241 | 2190 | ||
| 2242 | // Replace the object in the object cache | 2191 | // Replace the object in the object cache |
| 2243 | - QPDFObjGen og(objid, generation); | ||
| 2244 | this->m->ever_replaced_objects = true; | 2192 | this->m->ever_replaced_objects = true; |
| 2245 | this->m->obj_cache[og] = | 2193 | this->m->obj_cache[og] = |
| 2246 | ObjCache(QPDFObjectHandle::ObjAccessor::getObject(oh), -1, -1); | 2194 | ObjCache(QPDFObjectHandle::ObjAccessor::getObject(oh), -1, -1); |
| @@ -2540,8 +2488,7 @@ QPDF::copyStreamData(QPDFObjectHandle result, QPDFObjectHandle foreign) | @@ -2540,8 +2488,7 @@ QPDF::copyStreamData(QPDFObjectHandle result, QPDFObjectHandle foreign) | ||
| 2540 | auto foreign_stream_data = std::make_shared<ForeignStreamData>( | 2488 | auto foreign_stream_data = std::make_shared<ForeignStreamData>( |
| 2541 | foreign_stream_qpdf->m->encp, | 2489 | foreign_stream_qpdf->m->encp, |
| 2542 | foreign_stream_qpdf->m->file, | 2490 | foreign_stream_qpdf->m->file, |
| 2543 | - foreign.getObjectID(), | ||
| 2544 | - foreign.getGeneration(), | 2491 | + foreign.getObjGen(), |
| 2545 | stream->getOffset(), | 2492 | stream->getOffset(), |
| 2546 | stream->getLength(), | 2493 | stream->getLength(), |
| 2547 | dict); | 2494 | dict); |
| @@ -2555,20 +2502,19 @@ QPDF::copyStreamData(QPDFObjectHandle result, QPDFObjectHandle foreign) | @@ -2555,20 +2502,19 @@ QPDF::copyStreamData(QPDFObjectHandle result, QPDFObjectHandle foreign) | ||
| 2555 | } | 2502 | } |
| 2556 | 2503 | ||
| 2557 | void | 2504 | void |
| 2558 | -QPDF::swapObjects(QPDFObjGen const& og1, QPDFObjGen const& og2) | 2505 | +QPDF::swapObjects(int objid1, int generation1, int objid2, int generation2) |
| 2559 | { | 2506 | { |
| 2560 | - swapObjects(og1.getObj(), og1.getGen(), og2.getObj(), og2.getGen()); | 2507 | + swapObjects( |
| 2508 | + QPDFObjGen(objid1, generation1), QPDFObjGen(objid2, generation2)); | ||
| 2561 | } | 2509 | } |
| 2562 | 2510 | ||
| 2563 | void | 2511 | void |
| 2564 | -QPDF::swapObjects(int objid1, int generation1, int objid2, int generation2) | 2512 | +QPDF::swapObjects(QPDFObjGen const& og1, QPDFObjGen const& og2) |
| 2565 | { | 2513 | { |
| 2566 | // Force objects to be loaded into cache; then swap them in the | 2514 | // Force objects to be loaded into cache; then swap them in the |
| 2567 | // cache. | 2515 | // cache. |
| 2568 | - resolve(objid1, generation1); | ||
| 2569 | - resolve(objid2, generation2); | ||
| 2570 | - QPDFObjGen og1(objid1, generation1); | ||
| 2571 | - QPDFObjGen og2(objid2, generation2); | 2516 | + resolve(og1); |
| 2517 | + resolve(og2); | ||
| 2572 | ObjCache t = this->m->obj_cache[og1]; | 2518 | ObjCache t = this->m->obj_cache[og1]; |
| 2573 | this->m->ever_replaced_objects = true; | 2519 | this->m->ever_replaced_objects = true; |
| 2574 | this->m->obj_cache[og1] = this->m->obj_cache[og2]; | 2520 | this->m->obj_cache[og1] = this->m->obj_cache[og2]; |
| @@ -2752,8 +2698,7 @@ QPDF::pipeStreamData( | @@ -2752,8 +2698,7 @@ QPDF::pipeStreamData( | ||
| 2752 | std::shared_ptr<EncryptionParameters> encp, | 2698 | std::shared_ptr<EncryptionParameters> encp, |
| 2753 | std::shared_ptr<InputSource> file, | 2699 | std::shared_ptr<InputSource> file, |
| 2754 | QPDF& qpdf_for_warning, | 2700 | QPDF& qpdf_for_warning, |
| 2755 | - int objid, | ||
| 2756 | - int generation, | 2701 | + QPDFObjGen const& og, |
| 2757 | qpdf_offset_t offset, | 2702 | qpdf_offset_t offset, |
| 2758 | size_t length, | 2703 | size_t length, |
| 2759 | QPDFObjectHandle stream_dict, | 2704 | QPDFObjectHandle stream_dict, |
| @@ -2764,14 +2709,7 @@ QPDF::pipeStreamData( | @@ -2764,14 +2709,7 @@ QPDF::pipeStreamData( | ||
| 2764 | std::vector<std::shared_ptr<Pipeline>> to_delete; | 2709 | std::vector<std::shared_ptr<Pipeline>> to_delete; |
| 2765 | if (encp->encrypted) { | 2710 | if (encp->encrypted) { |
| 2766 | decryptStream( | 2711 | decryptStream( |
| 2767 | - encp, | ||
| 2768 | - file, | ||
| 2769 | - qpdf_for_warning, | ||
| 2770 | - pipeline, | ||
| 2771 | - objid, | ||
| 2772 | - generation, | ||
| 2773 | - stream_dict, | ||
| 2774 | - to_delete); | 2712 | + encp, file, qpdf_for_warning, pipeline, og, stream_dict, to_delete); |
| 2775 | } | 2713 | } |
| 2776 | 2714 | ||
| 2777 | bool success = false; | 2715 | bool success = false; |
| @@ -2809,8 +2747,7 @@ QPDF::pipeStreamData( | @@ -2809,8 +2747,7 @@ QPDF::pipeStreamData( | ||
| 2809 | "", | 2747 | "", |
| 2810 | file->getLastOffset(), | 2748 | file->getLastOffset(), |
| 2811 | ("error decoding stream data for object " + | 2749 | ("error decoding stream data for object " + |
| 2812 | - QUtil::int_to_string(objid) + " " + | ||
| 2813 | - QUtil::int_to_string(generation) + ": " + e.what()))); | 2750 | + og.unparse(' ') + ": " + e.what()))); |
| 2814 | if (will_retry) { | 2751 | if (will_retry) { |
| 2815 | qpdf_for_warning.warn( | 2752 | qpdf_for_warning.warn( |
| 2816 | // line-break | 2753 | // line-break |
| @@ -2836,8 +2773,7 @@ QPDF::pipeStreamData( | @@ -2836,8 +2773,7 @@ QPDF::pipeStreamData( | ||
| 2836 | 2773 | ||
| 2837 | bool | 2774 | bool |
| 2838 | QPDF::pipeStreamData( | 2775 | QPDF::pipeStreamData( |
| 2839 | - int objid, | ||
| 2840 | - int generation, | 2776 | + QPDFObjGen const& og, |
| 2841 | qpdf_offset_t offset, | 2777 | qpdf_offset_t offset, |
| 2842 | size_t length, | 2778 | size_t length, |
| 2843 | QPDFObjectHandle stream_dict, | 2779 | QPDFObjectHandle stream_dict, |
| @@ -2849,8 +2785,7 @@ QPDF::pipeStreamData( | @@ -2849,8 +2785,7 @@ QPDF::pipeStreamData( | ||
| 2849 | this->m->encp, | 2785 | this->m->encp, |
| 2850 | this->m->file, | 2786 | this->m->file, |
| 2851 | *this, | 2787 | *this, |
| 2852 | - objid, | ||
| 2853 | - generation, | 2788 | + og, |
| 2854 | offset, | 2789 | offset, |
| 2855 | length, | 2790 | length, |
| 2856 | stream_dict, | 2791 | stream_dict, |
| @@ -2873,8 +2808,7 @@ QPDF::pipeForeignStreamData( | @@ -2873,8 +2808,7 @@ QPDF::pipeForeignStreamData( | ||
| 2873 | foreign->encp, | 2808 | foreign->encp, |
| 2874 | foreign->file, | 2809 | foreign->file, |
| 2875 | *this, | 2810 | *this, |
| 2876 | - foreign->foreign_objid, | ||
| 2877 | - foreign->foreign_generation, | 2811 | + foreign->foreign_og, |
| 2878 | foreign->offset, | 2812 | foreign->offset, |
| 2879 | foreign->length, | 2813 | foreign->length, |
| 2880 | foreign->local_dict, | 2814 | foreign->local_dict, |
libqpdf/QPDFAcroFormDocumentHelper.cc
| @@ -991,8 +991,8 @@ QPDFAcroFormDocumentHelper::transformAnnotations( | @@ -991,8 +991,8 @@ QPDFAcroFormDocumentHelper::transformAnnotations( | ||
| 991 | } else { | 991 | } else { |
| 992 | parent.warnIfPossible( | 992 | parent.warnIfPossible( |
| 993 | "while traversing field " + | 993 | "while traversing field " + |
| 994 | - obj.getObjGen().unparse() + ", found parent (" + | ||
| 995 | - parent_og.unparse() + | 994 | + obj.getObjGen().unparse(',') + ", found parent (" + |
| 995 | + parent_og.unparse(',') + | ||
| 996 | ") that had not been seen, indicating likely" | 996 | ") that had not been seen, indicating likely" |
| 997 | " invalid field structure"); | 997 | " invalid field structure"); |
| 998 | } | 998 | } |
libqpdf/QPDFJob.cc
| @@ -49,8 +49,7 @@ namespace | @@ -49,8 +49,7 @@ namespace | ||
| 49 | size_t oi_min_area, | 49 | size_t oi_min_area, |
| 50 | QPDFObjectHandle& image); | 50 | QPDFObjectHandle& image); |
| 51 | virtual ~ImageOptimizer() = default; | 51 | virtual ~ImageOptimizer() = default; |
| 52 | - virtual void | ||
| 53 | - provideStreamData(int objid, int generation, Pipeline* pipeline); | 52 | + virtual void provideStreamData(QPDFObjGen const&, Pipeline* pipeline); |
| 54 | std::shared_ptr<Pipeline> | 53 | std::shared_ptr<Pipeline> |
| 55 | makePipeline(std::string const& description, Pipeline* next); | 54 | makePipeline(std::string const& description, Pipeline* next); |
| 56 | bool evaluate(std::string const& description); | 55 | bool evaluate(std::string const& description); |
| @@ -250,7 +249,7 @@ ImageOptimizer::evaluate(std::string const& description) | @@ -250,7 +249,7 @@ ImageOptimizer::evaluate(std::string const& description) | ||
| 250 | } | 249 | } |
| 251 | 250 | ||
| 252 | void | 251 | void |
| 253 | -ImageOptimizer::provideStreamData(int, int, Pipeline* pipeline) | 252 | +ImageOptimizer::provideStreamData(QPDFObjGen const&, Pipeline* pipeline) |
| 254 | { | 253 | { |
| 255 | std::shared_ptr<Pipeline> p = makePipeline("", pipeline); | 254 | std::shared_ptr<Pipeline> p = makePipeline("", pipeline); |
| 256 | if (p.get() == nullptr) { | 255 | if (p.get() == nullptr) { |
| @@ -947,7 +946,7 @@ QPDFJob::doShowObj(QPDF& pdf) | @@ -947,7 +946,7 @@ QPDFJob::doShowObj(QPDF& pdf) | ||
| 947 | } | 946 | } |
| 948 | if (error) { | 947 | if (error) { |
| 949 | throw std::runtime_error( | 948 | throw std::runtime_error( |
| 950 | - "unable to get object " + obj.getObjGen().unparse()); | 949 | + "unable to get object " + obj.getObjGen().unparse(',')); |
| 951 | } | 950 | } |
| 952 | } | 951 | } |
| 953 | 952 | ||
| @@ -995,7 +994,8 @@ QPDFJob::doListAttachments(QPDF& pdf) | @@ -995,7 +994,8 @@ QPDFJob::doListAttachments(QPDF& pdf) | ||
| 995 | auto efoh = i.second; | 994 | auto efoh = i.second; |
| 996 | *this->m->log->getInfo() | 995 | *this->m->log->getInfo() |
| 997 | << key << " -> " | 996 | << key << " -> " |
| 998 | - << efoh->getEmbeddedFileStream().getObjGen().unparse() << "\n"; | 997 | + << efoh->getEmbeddedFileStream().getObjGen().unparse(',') |
| 998 | + << "\n"; | ||
| 999 | doIfVerbose([&](Pipeline& v, std::string const& prefix) { | 999 | doIfVerbose([&](Pipeline& v, std::string const& prefix) { |
| 1000 | auto desc = efoh->getDescription(); | 1000 | auto desc = efoh->getDescription(); |
| 1001 | if (!desc.empty()) { | 1001 | if (!desc.empty()) { |
| @@ -1010,7 +1010,7 @@ QPDFJob::doListAttachments(QPDF& pdf) | @@ -1010,7 +1010,7 @@ QPDFJob::doListAttachments(QPDF& pdf) | ||
| 1010 | for (auto i2: efoh->getEmbeddedFileStreams().ditems()) { | 1010 | for (auto i2: efoh->getEmbeddedFileStreams().ditems()) { |
| 1011 | auto efs = QPDFEFStreamObjectHelper(i2.second); | 1011 | auto efs = QPDFEFStreamObjectHelper(i2.second); |
| 1012 | v << " " << i2.first << " -> " | 1012 | v << " " << i2.first << " -> " |
| 1013 | - << efs.getObjectHandle().getObjGen().unparse() << "\n"; | 1013 | + << efs.getObjectHandle().getObjGen().unparse(',') << "\n"; |
| 1014 | v << " creation date: " << efs.getCreationDate() | 1014 | v << " creation date: " << efs.getCreationDate() |
| 1015 | << "\n" | 1015 | << "\n" |
| 1016 | << " modification date: " << efs.getModDate() << "\n" | 1016 | << " modification date: " << efs.getModDate() << "\n" |
| @@ -2463,7 +2463,7 @@ QPDFJob::shouldRemoveUnreferencedResources(QPDF& pdf) | @@ -2463,7 +2463,7 @@ QPDFJob::shouldRemoveUnreferencedResources(QPDF& pdf) | ||
| 2463 | QTC::TC("qpdf", "QPDFJob found resources in non-leaf"); | 2463 | QTC::TC("qpdf", "QPDFJob found resources in non-leaf"); |
| 2464 | doIfVerbose([&](Pipeline& v, std::string const& prefix) { | 2464 | doIfVerbose([&](Pipeline& v, std::string const& prefix) { |
| 2465 | v << " found resources in non-leaf page node " | 2465 | v << " found resources in non-leaf page node " |
| 2466 | - << og.getObj() << " " << og.getGen() << "\n"; | 2466 | + << og.unparse(' ') << "\n"; |
| 2467 | }); | 2467 | }); |
| 2468 | return true; | 2468 | return true; |
| 2469 | } | 2469 | } |
| @@ -2480,9 +2480,8 @@ QPDFJob::shouldRemoveUnreferencedResources(QPDF& pdf) | @@ -2480,9 +2480,8 @@ QPDFJob::shouldRemoveUnreferencedResources(QPDF& pdf) | ||
| 2480 | QTC::TC("qpdf", "QPDFJob found shared resources in leaf"); | 2480 | QTC::TC("qpdf", "QPDFJob found shared resources in leaf"); |
| 2481 | doIfVerbose([&](Pipeline& v, std::string const& prefix) { | 2481 | doIfVerbose([&](Pipeline& v, std::string const& prefix) { |
| 2482 | v << " found shared resources in leaf node " | 2482 | v << " found shared resources in leaf node " |
| 2483 | - << og.getObj() << " " << og.getGen() << ": " | ||
| 2484 | - << resources_og.getObj() << " " | ||
| 2485 | - << resources_og.getGen() << "\n"; | 2483 | + << og.unparse(' ') << ": " |
| 2484 | + << resources_og.unparse(' ') << "\n"; | ||
| 2486 | }); | 2485 | }); |
| 2487 | return true; | 2486 | return true; |
| 2488 | } | 2487 | } |
| @@ -2497,8 +2496,7 @@ QPDFJob::shouldRemoveUnreferencedResources(QPDF& pdf) | @@ -2497,8 +2496,7 @@ QPDFJob::shouldRemoveUnreferencedResources(QPDF& pdf) | ||
| 2497 | QTC::TC("qpdf", "QPDFJob found shared xobject in leaf"); | 2496 | QTC::TC("qpdf", "QPDFJob found shared xobject in leaf"); |
| 2498 | doIfVerbose([&](Pipeline& v, std::string const& prefix) { | 2497 | doIfVerbose([&](Pipeline& v, std::string const& prefix) { |
| 2499 | v << " found shared xobject in leaf node " | 2498 | v << " found shared xobject in leaf node " |
| 2500 | - << og.getObj() << " " << og.getGen() << ": " | ||
| 2501 | - << xobject_og.getObj() << " " << xobject_og.getGen() | 2499 | + << og.unparse(' ') << ": " << xobject_og.unparse(' ') |
| 2502 | << "\n"; | 2500 | << "\n"; |
| 2503 | }); | 2501 | }); |
| 2504 | return true; | 2502 | return true; |
| @@ -3375,7 +3373,7 @@ QPDFJob::writeJSON(QPDF& pdf) | @@ -3375,7 +3373,7 @@ QPDFJob::writeJSON(QPDF& pdf) | ||
| 3375 | auto wanted = getWantedJSONObjects(); | 3373 | auto wanted = getWantedJSONObjects(); |
| 3376 | for (auto const& og: wanted) { | 3374 | for (auto const& og: wanted) { |
| 3377 | std::ostringstream s; | 3375 | std::ostringstream s; |
| 3378 | - s << "obj:" << og.getObj() << " " << og.getGen() << " R"; | 3376 | + s << "obj:" << og.unparse(' ') << " R"; |
| 3379 | json_objects.insert(s.str()); | 3377 | json_objects.insert(s.str()); |
| 3380 | } | 3378 | } |
| 3381 | pdf.writeJSON( | 3379 | pdf.writeJSON( |
libqpdf/QPDFObjGen.cc
0 โ 100644
| 1 | +#include <qpdf/QPDFObjGen.hh> | ||
| 2 | + | ||
| 3 | +#include <qpdf/QUtil.hh> | ||
| 4 | + | ||
| 5 | +std::ostream& | ||
| 6 | +operator<<(std::ostream& os, const QPDFObjGen& og) | ||
| 7 | +{ | ||
| 8 | + os << og.obj << "," << og.gen; | ||
| 9 | + return os; | ||
| 10 | +} | ||
| 11 | + | ||
| 12 | +std::string | ||
| 13 | +QPDFObjGen::unparse(char separator) const | ||
| 14 | +{ | ||
| 15 | + return QUtil::int_to_string(this->obj) + separator + | ||
| 16 | + QUtil::int_to_string(this->gen); | ||
| 17 | +} |
libqpdf/QPDFObjectHandle.cc
| @@ -53,6 +53,24 @@ QPDFObjectHandle::StreamDataProvider::~StreamDataProvider() | @@ -53,6 +53,24 @@ QPDFObjectHandle::StreamDataProvider::~StreamDataProvider() | ||
| 53 | 53 | ||
| 54 | void | 54 | void |
| 55 | QPDFObjectHandle::StreamDataProvider::provideStreamData( | 55 | QPDFObjectHandle::StreamDataProvider::provideStreamData( |
| 56 | + QPDFObjGen const& og, Pipeline* pipeline) | ||
| 57 | +{ | ||
| 58 | + return provideStreamData(og.getObj(), og.getGen(), pipeline); | ||
| 59 | +} | ||
| 60 | + | ||
| 61 | +bool | ||
| 62 | +QPDFObjectHandle::StreamDataProvider::provideStreamData( | ||
| 63 | + QPDFObjGen const& og, | ||
| 64 | + Pipeline* pipeline, | ||
| 65 | + bool suppress_warnings, | ||
| 66 | + bool will_retry) | ||
| 67 | +{ | ||
| 68 | + return provideStreamData( | ||
| 69 | + og.getObj(), og.getGen(), pipeline, suppress_warnings, will_retry); | ||
| 70 | +} | ||
| 71 | + | ||
| 72 | +void | ||
| 73 | +QPDFObjectHandle::StreamDataProvider::provideStreamData( | ||
| 56 | int objid, int generation, Pipeline* pipeline) | 74 | int objid, int generation, Pipeline* pipeline) |
| 57 | { | 75 | { |
| 58 | throw std::logic_error( | 76 | throw std::logic_error( |
| @@ -90,8 +108,7 @@ namespace | @@ -90,8 +108,7 @@ namespace | ||
| 90 | { | 108 | { |
| 91 | } | 109 | } |
| 92 | virtual ~CoalesceProvider() = default; | 110 | virtual ~CoalesceProvider() = default; |
| 93 | - virtual void | ||
| 94 | - provideStreamData(int objid, int generation, Pipeline* pipeline); | 111 | + virtual void provideStreamData(QPDFObjGen const&, Pipeline* pipeline); |
| 95 | 112 | ||
| 96 | private: | 113 | private: |
| 97 | QPDFObjectHandle containing_page; | 114 | QPDFObjectHandle containing_page; |
| @@ -100,12 +117,11 @@ namespace | @@ -100,12 +117,11 @@ namespace | ||
| 100 | } // namespace | 117 | } // namespace |
| 101 | 118 | ||
| 102 | void | 119 | void |
| 103 | -CoalesceProvider::provideStreamData(int, int, Pipeline* p) | 120 | +CoalesceProvider::provideStreamData(QPDFObjGen const&, Pipeline* p) |
| 104 | { | 121 | { |
| 105 | QTC::TC("qpdf", "QPDFObjectHandle coalesce provide stream data"); | 122 | QTC::TC("qpdf", "QPDFObjectHandle coalesce provide stream data"); |
| 106 | - std::string description = "page object " + | ||
| 107 | - QUtil::int_to_string(containing_page.getObjectID()) + " " + | ||
| 108 | - QUtil::int_to_string(containing_page.getGeneration()); | 123 | + std::string description = |
| 124 | + "page object " + containing_page.getObjGen().unparse(' '); | ||
| 109 | std::string all_description; | 125 | std::string all_description; |
| 110 | old_contents.pipeContentStreams(p, description, all_description); | 126 | old_contents.pipeContentStreams(p, description, all_description); |
| 111 | } | 127 | } |
| @@ -219,27 +235,22 @@ LastChar::getLastChar() | @@ -219,27 +235,22 @@ LastChar::getLastChar() | ||
| 219 | 235 | ||
| 220 | QPDFObjectHandle::QPDFObjectHandle() : | 236 | QPDFObjectHandle::QPDFObjectHandle() : |
| 221 | initialized(false), | 237 | initialized(false), |
| 222 | - qpdf(0), | ||
| 223 | - objid(0), | ||
| 224 | - generation(0), | 238 | + qpdf(nullptr), |
| 225 | reserved(false) | 239 | reserved(false) |
| 226 | { | 240 | { |
| 227 | } | 241 | } |
| 228 | 242 | ||
| 229 | -QPDFObjectHandle::QPDFObjectHandle(QPDF* qpdf, int objid, int generation) : | 243 | +QPDFObjectHandle::QPDFObjectHandle(QPDF* qpdf, QPDFObjGen const& og) : |
| 230 | initialized(true), | 244 | initialized(true), |
| 231 | qpdf(qpdf), | 245 | qpdf(qpdf), |
| 232 | - objid(objid), | ||
| 233 | - generation(generation), | 246 | + og(og), |
| 234 | reserved(false) | 247 | reserved(false) |
| 235 | { | 248 | { |
| 236 | } | 249 | } |
| 237 | 250 | ||
| 238 | QPDFObjectHandle::QPDFObjectHandle(std::shared_ptr<QPDFObject> const& data) : | 251 | QPDFObjectHandle::QPDFObjectHandle(std::shared_ptr<QPDFObject> const& data) : |
| 239 | initialized(true), | 252 | initialized(true), |
| 240 | - qpdf(0), | ||
| 241 | - objid(0), | ||
| 242 | - generation(0), | 253 | + qpdf(nullptr), |
| 243 | obj(data), | 254 | obj(data), |
| 244 | reserved(false) | 255 | reserved(false) |
| 245 | { | 256 | { |
| @@ -1431,15 +1442,14 @@ namespace | @@ -1431,15 +1442,14 @@ namespace | ||
| 1431 | } | 1442 | } |
| 1432 | 1443 | ||
| 1433 | virtual void | 1444 | virtual void |
| 1434 | - provideStreamData(int, int, Pipeline* pipeline) override | 1445 | + provideStreamData(QPDFObjGen const&, Pipeline* pipeline) override |
| 1435 | { | 1446 | { |
| 1436 | p1(pipeline); | 1447 | p1(pipeline); |
| 1437 | } | 1448 | } |
| 1438 | 1449 | ||
| 1439 | virtual bool | 1450 | virtual bool |
| 1440 | provideStreamData( | 1451 | provideStreamData( |
| 1441 | - int, | ||
| 1442 | - int, | 1452 | + QPDFObjGen const&, |
| 1443 | Pipeline* pipeline, | 1453 | Pipeline* pipeline, |
| 1444 | bool suppress_warnings, | 1454 | bool suppress_warnings, |
| 1445 | bool will_retry) override | 1455 | bool will_retry) override |
| @@ -1482,26 +1492,19 @@ QPDFObjectHandle::replaceStreamData( | @@ -1482,26 +1492,19 @@ QPDFObjectHandle::replaceStreamData( | ||
| 1482 | QPDFObjGen | 1492 | QPDFObjGen |
| 1483 | QPDFObjectHandle::getObjGen() const | 1493 | QPDFObjectHandle::getObjGen() const |
| 1484 | { | 1494 | { |
| 1485 | - return QPDFObjGen(this->objid, this->generation); | ||
| 1486 | -} | ||
| 1487 | - | ||
| 1488 | -std::string | ||
| 1489 | -QPDFObjectHandle::getObjGenAsStr() const | ||
| 1490 | -{ | ||
| 1491 | - return QUtil::int_to_string(this->objid) + " " + | ||
| 1492 | - QUtil::int_to_string(this->generation); | 1495 | + return og; |
| 1493 | } | 1496 | } |
| 1494 | 1497 | ||
| 1495 | int | 1498 | int |
| 1496 | QPDFObjectHandle::getObjectID() const | 1499 | QPDFObjectHandle::getObjectID() const |
| 1497 | { | 1500 | { |
| 1498 | - return this->objid; | 1501 | + return og.getObj(); |
| 1499 | } | 1502 | } |
| 1500 | 1503 | ||
| 1501 | int | 1504 | int |
| 1502 | QPDFObjectHandle::getGeneration() const | 1505 | QPDFObjectHandle::getGeneration() const |
| 1503 | { | 1506 | { |
| 1504 | - return this->generation; | 1507 | + return og.getGen(); |
| 1505 | } | 1508 | } |
| 1506 | 1509 | ||
| 1507 | std::map<std::string, QPDFObjectHandle> | 1510 | std::map<std::string, QPDFObjectHandle> |
| @@ -1556,7 +1559,7 @@ QPDFObjectHandle::arrayOrStreamToStreamArray( | @@ -1556,7 +1559,7 @@ QPDFObjectHandle::arrayOrStreamToStreamArray( | ||
| 1556 | } else { | 1559 | } else { |
| 1557 | all_description += ","; | 1560 | all_description += ","; |
| 1558 | } | 1561 | } |
| 1559 | - all_description += " stream " + item.getObjGenAsStr(); | 1562 | + all_description += " stream " + item.getObjGen().unparse(' '); |
| 1560 | } | 1563 | } |
| 1561 | 1564 | ||
| 1562 | return result; | 1565 | return result; |
| @@ -1565,7 +1568,7 @@ QPDFObjectHandle::arrayOrStreamToStreamArray( | @@ -1565,7 +1568,7 @@ QPDFObjectHandle::arrayOrStreamToStreamArray( | ||
| 1565 | std::vector<QPDFObjectHandle> | 1568 | std::vector<QPDFObjectHandle> |
| 1566 | QPDFObjectHandle::getPageContents() | 1569 | QPDFObjectHandle::getPageContents() |
| 1567 | { | 1570 | { |
| 1568 | - std::string description = "page object " + getObjGenAsStr(); | 1571 | + std::string description = "page object " + getObjGen().unparse(' '); |
| 1569 | std::string all_description; | 1572 | std::string all_description; |
| 1570 | return this->getKey("/Contents") | 1573 | return this->getKey("/Contents") |
| 1571 | .arrayOrStreamToStreamArray(description, all_description); | 1574 | .arrayOrStreamToStreamArray(description, all_description); |
| @@ -1674,7 +1677,7 @@ QPDFObjectHandle::unparse() | @@ -1674,7 +1677,7 @@ QPDFObjectHandle::unparse() | ||
| 1674 | { | 1677 | { |
| 1675 | std::string result; | 1678 | std::string result; |
| 1676 | if (this->isIndirect()) { | 1679 | if (this->isIndirect()) { |
| 1677 | - result = getObjGenAsStr() + " R"; | 1680 | + result = getObjGen().unparse(' ') + " R"; |
| 1678 | } else { | 1681 | } else { |
| 1679 | result = unparseResolved(); | 1682 | result = unparseResolved(); |
| 1680 | } | 1683 | } |
| @@ -1789,7 +1792,7 @@ QPDFObjectHandle::parse( | @@ -1789,7 +1792,7 @@ QPDFObjectHandle::parse( | ||
| 1789 | void | 1792 | void |
| 1790 | QPDFObjectHandle::pipePageContents(Pipeline* p) | 1793 | QPDFObjectHandle::pipePageContents(Pipeline* p) |
| 1791 | { | 1794 | { |
| 1792 | - std::string description = "page object " + getObjGenAsStr(); | 1795 | + std::string description = "page object " + getObjGen().unparse(' '); |
| 1793 | std::string all_description; | 1796 | std::string all_description; |
| 1794 | this->getKey("/Contents") | 1797 | this->getKey("/Contents") |
| 1795 | .pipeContentStreams(p, description, all_description); | 1798 | .pipeContentStreams(p, description, all_description); |
| @@ -1813,7 +1816,7 @@ QPDFObjectHandle::pipeContentStreams( | @@ -1813,7 +1816,7 @@ QPDFObjectHandle::pipeContentStreams( | ||
| 1813 | throw QPDFExc( | 1816 | throw QPDFExc( |
| 1814 | qpdf_e_damaged_pdf, | 1817 | qpdf_e_damaged_pdf, |
| 1815 | "content stream", | 1818 | "content stream", |
| 1816 | - "content stream object " + stream.getObjGenAsStr(), | 1819 | + "content stream object " + stream.getObjGen().unparse(' '), |
| 1817 | 0, | 1820 | 0, |
| 1818 | "errors while decoding content stream"); | 1821 | "errors while decoding content stream"); |
| 1819 | } | 1822 | } |
| @@ -1829,7 +1832,7 @@ QPDFObjectHandle::pipeContentStreams( | @@ -1829,7 +1832,7 @@ QPDFObjectHandle::pipeContentStreams( | ||
| 1829 | void | 1832 | void |
| 1830 | QPDFObjectHandle::parsePageContents(ParserCallbacks* callbacks) | 1833 | QPDFObjectHandle::parsePageContents(ParserCallbacks* callbacks) |
| 1831 | { | 1834 | { |
| 1832 | - std::string description = "page object " + getObjGenAsStr(); | 1835 | + std::string description = "page object " + getObjGen().unparse(' '); |
| 1833 | this->getKey("/Contents") | 1836 | this->getKey("/Contents") |
| 1834 | .parseContentStream_internal(description, callbacks); | 1837 | .parseContentStream_internal(description, callbacks); |
| 1835 | } | 1838 | } |
| @@ -1837,14 +1840,15 @@ QPDFObjectHandle::parsePageContents(ParserCallbacks* callbacks) | @@ -1837,14 +1840,15 @@ QPDFObjectHandle::parsePageContents(ParserCallbacks* callbacks) | ||
| 1837 | void | 1840 | void |
| 1838 | QPDFObjectHandle::parseAsContents(ParserCallbacks* callbacks) | 1841 | QPDFObjectHandle::parseAsContents(ParserCallbacks* callbacks) |
| 1839 | { | 1842 | { |
| 1840 | - std::string description = "object " + getObjGenAsStr(); | 1843 | + std::string description = "object " + getObjGen().unparse(' '); |
| 1841 | this->parseContentStream_internal(description, callbacks); | 1844 | this->parseContentStream_internal(description, callbacks); |
| 1842 | } | 1845 | } |
| 1843 | 1846 | ||
| 1844 | void | 1847 | void |
| 1845 | QPDFObjectHandle::filterPageContents(TokenFilter* filter, Pipeline* next) | 1848 | QPDFObjectHandle::filterPageContents(TokenFilter* filter, Pipeline* next) |
| 1846 | { | 1849 | { |
| 1847 | - auto description = "token filter for page object " + getObjGenAsStr(); | 1850 | + auto description = |
| 1851 | + "token filter for page object " + getObjGen().unparse(' '); | ||
| 1848 | Pl_QPDFTokenizer token_pipeline(description.c_str(), filter, next); | 1852 | Pl_QPDFTokenizer token_pipeline(description.c_str(), filter, next); |
| 1849 | this->pipePageContents(&token_pipeline); | 1853 | this->pipePageContents(&token_pipeline); |
| 1850 | } | 1854 | } |
| @@ -1852,7 +1856,7 @@ QPDFObjectHandle::filterPageContents(TokenFilter* filter, Pipeline* next) | @@ -1852,7 +1856,7 @@ QPDFObjectHandle::filterPageContents(TokenFilter* filter, Pipeline* next) | ||
| 1852 | void | 1856 | void |
| 1853 | QPDFObjectHandle::filterAsContents(TokenFilter* filter, Pipeline* next) | 1857 | QPDFObjectHandle::filterAsContents(TokenFilter* filter, Pipeline* next) |
| 1854 | { | 1858 | { |
| 1855 | - auto description = "token filter for object " + getObjGenAsStr(); | 1859 | + auto description = "token filter for object " + getObjGen().unparse(' '); |
| 1856 | Pl_QPDFTokenizer token_pipeline(description.c_str(), filter, next); | 1860 | Pl_QPDFTokenizer token_pipeline(description.c_str(), filter, next); |
| 1857 | this->pipeStreamData(&token_pipeline, 0, qpdf_dl_specialized); | 1861 | this->pipeStreamData(&token_pipeline, 0, qpdf_dl_specialized); |
| 1858 | } | 1862 | } |
| @@ -2192,8 +2196,9 @@ QPDFObjectHandle::parseInternal( | @@ -2192,8 +2196,9 @@ QPDFObjectHandle::parseInternal( | ||
| 2192 | // Try to resolve indirect objects | 2196 | // Try to resolve indirect objects |
| 2193 | object = newIndirect( | 2197 | object = newIndirect( |
| 2194 | context, | 2198 | context, |
| 2195 | - olist.at(olist.size() - 2).getIntValueAsInt(), | ||
| 2196 | - olist.at(olist.size() - 1).getIntValueAsInt()); | 2199 | + QPDFObjGen( |
| 2200 | + olist.at(olist.size() - 2).getIntValueAsInt(), | ||
| 2201 | + olist.at(olist.size() - 1).getIntValueAsInt())); | ||
| 2197 | olist.remove_last(); | 2202 | olist.remove_last(); |
| 2198 | olist.remove_last(); | 2203 | olist.remove_last(); |
| 2199 | } else if ((value == "endobj") && (state == st_top)) { | 2204 | } else if ((value == "endobj") && (state == st_top)) { |
| @@ -2481,9 +2486,9 @@ QPDFObjectHandle::setParsedOffset(qpdf_offset_t offset) | @@ -2481,9 +2486,9 @@ QPDFObjectHandle::setParsedOffset(qpdf_offset_t offset) | ||
| 2481 | } | 2486 | } |
| 2482 | 2487 | ||
| 2483 | QPDFObjectHandle | 2488 | QPDFObjectHandle |
| 2484 | -QPDFObjectHandle::newIndirect(QPDF* qpdf, int objid, int generation) | 2489 | +QPDFObjectHandle::newIndirect(QPDF* qpdf, QPDFObjGen const& og) |
| 2485 | { | 2490 | { |
| 2486 | - if (objid == 0) { | 2491 | + if (!og.isIndirect()) { |
| 2487 | // Special case: QPDF uses objid 0 as a sentinel for direct | 2492 | // Special case: QPDF uses objid 0 as a sentinel for direct |
| 2488 | // objects, and the PDF specification doesn't allow for object | 2493 | // objects, and the PDF specification doesn't allow for object |
| 2489 | // 0. Treat indirect references to object 0 as null so that we | 2494 | // 0. Treat indirect references to object 0 as null so that we |
| @@ -2492,7 +2497,7 @@ QPDFObjectHandle::newIndirect(QPDF* qpdf, int objid, int generation) | @@ -2492,7 +2497,7 @@ QPDFObjectHandle::newIndirect(QPDF* qpdf, int objid, int generation) | ||
| 2492 | return newNull(); | 2497 | return newNull(); |
| 2493 | } | 2498 | } |
| 2494 | 2499 | ||
| 2495 | - return QPDFObjectHandle(qpdf, objid, generation); | 2500 | + return QPDFObjectHandle(qpdf, og); |
| 2496 | } | 2501 | } |
| 2497 | 2502 | ||
| 2498 | QPDFObjectHandle | 2503 | QPDFObjectHandle |
| @@ -2640,14 +2645,13 @@ QPDFObjectHandle::newDictionary( | @@ -2640,14 +2645,13 @@ QPDFObjectHandle::newDictionary( | ||
| 2640 | QPDFObjectHandle | 2645 | QPDFObjectHandle |
| 2641 | QPDFObjectHandle::newStream( | 2646 | QPDFObjectHandle::newStream( |
| 2642 | QPDF* qpdf, | 2647 | QPDF* qpdf, |
| 2643 | - int objid, | ||
| 2644 | - int generation, | 2648 | + QPDFObjGen const& og, |
| 2645 | QPDFObjectHandle stream_dict, | 2649 | QPDFObjectHandle stream_dict, |
| 2646 | qpdf_offset_t offset, | 2650 | qpdf_offset_t offset, |
| 2647 | size_t length) | 2651 | size_t length) |
| 2648 | { | 2652 | { |
| 2649 | - QPDFObjectHandle result = QPDFObjectHandle(QPDF_Stream::create( | ||
| 2650 | - qpdf, objid, generation, stream_dict, offset, length)); | 2653 | + QPDFObjectHandle result = QPDFObjectHandle( |
| 2654 | + QPDF_Stream::create(qpdf, og, stream_dict, offset, length)); | ||
| 2651 | if (offset) { | 2655 | if (offset) { |
| 2652 | result.setParsedOffset(offset); | 2656 | result.setParsedOffset(offset); |
| 2653 | } | 2657 | } |
| @@ -2663,11 +2667,11 @@ QPDFObjectHandle::newStream(QPDF* qpdf) | @@ -2663,11 +2667,11 @@ QPDFObjectHandle::newStream(QPDF* qpdf) | ||
| 2663 | } | 2667 | } |
| 2664 | QTC::TC("qpdf", "QPDFObjectHandle newStream"); | 2668 | QTC::TC("qpdf", "QPDFObjectHandle newStream"); |
| 2665 | QPDFObjectHandle stream_dict = newDictionary(); | 2669 | QPDFObjectHandle stream_dict = newDictionary(); |
| 2666 | - QPDFObjectHandle result = qpdf->makeIndirectObject( | ||
| 2667 | - QPDFObjectHandle(QPDF_Stream::create(qpdf, 0, 0, stream_dict, 0, 0))); | 2670 | + QPDFObjectHandle result = qpdf->makeIndirectObject(QPDFObjectHandle( |
| 2671 | + QPDF_Stream::create(qpdf, QPDFObjGen(), stream_dict, 0, 0))); | ||
| 2668 | result.dereference(); | 2672 | result.dereference(); |
| 2669 | QPDF_Stream* stream = dynamic_cast<QPDF_Stream*>(result.obj.get()); | 2673 | QPDF_Stream* stream = dynamic_cast<QPDF_Stream*>(result.obj.get()); |
| 2670 | - stream->setObjGen(result.getObjectID(), result.getGeneration()); | 2674 | + stream->setObjGen(result.getObjGen()); |
| 2671 | return result; | 2675 | return result; |
| 2672 | } | 2676 | } |
| 2673 | 2677 | ||
| @@ -2695,8 +2699,7 @@ QPDFObjectHandle::newReserved(QPDF* qpdf) | @@ -2695,8 +2699,7 @@ QPDFObjectHandle::newReserved(QPDF* qpdf) | ||
| 2695 | // Reserve a spot for this object by assigning it an object | 2699 | // Reserve a spot for this object by assigning it an object |
| 2696 | // number, but then return an unresolved handle to the object. | 2700 | // number, but then return an unresolved handle to the object. |
| 2697 | QPDFObjectHandle reserved = qpdf->makeIndirectObject(makeReserved()); | 2701 | QPDFObjectHandle reserved = qpdf->makeIndirectObject(makeReserved()); |
| 2698 | - QPDFObjectHandle result = | ||
| 2699 | - newIndirect(qpdf, reserved.objid, reserved.generation); | 2702 | + QPDFObjectHandle result = newIndirect(qpdf, reserved.getObjGen()); |
| 2700 | result.reserved = true; | 2703 | result.reserved = true; |
| 2701 | return result; | 2704 | return result; |
| 2702 | } | 2705 | } |
| @@ -2796,9 +2799,8 @@ QPDFObjectHandle::copyObject( | @@ -2796,9 +2799,8 @@ QPDFObjectHandle::copyObject( | ||
| 2796 | " reserved object handle direct"); | 2799 | " reserved object handle direct"); |
| 2797 | } | 2800 | } |
| 2798 | 2801 | ||
| 2799 | - this->qpdf = 0; | ||
| 2800 | - this->objid = 0; | ||
| 2801 | - this->generation = 0; | 2802 | + qpdf = nullptr; |
| 2803 | + og = QPDFObjGen(); | ||
| 2802 | 2804 | ||
| 2803 | std::shared_ptr<QPDFObject> new_obj; | 2805 | std::shared_ptr<QPDFObject> new_obj; |
| 2804 | 2806 | ||
| @@ -3112,7 +3114,7 @@ QPDFObjectHandle::dereference() | @@ -3112,7 +3114,7 @@ QPDFObjectHandle::dereference() | ||
| 3112 | } | 3114 | } |
| 3113 | if (this->obj.get() == 0) { | 3115 | if (this->obj.get() == 0) { |
| 3114 | std::shared_ptr<QPDFObject> obj = | 3116 | std::shared_ptr<QPDFObject> obj = |
| 3115 | - QPDF::Resolver::resolve(this->qpdf, getObjectID(), getGeneration()); | 3117 | + QPDF::Resolver::resolve(this->qpdf, getObjGen()); |
| 3116 | if (obj.get() == 0) { | 3118 | if (obj.get() == 0) { |
| 3117 | // QPDF::resolve never returns an uninitialized object, but | 3119 | // QPDF::resolve never returns an uninitialized object, but |
| 3118 | // check just in case. | 3120 | // check just in case. |
libqpdf/QPDFPageObjectHelper.cc
| @@ -21,8 +21,7 @@ namespace | @@ -21,8 +21,7 @@ namespace | ||
| 21 | { | 21 | { |
| 22 | } | 22 | } |
| 23 | virtual ~ContentProvider() = default; | 23 | virtual ~ContentProvider() = default; |
| 24 | - virtual void | ||
| 25 | - provideStreamData(int objid, int generation, Pipeline* pipeline); | 24 | + virtual void provideStreamData(QPDFObjGen const&, Pipeline* pipeline); |
| 26 | 25 | ||
| 27 | private: | 26 | private: |
| 28 | QPDFObjectHandle from_page; | 27 | QPDFObjectHandle from_page; |
| @@ -30,12 +29,11 @@ namespace | @@ -30,12 +29,11 @@ namespace | ||
| 30 | } // namespace | 29 | } // namespace |
| 31 | 30 | ||
| 32 | void | 31 | void |
| 33 | -ContentProvider::provideStreamData(int, int, Pipeline* p) | 32 | +ContentProvider::provideStreamData(QPDFObjGen const&, Pipeline* p) |
| 34 | { | 33 | { |
| 35 | Pl_Concatenate concat("concatenate", p); | 34 | Pl_Concatenate concat("concatenate", p); |
| 36 | - std::string description = "contents from page object " + | ||
| 37 | - QUtil::int_to_string(from_page.getObjectID()) + " " + | ||
| 38 | - QUtil::int_to_string(from_page.getGeneration()); | 35 | + std::string description = |
| 36 | + "contents from page object " + from_page.getObjGen().unparse(' '); | ||
| 39 | std::string all_description; | 37 | std::string all_description; |
| 40 | from_page.getKey("/Contents") | 38 | from_page.getKey("/Contents") |
| 41 | .pipeContentStreams(&concat, description, all_description); | 39 | .pipeContentStreams(&concat, description, all_description); |
libqpdf/QPDFWriter.cc
| @@ -1990,9 +1990,8 @@ QPDFWriter::writeObject(QPDFObjectHandle object, int object_stream_index) | @@ -1990,9 +1990,8 @@ QPDFWriter::writeObject(QPDFObjectHandle object, int object_stream_index) | ||
| 1990 | if (object_stream_index == -1) { | 1990 | if (object_stream_index == -1) { |
| 1991 | if (this->m->qdf_mode && (!this->m->suppress_original_object_ids)) { | 1991 | if (this->m->qdf_mode && (!this->m->suppress_original_object_ids)) { |
| 1992 | writeString( | 1992 | writeString( |
| 1993 | - "%% Original object ID: " + | ||
| 1994 | - QUtil::int_to_string(object.getObjectID()) + " " + | ||
| 1995 | - QUtil::int_to_string(object.getGeneration()) + "\n"); | 1993 | + "%% Original object ID: " + object.getObjGen().unparse(' ') + |
| 1994 | + "\n"); | ||
| 1996 | } | 1995 | } |
| 1997 | openObject(new_id); | 1996 | openObject(new_id); |
| 1998 | setDataKey(new_id); | 1997 | setDataKey(new_id); |
libqpdf/QPDF_Stream.cc
| @@ -110,14 +110,12 @@ StreamBlobProvider::operator()(Pipeline* p) | @@ -110,14 +110,12 @@ StreamBlobProvider::operator()(Pipeline* p) | ||
| 110 | 110 | ||
| 111 | QPDF_Stream::QPDF_Stream( | 111 | QPDF_Stream::QPDF_Stream( |
| 112 | QPDF* qpdf, | 112 | QPDF* qpdf, |
| 113 | - int objid, | ||
| 114 | - int generation, | 113 | + QPDFObjGen const& og, |
| 115 | QPDFObjectHandle stream_dict, | 114 | QPDFObjectHandle stream_dict, |
| 116 | qpdf_offset_t offset, | 115 | qpdf_offset_t offset, |
| 117 | size_t length) : | 116 | size_t length) : |
| 118 | qpdf(qpdf), | 117 | qpdf(qpdf), |
| 119 | - objid(objid), | ||
| 120 | - generation(generation), | 118 | + og(og), |
| 121 | filter_on_write(true), | 119 | filter_on_write(true), |
| 122 | stream_dict(stream_dict), | 120 | stream_dict(stream_dict), |
| 123 | offset(offset), | 121 | offset(offset), |
| @@ -128,23 +126,18 @@ QPDF_Stream::QPDF_Stream( | @@ -128,23 +126,18 @@ QPDF_Stream::QPDF_Stream( | ||
| 128 | "object for dictionary"); | 126 | "object for dictionary"); |
| 129 | } | 127 | } |
| 130 | setDescription( | 128 | setDescription( |
| 131 | - this->qpdf, | ||
| 132 | - this->qpdf->getFilename() + ", stream object " + | ||
| 133 | - QUtil::int_to_string(this->objid) + " " + | ||
| 134 | - QUtil::int_to_string(this->generation)); | 129 | + qpdf, qpdf->getFilename() + ", stream object " + og.unparse(' ')); |
| 135 | } | 130 | } |
| 136 | 131 | ||
| 137 | std::shared_ptr<QPDFObject> | 132 | std::shared_ptr<QPDFObject> |
| 138 | QPDF_Stream::create( | 133 | QPDF_Stream::create( |
| 139 | QPDF* qpdf, | 134 | QPDF* qpdf, |
| 140 | - int objid, | ||
| 141 | - int generation, | 135 | + QPDFObjGen const& og, |
| 142 | QPDFObjectHandle stream_dict, | 136 | QPDFObjectHandle stream_dict, |
| 143 | qpdf_offset_t offset, | 137 | qpdf_offset_t offset, |
| 144 | size_t length) | 138 | size_t length) |
| 145 | { | 139 | { |
| 146 | - return do_create( | ||
| 147 | - new QPDF_Stream(qpdf, objid, generation, stream_dict, offset, length)); | 140 | + return do_create(new QPDF_Stream(qpdf, og, stream_dict, offset, length)); |
| 148 | } | 141 | } |
| 149 | 142 | ||
| 150 | std::shared_ptr<QPDFObject> | 143 | std::shared_ptr<QPDFObject> |
| @@ -181,23 +174,21 @@ QPDF_Stream::releaseResolved() | @@ -181,23 +174,21 @@ QPDF_Stream::releaseResolved() | ||
| 181 | } | 174 | } |
| 182 | 175 | ||
| 183 | void | 176 | void |
| 184 | -QPDF_Stream::setObjGen(int objid, int generation) | 177 | +QPDF_Stream::setObjGen(QPDFObjGen const& og) |
| 185 | { | 178 | { |
| 186 | - if (!((this->objid == 0) && (this->generation == 0))) { | 179 | + if (this->og.isIndirect()) { |
| 187 | throw std::logic_error( | 180 | throw std::logic_error( |
| 188 | "attempt to set object ID and generation of a stream" | 181 | "attempt to set object ID and generation of a stream" |
| 189 | " that already has them"); | 182 | " that already has them"); |
| 190 | } | 183 | } |
| 191 | - this->objid = objid; | ||
| 192 | - this->generation = generation; | 184 | + this->og = og; |
| 193 | } | 185 | } |
| 194 | 186 | ||
| 195 | std::string | 187 | std::string |
| 196 | QPDF_Stream::unparse() | 188 | QPDF_Stream::unparse() |
| 197 | { | 189 | { |
| 198 | // Unparse stream objects as indirect references | 190 | // Unparse stream objects as indirect references |
| 199 | - return QUtil::int_to_string(this->objid) + " " + | ||
| 200 | - QUtil::int_to_string(this->generation) + " R"; | 191 | + return og.unparse(' ') + " R"; |
| 201 | } | 192 | } |
| 202 | 193 | ||
| 203 | JSON | 194 | JSON |
| @@ -619,17 +610,12 @@ QPDF_Stream::pipeStreamData( | @@ -619,17 +610,12 @@ QPDF_Stream::pipeStreamData( | ||
| 619 | Pl_Count count("stream provider count", pipeline); | 610 | Pl_Count count("stream provider count", pipeline); |
| 620 | if (this->stream_provider->supportsRetry()) { | 611 | if (this->stream_provider->supportsRetry()) { |
| 621 | if (!this->stream_provider->provideStreamData( | 612 | if (!this->stream_provider->provideStreamData( |
| 622 | - this->objid, | ||
| 623 | - this->generation, | ||
| 624 | - &count, | ||
| 625 | - suppress_warnings, | ||
| 626 | - will_retry)) { | 613 | + og, &count, suppress_warnings, will_retry)) { |
| 627 | filter = false; | 614 | filter = false; |
| 628 | success = false; | 615 | success = false; |
| 629 | } | 616 | } |
| 630 | } else { | 617 | } else { |
| 631 | - this->stream_provider->provideStreamData( | ||
| 632 | - this->objid, this->generation, &count); | 618 | + this->stream_provider->provideStreamData(og, &count); |
| 633 | } | 619 | } |
| 634 | qpdf_offset_t actual_length = count.getCount(); | 620 | qpdf_offset_t actual_length = count.getCount(); |
| 635 | qpdf_offset_t desired_length = 0; | 621 | qpdf_offset_t desired_length = 0; |
| @@ -642,10 +628,8 @@ QPDF_Stream::pipeStreamData( | @@ -642,10 +628,8 @@ QPDF_Stream::pipeStreamData( | ||
| 642 | // This would be caused by programmer error on the | 628 | // This would be caused by programmer error on the |
| 643 | // part of a library user, not by invalid input data. | 629 | // part of a library user, not by invalid input data. |
| 644 | throw std::runtime_error( | 630 | throw std::runtime_error( |
| 645 | - "stream data provider for " + | ||
| 646 | - QUtil::int_to_string(this->objid) + " " + | ||
| 647 | - QUtil::int_to_string(this->generation) + " provided " + | ||
| 648 | - QUtil::int_to_string(actual_length) + | 631 | + "stream data provider for " + og.unparse(' ') + |
| 632 | + " provided " + QUtil::int_to_string(actual_length) + | ||
| 649 | " bytes instead of expected " + | 633 | " bytes instead of expected " + |
| 650 | QUtil::int_to_string(desired_length) + " bytes"); | 634 | QUtil::int_to_string(desired_length) + " bytes"); |
| 651 | } | 635 | } |
| @@ -661,8 +645,7 @@ QPDF_Stream::pipeStreamData( | @@ -661,8 +645,7 @@ QPDF_Stream::pipeStreamData( | ||
| 661 | QTC::TC("qpdf", "QPDF_Stream pipe original stream data"); | 645 | QTC::TC("qpdf", "QPDF_Stream pipe original stream data"); |
| 662 | if (!QPDF::Pipe::pipeStreamData( | 646 | if (!QPDF::Pipe::pipeStreamData( |
| 663 | this->qpdf, | 647 | this->qpdf, |
| 664 | - this->objid, | ||
| 665 | - this->generation, | 648 | + og, |
| 666 | this->offset, | 649 | this->offset, |
| 667 | this->length, | 650 | this->length, |
| 668 | this->stream_dict, | 651 | this->stream_dict, |
libqpdf/QPDF_encryption.cc
| @@ -1075,8 +1075,7 @@ QPDF::initializeEncryption() | @@ -1075,8 +1075,7 @@ QPDF::initializeEncryption() | ||
| 1075 | std::string | 1075 | std::string |
| 1076 | QPDF::getKeyForObject( | 1076 | QPDF::getKeyForObject( |
| 1077 | std::shared_ptr<EncryptionParameters> encp, | 1077 | std::shared_ptr<EncryptionParameters> encp, |
| 1078 | - int objid, | ||
| 1079 | - int generation, | 1078 | + QPDFObjGen const& og, |
| 1080 | bool use_aes) | 1079 | bool use_aes) |
| 1081 | { | 1080 | { |
| 1082 | if (!encp->encrypted) { | 1081 | if (!encp->encrypted) { |
| @@ -1084,26 +1083,24 @@ QPDF::getKeyForObject( | @@ -1084,26 +1083,24 @@ QPDF::getKeyForObject( | ||
| 1084 | "request for encryption key in non-encrypted PDF"); | 1083 | "request for encryption key in non-encrypted PDF"); |
| 1085 | } | 1084 | } |
| 1086 | 1085 | ||
| 1087 | - if (!((objid == encp->cached_key_objid) && | ||
| 1088 | - (generation == encp->cached_key_generation))) { | 1086 | + if (og != encp->cached_key_og) { |
| 1089 | encp->cached_object_encryption_key = compute_data_key( | 1087 | encp->cached_object_encryption_key = compute_data_key( |
| 1090 | encp->encryption_key, | 1088 | encp->encryption_key, |
| 1091 | - objid, | ||
| 1092 | - generation, | 1089 | + og.getObj(), |
| 1090 | + og.getGen(), | ||
| 1093 | use_aes, | 1091 | use_aes, |
| 1094 | encp->encryption_V, | 1092 | encp->encryption_V, |
| 1095 | encp->encryption_R); | 1093 | encp->encryption_R); |
| 1096 | - encp->cached_key_objid = objid; | ||
| 1097 | - encp->cached_key_generation = generation; | 1094 | + encp->cached_key_og = og; |
| 1098 | } | 1095 | } |
| 1099 | 1096 | ||
| 1100 | return encp->cached_object_encryption_key; | 1097 | return encp->cached_object_encryption_key; |
| 1101 | } | 1098 | } |
| 1102 | 1099 | ||
| 1103 | void | 1100 | void |
| 1104 | -QPDF::decryptString(std::string& str, int objid, int generation) | 1101 | +QPDF::decryptString(std::string& str, QPDFObjGen const& og) |
| 1105 | { | 1102 | { |
| 1106 | - if (objid == 0) { | 1103 | + if (!og.isIndirect()) { |
| 1107 | return; | 1104 | return; |
| 1108 | } | 1105 | } |
| 1109 | bool use_aes = false; | 1106 | bool use_aes = false; |
| @@ -1139,8 +1136,7 @@ QPDF::decryptString(std::string& str, int objid, int generation) | @@ -1139,8 +1136,7 @@ QPDF::decryptString(std::string& str, int objid, int generation) | ||
| 1139 | } | 1136 | } |
| 1140 | } | 1137 | } |
| 1141 | 1138 | ||
| 1142 | - std::string key = | ||
| 1143 | - getKeyForObject(this->m->encp, objid, generation, use_aes); | 1139 | + std::string key = getKeyForObject(this->m->encp, og, use_aes); |
| 1144 | try { | 1140 | try { |
| 1145 | if (use_aes) { | 1141 | if (use_aes) { |
| 1146 | QTC::TC("qpdf", "QPDF_encryption aes decode string"); | 1142 | QTC::TC("qpdf", "QPDF_encryption aes decode string"); |
| @@ -1175,9 +1171,8 @@ QPDF::decryptString(std::string& str, int objid, int generation) | @@ -1175,9 +1171,8 @@ QPDF::decryptString(std::string& str, int objid, int generation) | ||
| 1175 | this->m->file->getName(), | 1171 | this->m->file->getName(), |
| 1176 | this->m->last_object_description, | 1172 | this->m->last_object_description, |
| 1177 | this->m->file->getLastOffset(), | 1173 | this->m->file->getLastOffset(), |
| 1178 | - "error decrypting string for object " + | ||
| 1179 | - QUtil::int_to_string(objid) + " " + | ||
| 1180 | - QUtil::int_to_string(generation) + ": " + e.what()); | 1174 | + "error decrypting string for object " + og.unparse() + ": " + |
| 1175 | + e.what()); | ||
| 1181 | } | 1176 | } |
| 1182 | } | 1177 | } |
| 1183 | 1178 | ||
| @@ -1187,8 +1182,7 @@ QPDF::decryptStream( | @@ -1187,8 +1182,7 @@ QPDF::decryptStream( | ||
| 1187 | std::shared_ptr<InputSource> file, | 1182 | std::shared_ptr<InputSource> file, |
| 1188 | QPDF& qpdf_for_warning, | 1183 | QPDF& qpdf_for_warning, |
| 1189 | Pipeline*& pipeline, | 1184 | Pipeline*& pipeline, |
| 1190 | - int objid, | ||
| 1191 | - int generation, | 1185 | + QPDFObjGen const& og, |
| 1192 | QPDFObjectHandle& stream_dict, | 1186 | QPDFObjectHandle& stream_dict, |
| 1193 | std::vector<std::shared_ptr<Pipeline>>& heap) | 1187 | std::vector<std::shared_ptr<Pipeline>>& heap) |
| 1194 | { | 1188 | { |
| @@ -1283,7 +1277,7 @@ QPDF::decryptStream( | @@ -1283,7 +1277,7 @@ QPDF::decryptStream( | ||
| 1283 | break; | 1277 | break; |
| 1284 | } | 1278 | } |
| 1285 | } | 1279 | } |
| 1286 | - std::string key = getKeyForObject(encp, objid, generation, use_aes); | 1280 | + std::string key = getKeyForObject(encp, og, use_aes); |
| 1287 | std::shared_ptr<Pipeline> new_pipeline; | 1281 | std::shared_ptr<Pipeline> new_pipeline; |
| 1288 | if (use_aes) { | 1282 | if (use_aes) { |
| 1289 | QTC::TC("qpdf", "QPDF_encryption aes decode stream"); | 1283 | QTC::TC("qpdf", "QPDF_encryption aes decode stream"); |
libqpdf/QPDF_json.cc
| @@ -371,9 +371,10 @@ QPDF::JSONReactor::containerEnd(JSON const& value) | @@ -371,9 +371,10 @@ QPDF::JSONReactor::containerEnd(JSON const& value) | ||
| 371 | QPDFObjectHandle | 371 | QPDFObjectHandle |
| 372 | QPDF::JSONReactor::reserveObject(int obj, int gen) | 372 | QPDF::JSONReactor::reserveObject(int obj, int gen) |
| 373 | { | 373 | { |
| 374 | - auto oh = pdf.reserveObjectIfNotExists(obj, gen); | 374 | + QPDFObjGen og(obj, gen); |
| 375 | + auto oh = pdf.reserveObjectIfNotExists(og); | ||
| 375 | if (oh.isReserved()) { | 376 | if (oh.isReserved()) { |
| 376 | - this->reserved.insert(QPDFObjGen(obj, gen)); | 377 | + this->reserved.insert(og); |
| 377 | } | 378 | } |
| 378 | return oh; | 379 | return oh; |
| 379 | } | 380 | } |
| @@ -495,8 +496,7 @@ QPDF::JSONReactor::dictionaryItem(std::string const& key, JSON const& value) | @@ -495,8 +496,7 @@ QPDF::JSONReactor::dictionaryItem(std::string const& key, JSON const& value) | ||
| 495 | QTC::TC("qpdf", "QPDF_json updating existing stream"); | 496 | QTC::TC("qpdf", "QPDF_json updating existing stream"); |
| 496 | } else { | 497 | } else { |
| 497 | this->this_stream_needs_data = true; | 498 | this->this_stream_needs_data = true; |
| 498 | - replacement = | ||
| 499 | - pdf.reserveStream(tos.getObjectID(), tos.getGeneration()); | 499 | + replacement = pdf.reserveStream(tos.getObjGen()); |
| 500 | replaceObject(tos, replacement, value); | 500 | replaceObject(tos, replacement, value); |
| 501 | } | 501 | } |
| 502 | } else { | 502 | } else { |
libqpdf/QPDF_linearization.cc
| @@ -137,8 +137,8 @@ QPDF::isLinearized() | @@ -137,8 +137,8 @@ QPDF::isLinearized() | ||
| 137 | return false; | 137 | return false; |
| 138 | } | 138 | } |
| 139 | 139 | ||
| 140 | - QPDFObjectHandle candidate = | ||
| 141 | - QPDFObjectHandle::Factory::newIndirect(this, lindict_obj, 0); | 140 | + QPDFObjectHandle candidate = QPDFObjectHandle::Factory::newIndirect( |
| 141 | + this, QPDFObjGen(lindict_obj, 0)); | ||
| 142 | if (!candidate.isDictionary()) { | 142 | if (!candidate.isDictionary()) { |
| 143 | return false; | 143 | return false; |
| 144 | } | 144 | } |
| @@ -325,11 +325,10 @@ QPDF::readLinearizationData() | @@ -325,11 +325,10 @@ QPDF::readLinearizationData() | ||
| 325 | QPDFObjectHandle | 325 | QPDFObjectHandle |
| 326 | QPDF::readHintStream(Pipeline& pl, qpdf_offset_t offset, size_t length) | 326 | QPDF::readHintStream(Pipeline& pl, qpdf_offset_t offset, size_t length) |
| 327 | { | 327 | { |
| 328 | - int obj; | ||
| 329 | - int gen; | 328 | + QPDFObjGen og; |
| 330 | QPDFObjectHandle H = readObjectAtOffset( | 329 | QPDFObjectHandle H = readObjectAtOffset( |
| 331 | - false, offset, "linearization hint stream", 0, 0, obj, gen); | ||
| 332 | - ObjCache& oc = this->m->obj_cache[QPDFObjGen(obj, gen)]; | 330 | + false, offset, "linearization hint stream", QPDFObjGen(0, 0), og); |
| 331 | + ObjCache& oc = this->m->obj_cache[og]; | ||
| 333 | qpdf_offset_t min_end_offset = oc.end_before_space; | 332 | qpdf_offset_t min_end_offset = oc.end_before_space; |
| 334 | qpdf_offset_t max_end_offset = oc.end_after_space; | 333 | qpdf_offset_t max_end_offset = oc.end_after_space; |
| 335 | if (!H.isStream()) { | 334 | if (!H.isStream()) { |
| @@ -707,7 +706,7 @@ QPDF::getUncompressedObject( | @@ -707,7 +706,7 @@ QPDF::getUncompressedObject( | ||
| 707 | return obj; | 706 | return obj; |
| 708 | } else { | 707 | } else { |
| 709 | int repl = (*(object_stream_data.find(obj.getObjectID()))).second; | 708 | int repl = (*(object_stream_data.find(obj.getObjectID()))).second; |
| 710 | - return objGenToIndirect(QPDFObjGen(repl, 0)); | 709 | + return getObjectByObjGen(QPDFObjGen(repl, 0)); |
| 711 | } | 710 | } |
| 712 | } | 711 | } |
| 713 | 712 | ||
| @@ -1144,12 +1143,6 @@ QPDF::dumpHGeneric(HGeneric& t) | @@ -1144,12 +1143,6 @@ QPDF::dumpHGeneric(HGeneric& t) | ||
| 1144 | << "group_length: " << t.group_length << "\n"; | 1143 | << "group_length: " << t.group_length << "\n"; |
| 1145 | } | 1144 | } |
| 1146 | 1145 | ||
| 1147 | -QPDFObjectHandle | ||
| 1148 | -QPDF::objGenToIndirect(QPDFObjGen const& og) | ||
| 1149 | -{ | ||
| 1150 | - return getObjectByID(og.getObj(), og.getGen()); | ||
| 1151 | -} | ||
| 1152 | - | ||
| 1153 | void | 1146 | void |
| 1154 | QPDF::calculateLinearizationData(std::map<int, int> const& object_stream_data) | 1147 | QPDF::calculateLinearizationData(std::map<int, int> const& object_stream_data) |
| 1155 | { | 1148 | { |
| @@ -1388,9 +1381,9 @@ QPDF::calculateLinearizationData(std::map<int, int> const& object_stream_data) | @@ -1388,9 +1381,9 @@ QPDF::calculateLinearizationData(std::map<int, int> const& object_stream_data) | ||
| 1388 | stopOnError("found other than one root while" | 1381 | stopOnError("found other than one root while" |
| 1389 | " calculating linearization data"); | 1382 | " calculating linearization data"); |
| 1390 | } | 1383 | } |
| 1391 | - this->m->part4.push_back(objGenToIndirect(*(lc_root.begin()))); | 1384 | + this->m->part4.push_back(getObjectByObjGen(*(lc_root.begin()))); |
| 1392 | for (auto const& og: lc_open_document) { | 1385 | for (auto const& og: lc_open_document) { |
| 1393 | - this->m->part4.push_back(objGenToIndirect(og)); | 1386 | + this->m->part4.push_back(getObjectByObjGen(og)); |
| 1394 | } | 1387 | } |
| 1395 | 1388 | ||
| 1396 | // Part 6: first page objects. Note: implementation note 124 | 1389 | // Part 6: first page objects. Note: implementation note 124 |
| @@ -1419,11 +1412,11 @@ QPDF::calculateLinearizationData(std::map<int, int> const& object_stream_data) | @@ -1419,11 +1412,11 @@ QPDF::calculateLinearizationData(std::map<int, int> const& object_stream_data) | ||
| 1419 | // hint tables. | 1412 | // hint tables. |
| 1420 | 1413 | ||
| 1421 | for (auto const& og: lc_first_page_private) { | 1414 | for (auto const& og: lc_first_page_private) { |
| 1422 | - this->m->part6.push_back(objGenToIndirect(og)); | 1415 | + this->m->part6.push_back(getObjectByObjGen(og)); |
| 1423 | } | 1416 | } |
| 1424 | 1417 | ||
| 1425 | for (auto const& og: lc_first_page_shared) { | 1418 | for (auto const& og: lc_first_page_shared) { |
| 1426 | - this->m->part6.push_back(objGenToIndirect(og)); | 1419 | + this->m->part6.push_back(getObjectByObjGen(og)); |
| 1427 | } | 1420 | } |
| 1428 | 1421 | ||
| 1429 | // Place the outline dictionary if it goes in the first page section. | 1422 | // Place the outline dictionary if it goes in the first page section. |
| @@ -1469,7 +1462,7 @@ QPDF::calculateLinearizationData(std::map<int, int> const& object_stream_data) | @@ -1469,7 +1462,7 @@ QPDF::calculateLinearizationData(std::map<int, int> const& object_stream_data) | ||
| 1469 | for (auto const& og: this->m->obj_user_to_objects[ou]) { | 1462 | for (auto const& og: this->m->obj_user_to_objects[ou]) { |
| 1470 | if (lc_other_page_private.count(og)) { | 1463 | if (lc_other_page_private.count(og)) { |
| 1471 | lc_other_page_private.erase(og); | 1464 | lc_other_page_private.erase(og); |
| 1472 | - this->m->part7.push_back(objGenToIndirect(og)); | 1465 | + this->m->part7.push_back(getObjectByObjGen(og)); |
| 1473 | ++this->m->c_page_offset_data.entries.at(i).nobjects; | 1466 | ++this->m->c_page_offset_data.entries.at(i).nobjects; |
| 1474 | } | 1467 | } |
| 1475 | } | 1468 | } |
| @@ -1486,7 +1479,7 @@ QPDF::calculateLinearizationData(std::map<int, int> const& object_stream_data) | @@ -1486,7 +1479,7 @@ QPDF::calculateLinearizationData(std::map<int, int> const& object_stream_data) | ||
| 1486 | 1479 | ||
| 1487 | // Order is unimportant. | 1480 | // Order is unimportant. |
| 1488 | for (auto const& og: lc_other_page_shared) { | 1481 | for (auto const& og: lc_other_page_shared) { |
| 1489 | - this->m->part8.push_back(objGenToIndirect(og)); | 1482 | + this->m->part8.push_back(getObjectByObjGen(og)); |
| 1490 | } | 1483 | } |
| 1491 | 1484 | ||
| 1492 | // Part 9: other objects | 1485 | // Part 9: other objects |
| @@ -1508,7 +1501,7 @@ QPDF::calculateLinearizationData(std::map<int, int> const& object_stream_data) | @@ -1508,7 +1501,7 @@ QPDF::calculateLinearizationData(std::map<int, int> const& object_stream_data) | ||
| 1508 | for (auto const& og: pages_ogs) { | 1501 | for (auto const& og: pages_ogs) { |
| 1509 | if (lc_other.count(og)) { | 1502 | if (lc_other.count(og)) { |
| 1510 | lc_other.erase(og); | 1503 | lc_other.erase(og); |
| 1511 | - this->m->part9.push_back(objGenToIndirect(og)); | 1504 | + this->m->part9.push_back(getObjectByObjGen(og)); |
| 1512 | } | 1505 | } |
| 1513 | } | 1506 | } |
| 1514 | 1507 | ||
| @@ -1538,7 +1531,7 @@ QPDF::calculateLinearizationData(std::map<int, int> const& object_stream_data) | @@ -1538,7 +1531,7 @@ QPDF::calculateLinearizationData(std::map<int, int> const& object_stream_data) | ||
| 1538 | for (auto const& og: ogs) { | 1531 | for (auto const& og: ogs) { |
| 1539 | if (lc_thumbnail_private.count(og)) { | 1532 | if (lc_thumbnail_private.count(og)) { |
| 1540 | lc_thumbnail_private.erase(og); | 1533 | lc_thumbnail_private.erase(og); |
| 1541 | - this->m->part9.push_back(objGenToIndirect(og)); | 1534 | + this->m->part9.push_back(getObjectByObjGen(og)); |
| 1542 | } | 1535 | } |
| 1543 | } | 1536 | } |
| 1544 | } | 1537 | } |
| @@ -1551,7 +1544,7 @@ QPDF::calculateLinearizationData(std::map<int, int> const& object_stream_data) | @@ -1551,7 +1544,7 @@ QPDF::calculateLinearizationData(std::map<int, int> const& object_stream_data) | ||
| 1551 | 1544 | ||
| 1552 | // Place shared thumbnail objects | 1545 | // Place shared thumbnail objects |
| 1553 | for (auto const& og: lc_thumbnail_shared) { | 1546 | for (auto const& og: lc_thumbnail_shared) { |
| 1554 | - this->m->part9.push_back(objGenToIndirect(og)); | 1547 | + this->m->part9.push_back(getObjectByObjGen(og)); |
| 1555 | } | 1548 | } |
| 1556 | 1549 | ||
| 1557 | // Place outlines unless in first page | 1550 | // Place outlines unless in first page |
| @@ -1561,7 +1554,7 @@ QPDF::calculateLinearizationData(std::map<int, int> const& object_stream_data) | @@ -1561,7 +1554,7 @@ QPDF::calculateLinearizationData(std::map<int, int> const& object_stream_data) | ||
| 1561 | 1554 | ||
| 1562 | // Place all remaining objects | 1555 | // Place all remaining objects |
| 1563 | for (auto const& og: lc_other) { | 1556 | for (auto const& og: lc_other) { |
| 1564 | - this->m->part9.push_back(objGenToIndirect(og)); | 1557 | + this->m->part9.push_back(getObjectByObjGen(og)); |
| 1565 | } | 1558 | } |
| 1566 | 1559 | ||
| 1567 | // Make sure we got everything exactly once. | 1560 | // Make sure we got everything exactly once. |
| @@ -1663,7 +1656,7 @@ QPDF::pushOutlinesToPart( | @@ -1663,7 +1656,7 @@ QPDF::pushOutlinesToPart( | ||
| 1663 | lc_outlines.erase(outlines_og); | 1656 | lc_outlines.erase(outlines_og); |
| 1664 | part.push_back(outlines); | 1657 | part.push_back(outlines); |
| 1665 | for (auto const& og: lc_outlines) { | 1658 | for (auto const& og: lc_outlines) { |
| 1666 | - part.push_back(objGenToIndirect(og)); | 1659 | + part.push_back(getObjectByObjGen(og)); |
| 1667 | ++this->m->c_outline_data.nobjects; | 1660 | ++this->m->c_outline_data.nobjects; |
| 1668 | } | 1661 | } |
| 1669 | } | 1662 | } |
libqpdf/QPDF_optimization.cc
| @@ -252,9 +252,7 @@ QPDF::pushInheritedAttributesToPageInternal( | @@ -252,9 +252,7 @@ QPDF::pushInheritedAttributesToPageInternal( | ||
| 252 | if ((warn_skipped_keys) && (cur_pages.hasKey("/Parent"))) { | 252 | if ((warn_skipped_keys) && (cur_pages.hasKey("/Parent"))) { |
| 253 | QTC::TC("qpdf", "QPDF unknown key not inherited"); | 253 | QTC::TC("qpdf", "QPDF unknown key not inherited"); |
| 254 | setLastObjectDescription( | 254 | setLastObjectDescription( |
| 255 | - "Pages object", | ||
| 256 | - cur_pages.getObjectID(), | ||
| 257 | - cur_pages.getGeneration()); | 255 | + "Pages object", cur_pages.getObjGen()); |
| 258 | warn( | 256 | warn( |
| 259 | qpdf_e_pages, | 257 | qpdf_e_pages, |
| 260 | this->m->last_object_description, | 258 | this->m->last_object_description, |
libqpdf/QPDF_pages.cc
| @@ -207,8 +207,7 @@ QPDF::insertPageobjToPage( | @@ -207,8 +207,7 @@ QPDF::insertPageobjToPage( | ||
| 207 | // that causes this to happen. | 207 | // that causes this to happen. |
| 208 | setLastObjectDescription( | 208 | setLastObjectDescription( |
| 209 | "page " + QUtil::int_to_string(pos) + " (numbered from zero)", | 209 | "page " + QUtil::int_to_string(pos) + " (numbered from zero)", |
| 210 | - og.getObj(), | ||
| 211 | - og.getGen()); | 210 | + og); |
| 212 | throw QPDFExc( | 211 | throw QPDFExc( |
| 213 | qpdf_e_pages, | 212 | qpdf_e_pages, |
| 214 | this->m->file->getName(), | 213 | this->m->file->getName(), |
| @@ -334,7 +333,7 @@ QPDF::findPage(QPDFObjGen const& og) | @@ -334,7 +333,7 @@ QPDF::findPage(QPDFObjGen const& og) | ||
| 334 | auto it = this->m->pageobj_to_pages_pos.find(og); | 333 | auto it = this->m->pageobj_to_pages_pos.find(og); |
| 335 | if (it == this->m->pageobj_to_pages_pos.end()) { | 334 | if (it == this->m->pageobj_to_pages_pos.end()) { |
| 336 | QTC::TC("qpdf", "QPDF_pages findPage not found"); | 335 | QTC::TC("qpdf", "QPDF_pages findPage not found"); |
| 337 | - setLastObjectDescription("page object", og.getObj(), og.getGen()); | 336 | + setLastObjectDescription("page object", og); |
| 338 | throw QPDFExc( | 337 | throw QPDFExc( |
| 339 | qpdf_e_pages, | 338 | qpdf_e_pages, |
| 340 | this->m->file->getName(), | 339 | this->m->file->getName(), |
libqpdf/qpdf/QPDF_Stream.hh
| @@ -19,8 +19,7 @@ class QPDF_Stream: public QPDFObject | @@ -19,8 +19,7 @@ class QPDF_Stream: public QPDFObject | ||
| 19 | virtual ~QPDF_Stream() = default; | 19 | virtual ~QPDF_Stream() = default; |
| 20 | static std::shared_ptr<QPDFObject> create( | 20 | static std::shared_ptr<QPDFObject> create( |
| 21 | QPDF*, | 21 | QPDF*, |
| 22 | - int objid, | ||
| 23 | - int generation, | 22 | + QPDFObjGen const& og, |
| 24 | QPDFObjectHandle stream_dict, | 23 | QPDFObjectHandle stream_dict, |
| 25 | qpdf_offset_t offset, | 24 | qpdf_offset_t offset, |
| 26 | size_t length); | 25 | size_t length); |
| @@ -78,7 +77,7 @@ class QPDF_Stream: public QPDFObject | @@ -78,7 +77,7 @@ class QPDF_Stream: public QPDFObject | ||
| 78 | // Replace object ID and generation. This may only be called if | 77 | // Replace object ID and generation. This may only be called if |
| 79 | // object ID and generation are 0. It is used by QPDFObjectHandle | 78 | // object ID and generation are 0. It is used by QPDFObjectHandle |
| 80 | // when adding streams to files. | 79 | // when adding streams to files. |
| 81 | - void setObjGen(int objid, int generation); | 80 | + void setObjGen(QPDFObjGen const& og); |
| 82 | 81 | ||
| 83 | protected: | 82 | protected: |
| 84 | virtual void releaseResolved(); | 83 | virtual void releaseResolved(); |
| @@ -86,8 +85,7 @@ class QPDF_Stream: public QPDFObject | @@ -86,8 +85,7 @@ class QPDF_Stream: public QPDFObject | ||
| 86 | private: | 85 | private: |
| 87 | QPDF_Stream( | 86 | QPDF_Stream( |
| 88 | QPDF*, | 87 | QPDF*, |
| 89 | - int objid, | ||
| 90 | - int generation, | 88 | + QPDFObjGen const& og, |
| 91 | QPDFObjectHandle stream_dict, | 89 | QPDFObjectHandle stream_dict, |
| 92 | qpdf_offset_t offset, | 90 | qpdf_offset_t offset, |
| 93 | size_t length); | 91 | size_t length); |
| @@ -111,8 +109,7 @@ class QPDF_Stream: public QPDFObject | @@ -111,8 +109,7 @@ class QPDF_Stream: public QPDFObject | ||
| 111 | void setDictDescription(); | 109 | void setDictDescription(); |
| 112 | 110 | ||
| 113 | QPDF* qpdf; | 111 | QPDF* qpdf; |
| 114 | - int objid; | ||
| 115 | - int generation; | 112 | + QPDFObjGen og; |
| 116 | bool filter_on_write; | 113 | bool filter_on_write; |
| 117 | QPDFObjectHandle stream_dict; | 114 | QPDFObjectHandle stream_dict; |
| 118 | qpdf_offset_t offset; | 115 | qpdf_offset_t offset; |
qpdf/test_driver.cc
| @@ -56,6 +56,8 @@ class Provider: public QPDFObjectHandle::StreamDataProvider | @@ -56,6 +56,8 @@ class Provider: public QPDFObjectHandle::StreamDataProvider | ||
| 56 | virtual void | 56 | virtual void |
| 57 | provideStreamData(int objid, int generation, Pipeline* p) | 57 | provideStreamData(int objid, int generation, Pipeline* p) |
| 58 | { | 58 | { |
| 59 | + // Don't change signature to use QPDFObjGen const& to detect | ||
| 60 | + // problems forwarding to legacy implementations. | ||
| 59 | p->write(b->getBuffer(), b->getSize()); | 61 | p->write(b->getBuffer(), b->getSize()); |
| 60 | if (this->bad_length) { | 62 | if (this->bad_length) { |
| 61 | unsigned char ch = ' '; | 63 | unsigned char ch = ' '; |