draft-ietf-httpbis-header-compression-12.txt | draft-ietf-httpbis-header-compression-latest.txt | |||
---|---|---|---|---|
HTTPbis Working Group R. Peon | HTTPbis Working Group R. Peon | |||
Internet-Draft Google, Inc | Internet-Draft Google, Inc | |||
Intended status: Standards Track H. Ruellan | Intended status: Standards Track H. Ruellan | |||
Expires: August 21, 2015 Canon CRF | Expires: January 7, 2025 Canon CRF | |||
February 17, 2015 | July 6, 2024 | |||
HPACK - Header Compression for HTTP/2 | HPACK: Header Compression for HTTP/2 | |||
draft-ietf-httpbis-header-compression-latest | draft-ietf-httpbis-header-compression-latest | |||
Abstract | Abstract | |||
This specification defines HPACK, a compression format for | This specification defines HPACK, a compression format for | |||
efficiently representing HTTP header fields, to be used in HTTP/2. | efficiently representing HTTP header fields, to be used in HTTP/2. | |||
Editorial Note (To be removed by RFC Editor) | Editorial Note (To be removed by RFC Editor) | |||
Discussion of this draft takes place on the HTTPBIS working group | Discussion of this draft takes place on the HTTPBIS working group | |||
mailing list (ietf-http-wg@w3.org), which is archived at | mailing list (ietf-http-wg@w3.org), which is archived at | |||
<https://lists.w3.org/Archives/Public/ietf-http-wg/>. | <https://lists.w3.org/Archives/Public/ietf-http-wg/>. | |||
Working Group information can be found at | Working Group information can be found at <http://tools.ietf.org/wg/ | |||
<http://tools.ietf.org/wg/httpbis/>; that specific to HTTP/2 are at | httpbis/>; that specific to HTTP/2 are at <http://http2.github.io/>. | |||
<http://http2.github.io/>. | ||||
The changes in this draft are summarized in Appendix D.2. | ||||
Status of This Memo | Status of This Memo | |||
This Internet-Draft is submitted in full conformance with the | This Internet-Draft is submitted in full conformance with the | |||
provisions of BCP 78 and BCP 79. | provisions of BCP 78 and BCP 79. | |||
Internet-Drafts are working documents of the Internet Engineering | Internet-Drafts are working documents of the Internet Engineering | |||
Task Force (IETF). Note that other groups may also distribute | Task Force (IETF). Note that other groups may also distribute | |||
working documents as Internet-Drafts. The list of current Internet- | working documents as Internet-Drafts. The list of current Internet- | |||
Drafts is at http://datatracker.ietf.org/drafts/current/. | Drafts is at https://datatracker.ietf.org/drafts/current/. | |||
Internet-Drafts are draft documents valid for a maximum of six months | Internet-Drafts are draft documents valid for a maximum of six months | |||
and may be updated, replaced, or obsoleted by other documents at any | and may be updated, replaced, or obsoleted by other documents at any | |||
time. It is inappropriate to use Internet-Drafts as reference | time. It is inappropriate to use Internet-Drafts as reference | |||
material or to cite them other than as "work in progress." | material or to cite them other than as "work in progress." | |||
This Internet-Draft will expire on August 21, 2015. | This Internet-Draft will expire on January 7, 2025. | |||
Copyright Notice | Copyright Notice | |||
Copyright (c) 2015 IETF Trust and the persons identified as the | Copyright (c) 2024 IETF Trust and the persons identified as the | |||
document authors. All rights reserved. | document authors. All rights reserved. | |||
This document is subject to BCP 78 and the IETF Trust's Legal | This document is subject to BCP 78 and the IETF Trust's Legal | |||
Provisions Relating to IETF Documents | Provisions Relating to IETF Documents | |||
(http://trustee.ietf.org/license-info) in effect on the date of | (https://trustee.ietf.org/license-info) in effect on the date of | |||
publication of this document. Please review these documents | publication of this document. Please review these documents | |||
carefully, as they describe your rights and restrictions with respect | carefully, as they describe your rights and restrictions with respect | |||
to this document. Code Components extracted from this document must | to this document. Code Components extracted from this document must | |||
include Simplified BSD License text as described in Section 4.e of | include Simplified BSD License text as described in Section 4.e of | |||
the Trust Legal Provisions and are provided without warranty as | the Trust Legal Provisions and are provided without warranty as | |||
described in the Simplified BSD License. | described in the Simplified BSD License. | |||
Table of Contents | Table of Contents | |||
1. Introduction . . . . . . . . . . . . . . . . . . . . . . . . . 5 | 1. Introduction . . . . . . . . . . . . . . . . . . . . . . . . 3 | |||
1.1. Overview . . . . . . . . . . . . . . . . . . . . . . . . . 5 | 1.1. Overview . . . . . . . . . . . . . . . . . . . . . . . . 4 | |||
1.2. Conventions . . . . . . . . . . . . . . . . . . . . . . . 6 | 1.2. Conventions . . . . . . . . . . . . . . . . . . . . . . . 4 | |||
1.3. Terminology . . . . . . . . . . . . . . . . . . . . . . . 6 | 1.3. Terminology . . . . . . . . . . . . . . . . . . . . . . . 5 | |||
2. Compression Process Overview . . . . . . . . . . . . . . . . . 7 | 2. Compression Process Overview . . . . . . . . . . . . . . . . 5 | |||
2.1. Header List Ordering . . . . . . . . . . . . . . . . . . . 7 | 2.1. Header List Ordering . . . . . . . . . . . . . . . . . . 5 | |||
2.2. Encoding and Decoding Contexts . . . . . . . . . . . . . . 7 | 2.2. Encoding and Decoding Contexts . . . . . . . . . . . . . 6 | |||
2.3. Indexing Tables . . . . . . . . . . . . . . . . . . . . . 7 | 2.3. Indexing Tables . . . . . . . . . . . . . . . . . . . . . 6 | |||
2.3.1. Static Table . . . . . . . . . . . . . . . . . . . . . 7 | 2.3.1. Static Table . . . . . . . . . . . . . . . . . . . . 6 | |||
2.3.2. Dynamic Table . . . . . . . . . . . . . . . . . . . . 7 | 2.3.2. Dynamic Table . . . . . . . . . . . . . . . . . . . . 6 | |||
2.3.3. Index Address Space . . . . . . . . . . . . . . . . . 8 | 2.3.3. Index Address Space . . . . . . . . . . . . . . . . . 7 | |||
2.4. Header Field Representation . . . . . . . . . . . . . . . 9 | 2.4. Header Field Representation . . . . . . . . . . . . . . . 7 | |||
3. Header Block Decoding . . . . . . . . . . . . . . . . . . . . 9 | 3. Header Block Decoding . . . . . . . . . . . . . . . . . . . . 8 | |||
3.1. Header Block Processing . . . . . . . . . . . . . . . . . 9 | 3.1. Header Block Processing . . . . . . . . . . . . . . . . . 8 | |||
3.2. Header Field Representation Processing . . . . . . . . . . 10 | 3.2. Header Field Representation Processing . . . . . . . . . 8 | |||
4. Dynamic Table Management . . . . . . . . . . . . . . . . . . . 10 | 4. Dynamic Table Management . . . . . . . . . . . . . . . . . . 9 | |||
4.1. Calculating Table Size . . . . . . . . . . . . . . . . . . 11 | 4.1. Calculating Table Size . . . . . . . . . . . . . . . . . 9 | |||
4.2. Maximum Table Size . . . . . . . . . . . . . . . . . . . . 11 | 4.2. Maximum Table Size . . . . . . . . . . . . . . . . . . . 9 | |||
4.3. Entry Eviction when Dynamic Table Size Changes . . . . . . 12 | 4.3. Entry Eviction When Dynamic Table Size Changes . . . . . 10 | |||
4.4. Entry Eviction when Adding New Entries . . . . . . . . . . 12 | 4.4. Entry Eviction When Adding New Entries . . . . . . . . . 10 | |||
5. Primitive Type Representations . . . . . . . . . . . . . . . . 12 | 5. Primitive Type Representations . . . . . . . . . . . . . . . 11 | |||
5.1. Integer Representation . . . . . . . . . . . . . . . . . . 12 | 5.1. Integer Representation . . . . . . . . . . . . . . . . . 11 | |||
5.2. String Literal Representation . . . . . . . . . . . . . . 14 | 5.2. String Literal Representation . . . . . . . . . . . . . . 13 | |||
6. Binary Format . . . . . . . . . . . . . . . . . . . . . . . . 15 | 6. Binary Format . . . . . . . . . . . . . . . . . . . . . . . . 14 | |||
6.1. Indexed Header Field Representation . . . . . . . . . . . 15 | 6.1. Indexed Header Field Representation . . . . . . . . . . . 14 | |||
6.2. Literal Header Field Representation . . . . . . . . . . . 16 | 6.2. Literal Header Field Representation . . . . . . . . . . . 14 | |||
6.2.1. Literal Header Field with Incremental Indexing . . . . 16 | 6.2.1. Literal Header Field with Incremental Indexing . . . 14 | |||
6.2.2. Literal Header Field without Indexing . . . . . . . . 17 | 6.2.2. Literal Header Field without Indexing . . . . . . . . 15 | |||
6.2.3. Literal Header Field never Indexed . . . . . . . . . . 18 | 6.2.3. Literal Header Field Never Indexed . . . . . . . . . 16 | |||
6.3. Dynamic Table Size Update . . . . . . . . . . . . . . . . 19 | 6.3. Dynamic Table Size Update . . . . . . . . . . . . . . . . 17 | |||
7. Security Considerations . . . . . . . . . . . . . . . . . . . 20 | 7. Security Considerations . . . . . . . . . . . . . . . . . . . 18 | |||
7.1. Probing Dynamic Table State . . . . . . . . . . . . . . . 20 | 7.1. Probing Dynamic Table State . . . . . . . . . . . . . . . 18 | |||
7.1.1. Applicability to HPACK and HTTP . . . . . . . . . . . 21 | 7.1.1. Applicability to HPACK and HTTP . . . . . . . . . . . 19 | |||
7.1.2. Mitigation . . . . . . . . . . . . . . . . . . . . . . 21 | 7.1.2. Mitigation . . . . . . . . . . . . . . . . . . . . . 20 | |||
7.1.3. Never Indexed Literals . . . . . . . . . . . . . . . . 22 | 7.1.3. Never-Indexed Literals . . . . . . . . . . . . . . . 21 | |||
7.2. Static Huffman Encoding . . . . . . . . . . . . . . . . . 23 | 7.2. Static Huffman Encoding . . . . . . . . . . . . . . . . . 21 | |||
7.3. Memory Consumption . . . . . . . . . . . . . . . . . . . . 23 | 7.3. Memory Consumption . . . . . . . . . . . . . . . . . . . 21 | |||
7.4. Implementation Limits . . . . . . . . . . . . . . . . . . 24 | 7.4. Implementation Limits . . . . . . . . . . . . . . . . . . 22 | |||
8. IANA Considerations . . . . . . . . . . . . . . . . . . . . . 24 | ||||
9. Acknowledgments . . . . . . . . . . . . . . . . . . . . . . . 24 | 8. References . . . . . . . . . . . . . . . . . . . . . . . . . 22 | |||
10. References . . . . . . . . . . . . . . . . . . . . . . . . . . 24 | 8.1. Normative References . . . . . . . . . . . . . . . . . . 22 | |||
10.1. Normative References . . . . . . . . . . . . . . . . . . . 24 | 8.2. Informative References . . . . . . . . . . . . . . . . . 23 | |||
10.2. Informative References . . . . . . . . . . . . . . . . . . 25 | Appendix A. Static Table Definition . . . . . . . . . . . . . . 24 | |||
Appendix A. Static Table Definition . . . . . . . . . . . . . . . 25 | Appendix B. Huffman Code . . . . . . . . . . . . . . . . . . . . 25 | |||
Appendix B. Huffman Code . . . . . . . . . . . . . . . . . . . . 27 | Appendix C. Examples . . . . . . . . . . . . . . . . . . . . . . 31 | |||
Appendix C. Examples . . . . . . . . . . . . . . . . . . . . . . 33 | C.1. Integer Representation Examples . . . . . . . . . . . . . 32 | |||
C.1. Integer Representation Examples . . . . . . . . . . . . . 33 | C.1.1. Example 1: Encoding 10 Using a 5-Bit Prefix . . . . . 32 | |||
C.1.1. Example 1: Encoding 10 Using a 5-bit Prefix . . . . . 33 | C.1.2. Example 2: Encoding 1337 Using a 5-Bit Prefix . . . . 32 | |||
C.1.2. Example 2: Encoding 1337 Using a 5-bit Prefix . . . . 34 | C.1.3. Example 3: Encoding 42 Starting at an Octet Boundary 33 | |||
C.1.3. Example 3: Encoding 42 Starting at an Octet | C.2. Header Field Representation Examples . . . . . . . . . . 33 | |||
Boundary . . . . . . . . . . . . . . . . . . . . . . . 35 | C.2.1. Literal Header Field with Indexing . . . . . . . . . 33 | |||
C.2. Header Field Representation Examples . . . . . . . . . . . 35 | C.2.2. Literal Header Field without Indexing . . . . . . . . 34 | |||
C.2.1. Literal Header Field with Indexing . . . . . . . . . . 35 | C.2.3. Literal Header Field Never Indexed . . . . . . . . . 35 | |||
C.2.2. Literal Header Field without Indexing . . . . . . . . 36 | C.2.4. Indexed Header Field . . . . . . . . . . . . . . . . 35 | |||
C.2.3. Literal Header Field never Indexed . . . . . . . . . . 37 | C.3. Request Examples without Huffman Coding . . . . . . . . . 36 | |||
C.2.4. Indexed Header Field . . . . . . . . . . . . . . . . . 37 | C.3.1. First Request . . . . . . . . . . . . . . . . . . . . 36 | |||
C.3. Request Examples without Huffman Coding . . . . . . . . . 38 | C.3.2. Second Request . . . . . . . . . . . . . . . . . . . 37 | |||
C.3.1. First Request . . . . . . . . . . . . . . . . . . . . 38 | C.3.3. Third Request . . . . . . . . . . . . . . . . . . . . 38 | |||
C.3.2. Second Request . . . . . . . . . . . . . . . . . . . . 39 | C.4. Request Examples with Huffman Coding . . . . . . . . . . 39 | |||
C.3.3. Third Request . . . . . . . . . . . . . . . . . . . . 40 | C.4.1. First Request . . . . . . . . . . . . . . . . . . . . 39 | |||
C.4. Request Examples with Huffman Coding . . . . . . . . . . . 41 | C.4.2. Second Request . . . . . . . . . . . . . . . . . . . 40 | |||
C.4.1. First Request . . . . . . . . . . . . . . . . . . . . 42 | C.4.3. Third Request . . . . . . . . . . . . . . . . . . . . 41 | |||
C.4.2. Second Request . . . . . . . . . . . . . . . . . . . . 43 | C.5. Response Examples without Huffman Coding . . . . . . . . 43 | |||
C.4.3. Third Request . . . . . . . . . . . . . . . . . . . . 44 | C.5.1. First Response . . . . . . . . . . . . . . . . . . . 43 | |||
C.5. Response Examples without Huffman Coding . . . . . . . . . 45 | C.5.2. Second Response . . . . . . . . . . . . . . . . . . . 45 | |||
C.5.1. First Response . . . . . . . . . . . . . . . . . . . . 46 | C.5.3. Third Response . . . . . . . . . . . . . . . . . . . 46 | |||
C.5.2. Second Response . . . . . . . . . . . . . . . . . . . 48 | C.6. Response Examples with Huffman Coding . . . . . . . . . . 48 | |||
C.5.3. Third Response . . . . . . . . . . . . . . . . . . . . 49 | C.6.1. First Response . . . . . . . . . . . . . . . . . . . 48 | |||
C.6. Response Examples with Huffman Coding . . . . . . . . . . 51 | C.6.2. Second Response . . . . . . . . . . . . . . . . . . . 50 | |||
C.6.1. First Response . . . . . . . . . . . . . . . . . . . . 51 | C.6.3. Third Response . . . . . . . . . . . . . . . . . . . 51 | |||
C.6.2. Second Response . . . . . . . . . . . . . . . . . . . 53 | Acknowledgments . . . . . . . . . . . . . . . . . . . . . . . . . 53 | |||
C.6.3. Third Response . . . . . . . . . . . . . . . . . . . . 54 | Authors' Addresses . . . . . . . . . . . . . . . . . . . . . . . 54 | |||
Appendix D. Change Log (to be removed by RFC Editor before | ||||
publication) . . . . . . . . . . . . . . . . . . . . 56 | ||||
D.1. Since draft-ietf-httpbis-header-compression-10 . . . . . . 56 | ||||
D.2. Since draft-ietf-httpbis-header-compression-09 . . . . . . 57 | ||||
D.3. Since draft-ietf-httpbis-header-compression-08 . . . . . . 57 | ||||
D.4. Since draft-ietf-httpbis-header-compression-07 . . . . . . 57 | ||||
D.5. Since draft-ietf-httpbis-header-compression-06 . . . . . . 58 | ||||
D.6. Since draft-ietf-httpbis-header-compression-05 . . . . . . 58 | ||||
D.7. Since draft-ietf-httpbis-header-compression-04 . . . . . . 58 | ||||
D.8. Since draft-ietf-httpbis-header-compression-03 . . . . . . 59 | ||||
D.9. Since draft-ietf-httpbis-header-compression-02 . . . . . . 59 | ||||
D.10. Since draft-ietf-httpbis-header-compression-01 . . . . . . 59 | ||||
D.11. Since draft-ietf-httpbis-header-compression-00 . . . . . . 59 | ||||
1. Introduction | 1. Introduction | |||
In HTTP/1.1 (see [RFC7230]), header fields are not compressed. As | In HTTP/1.1 (see [RFC7230]), header fields are not compressed. As | |||
Web pages have grown to require dozens to hundreds of requests, the | web pages have grown to require dozens to hundreds of requests, the | |||
redundant header fields in these requests unnecessarily consume | redundant header fields in these requests unnecessarily consume | |||
bandwidth, measurably increasing latency. | bandwidth, measurably increasing latency. | |||
SPDY [SPDY] initially addressed this redundancy by compressing header | SPDY [SPDY] initially addressed this redundancy by compressing header | |||
fields using the DEFLATE [DEFLATE] format, which proved very | fields using the DEFLATE [DEFLATE] format, which proved very | |||
effective at efficiently representing the redundant header fields. | effective at efficiently representing the redundant header fields. | |||
However, that approach exposed a security risk as demonstrated by the | However, that approach exposed a security risk as demonstrated by the | |||
CRIME attack (see [CRIME]). | CRIME (Compression Ratio Info-leak Made Easy) attack (see [CRIME]). | |||
This specification defines HPACK, a new compressor for header fields | This specification defines HPACK, a new compressor that eliminates | |||
which eliminates redundant header fields, limits vulnerability to | redundant header fields, limits vulnerability to known security | |||
known security attacks, and which has a bounded memory requirement | attacks, and has a bounded memory requirement for use in constrained | |||
for use in constrained environments. Potential security concerns for | environments. Potential security concerns for HPACK are described in | |||
HPACK are described in Section 7. | Section 7. | |||
The HPACK format is intentionally simple and inflexible. Both | The HPACK format is intentionally simple and inflexible. Both | |||
characteristics reduce the risk of interoperability or security | characteristics reduce the risk of interoperability or security | |||
issues due to implementation error. No extensibility mechanisms are | issues due to implementation error. No extensibility mechanisms are | |||
defined; changes to the format are only possible by defining a | defined; changes to the format are only possible by defining a | |||
complete replacement. | complete replacement. | |||
1.1. Overview | 1.1. Overview | |||
The format defined in this specification treats a list of header | The format defined in this specification treats a list of header | |||
skipping to change at page 5, line 47 ¶ | skipping to change at page 4, line 34 ¶ | |||
Encoding is informed by header field tables that map header fields to | Encoding is informed by header field tables that map header fields to | |||
indexed values. These header field tables can be incrementally | indexed values. These header field tables can be incrementally | |||
updated as new header fields are encoded or decoded. | updated as new header fields are encoded or decoded. | |||
In the encoded form, a header field is represented either literally | In the encoded form, a header field is represented either literally | |||
or as a reference to a header field in one of the header field | or as a reference to a header field in one of the header field | |||
tables. Therefore, a list of header fields can be encoded using a | tables. Therefore, a list of header fields can be encoded using a | |||
mixture of references and literal values. | mixture of references and literal values. | |||
Literal values are either encoded directly or using a static Huffman | Literal values are either encoded directly or use a static Huffman | |||
code. | code. | |||
The encoder is responsible for deciding which header fields to insert | The encoder is responsible for deciding which header fields to insert | |||
as new entries in the header field tables. The decoder executes the | as new entries in the header field tables. The decoder executes the | |||
modifications to the header field tables prescribed by the encoder, | modifications to the header field tables prescribed by the encoder, | |||
reconstructing the list of header fields in the process. This | reconstructing the list of header fields in the process. This | |||
enables decoders to remain simple and interoperate with a wide | enables decoders to remain simple and interoperate with a wide | |||
variety of encoders. | variety of encoders. | |||
Examples illustrating the use of these different mechanisms to | Examples illustrating the use of these different mechanisms to | |||
skipping to change at page 6, line 35 ¶ | skipping to change at page 5, line 23 ¶ | |||
Header Field: A name-value pair. Both the name and value are | Header Field: A name-value pair. Both the name and value are | |||
treated as opaque sequences of octets. | treated as opaque sequences of octets. | |||
Dynamic Table: The dynamic table (see Section 2.3.2) is a table that | Dynamic Table: The dynamic table (see Section 2.3.2) is a table that | |||
associates stored header fields with index values. This table is | associates stored header fields with index values. This table is | |||
dynamic and specific to an encoding or decoding context. | dynamic and specific to an encoding or decoding context. | |||
Static Table: The static table (see Section 2.3.1) is a table that | Static Table: The static table (see Section 2.3.1) is a table that | |||
statically associates header fields that occur frequently with | statically associates header fields that occur frequently with | |||
index values. This table is ordered, read-only, always | index values. This table is ordered, read-only, always | |||
accessible, and may be shared amongst all encoding or decoding | accessible, and it may be shared amongst all encoding or decoding | |||
contexts. | contexts. | |||
Header List: A header list is an ordered collection of header fields | Header List: A header list is an ordered collection of header fields | |||
that are encoded jointly, and can contain duplicate header fields. | that are encoded jointly and can contain duplicate header fields. | |||
A complete list of header fields contained in an HTTP/2 header | A complete list of header fields contained in an HTTP/2 header | |||
block is a header list. | block is a header list. | |||
Header Field Representation: A header field can be represented in | Header Field Representation: A header field can be represented in | |||
encoded form either as a literal or as an index (see Section 2.4). | encoded form either as a literal or as an index (see Section 2.4). | |||
Header Block: An ordered list of header field representations which, | Header Block: An ordered list of header field representations, | |||
when decoded, yields a complete header list. | which, when decoded, yields a complete header list. | |||
2. Compression Process Overview | 2. Compression Process Overview | |||
This specification does not describe a specific algorithm for an | This specification does not describe a specific algorithm for an | |||
encoder. Instead, it defines precisely how a decoder is expected to | encoder. Instead, it defines precisely how a decoder is expected to | |||
operate, allowing encoders to produce any encoding that this | operate, allowing encoders to produce any encoding that this | |||
definition permits. | definition permits. | |||
2.1. Header List Ordering | 2.1. Header List Ordering | |||
skipping to change at page 7, line 28 ¶ | skipping to change at page 6, line 13 ¶ | |||
to their ordering in the header block. | to their ordering in the header block. | |||
2.2. Encoding and Decoding Contexts | 2.2. Encoding and Decoding Contexts | |||
To decompress header blocks, a decoder only needs to maintain a | To decompress header blocks, a decoder only needs to maintain a | |||
dynamic table (see Section 2.3.2) as a decoding context. No other | dynamic table (see Section 2.3.2) as a decoding context. No other | |||
dynamic state is needed. | dynamic state is needed. | |||
When used for bidirectional communication, such as in HTTP, the | When used for bidirectional communication, such as in HTTP, the | |||
encoding and decoding dynamic tables maintained by an endpoint are | encoding and decoding dynamic tables maintained by an endpoint are | |||
completely independent. I.e., the request and response dynamic | completely independent, i.e., the request and response dynamic tables | |||
tables are separate. | are separate. | |||
2.3. Indexing Tables | 2.3. Indexing Tables | |||
HPACK uses two tables for associating header fields to indexes. The | HPACK uses two tables for associating header fields to indexes. The | |||
static table (see Section 2.3.1) is predefined and contains common | static table (see Section 2.3.1) is predefined and contains common | |||
header fields (most of them with an empty value). The dynamic table | header fields (most of them with an empty value). The dynamic table | |||
(see Section 2.3.2) is dynamic and can be used by the encoder to | (see Section 2.3.2) is dynamic and can be used by the encoder to | |||
index header fields repeated in the encoded header lists. | index header fields repeated in the encoded header lists. | |||
These two tables are combined into a single address space for | These two tables are combined into a single address space for | |||
skipping to change at page 10, line 11 ¶ | skipping to change at page 8, line 41 ¶ | |||
A header block is the concatenation of header field representations. | A header block is the concatenation of header field representations. | |||
The different possible header field representations are described in | The different possible header field representations are described in | |||
Section 6. | Section 6. | |||
Once a header field is decoded and added to the reconstructed header | Once a header field is decoded and added to the reconstructed header | |||
list, the header field cannot be removed. A header field added to | list, the header field cannot be removed. A header field added to | |||
the header list can be safely passed to the application. | the header list can be safely passed to the application. | |||
By passing the resulting header fields to the application, a decoder | By passing the resulting header fields to the application, a decoder | |||
can be implemented with minimal transitory memory commitment in | can be implemented with minimal transitory memory commitment in | |||
addition to the dynamic table. | addition to the memory required for the dynamic table. | |||
3.2. Header Field Representation Processing | 3.2. Header Field Representation Processing | |||
The processing of a header block to obtain a header list is defined | The processing of a header block to obtain a header list is defined | |||
in this section. To ensure that the decoding will successfully | in this section. To ensure that the decoding will successfully | |||
produce a header list, a decoder MUST obey the following rules. | produce a header list, a decoder MUST obey the following rules. | |||
All the header field representations contained in a header block are | All the header field representations contained in a header block are | |||
processed in the order in which they appear, as specified below. | processed in the order in which they appear, as specified below. | |||
Details on the formatting of the various header field | Details on the formatting of the various header field representations | |||
representations, and some additional processing instructions are | and some additional processing instructions are found in Section 6. | |||
found in Section 6. | ||||
An _indexed representation_ entails the following actions: | An _indexed representation_ entails the following actions: | |||
o The header field corresponding to the referenced entry in either | o The header field corresponding to the referenced entry in either | |||
the static table or dynamic table is appended to the decoded | the static table or dynamic table is appended to the decoded | |||
header list. | header list. | |||
A _literal representation_ that is _not added_ to the dynamic table | A _literal representation_ that is _not added_ to the dynamic table | |||
entails the following action: | entails the following action: | |||
skipping to change at page 11, line 10 ¶ | skipping to change at page 9, line 35 ¶ | |||
4. Dynamic Table Management | 4. Dynamic Table Management | |||
To limit the memory requirements on the decoder side, the dynamic | To limit the memory requirements on the decoder side, the dynamic | |||
table is constrained in size. | table is constrained in size. | |||
4.1. Calculating Table Size | 4.1. Calculating Table Size | |||
The size of the dynamic table is the sum of the size of its entries. | The size of the dynamic table is the sum of the size of its entries. | |||
The size of an entry is the sum of its name's length in octets (as | The size of an entry is the sum of its name's length in octets (as | |||
defined in Section 5.2), its value's length in octets, plus 32. | defined in Section 5.2), its value's length in octets, and 32. | |||
The size of an entry is calculated using the length of its name and | The size of an entry is calculated using the length of its name and | |||
value without any Huffman encoding applied. | value without any Huffman encoding applied. | |||
Note: The additional 32 octets account for an estimated overhead | Note: The additional 32 octets account for an estimated overhead | |||
associated with an entry. For example, an entry structure using | associated with an entry. For example, an entry structure using | |||
two 64-bit pointers to reference the name and the value of the | two 64-bit pointers to reference the name and the value of the | |||
entry, and two 64-bit integers for counting the number of | entry and two 64-bit integers for counting the number of | |||
references to the name and value would have 32 octets of overhead. | references to the name and value would have 32 octets of overhead. | |||
4.2. Maximum Table Size | 4.2. Maximum Table Size | |||
Protocols that use HPACK determine the maximum size that the encoder | Protocols that use HPACK determine the maximum size that the encoder | |||
is permitted to use for the dynamic table. In HTTP/2, this value is | is permitted to use for the dynamic table. In HTTP/2, this value is | |||
determined by the SETTINGS_HEADER_TABLE_SIZE setting (see Section | determined by the SETTINGS_HEADER_TABLE_SIZE setting (see | |||
6.5.2 of [HTTP2]). | Section 6.5.2 of [HTTP2]). | |||
An encoder can choose to use less capacity than this maximum size | An encoder can choose to use less capacity than this maximum size | |||
(see Section 6.3), but the chosen size MUST stay lower than or equal | (see Section 6.3), but the chosen size MUST stay lower than or equal | |||
to the maximum set by the protocol. | to the maximum set by the protocol. | |||
A change in the maximum size of the dynamic table is signaled via an | A change in the maximum size of the dynamic table is signaled via a | |||
encoding context update (see Section 6.3). This encoding context | dynamic table size update (see Section 6.3). This dynamic table size | |||
update MUST occur at the beginning of the first header block | update MUST occur at the beginning of the first header block | |||
following the change to the dynamic table size. In HTTP/2, this | following the change to the dynamic table size. In HTTP/2, this | |||
follows a settings acknowledgment (see Section 6.5.3 of [HTTP2]). | follows a settings acknowledgment (see Section 6.5.3 of [HTTP2]). | |||
Multiple updates to the maximum table size can occur between the | Multiple updates to the maximum table size can occur between the | |||
transmission of two header blocks. In the case that this size is | transmission of two header blocks. In the case that this size is | |||
changed more than once in this interval, the smallest maximum table | changed more than once in this interval, the smallest maximum table | |||
size that occurs in that interval MUST be signaled in an encoding | size that occurs in that interval MUST be signaled in a dynamic table | |||
context update. The final maximum size is always signaled, resulting | size update. The final maximum size is always signaled, resulting in | |||
in at most two encoding context updates. This ensures that the | at most two dynamic table size updates. This ensures that the | |||
decoder is able to perform eviction based on reductions in dynamic | decoder is able to perform eviction based on reductions in dynamic | |||
table size (see Section 4.3). | table size (see Section 4.3). | |||
This mechanism can be used to completely clear entries from the | This mechanism can be used to completely clear entries from the | |||
dynamic table by setting a maximum size of 0, which can subsequently | dynamic table by setting a maximum size of 0, which can subsequently | |||
be restored. | be restored. | |||
4.3. Entry Eviction when Dynamic Table Size Changes | 4.3. Entry Eviction When Dynamic Table Size Changes | |||
Whenever the maximum size for the dynamic table is reduced, entries | Whenever the maximum size for the dynamic table is reduced, entries | |||
are evicted from the end of the dynamic table until the size of the | are evicted from the end of the dynamic table until the size of the | |||
dynamic table is less than or equal to the maximum size. | dynamic table is less than or equal to the maximum size. | |||
4.4. Entry Eviction when Adding New Entries | 4.4. Entry Eviction When Adding New Entries | |||
Before a new entry is added to the dynamic table, entries are evicted | Before a new entry is added to the dynamic table, entries are evicted | |||
from the end of the dynamic table until the size of the dynamic table | from the end of the dynamic table until the size of the dynamic table | |||
is less than or equal to (maximum size - new entry size), or until | is less than or equal to (maximum size - new entry size) or until the | |||
the table is empty. | table is empty. | |||
If the size of the new entry is less than or equal to the maximum | If the size of the new entry is less than or equal to the maximum | |||
size, that entry is added to the table. It is not an error to | size, that entry is added to the table. It is not an error to | |||
attempt to add an entry that is larger than the maximum size; an | attempt to add an entry that is larger than the maximum size; an | |||
attempt to add an entry larger than the maximum size causes the table | attempt to add an entry larger than the maximum size causes the table | |||
to be emptied of all existing entries, and results in an empty table. | to be emptied of all existing entries and results in an empty table. | |||
A new entry can reference the name of an entry in the dynamic table | A new entry can reference the name of an entry in the dynamic table | |||
that will be evicted when adding this new entry into the dynamic | that will be evicted when adding this new entry into the dynamic | |||
table. Implementations are cautioned to avoid deleting the | table. Implementations are cautioned to avoid deleting the | |||
referenced name if the referenced entry is evicted from the dynamic | referenced name if the referenced entry is evicted from the dynamic | |||
table prior to inserting the new entry. | table prior to inserting the new entry. | |||
5. Primitive Type Representations | 5. Primitive Type Representations | |||
HPACK encoding uses two primitive types: unsigned variable length | HPACK encoding uses two primitive types: unsigned variable-length | |||
integers, and strings of octets. | integers and strings of octets. | |||
5.1. Integer Representation | 5.1. Integer Representation | |||
Integers are used to represent name indexes, header field indexes or | Integers are used to represent name indexes, header field indexes, or | |||
string lengths. An integer representation can start anywhere within | string lengths. An integer representation can start anywhere within | |||
an octet. To allow for optimized processing, an integer | an octet. To allow for optimized processing, an integer | |||
representation always finishes at the end of an octet. | representation always finishes at the end of an octet. | |||
An integer is represented in two parts: a prefix that fills the | An integer is represented in two parts: a prefix that fills the | |||
current octet and an optional list of octets that are used if the | current octet and an optional list of octets that are used if the | |||
integer value does not fit within the prefix. The number of bits of | integer value does not fit within the prefix. The number of bits of | |||
the prefix (called N) is a parameter of the integer representation. | the prefix (called N) is a parameter of the integer representation. | |||
If the integer value is small enough, i.e., strictly less than 2^N-1, | If the integer value is small enough, i.e., strictly less than 2^N-1, | |||
it is encoded within the N-bit prefix. | it is encoded within the N-bit prefix. | |||
0 1 2 3 4 5 6 7 | 0 1 2 3 4 5 6 7 | |||
+---+---+---+---+---+---+---+---+ | +---+---+---+---+---+---+---+---+ | |||
| ? | ? | ? | Value | | | ? | ? | ? | Value | | |||
+---+---+---+-------------------+ | +---+---+---+-------------------+ | |||
Figure 2: Integer Value Encoded within the Prefix (shown for N = 5) | Figure 2: Integer Value Encoded within the Prefix (Shown for N = 5) | |||
Otherwise, all the bits of the prefix are set to 1 and the value, | Otherwise, all the bits of the prefix are set to 1, and the value, | |||
decreased by 2^N-1, is encoded using a list of one or more octets. | decreased by 2^N-1, is encoded using a list of one or more octets. | |||
The most significant bit of each octet is used as a continuation | The most significant bit of each octet is used as a continuation | |||
flag: its value is set to 1 except for the last octet in the list. | flag: its value is set to 1 except for the last octet in the list. | |||
The remaining bits of the octets are used to encode the decreased | The remaining bits of the octets are used to encode the decreased | |||
value. | value. | |||
0 1 2 3 4 5 6 7 | 0 1 2 3 4 5 6 7 | |||
+---+---+---+---+---+---+---+---+ | +---+---+---+---+---+---+---+---+ | |||
| ? | ? | ? | 1 1 1 1 1 | | | ? | ? | ? | 1 1 1 1 1 | | |||
+---+---+---+-------------------+ | +---+---+---+-------------------+ | |||
| 1 | Value-(2^N-1) LSB | | | 1 | Value-(2^N-1) LSB | | |||
+---+---------------------------+ | +---+---------------------------+ | |||
... | ... | |||
+---+---------------------------+ | +---+---------------------------+ | |||
| 0 | Value-(2^N-1) MSB | | | 0 | Value-(2^N-1) MSB | | |||
+---+---------------------------+ | +---+---------------------------+ | |||
Figure 3: Integer Value Encoded after the Prefix (shown for N = 5) | Figure 3: Integer Value Encoded after the Prefix (Shown for N = 5) | |||
Decoding the integer value from the list of octets starts by | Decoding the integer value from the list of octets starts by | |||
reversing the order of the octets in the list. Then, for each octet, | reversing the order of the octets in the list. Then, for each octet, | |||
its most significant bit is removed. The remaining bits of the | its most significant bit is removed. The remaining bits of the | |||
octets are concatenated and the resulting value is increased by 2^N-1 | octets are concatenated, and the resulting value is increased by | |||
to obtain the integer value. | 2^N-1 to obtain the integer value. | |||
The prefix size, N, is always between 1 and 8 bits. An integer | The prefix size, N, is always between 1 and 8 bits. An integer | |||
starting at an octet-boundary will have an 8-bit prefix. | starting at an octet boundary will have an 8-bit prefix. | |||
Pseudo-code to represent an integer I is as follows: | Pseudocode to represent an integer I is as follows: | |||
if I < 2^N - 1, encode I on N bits | if I < 2^N - 1, encode I on N bits | |||
else | else | |||
encode (2^N - 1) on N bits | encode (2^N - 1) on N bits | |||
I = I - (2^N - 1) | I = I - (2^N - 1) | |||
while I >= 128 | while I >= 128 | |||
encode (I % 128 + 128) on 8 bits | encode (I % 128 + 128) on 8 bits | |||
I = I / 128 | I = I / 128 | |||
encode I on 8 bits | encode I on 8 bits | |||
Pseudo-code to decode an integer I is as follows: | Pseudocode to decode an integer I is as follows: | |||
decode I from the next N bits | decode I from the next N bits | |||
if I < 2^N - 1, return I | if I < 2^N - 1, return I | |||
else | else | |||
M = 0 | M = 0 | |||
repeat | repeat | |||
B = next octet | B = next octet | |||
I = I + (B & 127) * 2^M | I = I + (B & 127) * 2^M | |||
M = M + 7 | M = M + 7 | |||
while B & 128 == 128 | while B & 128 == 128 | |||
return I | return I | |||
Examples illustrating the encoding of integers are available in | Examples illustrating the encoding of integers are available in | |||
Appendix C.1. | Appendix C.1. | |||
This integer representation allows for values of indefinite size. It | This integer representation allows for values of indefinite size. It | |||
is also possible for an encoder to send a large number of zero | is also possible for an encoder to send a large number of zero | |||
values, which can waste octets and could be used to overflow integer | values, which can waste octets and could be used to overflow integer | |||
values. Integer encodings that exceed an implementation limits - in | values. Integer encodings that exceed implementation limits -- in | |||
value or octet length - MUST be treated as a decoding error. | value or octet length -- MUST be treated as decoding errors. | |||
Different limits can be set for each of the different uses of | Different limits can be set for each of the different uses of | |||
integers, based on implementation constraints. | integers, based on implementation constraints. | |||
5.2. String Literal Representation | 5.2. String Literal Representation | |||
Header field names and header field values can be represented as | Header field names and header field values can be represented as | |||
literal strings. A literal string is encoded as a sequence of | string literals. A string literal is encoded as a sequence of | |||
octets, either by directly encoding the literal string's octets, or | octets, either by directly encoding the string literal's octets or by | |||
by using a Huffman code (see [HUFFMAN]). | using a Huffman code (see [HUFFMAN]). | |||
0 1 2 3 4 5 6 7 | 0 1 2 3 4 5 6 7 | |||
+---+---+---+---+---+---+---+---+ | +---+---+---+---+---+---+---+---+ | |||
| H | String Length (7+) | | | H | String Length (7+) | | |||
+---+---------------------------+ | +---+---------------------------+ | |||
| String Data (Length octets) | | | String Data (Length octets) | | |||
+-------------------------------+ | +-------------------------------+ | |||
Figure 4: String Literal Representation | Figure 4: String Literal Representation | |||
A literal string representation contains the following fields: | A string literal representation contains the following fields: | |||
H: A one bit flag, H, indicating whether or not the octets of the | H: A one-bit flag, H, indicating whether or not the octets of the | |||
string are Huffman encoded. | string are Huffman encoded. | |||
String Length: The number of octets used to encode the string | String Length: The number of octets used to encode the string | |||
literal, encoded as an integer with 7-bit prefix (see | literal, encoded as an integer with a 7-bit prefix (see | |||
Section 5.1). | Section 5.1). | |||
String Data: The encoded data of the string literal. If H is '0', | String Data: The encoded data of the string literal. If H is '0', | |||
then the encoded data is the raw octets of the string literal. If | then the encoded data is the raw octets of the string literal. If | |||
H is '1', then the encoded data is the Huffman encoding of the | H is '1', then the encoded data is the Huffman encoding of the | |||
string literal. | string literal. | |||
String literals which use Huffman encoding are encoded with the | String literals that use Huffman encoding are encoded with the | |||
Huffman code defined in Appendix B (see examples for requests in | Huffman code defined in Appendix B (see examples for requests in | |||
Appendix C.4 and for responses in Appendix C.6). The encoded data is | Appendix C.4 and for responses in Appendix C.6). The encoded data is | |||
the bitwise concatenation of the codes corresponding to each octet of | the bitwise concatenation of the codes corresponding to each octet of | |||
the string literal. | the string literal. | |||
As the Huffman encoded data doesn't always end at an octet boundary, | As the Huffman-encoded data doesn't always end at an octet boundary, | |||
some padding is inserted after it, up to the next octet boundary. To | some padding is inserted after it, up to the next octet boundary. To | |||
prevent this padding to be misinterpreted as part of the string | prevent this padding from being misinterpreted as part of the string | |||
literal, the most significant bits of the code corresponding to the | literal, the most significant bits of the code corresponding to the | |||
EOS (end-of-string) symbol are used. | EOS (end-of-string) symbol are used. | |||
Upon decoding, an incomplete code at the end of the encoded data is | Upon decoding, an incomplete code at the end of the encoded data is | |||
to be considered as padding and discarded. A padding strictly longer | to be considered as padding and discarded. A padding strictly longer | |||
than 7 bits MUST be treated as a decoding error. A padding not | than 7 bits MUST be treated as a decoding error. A padding not | |||
corresponding to the most significant bits of the code for the EOS | corresponding to the most significant bits of the code for the EOS | |||
symbol MUST be treated as a decoding error. A Huffman encoded string | symbol MUST be treated as a decoding error. A Huffman-encoded string | |||
literal containing the EOS symbol MUST be treated as a decoding | literal containing the EOS symbol MUST be treated as a decoding | |||
error. | error. | |||
6. Binary Format | 6. Binary Format | |||
This section describes the detailed format of each of the different | This section describes the detailed format of each of the different | |||
header field representations, plus the encoding context update | header field representations and the dynamic table size update | |||
instruction. | instruction. | |||
6.1. Indexed Header Field Representation | 6.1. Indexed Header Field Representation | |||
An indexed header field representation identifies an entry in either | An indexed header field representation identifies an entry in either | |||
the static table or the dynamic table (see Section 2.3). | the static table or the dynamic table (see Section 2.3). | |||
An indexed header field representation causes a header field to be | An indexed header field representation causes a header field to be | |||
added to the decoded header list, as described in Section 3.2. | added to the decoded header list, as described in Section 3.2. | |||
skipping to change at page 16, line 4 ¶ | skipping to change at page 14, line 25 ¶ | |||
An indexed header field representation identifies an entry in either | An indexed header field representation identifies an entry in either | |||
the static table or the dynamic table (see Section 2.3). | the static table or the dynamic table (see Section 2.3). | |||
An indexed header field representation causes a header field to be | An indexed header field representation causes a header field to be | |||
added to the decoded header list, as described in Section 3.2. | added to the decoded header list, as described in Section 3.2. | |||
0 1 2 3 4 5 6 7 | 0 1 2 3 4 5 6 7 | |||
+---+---+---+---+---+---+---+---+ | +---+---+---+---+---+---+---+---+ | |||
| 1 | Index (7+) | | | 1 | Index (7+) | | |||
+---+---------------------------+ | +---+---------------------------+ | |||
Figure 5: Indexed Header Field | Figure 5: Indexed Header Field | |||
An indexed header field starts with the '1' 1-bit pattern, followed | An indexed header field starts with the '1' 1-bit pattern, followed | |||
by the index of the matching header field, represented as an integer | by the index of the matching header field, represented as an integer | |||
with a 7-bit prefix (see Section 5.1). | with a 7-bit prefix (see Section 5.1). | |||
The index value of 0 is not used. It MUST be treated as a decoding | The index value of 0 is not used. It MUST be treated as a decoding | |||
error if found in an indexed header field representation. | error if found in an indexed header field representation. | |||
6.2. Literal Header Field Representation | 6.2. Literal Header Field Representation | |||
A literal header field representation contains a literal header field | A literal header field representation contains a literal header field | |||
value. Header field names are either provided as a literal or by | value. Header field names are provided either as a literal or by | |||
reference to an existing table entry, either from the static table or | reference to an existing table entry, either from the static table or | |||
the dynamic table (see Section 2.3). | the dynamic table (see Section 2.3). | |||
This specification defines three forms of literal header field | This specification defines three forms of literal header field | |||
representations; with indexing, without indexing, and never indexed. | representations: with indexing, without indexing, and never indexed. | |||
6.2.1. Literal Header Field with Incremental Indexing | 6.2.1. Literal Header Field with Incremental Indexing | |||
A literal header field with incremental indexing representation | A literal header field with incremental indexing representation | |||
results in appending a header field to the decoded header list and | results in appending a header field to the decoded header list and | |||
inserting it as a new entry into the dynamic table. | inserting it as a new entry into the dynamic table. | |||
0 1 2 3 4 5 6 7 | 0 1 2 3 4 5 6 7 | |||
+---+---+---+---+---+---+---+---+ | +---+---+---+---+---+---+---+---+ | |||
| 0 | 1 | Index (6+) | | | 0 | 1 | Index (6+) | | |||
+---+---+-----------------------+ | +---+---+-----------------------+ | |||
| H | Value Length (7+) | | | H | Value Length (7+) | | |||
+---+---------------------------+ | +---+---------------------------+ | |||
| Value String (Length octets) | | | Value String (Length octets) | | |||
+-------------------------------+ | +-------------------------------+ | |||
Figure 6: Literal Header Field with Incremental Indexing - Indexed | Figure 6: Literal Header Field with Incremental Indexing -- Indexed | |||
Name | Name | |||
0 1 2 3 4 5 6 7 | 0 1 2 3 4 5 6 7 | |||
+---+---+---+---+---+---+---+---+ | +---+---+---+---+---+---+---+---+ | |||
| 0 | 1 | 0 | | | 0 | 1 | 0 | | |||
+---+---+-----------------------+ | +---+---+-----------------------+ | |||
| H | Name Length (7+) | | | H | Name Length (7+) | | |||
+---+---------------------------+ | +---+---------------------------+ | |||
| Name String (Length octets) | | | Name String (Length octets) | | |||
+---+---------------------------+ | +---+---------------------------+ | |||
| H | Value Length (7+) | | | H | Value Length (7+) | | |||
+---+---------------------------+ | +---+---------------------------+ | |||
| Value String (Length octets) | | | Value String (Length octets) | | |||
+-------------------------------+ | +-------------------------------+ | |||
Figure 7: Literal Header Field with Incremental Indexing - New Name | Figure 7: Literal Header Field with Incremental Indexing -- New Name | |||
A literal header field with incremental indexing representation | A literal header field with incremental indexing representation | |||
starts with the '01' 2-bit pattern. | starts with the '01' 2-bit pattern. | |||
If the header field name matches the header field name of an entry | If the header field name matches the header field name of an entry | |||
stored in the static table or the dynamic table, the header field | stored in the static table or the dynamic table, the header field | |||
name can be represented using the index of that entry. In this case, | name can be represented using the index of that entry. In this case, | |||
the index of the entry is represented as an integer with a 6-bit | the index of the entry is represented as an integer with a 6-bit | |||
prefix (see Section 5.1). This value is always non-zero. | prefix (see Section 5.1). This value is always non-zero. | |||
Otherwise, the header field name is represented as a literal string | Otherwise, the header field name is represented as a string literal | |||
(see Section 5.2). A value 0 is used in place of the 6-bit index, | (see Section 5.2). A value 0 is used in place of the 6-bit index, | |||
followed by the header field name. | followed by the header field name. | |||
Either form of header field name representation is followed by the | Either form of header field name representation is followed by the | |||
header field value represented as a literal string (see Section 5.2). | header field value represented as a string literal (see Section 5.2). | |||
6.2.2. Literal Header Field without Indexing | 6.2.2. Literal Header Field without Indexing | |||
A literal header field without indexing representation results in | A literal header field without indexing representation results in | |||
appending a header field to the decoded header list without altering | appending a header field to the decoded header list without altering | |||
the dynamic table. | the dynamic table. | |||
0 1 2 3 4 5 6 7 | 0 1 2 3 4 5 6 7 | |||
+---+---+---+---+---+---+---+---+ | +---+---+---+---+---+---+---+---+ | |||
| 0 | 0 | 0 | 0 | Index (4+) | | | 0 | 0 | 0 | 0 | Index (4+) | | |||
+---+---+-----------------------+ | +---+---+-----------------------+ | |||
| H | Value Length (7+) | | | H | Value Length (7+) | | |||
+---+---------------------------+ | +---+---------------------------+ | |||
| Value String (Length octets) | | | Value String (Length octets) | | |||
+-------------------------------+ | +-------------------------------+ | |||
Figure 8: Literal Header Field without Indexing - Indexed Name | Figure 8: Literal Header Field without Indexing -- Indexed Name | |||
0 1 2 3 4 5 6 7 | 0 1 2 3 4 5 6 7 | |||
+---+---+---+---+---+---+---+---+ | +---+---+---+---+---+---+---+---+ | |||
| 0 | 0 | 0 | 0 | 0 | | | 0 | 0 | 0 | 0 | 0 | | |||
+---+---+-----------------------+ | +---+---+-----------------------+ | |||
| H | Name Length (7+) | | | H | Name Length (7+) | | |||
+---+---------------------------+ | +---+---------------------------+ | |||
| Name String (Length octets) | | | Name String (Length octets) | | |||
+---+---------------------------+ | +---+---------------------------+ | |||
| H | Value Length (7+) | | | H | Value Length (7+) | | |||
+---+---------------------------+ | +---+---------------------------+ | |||
| Value String (Length octets) | | | Value String (Length octets) | | |||
+-------------------------------+ | +-------------------------------+ | |||
Figure 9: Literal Header Field without Indexing - New Name | Figure 9: Literal Header Field without Indexing -- New Name | |||
A literal header field without indexing representation starts with | A literal header field without indexing representation starts with | |||
the '0000' 4-bit pattern. | the '0000' 4-bit pattern. | |||
If the header field name matches the header field name of an entry | If the header field name matches the header field name of an entry | |||
stored in the static table or the dynamic table, the header field | stored in the static table or the dynamic table, the header field | |||
name can be represented using the index of that entry. In this case, | name can be represented using the index of that entry. In this case, | |||
the index of the entry is represented as an integer with a 4-bit | the index of the entry is represented as an integer with a 4-bit | |||
prefix (see Section 5.1). This value is always non-zero. | prefix (see Section 5.1). This value is always non-zero. | |||
Otherwise, the header field name is represented as a literal string | Otherwise, the header field name is represented as a string literal | |||
(see Section 5.2). A value 0 is used in place of the 4-bit index, | (see Section 5.2). A value 0 is used in place of the 4-bit index, | |||
followed by the header field name. | followed by the header field name. | |||
Either form of header field name representation is followed by the | Either form of header field name representation is followed by the | |||
header field value represented as a literal string (see Section 5.2). | header field value represented as a string literal (see Section 5.2). | |||
6.2.3. Literal Header Field never Indexed | 6.2.3. Literal Header Field Never Indexed | |||
A literal header field never indexed representation results in | A literal header field never-indexed representation results in | |||
appending a header field to the decoded header list without altering | appending a header field to the decoded header list without altering | |||
the dynamic table. Intermediaries MUST use the same representation | the dynamic table. Intermediaries MUST use the same representation | |||
for encoding this header field. | for encoding this header field. | |||
0 1 2 3 4 5 6 7 | 0 1 2 3 4 5 6 7 | |||
+---+---+---+---+---+---+---+---+ | +---+---+---+---+---+---+---+---+ | |||
| 0 | 0 | 0 | 1 | Index (4+) | | | 0 | 0 | 0 | 1 | Index (4+) | | |||
+---+---+-----------------------+ | +---+---+-----------------------+ | |||
| H | Value Length (7+) | | | H | Value Length (7+) | | |||
+---+---------------------------+ | +---+---------------------------+ | |||
| Value String (Length octets) | | | Value String (Length octets) | | |||
+-------------------------------+ | +-------------------------------+ | |||
Figure 10: Literal Header Field never Indexed - Indexed Name | Figure 10: Literal Header Field Never Indexed -- Indexed Name | |||
0 1 2 3 4 5 6 7 | 0 1 2 3 4 5 6 7 | |||
+---+---+---+---+---+---+---+---+ | +---+---+---+---+---+---+---+---+ | |||
| 0 | 0 | 0 | 1 | 0 | | | 0 | 0 | 0 | 1 | 0 | | |||
+---+---+-----------------------+ | +---+---+-----------------------+ | |||
| H | Name Length (7+) | | | H | Name Length (7+) | | |||
+---+---------------------------+ | +---+---------------------------+ | |||
| Name String (Length octets) | | | Name String (Length octets) | | |||
+---+---------------------------+ | +---+---------------------------+ | |||
| H | Value Length (7+) | | | H | Value Length (7+) | | |||
+---+---------------------------+ | +---+---------------------------+ | |||
| Value String (Length octets) | | | Value String (Length octets) | | |||
+-------------------------------+ | +-------------------------------+ | |||
Figure 11: Literal Header Field never Indexed - New Name | Figure 11: Literal Header Field Never Indexed -- New Name | |||
A literal header field never indexed representation starts with the | A literal header field never-indexed representation starts with the | |||
'0001' 4-bit pattern. | '0001' 4-bit pattern. | |||
When a header field is represented as a literal header field never | When a header field is represented as a literal header field never | |||
indexed, it MUST always be encoded with this specific literal | indexed, it MUST always be encoded with this specific literal | |||
representation. In particular, when a peer sends a header field that | representation. In particular, when a peer sends a header field that | |||
it received represented as a literal header field never indexed, it | it received represented as a literal header field never indexed, it | |||
MUST use the same representation to forward this header field. | MUST use the same representation to forward this header field. | |||
This representation is intended for protecting header field values | This representation is intended for protecting header field values | |||
that are not to be put at risk by compressing them (see Section 7.1 | that are not to be put at risk by compressing them (see Section 7.1 | |||
skipping to change at page 19, line 52 ¶ | skipping to change at page 18, line 16 ¶ | |||
+---+---+---+---+---+---+---+---+ | +---+---+---+---+---+---+---+---+ | |||
| 0 | 0 | 1 | Max size (5+) | | | 0 | 0 | 1 | Max size (5+) | | |||
+---+---------------------------+ | +---+---------------------------+ | |||
Figure 12: Maximum Dynamic Table Size Change | Figure 12: Maximum Dynamic Table Size Change | |||
A dynamic table size update starts with the '001' 3-bit pattern, | A dynamic table size update starts with the '001' 3-bit pattern, | |||
followed by the new maximum size, represented as an integer with a | followed by the new maximum size, represented as an integer with a | |||
5-bit prefix (see Section 5.1). | 5-bit prefix (see Section 5.1). | |||
The new maximum size MUST be lower than or equal to the last value of | The new maximum size MUST be lower than or equal to the limit | |||
the maximum size of the dynamic table. A value that exceeds this | determined by the protocol using HPACK. A value that exceeds this | |||
limit MUST be treated as a decoding error. In HTTP/2, this limit is | limit MUST be treated as a decoding error. In HTTP/2, this limit is | |||
the last value of the SETTINGS_HEADER_TABLE_SIZE parameter (see | the last value of the SETTINGS_HEADER_TABLE_SIZE parameter (see | |||
Section 6.5.2 of [HTTP2]) received from the decoder and acknowledged | Section 6.5.2 of [HTTP2]) received from the decoder and acknowledged | |||
by the encoder (see Section 6.5.3 of [HTTP2]). | by the encoder (see Section 6.5.3 of [HTTP2]). | |||
Reducing the maximum size of the dynamic table can cause entries to | Reducing the maximum size of the dynamic table can cause entries to | |||
be evicted (see Section 4.3). | be evicted (see Section 4.3). | |||
7. Security Considerations | 7. Security Considerations | |||
skipping to change at page 20, line 40 ¶ | skipping to change at page 19, line 5 ¶ | |||
requests or responses. | requests or responses. | |||
The compression context used to encode header fields can be probed by | The compression context used to encode header fields can be probed by | |||
an attacker who can both define header fields to be encoded and | an attacker who can both define header fields to be encoded and | |||
transmitted and observe the length of those fields once they are | transmitted and observe the length of those fields once they are | |||
encoded. When an attacker can do both, they can adaptively modify | encoded. When an attacker can do both, they can adaptively modify | |||
requests in order to confirm guesses about the dynamic table state. | requests in order to confirm guesses about the dynamic table state. | |||
If a guess is compressed into a shorter length, the attacker can | If a guess is compressed into a shorter length, the attacker can | |||
observe the encoded length and infer that the guess was correct. | observe the encoded length and infer that the guess was correct. | |||
This is possible even over the Transport Layer Security Protocol | This is possible even over the Transport Layer Security (TLS) | |||
(TLS, see [TLS12]), because while TLS provides confidentiality | protocol (see [TLS12]), because while TLS provides confidentiality | |||
protection for content, it only provides a limited amount of | protection for content, it only provides a limited amount of | |||
protection for the length of that content. | protection for the length of that content. | |||
Note: Padding schemes only provide limited protection against an | Note: Padding schemes only provide limited protection against an | |||
attacker with these capabilities, potentially only forcing an | attacker with these capabilities, potentially only forcing an | |||
increased number of guesses to learn the length associated with a | increased number of guesses to learn the length associated with a | |||
given guess. Padding schemes also work directly against | given guess. Padding schemes also work directly against | |||
compression by increasing the number of bits that are transmitted. | compression by increasing the number of bits that are transmitted. | |||
Attacks like CRIME [CRIME] demonstrated the existence of these | Attacks like CRIME [CRIME] demonstrated the existence of these | |||
general attacker capabilities. The specific attack exploited the | general attacker capabilities. The specific attack exploited the | |||
fact that DEFLATE [DEFLATE] removes redundancy based on prefix | fact that DEFLATE [DEFLATE] removes redundancy based on prefix | |||
matching. This permitted the attacker to confirm guesses a character | matching. This permitted the attacker to confirm guesses a character | |||
at a time, reducing an exponential-time attack into a linear-time | at a time, reducing an exponential-time attack into a linear-time | |||
attack. | attack. | |||
7.1.1. Applicability to HPACK and HTTP | 7.1.1. Applicability to HPACK and HTTP | |||
HPACK mitigates but does not completely prevent attacks modeled on | HPACK mitigates but does not completely prevent attacks modeled on | |||
CRIME [CRIME] by forcing a guess to match an entire header field | CRIME [CRIME] by forcing a guess to match an entire header field | |||
value, rather than individual characters. An attacker can only learn | value rather than individual characters. Attackers can only learn | |||
whether a guess is correct or not, so is reduced to a brute force | whether a guess is correct or not, so they are reduced to brute-force | |||
guess for the header field values. | guesses for the header field values. | |||
The viability of recovering specific header field values therefore | The viability of recovering specific header field values therefore | |||
depends on the entropy of values. As a result, values with high | depends on the entropy of values. As a result, values with high | |||
entropy are unlikely to be recovered successfully. However, values | entropy are unlikely to be recovered successfully. However, values | |||
with low entropy remain vulnerable. | with low entropy remain vulnerable. | |||
Attacks of this nature are possible any time that two mutually | Attacks of this nature are possible any time that two mutually | |||
distrustful entities control requests or responses that are placed | distrustful entities control requests or responses that are placed | |||
onto a single HTTP/2 connection. If the shared HPACK compressor | onto a single HTTP/2 connection. If the shared HPACK compressor | |||
permits one entity to add entries to the dynamic table, and the other | permits one entity to add entries to the dynamic table and the other | |||
to access those entries, then the state of the table can be learned. | to access those entries, then the state of the table can be learned. | |||
Having requests or responses from mutually distrustful entities | Having requests or responses from mutually distrustful entities | |||
occurs when an intermediary either: | occurs when an intermediary either: | |||
o sends requests from multiple clients on a single connection toward | o sends requests from multiple clients on a single connection toward | |||
an origin server, or | an origin server, or | |||
o takes responses from multiple origin servers and places them on a | o takes responses from multiple origin servers and places them on a | |||
shared connection toward a client. | shared connection toward a client. | |||
skipping to change at page 22, line 19 ¶ | skipping to change at page 20, line 34 ¶ | |||
entity that created a particular value can extract that value. | entity that created a particular value can extract that value. | |||
To improve compression performance of this option, certain entries | To improve compression performance of this option, certain entries | |||
might be tagged as being public. For example, a web browser might | might be tagged as being public. For example, a web browser might | |||
make the values of the Accept-Encoding header field available in all | make the values of the Accept-Encoding header field available in all | |||
requests. | requests. | |||
An encoder without good knowledge of the provenance of header fields | An encoder without good knowledge of the provenance of header fields | |||
might instead introduce a penalty for a header field with many | might instead introduce a penalty for a header field with many | |||
different values, such that a large number of attempts to guess a | different values, such that a large number of attempts to guess a | |||
header field value results in the header field no more being compared | header field value results in the header field no longer being | |||
to the dynamic table entries in future messages, effectively | compared to the dynamic table entries in future messages, effectively | |||
preventing further guesses. | preventing further guesses. | |||
Note: Simply removing entries corresponding to the header field from | Note: Simply removing entries corresponding to the header field | |||
the dynamic table can be ineffectual if the attacker has a | from the dynamic table can be ineffectual if the attacker has a | |||
reliable way of causing values to be reinstalled. For example, a | reliable way of causing values to be reinstalled. For example, a | |||
request to load an image in a web browser typically includes the | request to load an image in a web browser typically includes the | |||
Cookie header field (a potentially highly valued target for this | Cookie header field (a potentially highly valued target for this | |||
sort of attack), and web sites can easily force an image to be | sort of attack), and web sites can easily force an image to be | |||
loaded, thereby refreshing the entry in the dynamic table. | loaded, thereby refreshing the entry in the dynamic table. | |||
This response might be made inversely proportional to the length of | This response might be made inversely proportional to the length of | |||
the header field value. Marking a header field as not using the | the header field value. Marking a header field as not using the | |||
dynamic table any more might occur for shorter values more quickly or | dynamic table anymore might occur for shorter values more quickly or | |||
with higher probability than for longer values. | with higher probability than for longer values. | |||
7.1.3. Never Indexed Literals | 7.1.3. Never-Indexed Literals | |||
Implementations can also choose to protect sensitive header fields by | Implementations can also choose to protect sensitive header fields by | |||
not compressing them and instead encoding their value as literals. | not compressing them and instead encoding their value as literals. | |||
Refusing to generate an indexed representation for a header field is | Refusing to generate an indexed representation for a header field is | |||
only effective if compression is avoided on all hops. The never | only effective if compression is avoided on all hops. The never- | |||
indexed literal (see Section 6.2.3) can be used to signal to | indexed literal (see Section 6.2.3) can be used to signal to | |||
intermediaries that a particular value was intentionally sent as a | intermediaries that a particular value was intentionally sent as a | |||
literal. | literal. | |||
An intermediary MUST NOT re-encode a value that uses the never | An intermediary MUST NOT re-encode a value that uses the never- | |||
indexed literal representation with another representation that would | indexed literal representation with another representation that would | |||
index it. If HPACK is used for re-encoding, the never indexed | index it. If HPACK is used for re-encoding, the never-indexed | |||
literal representation MUST be used. | literal representation MUST be used. | |||
The choice to use a never indexed literal representation for a header | The choice to use a never-indexed literal representation for a header | |||
field depends on several factors. Since HPACK doesn't protect | field depends on several factors. Since HPACK doesn't protect | |||
against guessing an entire header field value, short or low-entropy | against guessing an entire header field value, short or low-entropy | |||
values are more readily recovered by an adversary. Therefore, an | values are more readily recovered by an adversary. Therefore, an | |||
encoder might choose not to index values with low entropy. | encoder might choose not to index values with low entropy. | |||
An encoder might also choose not to index values for header fields | An encoder might also choose not to index values for header fields | |||
that are considered to be highly valuable or sensitive to recovery, | that are considered to be highly valuable or sensitive to recovery, | |||
such as the Cookie or Authorization header fields. | such as the Cookie or Authorization header fields. | |||
On the contrary, an encoder might prefer indexing values for header | On the contrary, an encoder might prefer indexing values for header | |||
fields that have little or no value if they were exposed. For | fields that have little or no value if they were exposed. For | |||
instance, a User-Agent header field does not commonly vary between | instance, a User-Agent header field does not commonly vary between | |||
requests and is sent to any server. In that case, confirmation that | requests and is sent to any server. In that case, confirmation that | |||
a particular User-Agent value has been used provides little value. | a particular User-Agent value has been used provides little value. | |||
Note that these criteria for deciding to use a never indexed literal | Note that these criteria for deciding to use a never-indexed literal | |||
representation will evolve over time as new attacks are discovered. | representation will evolve over time as new attacks are discovered. | |||
7.2. Static Huffman Encoding | 7.2. Static Huffman Encoding | |||
There is no currently known attack against a static Huffman encoding. | There is no currently known attack against a static Huffman encoding. | |||
A study has shown that using a static Huffman encoding table created | A study has shown that using a static Huffman encoding table created | |||
an information leakage, however this same study concluded that an | an information leakage; however, this same study concluded that an | |||
attacker could not take advantage of this information leakage to | attacker could not take advantage of this information leakage to | |||
recover any meaningful amount of information (see [PETAL]). | recover any meaningful amount of information (see [PETAL]). | |||
7.3. Memory Consumption | 7.3. Memory Consumption | |||
An attacker can try to cause an endpoint to exhaust its memory. | An attacker can try to cause an endpoint to exhaust its memory. | |||
HPACK is designed to limit both the peak and state amounts of memory | HPACK is designed to limit both the peak and state amounts of memory | |||
allocated by an endpoint. | allocated by an endpoint. | |||
The amount of memory used by the compressor is limited by the | The amount of memory used by the compressor is limited by the | |||
skipping to change at page 23, line 50 ¶ | skipping to change at page 22, line 17 ¶ | |||
the dynamic table. In HTTP/2, this value is controlled by the | the dynamic table. In HTTP/2, this value is controlled by the | |||
decoder through the setting parameter SETTINGS_HEADER_TABLE_SIZE (see | decoder through the setting parameter SETTINGS_HEADER_TABLE_SIZE (see | |||
Section 6.5.2 of [HTTP2]). This limit takes into account both the | Section 6.5.2 of [HTTP2]). This limit takes into account both the | |||
size of the data stored in the dynamic table, plus a small allowance | size of the data stored in the dynamic table, plus a small allowance | |||
for overhead. | for overhead. | |||
A decoder can limit the amount of state memory used by setting an | A decoder can limit the amount of state memory used by setting an | |||
appropriate value for the maximum size of the dynamic table. In | appropriate value for the maximum size of the dynamic table. In | |||
HTTP/2, this is realized by setting an appropriate value for the | HTTP/2, this is realized by setting an appropriate value for the | |||
SETTINGS_HEADER_TABLE_SIZE parameter. An encoder can limit the | SETTINGS_HEADER_TABLE_SIZE parameter. An encoder can limit the | |||
amount of state memory it uses by signaling lower dynamic table size | amount of state memory it uses by signaling a lower dynamic table | |||
than the decoder allows (see Section 6.3). | size than the decoder allows (see Section 6.3). | |||
The amount of temporary memory consumed by an encoder or decoder can | The amount of temporary memory consumed by an encoder or decoder can | |||
be limited by processing header fields sequentially. An | be limited by processing header fields sequentially. An | |||
implementation does not need to retain a complete list of header | implementation does not need to retain a complete list of header | |||
fields. Note however that it might be necessary for an application | fields. Note, however, that it might be necessary for an application | |||
to retain a complete header list for other reasons; even though HPACK | to retain a complete header list for other reasons; even though HPACK | |||
does not force this to occur, application constraints might make this | does not force this to occur, application constraints might make this | |||
necessary. | necessary. | |||
7.4. Implementation Limits | 7.4. Implementation Limits | |||
An implementation of HPACK needs to ensure that large values for | An implementation of HPACK needs to ensure that large values for | |||
integers, long encoding for integers, or long string literals do not | integers, long encoding for integers, or long string literals do not | |||
create security weaknesses. | create security weaknesses. | |||
An implementation has to set a limit for the values it accepts for | An implementation has to set a limit for the values it accepts for | |||
integers, as well as for the encoded length (see Section 5.1). In | integers, as well as for the encoded length (see Section 5.1). In | |||
the same way, it has to set a limit to the length it accepts for | the same way, it has to set a limit to the length it accepts for | |||
string literals (see Section 5.2). | string literals (see Section 5.2). | |||
8. IANA Considerations | 8. References | |||
This document has no IANA actions. | ||||
9. Acknowledgments | ||||
This specification includes substantial input from the following | ||||
individuals: | ||||
o Mike Bishop, Jeff Pinner, Julian Reschke, Martin Thomson | ||||
(substantial editorial contributions). | ||||
o Johnny Graettinger (Huffman code statistics). | ||||
10. References | ||||
10.1. Normative References | 8.1. Normative References | |||
[HTTP2] Belshe, M., Peon, R., and M. Thomson, Ed., "Hypertext | [HTTP2] Belshe, M., Peon, R., and M. Thomson, Ed., "Hypertext | |||
Transfer Protocol version 2", | Transfer Protocol Version 2 (HTTP/2)", RFC 7540, | |||
draft-ietf-httpbis-http2-17 (work in progress), | DOI 10.17487/RFC7540, May 2015, | |||
February 2015. | <https://www.rfc-editor.org/info/rfc7540>. | |||
[RFC2119] Bradner, S., "Key words for use in RFCs to Indicate | [RFC2119] Bradner, S., "Key words for use in RFCs to Indicate | |||
Requirement Levels", BCP 14, RFC 2119, March 1997. | Requirement Levels", BCP 14, RFC 2119, | |||
DOI 10.17487/RFC2119, March 1997, | ||||
<https://www.rfc-editor.org/info/rfc2119>. | ||||
[RFC7230] Fielding, R., Ed. and J. Reschke, Ed., "Hypertext | [RFC7230] Fielding, R., Ed. and J. Reschke, Ed., "Hypertext Transfer | |||
Transfer Protocol (HTTP/1.1): Message Syntax and | Protocol (HTTP/1.1): Message Syntax and Routing", | |||
Routing", RFC 7230, June 2014. | RFC 7230, DOI 10.17487/RFC7230, June 2014, | |||
<https://www.rfc-editor.org/info/rfc7230>. | ||||
10.2. Informative References | 8.2. Informative References | |||
[CANONICAL] Schwartz, E. and B. Kallick, "Generating a canonical | [CANONICAL] | |||
prefix encoding", Communications of the ACM Volume 7 | Schwartz, E. and B. Kallick, "Generating a canonical | |||
Issue 3, pp. 166-169, March 1964, | prefix encoding", Communications of the ACM, Volume 7 | |||
<https://dl.acm.org/citation.cfm?id=363991>. | Issue 3, pp. 166-169, March 1964, | |||
<https://dl.acm.org/citation.cfm?id=363991>. | ||||
[CRIME] Rizzo, J. and T. Duong, "The CRIME Attack", | [CRIME] Wikipedia, "CRIME", May 2015, <http://en.wikipedia.org/w/ | |||
September 2012, <https://docs.google.com/a/twist.com/ | index.php?title=CRIME&oldid=660948120>. | |||
presentation/d/ | ||||
11eBmGiHbYcHR9gL5nDyZChu_-lCa2GizeuOfaLU2HOU>. | ||||
[DEFLATE] Deutsch, P., "DEFLATE Compressed Data Format | [DEFLATE] Deutsch, P., "DEFLATE Compressed Data Format Specification | |||
Specification version 1.3", RFC 1951, May 1996. | version 1.3", RFC 1951, DOI 10.17487/RFC1951, May 1996, | |||
<https://www.rfc-editor.org/info/rfc1951>. | ||||
[HUFFMAN] Huffman, D., "A Method for the Construction of Minimum | [HUFFMAN] Huffman, D., "A Method for the Construction of Minimum- | |||
Redundancy Codes", Proceedings of the Institute of Radio | Redundancy Codes", Proceedings of the Institute of Radio | |||
Engineers Volume 40, Number 9, pp. 1098-1101, | Engineers, Volume 40, Number 9, pp. 1098-1101, September | |||
September 1952, <http://ieeexplore.ieee.org/xpl/ | 1952, <http://ieeexplore.ieee.org/xpl/ | |||
articleDetails.jsp?arnumber=4051119>. | articleDetails.jsp?arnumber=4051119>. | |||
[ORIGIN] Barth, A., "The Web Origin Concept", RFC 6454, | [ORIGIN] Barth, A., "The Web Origin Concept", RFC 6454, | |||
December 2011. | DOI 10.17487/RFC6454, December 2011, | |||
<https://www.rfc-editor.org/info/rfc6454>. | ||||
[PETAL] Tan, J. and J. Nahata, "PETAL: Preset Encoding Table | [PETAL] Tan, J. and J. Nahata, "PETAL: Preset Encoding | |||
Information Leakage", April 2013, <http:// | Table Information Leakage", April 2013, | |||
www.pdl.cmu.edu/PDL-FTP/associated/CMU-PDL-13-106.pdf>. | <http://www.pdl.cmu.edu/PDL-FTP/associated/CMU-PDL- | |||
13-106.pdf>. | ||||
[SPDY] Belshe, M. and R. Peon, "SPDY Protocol", | [SPDY] Belshe, M. and R. Peon, "SPDY Protocol", draft-mbelshe- | |||
draft-mbelshe-httpbis-spdy-00 (work in progress), | httpbis-spdy-00 (work in progress), February 2012. | |||
February 2012. | ||||
[TLS12] Dierks, T. and E. Rescorla, "The Transport Layer | [TLS12] Dierks, T. and E. Rescorla, "The Transport Layer Security | |||
Security (TLS) Protocol Version 1.2", RFC 5246, | (TLS) Protocol Version 1.2", RFC 5246, | |||
August 2008. | DOI 10.17487/RFC5246, August 2008, | |||
<https://www.rfc-editor.org/info/rfc5246>. | ||||
Appendix A. Static Table Definition | Appendix A. Static Table Definition | |||
The static table (see Section 2.3.1) consists in a predefined and | The static table (see Section 2.3.1) consists in a predefined and | |||
unchangeable list of header fields. | unchangeable list of header fields. | |||
The static table was created from the most frequent header fields | The static table was created from the most frequent header fields | |||
used by popular web sites, with the addition of HTTP/2-specific | used by popular web sites, with the addition of HTTP/2-specific | |||
pseudo-header fields (see Section 8.1.2.1 of [HTTP2]). For header | pseudo-header fields (see Section 8.1.2.1 of [HTTP2]). For header | |||
fields with a few frequent values, an entry was added for each of | fields with a few frequent values, an entry was added for each of | |||
these frequent values. For other header fields, an entry was added | these frequent values. For other header fields, an entry was added | |||
with an empty value. | with an empty value. | |||
The following table lists the predefined header fields that make-up | Table 1 lists the predefined header fields that make up the static | |||
the static table. | table and gives the index of each entry. | |||
+-------+-----------------------------+---------------+ | +-------+-----------------------------+---------------+ | |||
| Index | Header Name | Header Value | | | Index | Header Name | Header Value | | |||
+-------+-----------------------------+---------------+ | +-------+-----------------------------+---------------+ | |||
| 1 | :authority | | | | 1 | :authority | | | |||
| 2 | :method | GET | | | 2 | :method | GET | | |||
| 3 | :method | POST | | | 3 | :method | POST | | |||
| 4 | :path | / | | | 4 | :path | / | | |||
| 5 | :path | /index.html | | | 5 | :path | /index.html | | |||
| 6 | :scheme | http | | | 6 | :scheme | http | | |||
skipping to change at page 27, line 27 ¶ | skipping to change at page 25, line 39 ¶ | |||
| 56 | strict-transport-security | | | | 56 | strict-transport-security | | | |||
| 57 | transfer-encoding | | | | 57 | transfer-encoding | | | |||
| 58 | user-agent | | | | 58 | user-agent | | | |||
| 59 | vary | | | | 59 | vary | | | |||
| 60 | via | | | | 60 | via | | | |||
| 61 | www-authenticate | | | | 61 | www-authenticate | | | |||
+-------+-----------------------------+---------------+ | +-------+-----------------------------+---------------+ | |||
Table 1: Static Table Entries | Table 1: Static Table Entries | |||
Table 1 gives the index of each entry in the static table. | ||||
Appendix B. Huffman Code | Appendix B. Huffman Code | |||
The following Huffman code is used when encoding string literals with | The following Huffman code is used when encoding string literals with | |||
a Huffman coding (see Section 5.2). | a Huffman coding (see Section 5.2). | |||
This Huffman code was generated from statistics obtained on a large | This Huffman code was generated from statistics obtained on a large | |||
sample of HTTP headers. It is a canonical Huffman code (see | sample of HTTP headers. It is a canonical Huffman code (see | |||
[CANONICAL]) with some tweaking to ensure that no symbol has a unique | [CANONICAL]) with some tweaking to ensure that no symbol has a unique | |||
code length. | code length. | |||
skipping to change at page 33, line 38 ¶ | skipping to change at page 31, line 46 ¶ | |||
(250) |11111111|11111111|11111101|100 7ffffec [27] | (250) |11111111|11111111|11111101|100 7ffffec [27] | |||
(251) |11111111|11111111|11111101|101 7ffffed [27] | (251) |11111111|11111111|11111101|101 7ffffed [27] | |||
(252) |11111111|11111111|11111101|110 7ffffee [27] | (252) |11111111|11111111|11111101|110 7ffffee [27] | |||
(253) |11111111|11111111|11111101|111 7ffffef [27] | (253) |11111111|11111111|11111101|111 7ffffef [27] | |||
(254) |11111111|11111111|11111110|000 7fffff0 [27] | (254) |11111111|11111111|11111110|000 7fffff0 [27] | |||
(255) |11111111|11111111|11111011|10 3ffffee [26] | (255) |11111111|11111111|11111011|10 3ffffee [26] | |||
EOS (256) |11111111|11111111|11111111|111111 3fffffff [30] | EOS (256) |11111111|11111111|11111111|111111 3fffffff [30] | |||
Appendix C. Examples | Appendix C. Examples | |||
A number of examples are worked through here, covering integer | This appendix contains examples covering integer encoding, header | |||
encoding, header field representation, and the encoding of whole | field representation, and the encoding of whole lists of header | |||
lists of header fields, for both requests and responses, and with and | fields for both requests and responses, with and without Huffman | |||
without Huffman coding. | coding. | |||
C.1. Integer Representation Examples | C.1. Integer Representation Examples | |||
This section shows the representation of integer values in details | This section shows the representation of integer values in detail | |||
(see Section 5.1). | (see Section 5.1). | |||
C.1.1. Example 1: Encoding 10 Using a 5-bit Prefix | C.1.1. Example 1: Encoding 10 Using a 5-Bit Prefix | |||
The value 10 is to be encoded with a 5-bit prefix. | The value 10 is to be encoded with a 5-bit prefix. | |||
o 10 is less than 31 (2^5 - 1) and is represented using the 5-bit | o 10 is less than 31 (2^5 - 1) and is represented using the 5-bit | |||
prefix. | prefix. | |||
0 1 2 3 4 5 6 7 | 0 1 2 3 4 5 6 7 | |||
+---+---+---+---+---+---+---+---+ | +---+---+---+---+---+---+---+---+ | |||
| X | X | X | 0 | 1 | 0 | 1 | 0 | 10 stored on 5 bits | | X | X | X | 0 | 1 | 0 | 1 | 0 | 10 stored on 5 bits | |||
+---+---+---+---+---+---+---+---+ | +---+---+---+---+---+---+---+---+ | |||
C.1.2. Example 2: Encoding 1337 Using a 5-bit Prefix | C.1.2. Example 2: Encoding 1337 Using a 5-Bit Prefix | |||
The value I=1337 is to be encoded with a 5-bit prefix. | The value I=1337 is to be encoded with a 5-bit prefix. | |||
1337 is greater than 31 (2^5 - 1). | 1337 is greater than 31 (2^5 - 1). | |||
The 5-bit prefix is filled with its max value (31). | The 5-bit prefix is filled with its max value (31). | |||
I = 1337 - (2^5 - 1) = 1306. | I = 1337 - (2^5 - 1) = 1306. | |||
I (1306) is greater than or equal to 128, the while loop body | I (1306) is greater than or equal to 128, so the while loop | |||
executes: | body executes: | |||
I % 128 == 26 | I % 128 == 26 | |||
26 + 128 == 154 | 26 + 128 == 154 | |||
154 is encoded in 8 bits as: 10011010 | 154 is encoded in 8 bits as: 10011010 | |||
I is set to 10 (1306 / 128 == 10) | I is set to 10 (1306 / 128 == 10) | |||
I is no longer greater than or equal to 128, the while loop | I is no longer greater than or equal to 128, so the while | |||
terminates. | loop terminates. | |||
I, now 10, is encoded in 8 bits as: 00001010. | I, now 10, is encoded in 8 bits as: 00001010. | |||
The process ends. | The process ends. | |||
0 1 2 3 4 5 6 7 | 0 1 2 3 4 5 6 7 | |||
+---+---+---+---+---+---+---+---+ | +---+---+---+---+---+---+---+---+ | |||
| X | X | X | 1 | 1 | 1 | 1 | 1 | Prefix = 31, I = 1306 | | X | X | X | 1 | 1 | 1 | 1 | 1 | Prefix = 31, I = 1306 | |||
| 1 | 0 | 0 | 1 | 1 | 0 | 1 | 0 | 1306>=128, encode(154), I=1306/128 | | 1 | 0 | 0 | 1 | 1 | 0 | 1 | 0 | 1306>=128, encode(154), I=1306/128 | |||
| 0 | 0 | 0 | 0 | 1 | 0 | 1 | 0 | 10<128, encode(10), done | | 0 | 0 | 0 | 0 | 1 | 0 | 1 | 0 | 10<128, encode(10), done | |||
+---+---+---+---+---+---+---+---+ | +---+---+---+---+---+---+---+---+ | |||
C.1.3. Example 3: Encoding 42 Starting at an Octet Boundary | C.1.3. Example 3: Encoding 42 Starting at an Octet Boundary | |||
The value 42 is to be encoded starting at an octet-boundary. This | The value 42 is to be encoded starting at an octet boundary. This | |||
implies that a 8-bit prefix is used. | implies that a 8-bit prefix is used. | |||
o 42 is less than 255 (2^8 - 1) and is represented using the 8-bit | o 42 is less than 255 (2^8 - 1) and is represented using the 8-bit | |||
prefix. | prefix. | |||
0 1 2 3 4 5 6 7 | 0 1 2 3 4 5 6 7 | |||
+---+---+---+---+---+---+---+---+ | +---+---+---+---+---+---+---+---+ | |||
| 0 | 0 | 1 | 0 | 1 | 0 | 1 | 0 | 42 stored on 8 bits | | 0 | 0 | 1 | 0 | 1 | 0 | 1 | 0 | 42 stored on 8 bits | |||
+---+---+---+---+---+---+---+---+ | +---+---+---+---+---+---+---+---+ | |||
skipping to change at page 36, line 11 ¶ | skipping to change at page 34, line 11 ¶ | |||
400a 6375 7374 6f6d 2d6b 6579 0d63 7573 | @.custom-key.cus | 400a 6375 7374 6f6d 2d6b 6579 0d63 7573 | @.custom-key.cus | |||
746f 6d2d 6865 6164 6572 | tom-header | 746f 6d2d 6865 6164 6572 | tom-header | |||
Decoding process: | Decoding process: | |||
40 | == Literal indexed == | 40 | == Literal indexed == | |||
0a | Literal name (len = 10) | 0a | Literal name (len = 10) | |||
6375 7374 6f6d 2d6b 6579 | custom-key | 6375 7374 6f6d 2d6b 6579 | custom-key | |||
0d | Literal value (len = 13) | 0d | Literal value (len = 13) | |||
6375 7374 6f6d 2d68 6561 6465 72 | custom-header | 6375 7374 6f6d 2d68 6561 6465 72 | custom-header | |||
| -> custom-key: custom-head\ | | -> custom-key: | |||
| er | | custom-header | |||
Dynamic Table (after decoding): | Dynamic Table (after decoding): | |||
[ 1] (s = 55) custom-key: custom-header | [ 1] (s = 55) custom-key: custom-header | |||
Table size: 55 | Table size: 55 | |||
Decoded header list: | Decoded header list: | |||
custom-key: custom-header | custom-key: custom-header | |||
skipping to change at page 37, line 5 ¶ | skipping to change at page 35, line 5 ¶ | |||
0c | Literal value (len = 12) | 0c | Literal value (len = 12) | |||
2f73 616d 706c 652f 7061 7468 | /sample/path | 2f73 616d 706c 652f 7061 7468 | /sample/path | |||
| -> :path: /sample/path | | -> :path: /sample/path | |||
Dynamic table (after decoding): empty. | Dynamic table (after decoding): empty. | |||
Decoded header list: | Decoded header list: | |||
:path: /sample/path | :path: /sample/path | |||
C.2.3. Literal Header Field never Indexed | C.2.3. Literal Header Field Never Indexed | |||
The header field representation uses a literal name and a literal | The header field representation uses a literal name and a literal | |||
value. The header field is not added to the dynamic table, and must | value. The header field is not added to the dynamic table and must | |||
use the same representation if re-encoded by an intermediary. | use the same representation if re-encoded by an intermediary. | |||
Header list to encode: | Header list to encode: | |||
password: secret | password: secret | |||
Hex dump of encoded data: | Hex dump of encoded data: | |||
1008 7061 7373 776f 7264 0673 6563 7265 | ..password.secre | 1008 7061 7373 776f 7264 0673 6563 7265 | ..password.secre | |||
74 | t | 74 | t | |||
skipping to change at page 37, line 37 ¶ | skipping to change at page 35, line 37 ¶ | |||
| -> password: secret | | -> password: secret | |||
Dynamic table (after decoding): empty. | Dynamic table (after decoding): empty. | |||
Decoded header list: | Decoded header list: | |||
password: secret | password: secret | |||
C.2.4. Indexed Header Field | C.2.4. Indexed Header Field | |||
The header field representation uses an indexed header field, from | The header field representation uses an indexed header field from the | |||
the static table. | static table. | |||
Header list to encode: | Header list to encode: | |||
:method: GET | :method: GET | |||
Hex dump of encoded data: | Hex dump of encoded data: | |||
82 | . | 82 | . | |||
Decoding process: | Decoding process: | |||
skipping to change at page 39, line 4 ¶ | skipping to change at page 36, line 29 ¶ | |||
:method: GET | :method: GET | |||
:scheme: http | :scheme: http | |||
:path: / | :path: / | |||
:authority: www.example.com | :authority: www.example.com | |||
Hex dump of encoded data: | Hex dump of encoded data: | |||
8286 8441 0f77 7777 2e65 7861 6d70 6c65 | ...A.www.example | 8286 8441 0f77 7777 2e65 7861 6d70 6c65 | ...A.www.example | |||
2e63 6f6d | .com | 2e63 6f6d | .com | |||
Decoding process: | Decoding process: | |||
82 | == Indexed - Add == | 82 | == Indexed - Add == | |||
| idx = 2 | | idx = 2 | |||
| -> :method: GET | | -> :method: GET | |||
86 | == Indexed - Add == | 86 | == Indexed - Add == | |||
| idx = 6 | | idx = 6 | |||
| -> :scheme: http | | -> :scheme: http | |||
84 | == Indexed - Add == | 84 | == Indexed - Add == | |||
| idx = 4 | | idx = 4 | |||
| -> :path: / | | -> :path: / | |||
41 | == Literal indexed == | 41 | == Literal indexed == | |||
| Indexed name (idx = 1) | | Indexed name (idx = 1) | |||
| :authority | | :authority | |||
0f | Literal value (len = 15) | 0f | Literal value (len = 15) | |||
7777 772e 6578 616d 706c 652e 636f 6d | www.example.com | 7777 772e 6578 616d 706c 652e 636f 6d | www.example.com | |||
| -> :authority: www.example\ | | -> :authority: | |||
| .com | | www.example.com | |||
Dynamic Table (after decoding): | Dynamic Table (after decoding): | |||
[ 1] (s = 57) :authority: www.example.com | [ 1] (s = 57) :authority: www.example.com | |||
Table size: 57 | Table size: 57 | |||
Decoded header list: | Decoded header list: | |||
:method: GET | :method: GET | |||
:scheme: http | :scheme: http | |||
skipping to change at page 40, line 4 ¶ | skipping to change at page 37, line 25 ¶ | |||
:method: GET | :method: GET | |||
:scheme: http | :scheme: http | |||
:path: / | :path: / | |||
:authority: www.example.com | :authority: www.example.com | |||
cache-control: no-cache | cache-control: no-cache | |||
Hex dump of encoded data: | Hex dump of encoded data: | |||
8286 84be 5808 6e6f 2d63 6163 6865 | ....X.no-cache | 8286 84be 5808 6e6f 2d63 6163 6865 | ....X.no-cache | |||
Decoding process: | Decoding process: | |||
82 | == Indexed - Add == | 82 | == Indexed - Add == | |||
| idx = 2 | | idx = 2 | |||
| -> :method: GET | | -> :method: GET | |||
86 | == Indexed - Add == | 86 | == Indexed - Add == | |||
| idx = 6 | | idx = 6 | |||
| -> :scheme: http | | -> :scheme: http | |||
84 | == Indexed - Add == | 84 | == Indexed - Add == | |||
| idx = 4 | | idx = 4 | |||
| -> :path: / | | -> :path: / | |||
be | == Indexed - Add == | be | == Indexed - Add == | |||
| idx = 62 | | idx = 62 | |||
| -> :authority: www.example\ | | -> :authority: | |||
| .com | | www.example.com | |||
58 | == Literal indexed == | 58 | == Literal indexed == | |||
| Indexed name (idx = 24) | | Indexed name (idx = 24) | |||
| cache-control | | cache-control | |||
08 | Literal value (len = 8) | 08 | Literal value (len = 8) | |||
6e6f 2d63 6163 6865 | no-cache | 6e6f 2d63 6163 6865 | no-cache | |||
| -> cache-control: no-cache | | -> cache-control: no-cache | |||
Dynamic Table (after decoding): | Dynamic Table (after decoding): | |||
[ 1] (s = 53) cache-control: no-cache | [ 1] (s = 53) cache-control: no-cache | |||
skipping to change at page 41, line 4 ¶ | skipping to change at page 38, line 22 ¶ | |||
C.3.3. Third Request | C.3.3. Third Request | |||
Header list to encode: | Header list to encode: | |||
:method: GET | :method: GET | |||
:scheme: https | :scheme: https | |||
:path: /index.html | :path: /index.html | |||
:authority: www.example.com | :authority: www.example.com | |||
custom-key: custom-value | custom-key: custom-value | |||
Hex dump of encoded data: | Hex dump of encoded data: | |||
8287 85bf 400a 6375 7374 6f6d 2d6b 6579 | ....@.custom-key | 8287 85bf 400a 6375 7374 6f6d 2d6b 6579 | ....@.custom-key | |||
0c63 7573 746f 6d2d 7661 6c75 65 | .custom-value | 0c63 7573 746f 6d2d 7661 6c75 65 | .custom-value | |||
Decoding process: | Decoding process: | |||
82 | == Indexed - Add == | 82 | == Indexed - Add == | |||
| idx = 2 | | idx = 2 | |||
| -> :method: GET | | -> :method: GET | |||
87 | == Indexed - Add == | 87 | == Indexed - Add == | |||
| idx = 7 | | idx = 7 | |||
| -> :scheme: https | | -> :scheme: https | |||
85 | == Indexed - Add == | 85 | == Indexed - Add == | |||
| idx = 5 | | idx = 5 | |||
| -> :path: /index.html | | -> :path: /index.html | |||
bf | == Indexed - Add == | bf | == Indexed - Add == | |||
| idx = 63 | | idx = 63 | |||
| -> :authority: www.example\ | | -> :authority: | |||
| .com | | www.example.com | |||
40 | == Literal indexed == | 40 | == Literal indexed == | |||
0a | Literal name (len = 10) | 0a | Literal name (len = 10) | |||
6375 7374 6f6d 2d6b 6579 | custom-key | 6375 7374 6f6d 2d6b 6579 | custom-key | |||
0c | Literal value (len = 12) | 0c | Literal value (len = 12) | |||
6375 7374 6f6d 2d76 616c 7565 | custom-value | 6375 7374 6f6d 2d76 616c 7565 | custom-value | |||
| -> custom-key: custom-valu\ | | -> custom-key: | |||
| e | | custom-value | |||
Dynamic Table (after decoding): | Dynamic Table (after decoding): | |||
[ 1] (s = 54) custom-key: custom-value | [ 1] (s = 54) custom-key: custom-value | |||
[ 2] (s = 53) cache-control: no-cache | [ 2] (s = 53) cache-control: no-cache | |||
[ 3] (s = 57) :authority: www.example.com | [ 3] (s = 57) :authority: www.example.com | |||
Table size: 164 | Table size: 164 | |||
Decoded header list: | Decoded header list: | |||
:method: GET | :method: GET | |||
:scheme: https | :scheme: https | |||
:path: /index.html | :path: /index.html | |||
:authority: www.example.com | :authority: www.example.com | |||
custom-key: custom-value | custom-key: custom-value | |||
C.4. Request Examples with Huffman Coding | C.4. Request Examples with Huffman Coding | |||
This section shows the same examples as the previous section, but | This section shows the same examples as the previous section but uses | |||
using Huffman encoding for the literal values. | Huffman encoding for the literal values. | |||
C.4.1. First Request | C.4.1. First Request | |||
Header list to encode: | Header list to encode: | |||
:method: GET | :method: GET | |||
:scheme: http | :scheme: http | |||
:path: / | :path: / | |||
:authority: www.example.com | :authority: www.example.com | |||
skipping to change at page 42, line 38 ¶ | skipping to change at page 40, line 24 ¶ | |||
| idx = 4 | | idx = 4 | |||
| -> :path: / | | -> :path: / | |||
41 | == Literal indexed == | 41 | == Literal indexed == | |||
| Indexed name (idx = 1) | | Indexed name (idx = 1) | |||
| :authority | | :authority | |||
8c | Literal value (len = 12) | 8c | Literal value (len = 12) | |||
| Huffman encoded: | | Huffman encoded: | |||
f1e3 c2e5 f23a 6ba0 ab90 f4ff | .....:k..... | f1e3 c2e5 f23a 6ba0 ab90 f4ff | .....:k..... | |||
| Decoded: | | Decoded: | |||
| www.example.com | | www.example.com | |||
| -> :authority: www.example\ | | -> :authority: | |||
| .com | | www.example.com | |||
Dynamic Table (after decoding): | Dynamic Table (after decoding): | |||
[ 1] (s = 57) :authority: www.example.com | [ 1] (s = 57) :authority: www.example.com | |||
Table size: 57 | Table size: 57 | |||
Decoded header list: | Decoded header list: | |||
:method: GET | :method: GET | |||
:scheme: http | :scheme: http | |||
skipping to change at page 43, line 32 ¶ | skipping to change at page 41, line 18 ¶ | |||
| idx = 2 | | idx = 2 | |||
| -> :method: GET | | -> :method: GET | |||
86 | == Indexed - Add == | 86 | == Indexed - Add == | |||
| idx = 6 | | idx = 6 | |||
| -> :scheme: http | | -> :scheme: http | |||
84 | == Indexed - Add == | 84 | == Indexed - Add == | |||
| idx = 4 | | idx = 4 | |||
| -> :path: / | | -> :path: / | |||
be | == Indexed - Add == | be | == Indexed - Add == | |||
| idx = 62 | | idx = 62 | |||
| -> :authority: www.example\ | | -> :authority: | |||
| .com | | www.example.com | |||
58 | == Literal indexed == | 58 | == Literal indexed == | |||
| Indexed name (idx = 24) | | Indexed name (idx = 24) | |||
| cache-control | | cache-control | |||
86 | Literal value (len = 6) | 86 | Literal value (len = 6) | |||
| Huffman encoded: | | Huffman encoded: | |||
a8eb 1064 9cbf | ...d.. | a8eb 1064 9cbf | ...d.. | |||
| Decoded: | | Decoded: | |||
| no-cache | | no-cache | |||
| -> cache-control: no-cache | | -> cache-control: no-cache | |||
skipping to change at page 44, line 22 ¶ | skipping to change at page 42, line 4 ¶ | |||
C.4.3. Third Request | C.4.3. Third Request | |||
Header list to encode: | Header list to encode: | |||
:method: GET | :method: GET | |||
:scheme: https | :scheme: https | |||
:path: /index.html | :path: /index.html | |||
:authority: www.example.com | :authority: www.example.com | |||
custom-key: custom-value | custom-key: custom-value | |||
Hex dump of encoded data: | Hex dump of encoded data: | |||
8287 85bf 4088 25a8 49e9 5ba9 7d7f 8925 | ....@.%.I.[.}..% | 8287 85bf 4088 25a8 49e9 5ba9 7d7f 8925 | ....@.%.I.[.}..% | |||
a849 e95b b8e8 b4bf | .I.[.... | a849 e95b b8e8 b4bf | .I.[.... | |||
Decoding process: | Decoding process: | |||
82 | == Indexed - Add == | 82 | == Indexed - Add == | |||
| idx = 2 | | idx = 2 | |||
| -> :method: GET | | -> :method: GET | |||
87 | == Indexed - Add == | 87 | == Indexed - Add == | |||
| idx = 7 | | idx = 7 | |||
| -> :scheme: https | | -> :scheme: https | |||
85 | == Indexed - Add == | 85 | == Indexed - Add == | |||
| idx = 5 | | idx = 5 | |||
| -> :path: /index.html | | -> :path: /index.html | |||
bf | == Indexed - Add == | bf | == Indexed - Add == | |||
| idx = 63 | | idx = 63 | |||
| -> :authority: www.example\ | | -> :authority: | |||
| .com | | www.example.com | |||
40 | == Literal indexed == | 40 | == Literal indexed == | |||
88 | Literal name (len = 8) | 88 | Literal name (len = 8) | |||
| Huffman encoded: | | Huffman encoded: | |||
25a8 49e9 5ba9 7d7f | %.I.[.}. | 25a8 49e9 5ba9 7d7f | %.I.[.}. | |||
| Decoded: | | Decoded: | |||
| custom-key | | custom-key | |||
89 | Literal value (len = 9) | 89 | Literal value (len = 9) | |||
| Huffman encoded: | | Huffman encoded: | |||
25a8 49e9 5bb8 e8b4 bf | %.I.[.... | 25a8 49e9 5bb8 e8b4 bf | %.I.[.... | |||
| Decoded: | | Decoded: | |||
| custom-value | | custom-value | |||
| -> custom-key: custom-valu\ | | -> custom-key: | |||
| e | | custom-value | |||
Dynamic Table (after decoding): | Dynamic Table (after decoding): | |||
[ 1] (s = 54) custom-key: custom-value | [ 1] (s = 54) custom-key: custom-value | |||
[ 2] (s = 53) cache-control: no-cache | [ 2] (s = 53) cache-control: no-cache | |||
[ 3] (s = 57) :authority: www.example.com | [ 3] (s = 57) :authority: www.example.com | |||
Table size: 164 | Table size: 164 | |||
Decoded header list: | Decoded header list: | |||
skipping to change at page 47, line 24 ¶ | skipping to change at page 44, line 24 ¶ | |||
| cache-control | | cache-control | |||
07 | Literal value (len = 7) | 07 | Literal value (len = 7) | |||
7072 6976 6174 65 | private | 7072 6976 6174 65 | private | |||
| -> cache-control: private | | -> cache-control: private | |||
61 | == Literal indexed == | 61 | == Literal indexed == | |||
| Indexed name (idx = 33) | | Indexed name (idx = 33) | |||
| date | | date | |||
1d | Literal value (len = 29) | 1d | Literal value (len = 29) | |||
4d6f 6e2c 2032 3120 4f63 7420 3230 3133 | Mon, 21 Oct 2013 | 4d6f 6e2c 2032 3120 4f63 7420 3230 3133 | Mon, 21 Oct 2013 | |||
2032 303a 3133 3a32 3120 474d 54 | 20:13:21 GMT | 2032 303a 3133 3a32 3120 474d 54 | 20:13:21 GMT | |||
| -> date: Mon, 21 Oct 2013 \ | | -> date: Mon, 21 Oct 2013 | |||
| 20:13:21 GMT | | 20:13:21 GMT | |||
6e | == Literal indexed == | 6e | == Literal indexed == | |||
| Indexed name (idx = 46) | | Indexed name (idx = 46) | |||
| location | | location | |||
17 | Literal value (len = 23) | 17 | Literal value (len = 23) | |||
6874 7470 733a 2f2f 7777 772e 6578 616d | https://www.exam | 6874 7470 733a 2f2f 7777 772e 6578 616d | https://www.exam | |||
706c 652e 636f 6d | ple.com | 706c 652e 636f 6d | ple.com | |||
| -> location: https://www.e\ | | -> location: | |||
| xample.com | | https://www.example.com | |||
Dynamic Table (after decoding): | Dynamic Table (after decoding): | |||
[ 1] (s = 63) location: https://www.example.com | [ 1] (s = 63) location: https://www.example.com | |||
[ 2] (s = 65) date: Mon, 21 Oct 2013 20:13:21 GMT | [ 2] (s = 65) date: Mon, 21 Oct 2013 20:13:21 GMT | |||
[ 3] (s = 52) cache-control: private | [ 3] (s = 52) cache-control: private | |||
[ 4] (s = 42) :status: 302 | [ 4] (s = 42) :status: 302 | |||
Table size: 222 | Table size: 222 | |||
Decoded header list: | Decoded header list: | |||
skipping to change at page 48, line 35 ¶ | skipping to change at page 45, line 35 ¶ | |||
| :status | | :status | |||
03 | Literal value (len = 3) | 03 | Literal value (len = 3) | |||
3330 37 | 307 | 3330 37 | 307 | |||
| - evict: :status: 302 | | - evict: :status: 302 | |||
| -> :status: 307 | | -> :status: 307 | |||
c1 | == Indexed - Add == | c1 | == Indexed - Add == | |||
| idx = 65 | | idx = 65 | |||
| -> cache-control: private | | -> cache-control: private | |||
c0 | == Indexed - Add == | c0 | == Indexed - Add == | |||
| idx = 64 | | idx = 64 | |||
| -> date: Mon, 21 Oct 2013 \ | | -> date: Mon, 21 Oct 2013 | |||
| 20:13:21 GMT | | 20:13:21 GMT | |||
bf | == Indexed - Add == | bf | == Indexed - Add == | |||
| idx = 63 | | idx = 63 | |||
| -> location: https://www.e\ | | -> location: | |||
| xample.com | | https://www.example.com | |||
Dynamic Table (after decoding): | Dynamic Table (after decoding): | |||
[ 1] (s = 42) :status: 307 | [ 1] (s = 42) :status: 307 | |||
[ 2] (s = 63) location: https://www.example.com | [ 2] (s = 63) location: https://www.example.com | |||
[ 3] (s = 65) date: Mon, 21 Oct 2013 20:13:21 GMT | [ 3] (s = 65) date: Mon, 21 Oct 2013 20:13:21 GMT | |||
[ 4] (s = 52) cache-control: private | [ 4] (s = 52) cache-control: private | |||
Table size: 222 | Table size: 222 | |||
Decoded header list: | Decoded header list: | |||
skipping to change at page 50, line 18 ¶ | skipping to change at page 47, line 18 ¶ | |||
| -> :status: 200 | | -> :status: 200 | |||
c1 | == Indexed - Add == | c1 | == Indexed - Add == | |||
| idx = 65 | | idx = 65 | |||
| -> cache-control: private | | -> cache-control: private | |||
61 | == Literal indexed == | 61 | == Literal indexed == | |||
| Indexed name (idx = 33) | | Indexed name (idx = 33) | |||
| date | | date | |||
1d | Literal value (len = 29) | 1d | Literal value (len = 29) | |||
4d6f 6e2c 2032 3120 4f63 7420 3230 3133 | Mon, 21 Oct 2013 | 4d6f 6e2c 2032 3120 4f63 7420 3230 3133 | Mon, 21 Oct 2013 | |||
2032 303a 3133 3a32 3220 474d 54 | 20:13:22 GMT | 2032 303a 3133 3a32 3220 474d 54 | 20:13:22 GMT | |||
| - evict: cache-control: pr\ | | - evict: cache-control: | |||
| ivate | | private | |||
| -> date: Mon, 21 Oct 2013 \ | | -> date: Mon, 21 Oct 2013 | |||
| 20:13:22 GMT | | 20:13:22 GMT | |||
c0 | == Indexed - Add == | c0 | == Indexed - Add == | |||
| idx = 64 | | idx = 64 | |||
| -> location: https://www.e\ | | -> location: | |||
| xample.com | | https://www.example.com | |||
5a | == Literal indexed == | 5a | == Literal indexed == | |||
| Indexed name (idx = 26) | | Indexed name (idx = 26) | |||
| content-encoding | | content-encoding | |||
04 | Literal value (len = 4) | 04 | Literal value (len = 4) | |||
677a 6970 | gzip | 677a 6970 | gzip | |||
| - evict: date: Mon, 21 Oct\ | | - evict: date: Mon, 21 Oct | |||
| 2013 20:13:21 GMT | | 2013 20:13:21 GMT | |||
| -> content-encoding: gzip | | -> content-encoding: gzip | |||
77 | == Literal indexed == | 77 | == Literal indexed == | |||
| Indexed name (idx = 55) | | Indexed name (idx = 55) | |||
| set-cookie | | set-cookie | |||
38 | Literal value (len = 56) | 38 | Literal value (len = 56) | |||
666f 6f3d 4153 444a 4b48 514b 425a 584f | foo=ASDJKHQKBZXO | 666f 6f3d 4153 444a 4b48 514b 425a 584f | foo=ASDJKHQKBZXO | |||
5157 454f 5049 5541 5851 5745 4f49 553b | QWEOPIUAXQWEOIU; | 5157 454f 5049 5541 5851 5745 4f49 553b | QWEOPIUAXQWEOIU; | |||
206d 6178 2d61 6765 3d33 3630 303b 2076 | max-age=3600; v | 206d 6178 2d61 6765 3d33 3630 303b 2076 | max-age=3600; v | |||
6572 7369 6f6e 3d31 | ersion=1 | 6572 7369 6f6e 3d31 | ersion=1 | |||
| - evict: location: https:/\ | | - evict: location: | |||
| /www.example.com | | https://www.example.com | |||
| - evict: :status: 307 | | - evict: :status: 307 | |||
| -> set-cookie: foo=ASDJKHQ\ | | -> set-cookie: foo=ASDJKHQ | |||
| KBZXOQWEOPIUAXQWEOIU; ma\ | | KBZXOQWEOPIUAXQWEOIU; ma | |||
| x-age=3600; version=1 | | x-age=3600; version=1 | |||
Dynamic Table (after decoding): | Dynamic Table (after decoding): | |||
[ 1] (s = 98) set-cookie: foo=ASDJKHQKBZXOQWEOPIUAXQWEOIU; max-age\ | [ 1] (s = 98) set-cookie: foo=ASDJKHQKBZXOQWEOPIUAXQWEOIU; | |||
=3600; version=1 | max-age=3600; version=1 | |||
[ 2] (s = 52) content-encoding: gzip | [ 2] (s = 52) content-encoding: gzip | |||
[ 3] (s = 65) date: Mon, 21 Oct 2013 20:13:22 GMT | [ 3] (s = 65) date: Mon, 21 Oct 2013 20:13:22 GMT | |||
Table size: 215 | Table size: 215 | |||
Decoded header list: | Decoded header list: | |||
:status: 200 | :status: 200 | |||
cache-control: private | cache-control: private | |||
date: Mon, 21 Oct 2013 20:13:22 GMT | date: Mon, 21 Oct 2013 20:13:22 GMT | |||
location: https://www.example.com | location: https://www.example.com | |||
content-encoding: gzip | content-encoding: gzip | |||
set-cookie: foo=ASDJKHQKBZXOQWEOPIUAXQWEOIU; max-age=3600; version=1 | set-cookie: foo=ASDJKHQKBZXOQWEOPIUAXQWEOIU; max-age=3600; version=1 | |||
C.6. Response Examples with Huffman Coding | C.6. Response Examples with Huffman Coding | |||
This section shows the same examples as the previous section, but | This section shows the same examples as the previous section but uses | |||
using Huffman encoding for the literal values. The HTTP/2 setting | Huffman encoding for the literal values. The HTTP/2 setting | |||
parameter SETTINGS_HEADER_TABLE_SIZE is set to the value of 256 | parameter SETTINGS_HEADER_TABLE_SIZE is set to the value of 256 | |||
octets, causing some evictions to occur. The eviction mechanism uses | octets, causing some evictions to occur. The eviction mechanism uses | |||
the length of the decoded literal values, so the same evictions | the length of the decoded literal values, so the same evictions occur | |||
occurs as in the previous section. | as in the previous section. | |||
C.6.1. First Response | C.6.1. First Response | |||
Header list to encode: | Header list to encode: | |||
:status: 302 | :status: 302 | |||
cache-control: private | cache-control: private | |||
date: Mon, 21 Oct 2013 20:13:21 GMT | date: Mon, 21 Oct 2013 20:13:21 GMT | |||
location: https://www.example.com | location: https://www.example.com | |||
skipping to change at page 52, line 33 ¶ | skipping to change at page 49, line 33 ¶ | |||
| private | | private | |||
| -> cache-control: private | | -> cache-control: private | |||
61 | == Literal indexed == | 61 | == Literal indexed == | |||
| Indexed name (idx = 33) | | Indexed name (idx = 33) | |||
| date | | date | |||
96 | Literal value (len = 22) | 96 | Literal value (len = 22) | |||
| Huffman encoded: | | Huffman encoded: | |||
d07a be94 1054 d444 a820 0595 040b 8166 | .z...T.D. .....f | d07a be94 1054 d444 a820 0595 040b 8166 | .z...T.D. .....f | |||
e082 a62d 1bff | ...-.. | e082 a62d 1bff | ...-.. | |||
| Decoded: | | Decoded: | |||
| Mon, 21 Oct 2013 20:13:21 \ | | Mon, 21 Oct 2013 20:13:21 | |||
| GMT | | GMT | |||
| -> date: Mon, 21 Oct 2013 \ | | -> date: Mon, 21 Oct 2013 | |||
| 20:13:21 GMT | | 20:13:21 GMT | |||
6e | == Literal indexed == | 6e | == Literal indexed == | |||
| Indexed name (idx = 46) | | Indexed name (idx = 46) | |||
| location | | location | |||
91 | Literal value (len = 17) | 91 | Literal value (len = 17) | |||
| Huffman encoded: | | Huffman encoded: | |||
9d29 ad17 1863 c78f 0b97 c8e9 ae82 ae43 | .)...c.........C | 9d29 ad17 1863 c78f 0b97 c8e9 ae82 ae43 | .)...c.........C | |||
d3 | . | d3 | . | |||
| Decoded: | | Decoded: | |||
| https://www.example.com | | https://www.example.com | |||
| -> location: https://www.e\ | | -> location: | |||
| xample.com | | https://www.example.com | |||
Dynamic Table (after decoding): | Dynamic Table (after decoding): | |||
[ 1] (s = 63) location: https://www.example.com | [ 1] (s = 63) location: https://www.example.com | |||
[ 2] (s = 65) date: Mon, 21 Oct 2013 20:13:21 GMT | [ 2] (s = 65) date: Mon, 21 Oct 2013 20:13:21 GMT | |||
[ 3] (s = 52) cache-control: private | [ 3] (s = 52) cache-control: private | |||
[ 4] (s = 42) :status: 302 | [ 4] (s = 42) :status: 302 | |||
Table size: 222 | Table size: 222 | |||
Decoded header list: | Decoded header list: | |||
skipping to change at page 54, line 22 ¶ | skipping to change at page 51, line 22 ¶ | |||
640e ff | d.. | 640e ff | d.. | |||
| Decoded: | | Decoded: | |||
| 307 | | 307 | |||
| - evict: :status: 302 | | - evict: :status: 302 | |||
| -> :status: 307 | | -> :status: 307 | |||
c1 | == Indexed - Add == | c1 | == Indexed - Add == | |||
| idx = 65 | | idx = 65 | |||
| -> cache-control: private | | -> cache-control: private | |||
c0 | == Indexed - Add == | c0 | == Indexed - Add == | |||
| idx = 64 | | idx = 64 | |||
| -> date: Mon, 21 Oct 2013 \ | | -> date: Mon, 21 Oct 2013 | |||
| 20:13:21 GMT | | 20:13:21 GMT | |||
bf | == Indexed - Add == | bf | == Indexed - Add == | |||
| idx = 63 | | idx = 63 | |||
| -> location: https://www.e\ | | -> location: | |||
| xample.com | | https://www.example.com | |||
Dynamic Table (after decoding): | Dynamic Table (after decoding): | |||
[ 1] (s = 42) :status: 307 | [ 1] (s = 42) :status: 307 | |||
[ 2] (s = 63) location: https://www.example.com | [ 2] (s = 63) location: https://www.example.com | |||
[ 3] (s = 65) date: Mon, 21 Oct 2013 20:13:21 GMT | [ 3] (s = 65) date: Mon, 21 Oct 2013 20:13:21 GMT | |||
[ 4] (s = 52) cache-control: private | [ 4] (s = 52) cache-control: private | |||
Table size: 222 | Table size: 222 | |||
Decoded header list: | Decoded header list: | |||
skipping to change at page 55, line 38 ¶ | skipping to change at page 52, line 38 ¶ | |||
| idx = 65 | | idx = 65 | |||
| -> cache-control: private | | -> cache-control: private | |||
61 | == Literal indexed == | 61 | == Literal indexed == | |||
| Indexed name (idx = 33) | | Indexed name (idx = 33) | |||
| date | | date | |||
96 | Literal value (len = 22) | 96 | Literal value (len = 22) | |||
| Huffman encoded: | | Huffman encoded: | |||
d07a be94 1054 d444 a820 0595 040b 8166 | .z...T.D. .....f | d07a be94 1054 d444 a820 0595 040b 8166 | .z...T.D. .....f | |||
e084 a62d 1bff | ...-.. | e084 a62d 1bff | ...-.. | |||
| Decoded: | | Decoded: | |||
| Mon, 21 Oct 2013 20:13:22 \ | | Mon, 21 Oct 2013 20:13:22 | |||
| GMT | | GMT | |||
| - evict: cache-control: pr\ | | - evict: cache-control: | |||
| ivate | | private | |||
| -> date: Mon, 21 Oct 2013 \ | | -> date: Mon, 21 Oct 2013 | |||
| 20:13:22 GMT | | 20:13:22 GMT | |||
c0 | == Indexed - Add == | c0 | == Indexed - Add == | |||
| idx = 64 | | idx = 64 | |||
| -> location: https://www.e\ | | -> location: | |||
| xample.com | | https://www.example.com | |||
5a | == Literal indexed == | 5a | == Literal indexed == | |||
| Indexed name (idx = 26) | | Indexed name (idx = 26) | |||
| content-encoding | | content-encoding | |||
83 | Literal value (len = 3) | 83 | Literal value (len = 3) | |||
| Huffman encoded: | | Huffman encoded: | |||
9bd9 ab | ... | 9bd9 ab | ... | |||
| Decoded: | | Decoded: | |||
| gzip | | gzip | |||
| - evict: date: Mon, 21 Oct\ | | - evict: date: Mon, 21 Oct | |||
| 2013 20:13:21 GMT | | 2013 20:13:21 GMT | |||
| -> content-encoding: gzip | | -> content-encoding: gzip | |||
77 | == Literal indexed == | 77 | == Literal indexed == | |||
| Indexed name (idx = 55) | | Indexed name (idx = 55) | |||
| set-cookie | | set-cookie | |||
ad | Literal value (len = 45) | ad | Literal value (len = 45) | |||
| Huffman encoded: | | Huffman encoded: | |||
94e7 821d d7f2 e6c7 b335 dfdf cd5b 3960 | .........5...[9` | 94e7 821d d7f2 e6c7 b335 dfdf cd5b 3960 | .........5...[9` | |||
d5af 2708 7f36 72c1 ab27 0fb5 291f 9587 | ..'..6r..'..)... | d5af 2708 7f36 72c1 ab27 0fb5 291f 9587 | ..'..6r..'..)... | |||
3160 65c0 03ed 4ee5 b106 3d50 07 | 1`e...N...=P. | 3160 65c0 03ed 4ee5 b106 3d50 07 | 1`e...N...=P. | |||
| Decoded: | | Decoded: | |||
| foo=ASDJKHQKBZXOQWEOPIUAXQ\ | | foo=ASDJKHQKBZXOQWEOPIUAXQ | |||
| WEOIU; max-age=3600; versi\ | | WEOIU; max-age=3600; versi | |||
| on=1 | | on=1 | |||
| - evict: location: https:/\ | | - evict: location: | |||
| /www.example.com | | https://www.example.com | |||
| - evict: :status: 307 | | - evict: :status: 307 | |||
| -> set-cookie: foo=ASDJKHQ\ | | -> set-cookie: foo=ASDJKHQ | |||
| KBZXOQWEOPIUAXQWEOIU; ma\ | | KBZXOQWEOPIUAXQWEOIU; ma | |||
| x-age=3600; version=1 | | x-age=3600; version=1 | |||
Dynamic Table (after decoding): | Dynamic Table (after decoding): | |||
[ 1] (s = 98) set-cookie: foo=ASDJKHQKBZXOQWEOPIUAXQWEOIU; max-age\ | [ 1] (s = 98) set-cookie: foo=ASDJKHQKBZXOQWEOPIUAXQWEOIU; | |||
=3600; version=1 | max-age=3600; version=1 | |||
[ 2] (s = 52) content-encoding: gzip | [ 2] (s = 52) content-encoding: gzip | |||
[ 3] (s = 65) date: Mon, 21 Oct 2013 20:13:22 GMT | [ 3] (s = 65) date: Mon, 21 Oct 2013 20:13:22 GMT | |||
Table size: 215 | Table size: 215 | |||
Decoded header list: | Decoded header list: | |||
:status: 200 | :status: 200 | |||
cache-control: private | cache-control: private | |||
date: Mon, 21 Oct 2013 20:13:22 GMT | date: Mon, 21 Oct 2013 20:13:22 GMT | |||
location: https://www.example.com | location: https://www.example.com | |||
content-encoding: gzip | content-encoding: gzip | |||
set-cookie: foo=ASDJKHQKBZXOQWEOPIUAXQWEOIU; max-age=3600; version=1 | set-cookie: foo=ASDJKHQKBZXOQWEOPIUAXQWEOIU; max-age=3600; version=1 | |||
Appendix D. Change Log (to be removed by RFC Editor before publication) | Acknowledgments | |||
D.1. Since draft-ietf-httpbis-header-compression-10 | ||||
o Editorial corrections for taking into account IETF LC comments. | ||||
* Added links to security sections. | ||||
* Made spec more independent of HTTP/2. | ||||
* Expanded security section about never indexed literal usage. | ||||
o Removed most usages of 'name-value pair' instead of header field. | ||||
o Changed 'header table' to 'header field table'. | ||||
D.2. Since draft-ietf-httpbis-header-compression-09 | ||||
o Renamed header table to dynamic table. | ||||
o Updated integer representation. | ||||
o Editorial corrections. | ||||
D.3. Since draft-ietf-httpbis-header-compression-08 | ||||
o Removed the reference set. | ||||
o Removed header emission. | ||||
o Explicit handling of several SETTINGS_HEADER_TABLE_SIZE parameter | ||||
changes. | ||||
o Changed header set to header list, and forced ordering. | ||||
o Updated examples. | ||||
o Exchanged header and static table positions. | ||||
D.4. Since draft-ietf-httpbis-header-compression-07 | ||||
o Removed old text on index value of 0. | ||||
o Added clarification for signalling of maximum table size after a | ||||
SETTINGS_HEADER_TABLE_SIZE update. | ||||
o Rewrote security considerations. | ||||
o Many editorial clarifications or improvements. | ||||
o Added convention section. | ||||
o Reworked document's outline. | ||||
o Updated static table. Entry 16 has now "gzip, deflate" for value. | ||||
o Updated Huffman table, using data set provided by Google. | ||||
D.5. Since draft-ietf-httpbis-header-compression-06 | ||||
o Updated format to include literal headers that must never be | ||||
compressed. | ||||
o Updated security considerations. | ||||
o Moved integer encoding examples to the appendix. | ||||
o Updated Huffman table. | ||||
o Updated static header table (adding and removing status values). | ||||
o Updated examples. | ||||
D.6. Since draft-ietf-httpbis-header-compression-05 | ||||
o Regenerated examples. | ||||
o Only one Huffman table for requests and responses. | ||||
o Added maximum size for dynamic table, independent of | ||||
SETTINGS_HEADER_TABLE_SIZE. | ||||
o Added pseudo-code for integer decoding. | ||||
o Improved examples (removing unnecessary removals). | ||||
D.7. Since draft-ietf-httpbis-header-compression-04 | ||||
o Updated examples: take into account changes in the spec, and show | ||||
more features. | ||||
o Use 'octet' everywhere instead of having both 'byte' and 'octet'. | ||||
o Added reference set emptying. | ||||
o Editorial changes and clarifications. | ||||
o Added "host" header to the static table. | ||||
o Ordering for list of values (either NULL- or comma-separated). | ||||
D.8. Since draft-ietf-httpbis-header-compression-03 | ||||
o A large number of editorial changes; changed the description of | ||||
evicting/adding new entries. | ||||
o Removed substitution indexing | ||||
o Changed 'initial headers' to 'static headers', as per issue #258 | ||||
o Merged 'request' and 'response' static headers, as per issue #259 | ||||
o Changed text to indicate that new headers are added at index 0 and | ||||
expire from the largest index, as per issue #233 | ||||
D.9. Since draft-ietf-httpbis-header-compression-02 | ||||
o Corrected error in integer encoding pseudocode. | ||||
D.10. Since draft-ietf-httpbis-header-compression-01 | ||||
o Refactored of Header Encoding Section: split definitions and | ||||
processing rule. | ||||
o Backward incompatible change: Updated reference set management as | ||||
per issue #214. This changes how the interaction between the | ||||
reference set and eviction works. This also changes the working | ||||
of the reference set in some specific cases. | ||||
o Backward incompatible change: modified initial header list, as per | ||||
issue #188. | ||||
o Added example of 32 octets entry structure (issue #191). | ||||
o Added Header Set Completion section. Reflowed some text. | ||||
Clarified some writing which was akward. Added text about | ||||
duplicate header entry encoding. Clarified some language w.r.t | ||||
Header Set. Changed x-my-header to mynewheader. Added text in the | ||||
HeaderEmission section indicating that the application may also be | ||||
able to free up memory more quickly. Added information in | ||||
Security Considerations section. | ||||
D.11. Since draft-ietf-httpbis-header-compression-00 | ||||
Fixed bug/omission in integer representation algorithm. | ||||
Changed the document title. | ||||
Header matching text rewritten. | ||||
Changed the definition of header emission. | ||||
Changed the name of the setting which dictates how much memory the | ||||
compression context should use. | ||||
Removed "specific use cases" section | ||||
Corrected erroneous statement about what index can be contained in | This specification includes substantial input from the following | |||
one octet | individuals: | |||
Added descriptions of opcodes | o Mike Bishop, Jeff Pinner, Julian Reschke, and Martin Thomson | |||
(substantial editorial contributions). | ||||
Removed security claims from introduction. | o Johnny Graettinger (Huffman code statistics). | |||
Authors' Addresses | Authors' Addresses | |||
Roberto Peon | Roberto Peon | |||
Google, Inc | Google, Inc | |||
EMail: fenix@google.com | EMail: fenix@google.com | |||
Herve Ruellan | Herve Ruellan | |||
Canon CRF | Canon CRF | |||
End of changes. 149 change blocks. | ||||
489 lines changed or deleted | 311 lines changed or added | |||
This html diff was produced by rfcdiff 1.48. The latest version is available from http://tools.ietf.org/tools/rfcdiff/ |