From f0a8178091dfc87bbf9a6751f8fedf007e8eb144 Mon Sep 17 00:00:00 2001 From: m-holger Date: Thu, 16 Jun 2022 17:45:04 +0100 Subject: Refactor QPDFObject creation and cloning Move responsibility for creating shared pointers to objects and cloning from QPDFObjectHandle to QPDFObject. --- include/qpdf/QPDFObject.hh | 2 + include/qpdf/QPDFObjectHandle.hh | 2 +- libqpdf/QPDF.cc | 2 +- libqpdf/QPDFObject.cc | 7 ++++ libqpdf/QPDFObjectHandle.cc | 83 +++++++++++++++------------------------- libqpdf/QPDF_Array.cc | 24 +++++++++--- libqpdf/QPDF_Bool.cc | 12 ++++++ libqpdf/QPDF_Dictionary.cc | 12 ++++++ libqpdf/QPDF_InlineImage.cc | 14 ++++++- libqpdf/QPDF_Integer.cc | 12 ++++++ libqpdf/QPDF_Name.cc | 12 ++++++ libqpdf/QPDF_Null.cc | 12 ++++++ libqpdf/QPDF_Operator.cc | 14 ++++++- libqpdf/QPDF_Real.cc | 19 +++++++++ libqpdf/QPDF_Reserved.cc | 12 ++++++ libqpdf/QPDF_Stream.cc | 19 +++++++++ libqpdf/QPDF_String.cc | 19 +++++++-- libqpdf/qpdf/QPDF_Array.hh | 8 ++-- libqpdf/qpdf/QPDF_Bool.hh | 4 +- libqpdf/qpdf/QPDF_Dictionary.hh | 4 +- libqpdf/qpdf/QPDF_InlineImage.hh | 4 +- libqpdf/qpdf/QPDF_Integer.hh | 4 +- libqpdf/qpdf/QPDF_Name.hh | 4 +- libqpdf/qpdf/QPDF_Null.hh | 4 ++ libqpdf/qpdf/QPDF_Operator.hh | 4 +- libqpdf/qpdf/QPDF_Real.hh | 8 +++- libqpdf/qpdf/QPDF_Reserved.hh | 4 ++ libqpdf/qpdf/QPDF_Stream.hh | 12 +++++- libqpdf/qpdf/QPDF_String.hh | 8 +++- qpdf/qpdf.testcov | 11 ------ 30 files changed, 261 insertions(+), 95 deletions(-) diff --git a/include/qpdf/QPDFObject.hh b/include/qpdf/QPDFObject.hh index 982cd126..eb7c4b90 100644 --- a/include/qpdf/QPDFObject.hh +++ b/include/qpdf/QPDFObject.hh @@ -63,6 +63,7 @@ class QPDFObject static constexpr object_type_e ot_inlineimage = ::ot_inlineimage; virtual ~QPDFObject() = default; + virtual std::shared_ptr shallowCopy() = 0; virtual std::string unparse() = 0; virtual JSON getJSON(int json_version) = 0; @@ -102,6 +103,7 @@ class QPDFObject releaseResolved() { } + static std::shared_ptr do_create(QPDFObject*); private: QPDFObject(QPDFObject const&) = delete; diff --git a/include/qpdf/QPDFObjectHandle.hh b/include/qpdf/QPDFObjectHandle.hh index 07e70531..cda257f1 100644 --- a/include/qpdf/QPDFObjectHandle.hh +++ b/include/qpdf/QPDFObjectHandle.hh @@ -1551,7 +1551,7 @@ class QPDFObjectHandle private: QPDFObjectHandle(QPDF*, int objid, int generation); - QPDFObjectHandle(QPDFObject*); + QPDFObjectHandle(std::shared_ptr const&); enum parser_state_e { st_top, diff --git a/libqpdf/QPDF.cc b/libqpdf/QPDF.cc index b51c5571..9ad33376 100644 --- a/libqpdf/QPDF.cc +++ b/libqpdf/QPDF.cc @@ -1989,7 +1989,7 @@ QPDF::resolve(int objid, int generation) this->m->file->getLastOffset(), ("loop detected resolving object " + QUtil::int_to_string(objid) + " " + QUtil::int_to_string(generation))); - return std::shared_ptr(new QPDF_Null); + return QPDF_Null::create(); } ResolveRecorder rr(this, og); diff --git a/libqpdf/QPDFObject.cc b/libqpdf/QPDFObject.cc index 39eb01a2..39a5fa50 100644 --- a/libqpdf/QPDFObject.cc +++ b/libqpdf/QPDFObject.cc @@ -6,6 +6,13 @@ QPDFObject::QPDFObject() : { } +std::shared_ptr +QPDFObject::do_create(QPDFObject* object) +{ + std::shared_ptr obj(object); + return obj; +} + void QPDFObject::setDescription(QPDF* qpdf, std::string const& description) { diff --git a/libqpdf/QPDFObjectHandle.cc b/libqpdf/QPDFObjectHandle.cc index 4ef4f4d9..d39f93be 100644 --- a/libqpdf/QPDFObjectHandle.cc +++ b/libqpdf/QPDFObjectHandle.cc @@ -235,7 +235,7 @@ QPDFObjectHandle::QPDFObjectHandle(QPDF* qpdf, int objid, int generation) : { } -QPDFObjectHandle::QPDFObjectHandle(QPDFObject* data) : +QPDFObjectHandle::QPDFObjectHandle(std::shared_ptr const& data) : initialized(true), qpdf(0), objid(0), @@ -2335,7 +2335,7 @@ QPDFObjectHandle::parseInternal( if (old_state == st_array) { // There's no newArray(SparseOHArray) since // SparseOHArray is not part of the public API. - object = QPDFObjectHandle(new QPDF_Array(olist)); + object = QPDFObjectHandle(QPDF_Array::create(olist)); setObjectDescriptionFromInput( object, context, object_description, input, offset); // The `offset` points to the next of "[". Set the @@ -2499,25 +2499,25 @@ QPDFObjectHandle::newIndirect(QPDF* qpdf, int objid, int generation) QPDFObjectHandle QPDFObjectHandle::newBool(bool value) { - return QPDFObjectHandle(new QPDF_Bool(value)); + return QPDFObjectHandle(QPDF_Bool::create(value)); } QPDFObjectHandle QPDFObjectHandle::newNull() { - return QPDFObjectHandle(new QPDF_Null()); + return QPDFObjectHandle(QPDF_Null::create()); } QPDFObjectHandle QPDFObjectHandle::newInteger(long long value) { - return QPDFObjectHandle(new QPDF_Integer(value)); + return QPDFObjectHandle(QPDF_Integer::create(value)); } QPDFObjectHandle QPDFObjectHandle::newReal(std::string const& value) { - return QPDFObjectHandle(new QPDF_Real(value)); + return QPDFObjectHandle(QPDF_Real::create(value)); } QPDFObjectHandle @@ -2525,37 +2525,37 @@ QPDFObjectHandle::newReal( double value, int decimal_places, bool trim_trailing_zeroes) { return QPDFObjectHandle( - new QPDF_Real(value, decimal_places, trim_trailing_zeroes)); + QPDF_Real::create(value, decimal_places, trim_trailing_zeroes)); } QPDFObjectHandle QPDFObjectHandle::newName(std::string const& name) { - return QPDFObjectHandle(new QPDF_Name(name)); + return QPDFObjectHandle(QPDF_Name::create(name)); } QPDFObjectHandle QPDFObjectHandle::newString(std::string const& str) { - return QPDFObjectHandle(new QPDF_String(str)); + return QPDFObjectHandle(QPDF_String::create(str)); } QPDFObjectHandle QPDFObjectHandle::newUnicodeString(std::string const& utf8_str) { - return QPDFObjectHandle(QPDF_String::new_utf16(utf8_str)); + return QPDFObjectHandle(QPDF_String::create_utf16(utf8_str)); } QPDFObjectHandle QPDFObjectHandle::newOperator(std::string const& value) { - return QPDFObjectHandle(new QPDF_Operator(value)); + return QPDFObjectHandle(QPDF_Operator::create(value)); } QPDFObjectHandle QPDFObjectHandle::newInlineImage(std::string const& value) { - return QPDFObjectHandle(new QPDF_InlineImage(value)); + return QPDFObjectHandle(QPDF_InlineImage::create(value)); } QPDFObjectHandle @@ -2567,7 +2567,7 @@ QPDFObjectHandle::newArray() QPDFObjectHandle QPDFObjectHandle::newArray(std::vector const& items) { - return QPDFObjectHandle(new QPDF_Array(items)); + return QPDFObjectHandle(QPDF_Array::create(items)); } QPDFObjectHandle @@ -2635,7 +2635,7 @@ QPDFObjectHandle QPDFObjectHandle::newDictionary( std::map const& items) { - return QPDFObjectHandle(new QPDF_Dictionary(items)); + return QPDFObjectHandle(QPDF_Dictionary::create(items)); } QPDFObjectHandle @@ -2647,8 +2647,8 @@ QPDFObjectHandle::newStream( qpdf_offset_t offset, size_t length) { - QPDFObjectHandle result = QPDFObjectHandle( - new QPDF_Stream(qpdf, objid, generation, stream_dict, offset, length)); + QPDFObjectHandle result = QPDFObjectHandle(QPDF_Stream::create( + qpdf, objid, generation, stream_dict, offset, length)); if (offset) { result.setParsedOffset(offset); } @@ -2665,8 +2665,7 @@ QPDFObjectHandle::newStream(QPDF* qpdf) QTC::TC("qpdf", "QPDFObjectHandle newStream"); QPDFObjectHandle stream_dict = newDictionary(); QPDFObjectHandle result = qpdf->makeIndirectObject( - QPDFObjectHandle(new QPDF_Stream(qpdf, 0, 0, stream_dict, 0, 0))); - // Indirect objects are guaranteed to be initialized + QPDFObjectHandle(QPDF_Stream::create(qpdf, 0, 0, stream_dict, 0, 0))); result.dereference(); QPDF_Stream* stream = dynamic_cast(result.obj.get()); stream->setObjGen(result.getObjectID(), result.getGeneration()); @@ -2706,7 +2705,7 @@ QPDFObjectHandle::newReserved(QPDF* qpdf) QPDFObjectHandle QPDFObjectHandle::makeReserved() { - return QPDFObjectHandle(new QPDF_Reserved()); + return QPDFObjectHandle(QPDF_Reserved::create()); } void @@ -2753,17 +2752,9 @@ QPDFObjectHandle::shallowCopyInternal( throw std::runtime_error("attempt to make a shallow copy of a stream"); } - if (isArray()) { - QTC::TC("qpdf", "QPDFObjectHandle shallow copy array"); - // No newArray for shallow copying the sparse array - QPDF_Array* arr = dynamic_cast(obj.get()); - new_obj = - QPDFObjectHandle(new QPDF_Array(arr->getElementsForShallowCopy())); - } else if (isDictionary()) { - QTC::TC("qpdf", "QPDFObjectHandle shallow copy dictionary"); - new_obj = newDictionary(getDictAsMap()); + if (isArray() || isDictionary()) { + new_obj = QPDFObjectHandle(obj->shallowCopy()); } else { - QTC::TC("qpdf", "QPDFObjectHandle shallow copy scalar"); new_obj = *this; } @@ -2812,27 +2803,14 @@ QPDFObjectHandle::copyObject( std::shared_ptr new_obj; - if (isBool()) { - QTC::TC("qpdf", "QPDFObjectHandle clone bool"); - new_obj = std::shared_ptr(new QPDF_Bool(getBoolValue())); - } else if (isNull()) { - QTC::TC("qpdf", "QPDFObjectHandle clone null"); - new_obj = std::shared_ptr(new QPDF_Null()); - } else if (isInteger()) { - QTC::TC("qpdf", "QPDFObjectHandle clone integer"); - new_obj = std::shared_ptr(new QPDF_Integer(getIntValue())); - } else if (isReal()) { - QTC::TC("qpdf", "QPDFObjectHandle clone real"); - new_obj = std::shared_ptr(new QPDF_Real(getRealValue())); - } else if (isName()) { - QTC::TC("qpdf", "QPDFObjectHandle clone name"); - new_obj = std::shared_ptr(new QPDF_Name(getName())); - } else if (isString()) { - QTC::TC("qpdf", "QPDFObjectHandle clone string"); - new_obj = - std::shared_ptr(new QPDF_String(getStringValue())); + if (isBool() || + isInteger() || + isName() || + isNull() || + isReal() || + isString()) { + new_obj = obj->shallowCopy(); } else if (isArray()) { - QTC::TC("qpdf", "QPDFObjectHandle clone array"); std::vector items; int n = getArrayNItems(); for (int i = 0; i < n; ++i) { @@ -2843,9 +2821,8 @@ QPDFObjectHandle::copyObject( visited, cross_indirect, first_level_only, stop_at_streams); } } - new_obj = std::shared_ptr(new QPDF_Array(items)); + new_obj = QPDF_Array::create(items); } else if (isDictionary()) { - QTC::TC("qpdf", "QPDFObjectHandle clone dictionary"); std::map items; for (auto const& key: getKeys()) { items[key] = getKey(key); @@ -2855,7 +2832,7 @@ QPDFObjectHandle::copyObject( visited, cross_indirect, first_level_only, stop_at_streams); } } - new_obj = std::shared_ptr(new QPDF_Dictionary(items)); + new_obj = QPDF_Dictionary::create(items); } else { throw std::logic_error("QPDFObjectHandle::makeDirectInternal: " "unknown object type"); @@ -3144,7 +3121,7 @@ QPDFObjectHandle::dereference() if (obj.get() == 0) { // QPDF::resolve never returns an uninitialized object, but // check just in case. - this->obj = std::shared_ptr(new QPDF_Null()); + this->obj = QPDF_Null::create(); } else if (dynamic_cast(obj.get())) { // Do not resolve this->reserved = true; diff --git a/libqpdf/QPDF_Array.cc b/libqpdf/QPDF_Array.cc index fd046ec7..55e4d20a 100644 --- a/libqpdf/QPDF_Array.cc +++ b/libqpdf/QPDF_Array.cc @@ -14,6 +14,24 @@ QPDF_Array::QPDF_Array(SparseOHArray const& items) : { } +std::shared_ptr +QPDF_Array::create(std::vector const& items) +{ + return do_create(new QPDF_Array(items)); +} + +std::shared_ptr +QPDF_Array::create(SparseOHArray const& items) +{ + return do_create(new QPDF_Array(items)); +} + +std::shared_ptr +QPDF_Array::shallowCopy() +{ + return create(elements); +} + void QPDF_Array::releaseResolved() { @@ -121,12 +139,6 @@ QPDF_Array::eraseItem(int at) this->elements.erase(QIntC::to_size(at)); } -SparseOHArray const& -QPDF_Array::getElementsForShallowCopy() const -{ - return this->elements; -} - void QPDF_Array::addExplicitElementsToList(std::list& l) const { diff --git a/libqpdf/QPDF_Bool.cc b/libqpdf/QPDF_Bool.cc index 74d2ec3b..f26325c3 100644 --- a/libqpdf/QPDF_Bool.cc +++ b/libqpdf/QPDF_Bool.cc @@ -5,6 +5,18 @@ QPDF_Bool::QPDF_Bool(bool val) : { } +std::shared_ptr +QPDF_Bool::create(bool value) +{ + return do_create(new QPDF_Bool(value)); +} + +std::shared_ptr +QPDF_Bool::shallowCopy() +{ + return create(val); +} + std::string QPDF_Bool::unparse() { diff --git a/libqpdf/QPDF_Dictionary.cc b/libqpdf/QPDF_Dictionary.cc index 9453b64a..be3c5dcd 100644 --- a/libqpdf/QPDF_Dictionary.cc +++ b/libqpdf/QPDF_Dictionary.cc @@ -9,6 +9,18 @@ QPDF_Dictionary::QPDF_Dictionary( { } +std::shared_ptr +QPDF_Dictionary::create(std::map const& items) +{ + return do_create(new QPDF_Dictionary(items)); +} + +std::shared_ptr +QPDF_Dictionary::shallowCopy() +{ + return create(items); +} + void QPDF_Dictionary::releaseResolved() { diff --git a/libqpdf/QPDF_InlineImage.cc b/libqpdf/QPDF_InlineImage.cc index 84f4fa19..c3c656e0 100644 --- a/libqpdf/QPDF_InlineImage.cc +++ b/libqpdf/QPDF_InlineImage.cc @@ -1,12 +1,22 @@ #include -#include - QPDF_InlineImage::QPDF_InlineImage(std::string const& val) : val(val) { } +std::shared_ptr +QPDF_InlineImage::create(std::string const& val) +{ + return do_create(new QPDF_InlineImage(val)); +} + +std::shared_ptr +QPDF_InlineImage::shallowCopy() +{ + return create(val); +} + std::string QPDF_InlineImage::unparse() { diff --git a/libqpdf/QPDF_Integer.cc b/libqpdf/QPDF_Integer.cc index c42fa246..e8d23e4a 100644 --- a/libqpdf/QPDF_Integer.cc +++ b/libqpdf/QPDF_Integer.cc @@ -7,6 +7,18 @@ QPDF_Integer::QPDF_Integer(long long val) : { } +std::shared_ptr +QPDF_Integer::create(long long value) +{ + return do_create(new QPDF_Integer(value)); +} + +std::shared_ptr +QPDF_Integer::shallowCopy() +{ + return create(val); +} + std::string QPDF_Integer::unparse() { diff --git a/libqpdf/QPDF_Name.cc b/libqpdf/QPDF_Name.cc index 236d6133..73990775 100644 --- a/libqpdf/QPDF_Name.cc +++ b/libqpdf/QPDF_Name.cc @@ -9,6 +9,18 @@ QPDF_Name::QPDF_Name(std::string const& name) : { } +std::shared_ptr +QPDF_Name::create(std::string const& name) +{ + return do_create(new QPDF_Name(name)); +} + +std::shared_ptr +QPDF_Name::shallowCopy() +{ + return create(name); +} + std::string QPDF_Name::normalizeName(std::string const& name) { diff --git a/libqpdf/QPDF_Null.cc b/libqpdf/QPDF_Null.cc index 166b0302..b015ed8b 100644 --- a/libqpdf/QPDF_Null.cc +++ b/libqpdf/QPDF_Null.cc @@ -1,5 +1,17 @@ #include +std::shared_ptr +QPDF_Null::create() +{ + return do_create(new QPDF_Null()); +} + +std::shared_ptr +QPDF_Null::shallowCopy() +{ + return create(); +} + std::string QPDF_Null::unparse() { diff --git a/libqpdf/QPDF_Operator.cc b/libqpdf/QPDF_Operator.cc index f7da813a..cd5009ae 100644 --- a/libqpdf/QPDF_Operator.cc +++ b/libqpdf/QPDF_Operator.cc @@ -1,12 +1,22 @@ #include -#include - QPDF_Operator::QPDF_Operator(std::string const& val) : val(val) { } +std::shared_ptr +QPDF_Operator::create(std::string const& val) +{ + return do_create(new QPDF_Operator(val)); +} + +std::shared_ptr +QPDF_Operator::shallowCopy() +{ + return create(val); +} + std::string QPDF_Operator::unparse() { diff --git a/libqpdf/QPDF_Real.cc b/libqpdf/QPDF_Real.cc index 4b32b035..138bbb3c 100644 --- a/libqpdf/QPDF_Real.cc +++ b/libqpdf/QPDF_Real.cc @@ -13,6 +13,25 @@ QPDF_Real::QPDF_Real( { } +std::shared_ptr +QPDF_Real::create(std::string const& val) +{ + return do_create(new QPDF_Real(val)); +} + +std::shared_ptr +QPDF_Real::create(double value, int decimal_places, bool trim_trailing_zeroes) +{ + return do_create( + new QPDF_Real(value, decimal_places, trim_trailing_zeroes)); +} + +std::shared_ptr +QPDF_Real::shallowCopy() +{ + return create(val); +} + std::string QPDF_Real::unparse() { diff --git a/libqpdf/QPDF_Reserved.cc b/libqpdf/QPDF_Reserved.cc index 775dee02..5808a369 100644 --- a/libqpdf/QPDF_Reserved.cc +++ b/libqpdf/QPDF_Reserved.cc @@ -2,6 +2,18 @@ #include +std::shared_ptr +QPDF_Reserved::create() +{ + return do_create(new QPDF_Reserved()); +} + +std::shared_ptr +QPDF_Reserved::shallowCopy() +{ + return create(); +} + std::string QPDF_Reserved::unparse() { diff --git a/libqpdf/QPDF_Stream.cc b/libqpdf/QPDF_Stream.cc index edb4a739..c4c69659 100644 --- a/libqpdf/QPDF_Stream.cc +++ b/libqpdf/QPDF_Stream.cc @@ -134,6 +134,25 @@ QPDF_Stream::QPDF_Stream( QUtil::int_to_string(this->generation)); } +std::shared_ptr +QPDF_Stream::create( + QPDF* qpdf, + int objid, + int generation, + QPDFObjectHandle stream_dict, + qpdf_offset_t offset, + size_t length) +{ + return do_create( + new QPDF_Stream(qpdf, objid, generation, stream_dict, offset,length)); +} + +std::shared_ptr +QPDF_Stream::shallowCopy() +{ + throw std::logic_error("stream objects cannot be cloned"); +} + void QPDF_Stream::registerStreamFilter( std::string const& filter_name, diff --git a/libqpdf/QPDF_String.cc b/libqpdf/QPDF_String.cc index 4d45d851..b038366b 100644 --- a/libqpdf/QPDF_String.cc +++ b/libqpdf/QPDF_String.cc @@ -1,6 +1,5 @@ #include -#include #include // DO NOT USE ctype -- it is locale dependent for some things, and @@ -26,14 +25,26 @@ QPDF_String::QPDF_String(std::string const& val) : { } -QPDF_String* -QPDF_String::new_utf16(std::string const& utf8_val) +std::shared_ptr +QPDF_String::create(std::string const& val) +{ + return do_create(new QPDF_String(val)); +} + +std::shared_ptr +QPDF_String::create_utf16(std::string const& utf8_val) { std::string result; if (!QUtil::utf8_to_pdf_doc(utf8_val, result, '?')) { result = QUtil::utf8_to_utf16(utf8_val); } - return new QPDF_String(result); + return do_create(new QPDF_String(result)); +} + +std::shared_ptr +QPDF_String::shallowCopy() +{ + return create(val); } std::string diff --git a/libqpdf/qpdf/QPDF_Array.hh b/libqpdf/qpdf/QPDF_Array.hh index ac5d98be..e718c6e0 100644 --- a/libqpdf/qpdf/QPDF_Array.hh +++ b/libqpdf/qpdf/QPDF_Array.hh @@ -10,9 +10,10 @@ class QPDF_Array: public QPDFObject { public: - QPDF_Array(std::vector const& items); - QPDF_Array(SparseOHArray const& items); virtual ~QPDF_Array() = default; + static std::shared_ptr create(std::vector const& items); + static std::shared_ptr create(SparseOHArray const& items); + virtual std::shared_ptr shallowCopy(); virtual std::string unparse(); virtual JSON getJSON(int json_version); virtual QPDFObject::object_type_e getTypeCode() const; @@ -31,13 +32,14 @@ class QPDF_Array: public QPDFObject // Helper methods for QPDF and QPDFObjectHandle -- these are // public methods since the whole class is not part of the public // API. Otherwise, these would be wrapped in accessor classes. - SparseOHArray const& getElementsForShallowCopy() const; void addExplicitElementsToList(std::list&) const; protected: virtual void releaseResolved(); private: + QPDF_Array(std::vector const& items); + QPDF_Array(SparseOHArray const& items); SparseOHArray elements; }; diff --git a/libqpdf/qpdf/QPDF_Bool.hh b/libqpdf/qpdf/QPDF_Bool.hh index 576b1505..dbedc70a 100644 --- a/libqpdf/qpdf/QPDF_Bool.hh +++ b/libqpdf/qpdf/QPDF_Bool.hh @@ -6,8 +6,9 @@ class QPDF_Bool: public QPDFObject { public: - QPDF_Bool(bool val); virtual ~QPDF_Bool() = default; + static std::shared_ptr create(bool val); + virtual std::shared_ptr shallowCopy(); virtual std::string unparse(); virtual JSON getJSON(int json_version); virtual QPDFObject::object_type_e getTypeCode() const; @@ -15,6 +16,7 @@ class QPDF_Bool: public QPDFObject bool getVal() const; private: + QPDF_Bool(bool val); bool val; }; diff --git a/libqpdf/qpdf/QPDF_Dictionary.hh b/libqpdf/qpdf/QPDF_Dictionary.hh index be1c8733..3cd00c1e 100644 --- a/libqpdf/qpdf/QPDF_Dictionary.hh +++ b/libqpdf/qpdf/QPDF_Dictionary.hh @@ -11,8 +11,9 @@ class QPDF_Dictionary: public QPDFObject { public: - QPDF_Dictionary(std::map const& items); virtual ~QPDF_Dictionary() = default; + static std::shared_ptr create(std::map const& items); + virtual std::shared_ptr shallowCopy(); virtual std::string unparse(); virtual JSON getJSON(int json_version); virtual QPDFObject::object_type_e getTypeCode() const; @@ -36,6 +37,7 @@ class QPDF_Dictionary: public QPDFObject virtual void releaseResolved(); private: + QPDF_Dictionary(std::map const& items); std::map items; }; diff --git a/libqpdf/qpdf/QPDF_InlineImage.hh b/libqpdf/qpdf/QPDF_InlineImage.hh index 32b25093..caaeaf87 100644 --- a/libqpdf/qpdf/QPDF_InlineImage.hh +++ b/libqpdf/qpdf/QPDF_InlineImage.hh @@ -6,8 +6,9 @@ class QPDF_InlineImage: public QPDFObject { public: - QPDF_InlineImage(std::string const& val); virtual ~QPDF_InlineImage() = default; + static std::shared_ptr create(std::string const& val); + virtual std::shared_ptr shallowCopy(); virtual std::string unparse(); virtual JSON getJSON(int json_version); virtual QPDFObject::object_type_e getTypeCode() const; @@ -15,6 +16,7 @@ class QPDF_InlineImage: public QPDFObject std::string getVal() const; private: + QPDF_InlineImage(std::string const& val); std::string val; }; diff --git a/libqpdf/qpdf/QPDF_Integer.hh b/libqpdf/qpdf/QPDF_Integer.hh index 36001a14..2c17daf0 100644 --- a/libqpdf/qpdf/QPDF_Integer.hh +++ b/libqpdf/qpdf/QPDF_Integer.hh @@ -6,8 +6,9 @@ class QPDF_Integer: public QPDFObject { public: - QPDF_Integer(long long val); virtual ~QPDF_Integer() = default; + static std::shared_ptr create(long long value); + virtual std::shared_ptr shallowCopy(); virtual std::string unparse(); virtual JSON getJSON(int json_version); virtual QPDFObject::object_type_e getTypeCode() const; @@ -15,6 +16,7 @@ class QPDF_Integer: public QPDFObject long long getVal() const; private: + QPDF_Integer(long long val); long long val; }; diff --git a/libqpdf/qpdf/QPDF_Name.hh b/libqpdf/qpdf/QPDF_Name.hh index 5ee65d02..cf653b2e 100644 --- a/libqpdf/qpdf/QPDF_Name.hh +++ b/libqpdf/qpdf/QPDF_Name.hh @@ -6,8 +6,9 @@ class QPDF_Name: public QPDFObject { public: - QPDF_Name(std::string const& name); virtual ~QPDF_Name() = default; + static std::shared_ptr create(std::string const& name); + virtual std::shared_ptr shallowCopy(); virtual std::string unparse(); virtual JSON getJSON(int json_version); virtual QPDFObject::object_type_e getTypeCode() const; @@ -18,6 +19,7 @@ class QPDF_Name: public QPDFObject static std::string normalizeName(std::string const& name); private: + QPDF_Name(std::string const& name); std::string name; }; diff --git a/libqpdf/qpdf/QPDF_Null.hh b/libqpdf/qpdf/QPDF_Null.hh index 9d2d6223..8051e238 100644 --- a/libqpdf/qpdf/QPDF_Null.hh +++ b/libqpdf/qpdf/QPDF_Null.hh @@ -7,10 +7,14 @@ class QPDF_Null: public QPDFObject { public: virtual ~QPDF_Null() = default; + static std::shared_ptr create(); + virtual std::shared_ptr shallowCopy(); virtual std::string unparse(); virtual JSON getJSON(int json_version); virtual QPDFObject::object_type_e getTypeCode() const; virtual char const* getTypeName() const; + private: + QPDF_Null() = default; }; #endif // QPDF_NULL_HH diff --git a/libqpdf/qpdf/QPDF_Operator.hh b/libqpdf/qpdf/QPDF_Operator.hh index 672da728..1da43d72 100644 --- a/libqpdf/qpdf/QPDF_Operator.hh +++ b/libqpdf/qpdf/QPDF_Operator.hh @@ -6,8 +6,9 @@ class QPDF_Operator: public QPDFObject { public: - QPDF_Operator(std::string const& val); virtual ~QPDF_Operator() = default; + static std::shared_ptr create(std::string const& val); + virtual std::shared_ptr shallowCopy(); virtual std::string unparse(); virtual JSON getJSON(int json_version); virtual QPDFObject::object_type_e getTypeCode() const; @@ -15,6 +16,7 @@ class QPDF_Operator: public QPDFObject std::string getVal() const; private: + QPDF_Operator(std::string const& val); std::string val; }; diff --git a/libqpdf/qpdf/QPDF_Real.hh b/libqpdf/qpdf/QPDF_Real.hh index 1b9878c7..bf61091c 100644 --- a/libqpdf/qpdf/QPDF_Real.hh +++ b/libqpdf/qpdf/QPDF_Real.hh @@ -6,9 +6,11 @@ class QPDF_Real: public QPDFObject { public: - QPDF_Real(std::string const& val); - QPDF_Real(double value, int decimal_places, bool trim_trailing_zeroes); virtual ~QPDF_Real() = default; + static std::shared_ptr create(std::string const& val); + static std::shared_ptr create( + double value, int decimal_places, bool trim_trailing_zeroes); + virtual std::shared_ptr shallowCopy(); virtual std::string unparse(); virtual JSON getJSON(int json_version); virtual QPDFObject::object_type_e getTypeCode() const; @@ -16,6 +18,8 @@ class QPDF_Real: public QPDFObject std::string getVal(); private: + QPDF_Real(std::string const& val); + QPDF_Real(double value, int decimal_places, bool trim_trailing_zeroes); // Store reals as strings to avoid roundoff errors. std::string val; }; diff --git a/libqpdf/qpdf/QPDF_Reserved.hh b/libqpdf/qpdf/QPDF_Reserved.hh index a198f645..1a40447d 100644 --- a/libqpdf/qpdf/QPDF_Reserved.hh +++ b/libqpdf/qpdf/QPDF_Reserved.hh @@ -7,10 +7,14 @@ class QPDF_Reserved: public QPDFObject { public: virtual ~QPDF_Reserved() = default; + static std::shared_ptr create(); + virtual std::shared_ptr shallowCopy(); virtual std::string unparse(); virtual JSON getJSON(int json_version); virtual QPDFObject::object_type_e getTypeCode() const; virtual char const* getTypeName() const; + private: + QPDF_Reserved() = default; }; #endif // QPDF_RESERVED_HH diff --git a/libqpdf/qpdf/QPDF_Stream.hh b/libqpdf/qpdf/QPDF_Stream.hh index 4aaee0a2..3b7cf358 100644 --- a/libqpdf/qpdf/QPDF_Stream.hh +++ b/libqpdf/qpdf/QPDF_Stream.hh @@ -16,14 +16,15 @@ class QPDF; class QPDF_Stream: public QPDFObject { public: - QPDF_Stream( + virtual ~QPDF_Stream() = default; + static std::shared_ptr create( QPDF*, int objid, int generation, QPDFObjectHandle stream_dict, qpdf_offset_t offset, size_t length); - virtual ~QPDF_Stream() = default; + virtual std::shared_ptr shallowCopy(); virtual std::string unparse(); virtual JSON getJSON(int json_version); virtual QPDFObject::object_type_e getTypeCode() const; @@ -83,6 +84,13 @@ class QPDF_Stream: public QPDFObject virtual void releaseResolved(); private: + QPDF_Stream( + QPDF*, + int objid, + int generation, + QPDFObjectHandle stream_dict, + qpdf_offset_t offset, + size_t length); static std::map filter_abbreviations; static std:: map()>> diff --git a/libqpdf/qpdf/QPDF_String.hh b/libqpdf/qpdf/QPDF_String.hh index 6fd1b0e9..fc11d3ba 100644 --- a/libqpdf/qpdf/QPDF_String.hh +++ b/libqpdf/qpdf/QPDF_String.hh @@ -7,10 +7,13 @@ class QPDF_String: public QPDFObject { + friend class QPDFWriter; + public: - QPDF_String(std::string const& val); - static QPDF_String* new_utf16(std::string const& utf8_val); virtual ~QPDF_String() = default; + static std::shared_ptr create(std::string const& val); + static std::shared_ptr create_utf16(std::string const& utf8_val); + virtual std::shared_ptr shallowCopy(); virtual std::string unparse(); virtual QPDFObject::object_type_e getTypeCode() const; virtual char const* getTypeName() const; @@ -20,6 +23,7 @@ class QPDF_String: public QPDFObject std::string getUTF8Val() const; private: + QPDF_String(std::string const& val); bool useHexString() const; std::string val; }; diff --git a/qpdf/qpdf.testcov b/qpdf/qpdf.testcov index 93c658bb..bc4c2128 100644 --- a/qpdf/qpdf.testcov +++ b/qpdf/qpdf.testcov @@ -70,14 +70,6 @@ QPDFTokenizer null in name 0 QPDFTokenizer bad name 0 QPDF_Stream invalid filter 0 QPDF UseOutlines but no Outlines 0 -QPDFObjectHandle clone bool 0 -QPDFObjectHandle clone null 0 -QPDFObjectHandle clone integer 0 -QPDFObjectHandle clone real 0 -QPDFObjectHandle clone name 0 -QPDFObjectHandle clone string 0 -QPDFObjectHandle clone array 0 -QPDFObjectHandle clone dictionary 0 QPDFObjectHandle makeDirect loop 0 QPDFObjectHandle copy stream 1 QPDF default for xref stream field 0 0 @@ -199,9 +191,6 @@ QPDF updateAllPagesCache 0 QPDF insert non-indirect page 0 QPDF insert indirect page 0 QPDFObjectHandle ERR shallow copy stream 0 -QPDFObjectHandle shallow copy array 0 -QPDFObjectHandle shallow copy dictionary 0 -QPDFObjectHandle shallow copy scalar 0 QPDFObjectHandle newStream with string 0 QPDF unknown key not inherited 0 QPDF_Stream provider length not provided 0 -- cgit v1.2.3-54-g00ecf