lsquic_frame_reader.h revision ab5c8df2
1/* Copyright (c) 2017 LiteSpeed Technologies Inc.  See LICENSE. */
2/*
3 * lsquic_frame_reader.h -- Read HTTP frames from stream
4 */
5
6#ifndef LSQUIC_FRAME_READER_H
7#define LSQUIC_FRAME_READER_H 1
8
9#include <stddef.h>
10#include <stdint.h>
11#ifdef WIN32
12#include <vc_compat.h>
13#endif
14
15struct lsquic_hdec;
16struct lsquic_mm;
17struct lsquic_stream;
18struct lsquic_frame_reader;
19
20
21enum frame_reader_flags
22{
23    FRF_SERVER      = (1 << 0),
24    FRF_HAVE_PREV   = (1 << 1),
25};
26
27
28/* Frame reader may hit some error conditions which are reported using
29 * callback fc_on_error.  These codes are later mapped stream- or
30 * connection-level errors.
31 */
32enum frame_reader_error
33{
34    FR_ERR_DUPLICATE_PSEH = 1,  /* Duplicate pseudo-header */
35    FR_ERR_INCOMPL_REQ_PSEH,    /* Not all request pseudo-headers are present */
36    FR_ERR_UNNEC_REQ_PSEH,      /* Unnecessary request pseudo-header present in
37                                 * the response.
38                                 */
39    FR_ERR_INCOMPL_RESP_PSEH,   /* Not all response pseudo-headers are present */
40    FR_ERR_UNNEC_RESP_PSEH,     /* Unnecessary response pseudo-header present in
41                                 * the response.
42                                 */
43    FR_ERR_UNKNOWN_PSEH,        /* Unknown pseudo-header */
44    FR_ERR_UPPERCASE_HEADER,    /* Uppercase letter in header */
45    FR_ERR_MISPLACED_PSEH,
46    FR_ERR_MISSING_PSEH,
47    FR_ERR_DECOMPRESS,
48    FR_ERR_INVALID_FRAME_SIZE,  /* E.g. a SETTINGS frame length is not a multiple
49                                 * of 6 (RFC 7540, Section 6.5.1).
50                                 */
51    FR_ERR_NONZERO_STREAM_ID,
52    FR_ERR_ZERO_STREAM_ID,
53    FR_ERR_SELF_DEP_STREAM,     /* A stream in priority frame cannot depend on
54                                 * itself (RFC 7540, Section 5.3.1).
55                                 */
56    FR_ERR_HEADERS_TOO_LARGE,
57    FR_ERR_UNEXPECTED_PUSH,
58    FR_ERR_NOMEM,               /* Cannot allocate any more memory. */
59    FR_ERR_EXPECTED_CONTIN,     /* Expected continuation frame. */
60};
61
62
63/* This struct is used to return decoded HEADERS and PUSH_PROMISE frames.
64 * Some of the fields are only used for HEADERS frames.  They are marked
65 * with "H" comment below.
66 */
67struct uncompressed_headers
68{
69    uint32_t               uh_stream_id;
70    uint32_t               uh_oth_stream_id; /* For HEADERS frame, the ID of the
71                                              * stream that this stream depends
72                                              * on.  (Zero means unset.) For
73                                              * PUSH_PROMISE, the promised stream
74                                              * ID.
75                                              */
76    unsigned               uh_size;          /* Number of characters in uh_headers, not
77                                              * counting the NUL byte.
78                                              */
79    unsigned       /* H */ uh_off;
80    unsigned short /* H */ uh_weight;        /* 1 - 256; 0 means not set */
81    signed char    /* H */ uh_exclusive;     /* 0 or 1 when set; -1 means not set */
82    enum {
83                   /* H */ UH_FIN  = (1 << 0),
84                           UH_PP   = (1 << 1), /* Push promise */
85    }                      uh_flags:8;
86    char                   uh_headers[       /* NUL-terminated C string */
87#if FRAME_READER_TESTING
88                                         FRAME_READER_TESTING
89#else
90                                                    0
91#endif
92    ];
93};
94
95struct frame_reader_callbacks
96{
97    void (*frc_on_headers)      (void *frame_cb_ctx, struct uncompressed_headers *);
98    void (*frc_on_push_promise) (void *frame_cb_ctx, struct uncompressed_headers *);
99    void (*frc_on_settings)     (void *frame_cb_ctx, uint16_t setting_id,
100                                 uint32_t setting_value);
101    void (*frc_on_priority)     (void *frame_cb_ctx, uint32_t stream_id,
102                                 int exclusive, uint32_t dep_stream_id,
103                                 unsigned weight);
104    void (*frc_on_error)        (void *frame_cb_ctx, uint32_t stream_id,
105                                 enum frame_reader_error);
106};
107
108typedef ssize_t (*fr_stream_read_f)(struct lsquic_stream *, void *, size_t);
109
110struct lsquic_frame_reader *
111lsquic_frame_reader_new (enum frame_reader_flags, unsigned max_headers_sz,
112                         struct lsquic_mm *, struct lsquic_stream *,
113                         fr_stream_read_f, struct lsquic_hdec *,
114                         const struct frame_reader_callbacks *,
115                         void *fr_cb_ctx);
116
117int
118lsquic_frame_reader_read (struct lsquic_frame_reader *);
119
120void
121lsquic_frame_reader_destroy (struct lsquic_frame_reader *);
122
123size_t
124lsquic_frame_reader_mem_used (const struct lsquic_frame_reader *);
125
126#endif
127