Commit 35e7859bc7d903c0177ce2a14f2842e1a2dbb09a
1 parent
50decc9b
Make QPDFObjectHandle::is* return false for uninitialized objects
Showing
3 changed files
with
70 additions
and
1 deletions
ChangeLog
| 1 | +2021-01-29 Jay Berkenbilt <ejb@ql.org> | ||
| 2 | + | ||
| 3 | + * QPDFObjectHandle::is* methods to check type now return false on | ||
| 4 | + uninitialized objects rather than crashing or throwing a logic | ||
| 5 | + error. | ||
| 6 | + | ||
| 1 | 2021-01-24 Jay Berkenbilt <ejb@ql.org> | 7 | 2021-01-24 Jay Berkenbilt <ejb@ql.org> |
| 2 | 8 | ||
| 3 | * Implement remove for name and number trees as well as exposing | 9 | * Implement remove for name and number trees as well as exposing |
libqpdf/QPDFObjectHandle.cc
| @@ -314,6 +314,10 @@ class QPDFObjectTypeAccessor | @@ -314,6 +314,10 @@ class QPDFObjectTypeAccessor | ||
| 314 | bool | 314 | bool |
| 315 | QPDFObjectHandle::isBool() | 315 | QPDFObjectHandle::isBool() |
| 316 | { | 316 | { |
| 317 | + if (! this->initialized) | ||
| 318 | + { | ||
| 319 | + return false; | ||
| 320 | + } | ||
| 317 | dereference(); | 321 | dereference(); |
| 318 | return QPDFObjectTypeAccessor<QPDF_Bool>::check(obj.getPointer()); | 322 | return QPDFObjectTypeAccessor<QPDF_Bool>::check(obj.getPointer()); |
| 319 | } | 323 | } |
| @@ -328,6 +332,10 @@ QPDFObjectHandle::isDirectNull() const | @@ -328,6 +332,10 @@ QPDFObjectHandle::isDirectNull() const | ||
| 328 | bool | 332 | bool |
| 329 | QPDFObjectHandle::isNull() | 333 | QPDFObjectHandle::isNull() |
| 330 | { | 334 | { |
| 335 | + if (! this->initialized) | ||
| 336 | + { | ||
| 337 | + return false; | ||
| 338 | + } | ||
| 331 | dereference(); | 339 | dereference(); |
| 332 | return QPDFObjectTypeAccessor<QPDF_Null>::check(obj.getPointer()); | 340 | return QPDFObjectTypeAccessor<QPDF_Null>::check(obj.getPointer()); |
| 333 | } | 341 | } |
| @@ -335,6 +343,10 @@ QPDFObjectHandle::isNull() | @@ -335,6 +343,10 @@ QPDFObjectHandle::isNull() | ||
| 335 | bool | 343 | bool |
| 336 | QPDFObjectHandle::isInteger() | 344 | QPDFObjectHandle::isInteger() |
| 337 | { | 345 | { |
| 346 | + if (! this->initialized) | ||
| 347 | + { | ||
| 348 | + return false; | ||
| 349 | + } | ||
| 338 | dereference(); | 350 | dereference(); |
| 339 | return QPDFObjectTypeAccessor<QPDF_Integer>::check(obj.getPointer()); | 351 | return QPDFObjectTypeAccessor<QPDF_Integer>::check(obj.getPointer()); |
| 340 | } | 352 | } |
| @@ -342,6 +354,10 @@ QPDFObjectHandle::isInteger() | @@ -342,6 +354,10 @@ QPDFObjectHandle::isInteger() | ||
| 342 | bool | 354 | bool |
| 343 | QPDFObjectHandle::isReal() | 355 | QPDFObjectHandle::isReal() |
| 344 | { | 356 | { |
| 357 | + if (! this->initialized) | ||
| 358 | + { | ||
| 359 | + return false; | ||
| 360 | + } | ||
| 345 | dereference(); | 361 | dereference(); |
| 346 | return QPDFObjectTypeAccessor<QPDF_Real>::check(obj.getPointer()); | 362 | return QPDFObjectTypeAccessor<QPDF_Real>::check(obj.getPointer()); |
| 347 | } | 363 | } |
| @@ -375,6 +391,10 @@ QPDFObjectHandle::getNumericValue() | @@ -375,6 +391,10 @@ QPDFObjectHandle::getNumericValue() | ||
| 375 | bool | 391 | bool |
| 376 | QPDFObjectHandle::isName() | 392 | QPDFObjectHandle::isName() |
| 377 | { | 393 | { |
| 394 | + if (! this->initialized) | ||
| 395 | + { | ||
| 396 | + return false; | ||
| 397 | + } | ||
| 378 | dereference(); | 398 | dereference(); |
| 379 | return QPDFObjectTypeAccessor<QPDF_Name>::check(obj.getPointer()); | 399 | return QPDFObjectTypeAccessor<QPDF_Name>::check(obj.getPointer()); |
| 380 | } | 400 | } |
| @@ -382,6 +402,10 @@ QPDFObjectHandle::isName() | @@ -382,6 +402,10 @@ QPDFObjectHandle::isName() | ||
| 382 | bool | 402 | bool |
| 383 | QPDFObjectHandle::isString() | 403 | QPDFObjectHandle::isString() |
| 384 | { | 404 | { |
| 405 | + if (! this->initialized) | ||
| 406 | + { | ||
| 407 | + return false; | ||
| 408 | + } | ||
| 385 | dereference(); | 409 | dereference(); |
| 386 | return QPDFObjectTypeAccessor<QPDF_String>::check(obj.getPointer()); | 410 | return QPDFObjectTypeAccessor<QPDF_String>::check(obj.getPointer()); |
| 387 | } | 411 | } |
| @@ -389,6 +413,10 @@ QPDFObjectHandle::isString() | @@ -389,6 +413,10 @@ QPDFObjectHandle::isString() | ||
| 389 | bool | 413 | bool |
| 390 | QPDFObjectHandle::isOperator() | 414 | QPDFObjectHandle::isOperator() |
| 391 | { | 415 | { |
| 416 | + if (! this->initialized) | ||
| 417 | + { | ||
| 418 | + return false; | ||
| 419 | + } | ||
| 392 | dereference(); | 420 | dereference(); |
| 393 | return QPDFObjectTypeAccessor<QPDF_Operator>::check(obj.getPointer()); | 421 | return QPDFObjectTypeAccessor<QPDF_Operator>::check(obj.getPointer()); |
| 394 | } | 422 | } |
| @@ -396,6 +424,10 @@ QPDFObjectHandle::isOperator() | @@ -396,6 +424,10 @@ QPDFObjectHandle::isOperator() | ||
| 396 | bool | 424 | bool |
| 397 | QPDFObjectHandle::isInlineImage() | 425 | QPDFObjectHandle::isInlineImage() |
| 398 | { | 426 | { |
| 427 | + if (! this->initialized) | ||
| 428 | + { | ||
| 429 | + return false; | ||
| 430 | + } | ||
| 399 | dereference(); | 431 | dereference(); |
| 400 | return QPDFObjectTypeAccessor<QPDF_InlineImage>::check(obj.getPointer()); | 432 | return QPDFObjectTypeAccessor<QPDF_InlineImage>::check(obj.getPointer()); |
| 401 | } | 433 | } |
| @@ -403,6 +435,10 @@ QPDFObjectHandle::isInlineImage() | @@ -403,6 +435,10 @@ QPDFObjectHandle::isInlineImage() | ||
| 403 | bool | 435 | bool |
| 404 | QPDFObjectHandle::isArray() | 436 | QPDFObjectHandle::isArray() |
| 405 | { | 437 | { |
| 438 | + if (! this->initialized) | ||
| 439 | + { | ||
| 440 | + return false; | ||
| 441 | + } | ||
| 406 | dereference(); | 442 | dereference(); |
| 407 | return QPDFObjectTypeAccessor<QPDF_Array>::check(obj.getPointer()); | 443 | return QPDFObjectTypeAccessor<QPDF_Array>::check(obj.getPointer()); |
| 408 | } | 444 | } |
| @@ -410,6 +446,10 @@ QPDFObjectHandle::isArray() | @@ -410,6 +446,10 @@ QPDFObjectHandle::isArray() | ||
| 410 | bool | 446 | bool |
| 411 | QPDFObjectHandle::isDictionary() | 447 | QPDFObjectHandle::isDictionary() |
| 412 | { | 448 | { |
| 449 | + if (! this->initialized) | ||
| 450 | + { | ||
| 451 | + return false; | ||
| 452 | + } | ||
| 413 | dereference(); | 453 | dereference(); |
| 414 | return QPDFObjectTypeAccessor<QPDF_Dictionary>::check(obj.getPointer()); | 454 | return QPDFObjectTypeAccessor<QPDF_Dictionary>::check(obj.getPointer()); |
| 415 | } | 455 | } |
| @@ -417,6 +457,10 @@ QPDFObjectHandle::isDictionary() | @@ -417,6 +457,10 @@ QPDFObjectHandle::isDictionary() | ||
| 417 | bool | 457 | bool |
| 418 | QPDFObjectHandle::isStream() | 458 | QPDFObjectHandle::isStream() |
| 419 | { | 459 | { |
| 460 | + if (! this->initialized) | ||
| 461 | + { | ||
| 462 | + return false; | ||
| 463 | + } | ||
| 420 | dereference(); | 464 | dereference(); |
| 421 | return QPDFObjectTypeAccessor<QPDF_Stream>::check(obj.getPointer()); | 465 | return QPDFObjectTypeAccessor<QPDF_Stream>::check(obj.getPointer()); |
| 422 | } | 466 | } |
| @@ -424,6 +468,10 @@ QPDFObjectHandle::isStream() | @@ -424,6 +468,10 @@ QPDFObjectHandle::isStream() | ||
| 424 | bool | 468 | bool |
| 425 | QPDFObjectHandle::isReserved() | 469 | QPDFObjectHandle::isReserved() |
| 426 | { | 470 | { |
| 471 | + if (! this->initialized) | ||
| 472 | + { | ||
| 473 | + return false; | ||
| 474 | + } | ||
| 427 | // dereference will clear reserved if this has been replaced | 475 | // dereference will clear reserved if this has been replaced |
| 428 | dereference(); | 476 | dereference(); |
| 429 | return this->reserved; | 477 | return this->reserved; |
| @@ -432,7 +480,10 @@ QPDFObjectHandle::isReserved() | @@ -432,7 +480,10 @@ QPDFObjectHandle::isReserved() | ||
| 432 | bool | 480 | bool |
| 433 | QPDFObjectHandle::isIndirect() | 481 | QPDFObjectHandle::isIndirect() |
| 434 | { | 482 | { |
| 435 | - assertInitialized(); | 483 | + if (! this->initialized) |
| 484 | + { | ||
| 485 | + return false; | ||
| 486 | + } | ||
| 436 | return (this->objid != 0); | 487 | return (this->objid != 0); |
| 437 | } | 488 | } |
| 438 | 489 | ||
| @@ -2985,6 +3036,11 @@ QPDFObjectHandle::assertPageObject() | @@ -2985,6 +3036,11 @@ QPDFObjectHandle::assertPageObject() | ||
| 2985 | void | 3036 | void |
| 2986 | QPDFObjectHandle::dereference() | 3037 | QPDFObjectHandle::dereference() |
| 2987 | { | 3038 | { |
| 3039 | + if (! this->initialized) | ||
| 3040 | + { | ||
| 3041 | + throw std::logic_error( | ||
| 3042 | + "attempted to dereference an uninitialized QPDFObjectHandle"); | ||
| 3043 | + } | ||
| 2988 | if (this->obj.getPointer() == 0) | 3044 | if (this->obj.getPointer() == 0) |
| 2989 | { | 3045 | { |
| 2990 | PointerHolder<QPDFObject> obj = QPDF::Resolver::resolve( | 3046 | PointerHolder<QPDFObject> obj = QPDF::Resolver::resolve( |
manual/qpdf-manual.xml
| @@ -4855,6 +4855,13 @@ print "\n"; | @@ -4855,6 +4855,13 @@ print "\n"; | ||
| 4855 | </listitem> | 4855 | </listitem> |
| 4856 | <listitem> | 4856 | <listitem> |
| 4857 | <para> | 4857 | <para> |
| 4858 | + <function>QPDFObjectHandle::is*</function> methods now return | ||
| 4859 | + false rather than crashing when called with an uninitialized | ||
| 4860 | + <classname>QPDFObjectHandle</classname> object. | ||
| 4861 | + </para> | ||
| 4862 | + </listitem> | ||
| 4863 | + <listitem> | ||
| 4864 | + <para> | ||
| 4858 | Re-implement <classname>QPDFNameTreeObjectHelper</classname> | 4865 | Re-implement <classname>QPDFNameTreeObjectHelper</classname> |
| 4859 | and <classname>QPDFNumberTreeObjectHelper</classname> to be | 4866 | and <classname>QPDFNumberTreeObjectHelper</classname> to be |
| 4860 | more efficient, add an iterator-based API, give them the | 4867 | more efficient, add an iterator-based API, give them the |