Commit a15ec6967dd3312223a6ab7d4198655234e1a4bf
1 parent
1bb209a9
Enhancements to ParserCallbacks
Showing
3 changed files
with
37 additions
and
2 deletions
ChangeLog
| 1 | 2021-03-01 Jay Berkenbilt <ejb@ql.org> | 1 | 2021-03-01 Jay Berkenbilt <ejb@ql.org> |
| 2 | 2 | ||
| 3 | + * QPDFObjectHandle::ParserCallbacks: add virtual handleWarning | ||
| 4 | + method, and provide default (empty) implementation of it and | ||
| 5 | + handleEOF(). | ||
| 6 | + | ||
| 3 | * Add QPDF::numWarnings() -- useful to tell whether any warnings | 7 | * Add QPDF::numWarnings() -- useful to tell whether any warnings |
| 4 | were issued by a specific bit of code. | 8 | were issued by a specific bit of code. |
| 5 | 9 |
include/qpdf/QPDFObjectHandle.hh
| @@ -224,7 +224,16 @@ class QPDFObjectHandle | @@ -224,7 +224,16 @@ class QPDFObjectHandle | ||
| 224 | virtual void handleObject( | 224 | virtual void handleObject( |
| 225 | QPDFObjectHandle, size_t offset, size_t length); | 225 | QPDFObjectHandle, size_t offset, size_t length); |
| 226 | 226 | ||
| 227 | - virtual void handleEOF() = 0; | 227 | + // handleWarning is called if a warning was issued during the |
| 228 | + // parsing of the most recent object. There's no good way to | ||
| 229 | + // get information about the warning, but implementors can use | ||
| 230 | + // this to become aware that there was some problem while | ||
| 231 | + // parsing this content stream. | ||
| 232 | + QPDF_DLL | ||
| 233 | + virtual void handleWarning(); | ||
| 234 | + | ||
| 235 | + QPDF_DLL | ||
| 236 | + virtual void handleEOF(); | ||
| 228 | 237 | ||
| 229 | // Override this if you want to know the full size of the | 238 | // Override this if you want to know the full size of the |
| 230 | // contents, possibly after concatenation of multiple streams. | 239 | // contents, possibly after concatenation of multiple streams. |
libqpdf/QPDFObjectHandle.cc
| @@ -152,6 +152,16 @@ QPDFObjectHandle::ParserCallbacks::handleObject( | @@ -152,6 +152,16 @@ QPDFObjectHandle::ParserCallbacks::handleObject( | ||
| 152 | } | 152 | } |
| 153 | 153 | ||
| 154 | void | 154 | void |
| 155 | +QPDFObjectHandle::ParserCallbacks::handleWarning() | ||
| 156 | +{ | ||
| 157 | +} | ||
| 158 | + | ||
| 159 | +void | ||
| 160 | +QPDFObjectHandle::ParserCallbacks::handleEOF() | ||
| 161 | +{ | ||
| 162 | +} | ||
| 163 | + | ||
| 164 | +void | ||
| 155 | QPDFObjectHandle::ParserCallbacks::contentSize(size_t) | 165 | QPDFObjectHandle::ParserCallbacks::contentSize(size_t) |
| 156 | { | 166 | { |
| 157 | // Ignore by default; overriding this is optional. | 167 | // Ignore by default; overriding this is optional. |
| @@ -1847,10 +1857,15 @@ QPDFObjectHandle::parseContentStream_internal( | @@ -1847,10 +1857,15 @@ QPDFObjectHandle::parseContentStream_internal( | ||
| 1847 | pipeContentStreams(&buf, description, all_description); | 1857 | pipeContentStreams(&buf, description, all_description); |
| 1848 | PointerHolder<Buffer> stream_data = buf.getBuffer(); | 1858 | PointerHolder<Buffer> stream_data = buf.getBuffer(); |
| 1849 | callbacks->contentSize(stream_data->getSize()); | 1859 | callbacks->contentSize(stream_data->getSize()); |
| 1860 | + QPDF* context = getOwningQPDF(); | ||
| 1861 | + if ((! context) && isArray() && (getArrayNItems() > 0)) | ||
| 1862 | + { | ||
| 1863 | + context = getArrayItem(0).getOwningQPDF(); | ||
| 1864 | + } | ||
| 1850 | try | 1865 | try |
| 1851 | { | 1866 | { |
| 1852 | parseContentStream_data(stream_data, all_description, | 1867 | parseContentStream_data(stream_data, all_description, |
| 1853 | - callbacks, getOwningQPDF()); | 1868 | + callbacks, context); |
| 1854 | } | 1869 | } |
| 1855 | catch (TerminateParsing&) | 1870 | catch (TerminateParsing&) |
| 1856 | { | 1871 | { |
| @@ -1881,9 +1896,15 @@ QPDFObjectHandle::parseContentStream_data( | @@ -1881,9 +1896,15 @@ QPDFObjectHandle::parseContentStream_data( | ||
| 1881 | tokenizer.readToken(input, "content", true); | 1896 | tokenizer.readToken(input, "content", true); |
| 1882 | qpdf_offset_t offset = input->getLastOffset(); | 1897 | qpdf_offset_t offset = input->getLastOffset(); |
| 1883 | input->seek(offset, SEEK_SET); | 1898 | input->seek(offset, SEEK_SET); |
| 1899 | + size_t before_nwarnings = (context ? context->numWarnings() : 0); | ||
| 1884 | QPDFObjectHandle obj = | 1900 | QPDFObjectHandle obj = |
| 1885 | parseInternal(input, "content", tokenizer, | 1901 | parseInternal(input, "content", tokenizer, |
| 1886 | empty, 0, context, true); | 1902 | empty, 0, context, true); |
| 1903 | + size_t after_nwarnings = (context ? context->numWarnings() : 0); | ||
| 1904 | + if (after_nwarnings > before_nwarnings) | ||
| 1905 | + { | ||
| 1906 | + callbacks->handleWarning(); | ||
| 1907 | + } | ||
| 1887 | if (! obj.isInitialized()) | 1908 | if (! obj.isInitialized()) |
| 1888 | { | 1909 | { |
| 1889 | // EOF | 1910 | // EOF |
| @@ -1910,6 +1931,7 @@ QPDFObjectHandle::parseContentStream_data( | @@ -1910,6 +1931,7 @@ QPDFObjectHandle::parseContentStream_data( | ||
| 1910 | QPDFExc(qpdf_e_damaged_pdf, input->getName(), | 1931 | QPDFExc(qpdf_e_damaged_pdf, input->getName(), |
| 1911 | "stream data", input->tell(), | 1932 | "stream data", input->tell(), |
| 1912 | "EOF found while reading inline image")); | 1933 | "EOF found while reading inline image")); |
| 1934 | + callbacks->handleWarning(); | ||
| 1913 | } | 1935 | } |
| 1914 | else | 1936 | else |
| 1915 | { | 1937 | { |