A linearized PDF, which Acrobat calls “fast web view”, is ordered so that a viewer reading it over a network can show the first page before the rest has arrived, and can fetch any other page with a byte-range request. The objects of the first page come first, then each page’s objects in turn, and hint tables say where everything is. A linearized file is still an ordinary PDF: a reader that knows nothing of linearization reads it from the end as usual. Linearization dates from PDF 1.2; this page describes it as it is in PDF 1.5 to 2.0, where it must also deal with object streams and cross-reference streams.
The linearization parameter dictionary
The first object in the file, straight after the header, is a dictionary that says the file is linearized. It must lie wholly within the first 1,024 bytes, hold only direct values, and not be referred to by anything else.
43 0 obj
<< /Linearized 1.0 /L 54567 /H [475 598] /O 45 /E 5437 /N 11 /T 52786 >>
endobj
| Key | Type | Meaning |
|---|---|---|
Linearized | number | Required. The version of linearization, 1.0 |
L | integer | Required. The length of the whole file in bytes. If it does not match, the file is not to be read as linearized |
H | array | Required. The offset and length of the primary hint stream, and, if there is one, of the overflow hint stream. The offset is of the object’s start, and the length includes the obj lines |
O | integer | Required. The object number of the first page’s page object |
E | integer | Required. The offset of the end of the first page |
N | integer | Required. The number of pages |
T | integer | Required. With a table: the offset of the white space before the first entry of the main cross-reference table. With only cross-reference streams: the offset of the main cross-reference stream object |
P | integer | The number of the first page, from 0; default 0. Used when the document opens on another page |
The order of the parts
- The header.
- The linearization parameter dictionary.
- The first-page cross-reference section and its trailer: a table, or a
cross-reference stream, for the objects of parts 2 to 6, whose
Prevpoints at the main section at the end. - The document catalog and the document-level objects a viewer needs first: the
ViewerPreferences, thePageMode, the outline if it opens shown,AcroFormfields, theOCPropertiesand so on. - The primary hint stream.
- The first page: its page object, then everything only it uses, then the shared objects it uses.
- The other pages, each with the objects only it uses, in page order.
- The shared objects not used by the first page, in groups.
- Other objects: the page tree, thumbnails, the outline when it is not in part 4, threads, named destinations, the information dictionary, the rest of the form, the structure tree, renditions, embedded files.
- The overflow hint stream, if any.
- The main cross-reference section and trailer, for everything else.
Parts 5 and 6 may be swapped. The first page ends at E. A reader that has
the bytes up to E can show page one.
Hint streams
A hint stream is an ordinary stream, often Flate compressed, whose dictionary says where each hint table starts in the decoded data. The page offset hint table is always first, at 0; the others are named by these keys:
| Key | Hint table | Form |
|---|---|---|
S | Shared objects, required | own |
T | Thumbnails, if there are any | own |
O | Outline | generic |
A | Article threads | generic |
E | Named destinations | generic |
V | Interactive form | extended generic |
I | Information dictionary | generic |
C | Logical structure | extended generic |
L | Page labels | generic |
R | Renditions name tree (1.5) | extended generic |
B | Embedded file streams (1.5) | own |
The tables are bit streams, read most significant bit first, and each table starts on a byte boundary. Positions in them are offsets in the file, except that a position past the primary hint stream must have the hint stream’s length added: the tables are written as if the hint stream were not there. Most tables store each value as a difference from a least value in the header, in as few bits as the header says.
The page offset hint table
A header, then one entry for each page. In the header:
| Item | Bits | Meaning |
|---|---|---|
| 1 | 32 | The least number of objects in a page, the page object included |
| 2 | 32 | The location of the first page’s page object |
| 3 | 16 | Bits needed for the difference between the greatest and least objects in a page |
| 4 | 32 | The least length of a page in bytes |
| 5 | 16 | Bits needed for the difference between the greatest and least page length |
| 6 | 32 | The least offset of a page’s content stream from the start of the page |
| 7 | 16 | Bits needed for the difference in content stream offset |
| 8 | 32 | The least length of a content stream |
| 9 | 16 | Bits needed for the difference in content stream length |
| 10 | 16 | Bits needed for the greatest number of shared object references |
| 11 | 16 | Bits needed for the greatest shared object identifier |
| 12 | 16 | Bits needed for the numerator of the fractional position of a shared object reference |
| 13 | 16 | The denominator of that fraction, the same for the whole file |
Each page entry, its items in the bits given by the header:
| Item | Bits | Meaning |
|---|---|---|
| 1 | item 3 | Objects in the page, minus item 1. The first page’s objects start at O; the other pages’ objects are numbered on from 1 |
| 2 | item 5 | The page’s length in bytes, minus item 4 |
| 3 | item 10 | The number of shared objects the page uses (0 for the first page) |
| 4 | item 11 | For each of them: a shared object identifier, an index into the shared object hint table |
| 5 | item 12 | For each of them: the numerator of where in the content stream it is first needed. From 0 to d − 1 it is a fraction of the way through; d means before the images and other objects at the end of the page, and more than d after them |
| 6 | item 7 | The offset of the content stream from the start of the page, minus item 6 |
| 7 | item 9 | The length of the content stream, minus item 8 |
The items are not stored page by page but item by item: item 1 of every page, then item 2 of every page, then item 3, then items 4 and 5 for the pages after the first, then item 6 of every page and item 7 of every page.
The other hint tables
Thumbnails
A header of 12 items: the object number and location of the first thumbnail, the number of pages with thumbnails, bits for the longest run of pages without, the least thumbnail length and bits for the difference, the least number of objects and bits for the difference, and the object number, location, count and length of the shared thumbnail objects. Then for each page: the pages without a thumbnail before it, its objects and its length, each as a difference.
Generic and extended generic tables
A generic table has four 32-bit items: the first object number, its location, the number of objects, and the length of the group. The outline, threads, named destinations, information dictionary and page label tables use it. An extended generic table adds a 32-bit count of shared object references, 16 bits giving the width of each identifier, and the identifiers; the form, structure and renditions tables use it.
Embedded file streams
From PDF 1.5. A header of seven items: the object number and location of the first object of the first group, the number of groups, and bits for the greatest object number, objects in a group, group length and shared references. Then, item by item across all groups: the embedded file stream’s object number, the objects in the group, its length, its number of shared references, and the shared object identifiers.
With object streams and cross-reference streams
- The first-page section, part 3, may be a cross-reference stream, and so may the main
section at the end.
Tthen gives the offset of the main cross-reference stream object. - The linearization dictionary, the catalog and the page objects must stand alone, not in object streams.
- Other objects may be in object streams. A hint table cannot give the exact offset of an object inside an object stream; its positions then cover the byte range of the object stream that holds it, and a reader finds the object itself through the cross-reference stream.
Telling whether a file is linearized
- Read the first object after the header. It must be a dictionary with
Linearized. - Check that
Lequals the length of the file. An incremental update adds bytes at the end, so a linearized file that has been updated is no longer linearized; its first-page structures are then out of date and must be ignored. - Check that
Hpoints at a hint stream.
A viewer that reads a whole file from disk gains nothing from linearization, and most readers simply ignore it. Writers such as qpdf can linearize a file and check that the hints are right.