summaryrefslogtreecommitdiffstats
path: root/modules/http2/h2.h
diff options
context:
space:
mode:
Diffstat (limited to 'modules/http2/h2.h')
-rw-r--r--modules/http2/h2.h192
1 files changed, 192 insertions, 0 deletions
diff --git a/modules/http2/h2.h b/modules/http2/h2.h
new file mode 100644
index 0000000..250e726
--- /dev/null
+++ b/modules/http2/h2.h
@@ -0,0 +1,192 @@
+/* Licensed to the Apache Software Foundation (ASF) under one or more
+ * contributor license agreements. See the NOTICE file distributed with
+ * this work for additional information regarding copyright ownership.
+ * The ASF licenses this file to You under the Apache License, Version 2.0
+ * (the "License"); you may not use this file except in compliance with
+ * the License. You may obtain a copy of the License at
+ *
+ * http://www.apache.org/licenses/LICENSE-2.0
+ *
+ * Unless required by applicable law or agreed to in writing, software
+ * distributed under the License is distributed on an "AS IS" BASIS,
+ * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
+ * See the License for the specific language governing permissions and
+ * limitations under the License.
+ */
+
+#ifndef __mod_h2__h2__
+#define __mod_h2__h2__
+
+#include <apr_version.h>
+#include <ap_mmn.h>
+
+struct h2_session;
+struct h2_stream;
+
+/*
+ * When apr pollsets can poll file descriptors (e.g. pipes),
+ * we use it for polling stream input/output.
+ */
+#ifdef H2_NO_PIPES
+#define H2_USE_PIPES 0
+#else
+#define H2_USE_PIPES (APR_FILES_AS_SOCKETS && APR_VERSION_AT_LEAST(1,6,0))
+#endif
+
+/**
+ * The magic PRIamble of RFC 7540 that is always sent when starting
+ * a h2 communication.
+ */
+extern const char *H2_MAGIC_TOKEN;
+
+#define H2_ERR_NO_ERROR (0x00)
+#define H2_ERR_PROTOCOL_ERROR (0x01)
+#define H2_ERR_INTERNAL_ERROR (0x02)
+#define H2_ERR_FLOW_CONTROL_ERROR (0x03)
+#define H2_ERR_SETTINGS_TIMEOUT (0x04)
+#define H2_ERR_STREAM_CLOSED (0x05)
+#define H2_ERR_FRAME_SIZE_ERROR (0x06)
+#define H2_ERR_REFUSED_STREAM (0x07)
+#define H2_ERR_CANCEL (0x08)
+#define H2_ERR_COMPRESSION_ERROR (0x09)
+#define H2_ERR_CONNECT_ERROR (0x0a)
+#define H2_ERR_ENHANCE_YOUR_CALM (0x0b)
+#define H2_ERR_INADEQUATE_SECURITY (0x0c)
+#define H2_ERR_HTTP_1_1_REQUIRED (0x0d)
+
+#define H2_HEADER_METHOD ":method"
+#define H2_HEADER_METHOD_LEN 7
+#define H2_HEADER_SCHEME ":scheme"
+#define H2_HEADER_SCHEME_LEN 7
+#define H2_HEADER_AUTH ":authority"
+#define H2_HEADER_AUTH_LEN 10
+#define H2_HEADER_PATH ":path"
+#define H2_HEADER_PATH_LEN 5
+#define H2_CRLF "\r\n"
+
+/* Size of the frame header itself in HTTP/2 */
+#define H2_FRAME_HDR_LEN 9
+
+/* Max data size to write so it fits inside a TLS record */
+#define H2_DATA_CHUNK_SIZE ((16*1024) - 100 - H2_FRAME_HDR_LEN)
+
+/* Maximum number of padding bytes in a frame, rfc7540 */
+#define H2_MAX_PADLEN 256
+/* Initial default window size, RFC 7540 ch. 6.5.2 */
+#define H2_INITIAL_WINDOW_SIZE ((64*1024)-1)
+
+#define H2_STREAM_CLIENT_INITIATED(id) (id&0x01)
+
+#define H2_ALEN(a) (sizeof(a)/sizeof((a)[0]))
+
+#define H2MAX(x,y) ((x) > (y) ? (x) : (y))
+#define H2MIN(x,y) ((x) < (y) ? (x) : (y))
+
+typedef enum {
+ H2_DEPENDANT_AFTER,
+ H2_DEPENDANT_INTERLEAVED,
+ H2_DEPENDANT_BEFORE,
+} h2_dependency;
+
+typedef struct h2_priority {
+ h2_dependency dependency;
+ int weight;
+} h2_priority;
+
+typedef enum {
+ H2_PUSH_NONE,
+ H2_PUSH_DEFAULT,
+ H2_PUSH_HEAD,
+ H2_PUSH_FAST_LOAD,
+} h2_push_policy;
+
+typedef enum {
+ H2_SESSION_ST_INIT, /* send initial SETTINGS, etc. */
+ H2_SESSION_ST_DONE, /* finished, connection close */
+ H2_SESSION_ST_IDLE, /* nothing to write, expecting data inc */
+ H2_SESSION_ST_BUSY, /* read/write without stop */
+ H2_SESSION_ST_WAIT, /* waiting for c1 incoming + c2s output */
+ H2_SESSION_ST_CLEANUP, /* pool is being cleaned up */
+} h2_session_state;
+
+typedef struct h2_session_props {
+ int accepted_max; /* the highest remote stream id was/will be handled */
+ int completed_max; /* the highest remote stream completed */
+ int emitted_count; /* the number of local streams sent */
+ int emitted_max; /* the highest local stream id sent */
+ int error; /* the last session error encountered */
+ const char *error_msg; /* the short message given on the error */
+ unsigned int accepting : 1; /* if the session is accepting new streams */
+ unsigned int shutdown : 1; /* if the final GOAWAY has been sent */
+} h2_session_props;
+
+typedef enum h2_stream_state_t {
+ H2_SS_IDLE,
+ H2_SS_RSVD_R,
+ H2_SS_RSVD_L,
+ H2_SS_OPEN,
+ H2_SS_CLOSED_R,
+ H2_SS_CLOSED_L,
+ H2_SS_CLOSED,
+ H2_SS_CLEANUP,
+ H2_SS_MAX
+} h2_stream_state_t;
+
+typedef enum {
+ H2_SEV_CLOSED_L,
+ H2_SEV_CLOSED_R,
+ H2_SEV_CANCELLED,
+ H2_SEV_EOS_SENT,
+ H2_SEV_IN_ERROR,
+ H2_SEV_IN_DATA_PENDING,
+ H2_SEV_OUT_C1_BLOCK,
+} h2_stream_event_t;
+
+
+/* h2_request is the transformer of HTTP2 streams into HTTP/1.1 internal
+ * format that will be fed to various httpd input filters to finally
+ * become a request_rec to be handled by soemone.
+ */
+typedef struct h2_request h2_request;
+struct h2_request {
+ const char *method; /* pseudo header values, see ch. 8.1.2.3 */
+ const char *scheme;
+ const char *authority;
+ const char *path;
+ apr_table_t *headers;
+
+ apr_time_t request_time;
+ apr_off_t raw_bytes; /* RAW network bytes that generated this request - if known. */
+ int http_status; /* Store a possible HTTP status code that gets
+ * defined before creating the dummy HTTP/1.1
+ * request e.g. due to an error already
+ * detected.
+ */
+};
+
+/*
+ * A possible HTTP status code is not defined yet. See the http_status field
+ * in struct h2_request above for further explanation.
+ */
+#define H2_HTTP_STATUS_UNSET (0)
+
+typedef apr_status_t h2_io_data_cb(void *ctx, const char *data, apr_off_t len);
+
+typedef int h2_stream_pri_cmp_fn(int stream_id1, int stream_id2, void *session);
+typedef struct h2_stream *h2_stream_get_fn(struct h2_session *session, int stream_id);
+
+/* Note key to attach stream id to conn_rec/request_rec instances */
+#define H2_HDR_CONFORMANCE "http2-hdr-conformance"
+#define H2_HDR_CONFORMANCE_UNSAFE "unsafe"
+#define H2_PUSH_MODE_NOTE "http2-push-mode"
+
+
+#if AP_MODULE_MAGIC_AT_LEAST(20211221, 6)
+#define AP_HAS_RESPONSE_BUCKETS 1
+
+#else /* AP_MODULE_MAGIC_AT_LEAST(20211221, 6) */
+#define AP_HAS_RESPONSE_BUCKETS 0
+
+#endif /* else AP_MODULE_MAGIC_AT_LEAST(20211221, 6) */
+
+#endif /* defined(__mod_h2__h2__) */