diff options
Diffstat (limited to '')
-rw-r--r-- | modules/http2/h2_util.h | 161 |
1 files changed, 68 insertions, 93 deletions
diff --git a/modules/http2/h2_util.h b/modules/http2/h2_util.h index 1eb262d..d2e6548 100644 --- a/modules/http2/h2_util.h +++ b/modules/http2/h2_util.h @@ -18,6 +18,10 @@ #define __mod_h2__h2_util__ #include <nghttp2/nghttp2.h> +#include <http_protocol.h> + +#include "h2.h" +#include "h2_headers.h" /******************************************************************************* * some debugging/format helpers @@ -28,10 +32,6 @@ struct nghttp2_frame; size_t h2_util_hex_dump(char *buffer, size_t maxlen, const char *data, size_t datalen); -size_t h2_util_header_print(char *buffer, size_t maxlen, - const char *name, size_t namelen, - const char *value, size_t valuelen); - void h2_util_camel_case_header(char *s, size_t len); int h2_util_frame_print(const nghttp2_frame *frame, char *buffer, size_t maxlen); @@ -49,7 +49,7 @@ typedef int h2_ihash_iter_t(void *ctx, void *val); */ h2_ihash_t *h2_ihash_create(apr_pool_t *pool, size_t offset_of_int); -size_t h2_ihash_count(h2_ihash_t *ih); +unsigned int h2_ihash_count(h2_ihash_t *ih); int h2_ihash_empty(h2_ihash_t *ih); void *h2_ihash_get(h2_ihash_t *ih, int id); @@ -96,13 +96,13 @@ typedef int h2_iq_cmp(int i1, int i2, void *ctx); /** * Allocate a new queue from the pool and initialize. - * @param id the identifier of the queue * @param pool the memory pool + * @param capacity the initial capacity of the queue */ h2_iqueue *h2_iq_create(apr_pool_t *pool, int capacity); /** - * Return != 0 iff there are no tasks in the queue. + * Return != 0 iff there are no ints in the queue. * @param q the queue to check */ int h2_iq_empty(h2_iqueue *q); @@ -134,11 +134,10 @@ int h2_iq_add(h2_iqueue *q, int sid, h2_iq_cmp *cmp, void *ctx); int h2_iq_append(h2_iqueue *q, int sid); /** - * Remove the stream id from the queue. Return != 0 iff task - * was found in queue. - * @param q the task queue + * Remove the int from the queue. Return != 0 iff it was found. + * @param q the queue * @param sid the stream id to remove - * @return != 0 iff task was found in queue + * @return != 0 iff int was found in queue */ int h2_iq_remove(h2_iqueue *q, int sid); @@ -148,7 +147,7 @@ int h2_iq_remove(h2_iqueue *q, int sid); void h2_iq_clear(h2_iqueue *q); /** - * Sort the stream idqueue again. Call if the task ordering + * Sort the stream idqueue again. Call if the int ordering * has changed. * * @param q the queue to sort @@ -169,7 +168,7 @@ int h2_iq_shift(h2_iqueue *q); /** * Get the first max ids from the queue. All these ids will be removed. * - * @param q the queue to get the first task from + * @param q the queue to get the first ids from * @param pint the int array to receive the values * @param max the maximum number of ids to shift * @return the actual number of ids shifted @@ -179,7 +178,7 @@ size_t h2_iq_mshift(h2_iqueue *q, int *pint, size_t max); /** * Determine if int is in the queue already * - * @parm q the queue + * @param q the queue * @param sid the integer id to check for * @return != 0 iff sid is already in the queue */ @@ -209,7 +208,6 @@ apr_status_t h2_fifo_create(h2_fifo **pfifo, apr_pool_t *pool, int capacity); apr_status_t h2_fifo_set_create(h2_fifo **pfifo, apr_pool_t *pool, int capacity); apr_status_t h2_fifo_term(h2_fifo *fifo); -apr_status_t h2_fifo_interrupt(h2_fifo *fifo); int h2_fifo_count(h2_fifo *fifo); @@ -229,7 +227,7 @@ apr_status_t h2_fifo_try_pull(h2_fifo *fifo, void **pelem); typedef enum { H2_FIFO_OP_PULL, /* pull the element from the queue, ie discard it */ - H2_FIFO_OP_REPUSH, /* pull and immediatley re-push it */ + H2_FIFO_OP_REPUSH, /* pull and immediately re-push it */ } h2_fifo_op_t; typedef h2_fifo_op_t h2_fifo_peek_fn(void *head, void *ctx); @@ -280,7 +278,6 @@ apr_status_t h2_ififo_create(h2_ififo **pfifo, apr_pool_t *pool, int capacity); apr_status_t h2_ififo_set_create(h2_ififo **pfifo, apr_pool_t *pool, int capacity); apr_status_t h2_ififo_term(h2_ififo *fifo); -apr_status_t h2_ififo_interrupt(h2_ififo *fifo); int h2_ififo_count(h2_ififo *fifo); @@ -345,9 +342,8 @@ apr_size_t h2_util_table_bytes(apr_table_t *t, apr_size_t pair_extra); /******************************************************************************* * HTTP/2 header helpers ******************************************************************************/ -int h2_req_ignore_header(const char *name, size_t len); -int h2_req_ignore_trailer(const char *name, size_t len); -int h2_res_ignore_trailer(const char *name, size_t len); +int h2_ignore_req_trailer(const char *name, size_t len); +int h2_ignore_resp_trailer(const char *name, size_t len); /** * Set the push policy for the given request. Takes request headers into @@ -378,52 +374,37 @@ const char *h2_util_base64url_encode(const char *data, * nghttp2 helpers ******************************************************************************/ -#define H2_HD_MATCH_LIT_CS(l, name) \ - ((strlen(name) == sizeof(l) - 1) && !apr_strnatcasecmp(l, name)) - -#define H2_CREATE_NV_LIT_CS(nv, NAME, VALUE) nv->name = (uint8_t *)NAME; \ - nv->namelen = sizeof(NAME) - 1; \ - nv->value = (uint8_t *)VALUE; \ - nv->valuelen = strlen(VALUE) - -#define H2_CREATE_NV_CS_LIT(nv, NAME, VALUE) nv->name = (uint8_t *)NAME; \ - nv->namelen = strlen(NAME); \ - nv->value = (uint8_t *)VALUE; \ - nv->valuelen = sizeof(VALUE) - 1 - -#define H2_CREATE_NV_CS_CS(nv, NAME, VALUE) nv->name = (uint8_t *)NAME; \ - nv->namelen = strlen(NAME); \ - nv->value = (uint8_t *)VALUE; \ - nv->valuelen = strlen(VALUE) - -int h2_util_ignore_header(const char *name); - -struct h2_headers; +int h2_util_ignore_resp_header(const char *name); typedef struct h2_ngheader { nghttp2_nv *nv; apr_size_t nvlen; } h2_ngheader; +#if AP_HAS_RESPONSE_BUCKETS +apr_status_t h2_res_create_ngtrailer(h2_ngheader **ph, apr_pool_t *p, + ap_bucket_headers *headers); +apr_status_t h2_res_create_ngheader(h2_ngheader **ph, apr_pool_t *p, + ap_bucket_response *response); +apr_status_t h2_req_create_ngheader(h2_ngheader **ph, apr_pool_t *p, + const struct h2_request *req); +#else apr_status_t h2_res_create_ngtrailer(h2_ngheader **ph, apr_pool_t *p, struct h2_headers *headers); apr_status_t h2_res_create_ngheader(h2_ngheader **ph, apr_pool_t *p, struct h2_headers *headers); apr_status_t h2_req_create_ngheader(h2_ngheader **ph, apr_pool_t *p, const struct h2_request *req); +#endif +/** + * Add a HTTP/2 header and return the table key if it really was added + * and not ignored. + */ apr_status_t h2_req_add_header(apr_table_t *headers, apr_pool_t *pool, const char *name, size_t nlen, - const char *value, size_t vlen); - -/******************************************************************************* - * h2_request helpers - ******************************************************************************/ - -struct h2_request *h2_req_create(int id, apr_pool_t *pool, const char *method, - const char *scheme, const char *authority, - const char *path, apr_table_t *header, - int serialize); + const char *value, size_t vlen, + size_t max_field_len, int *pwas_added); /******************************************************************************* * apr brigade helpers @@ -445,43 +426,10 @@ apr_status_t h2_brigade_copy_length(apr_bucket_brigade *dest, apr_bucket_brigade *src, apr_off_t length); -/** - * Return != 0 iff there is a FLUSH or EOS bucket in the brigade. - * @param bb the brigade to check on - * @return != 0 iff brigade holds FLUSH or EOS bucket (or both) - */ -int h2_util_has_eos(apr_bucket_brigade *bb, apr_off_t len); - -/** - * Check how many bytes of the desired amount are available and if the - * end of stream is reached by that amount. - * @param bb the brigade to check - * @param plen the desired length and, on return, the available length - * @param on return, if eos has been reached - */ -apr_status_t h2_util_bb_avail(apr_bucket_brigade *bb, - apr_off_t *plen, int *peos); - -typedef apr_status_t h2_util_pass_cb(void *ctx, +typedef apr_status_t h2_util_pass_cb(void *ctx, const char *data, apr_off_t len); /** - * Read at most *plen bytes from the brigade and pass them into the - * given callback. If cb is NULL, just return the amount of data that - * could have been read. - * If an EOS was/would be encountered, set *peos != 0. - * @param bb the brigade to read from - * @param cb the callback to invoke for the read data - * @param ctx optional data passed to callback - * @param plen inout, as input gives the maximum number of bytes to read, - * on return specifies the actual/would be number of bytes - * @param peos != 0 iff an EOS bucket was/would be encountered. - */ -apr_status_t h2_util_bb_readx(apr_bucket_brigade *bb, - h2_util_pass_cb *cb, void *ctx, - apr_off_t *plen, int *peos); - -/** * Print a bucket's meta data (type and length) to the buffer. * @return number of characters printed */ @@ -506,14 +454,16 @@ apr_size_t h2_util_bb_print(char *buffer, apr_size_t bmax, * @param bb the brigade to log */ #define h2_util_bb_log(c, sid, level, tag, bb) \ -do { \ - char buffer[4 * 1024]; \ - const char *line = "(null)"; \ - apr_size_t len, bmax = sizeof(buffer)/sizeof(buffer[0]); \ - len = h2_util_bb_print(buffer, bmax, (tag), "", (bb)); \ - ap_log_cerror(APLOG_MARK, level, 0, (c), "bb_dump(%ld): %s", \ - ((c)->master? (c)->master->id : (c)->id), (len? buffer : line)); \ -} while(0) +if (APLOG_C_IS_LEVEL(c, level)) { \ + do { \ + char buffer[4 * 1024]; \ + const char *line = "(null)"; \ + apr_size_t len, bmax = sizeof(buffer)/sizeof(buffer[0]); \ + len = h2_util_bb_print(buffer, bmax, (tag), "", (bb)); \ + ap_log_cerror(APLOG_MARK, level, 0, (c), "bb_dump(%ld): %s", \ + ((c)->master? (c)->master->id : (c)->id), (len? buffer : line)); \ + } while(0); \ +} typedef int h2_bucket_gate(apr_bucket *b); @@ -541,4 +491,29 @@ apr_status_t h2_append_brigade(apr_bucket_brigade *to, */ apr_off_t h2_brigade_mem_size(apr_bucket_brigade *bb); +/** + * Drain a pipe used for notification. + */ +void h2_util_drain_pipe(apr_file_t *pipe); + +/** + * Wait on data arriving on a pipe. + */ +apr_status_t h2_util_wait_on_pipe(apr_file_t *pipe); + + +#if AP_HAS_RESPONSE_BUCKETS +/** + * Give an estimate of the length of the header fields, + * without compression or other formatting decorations. + */ +apr_size_t headers_length_estimate(ap_bucket_headers *hdrs); + +/** + * Give an estimate of the length of the response meta data size, + * without compression or other formatting decorations. + */ +apr_size_t response_length_estimate(ap_bucket_response *resp); +#endif /* AP_HAS_RESPONSE_BUCKETS */ + #endif /* defined(__mod_h2__h2_util__) */ |