summaryrefslogtreecommitdiff
path: root/serf_private.h
diff options
context:
space:
mode:
Diffstat (limited to 'serf_private.h')
-rw-r--r--serf_private.h353
1 files changed, 353 insertions, 0 deletions
diff --git a/serf_private.h b/serf_private.h
new file mode 100644
index 0000000..59e4db7
--- /dev/null
+++ b/serf_private.h
@@ -0,0 +1,353 @@
+/* Copyright 2002-2004 Justin Erenkrantz and Greg Stein
+ *
+ * Licensed 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 _SERF_PRIVATE_H_
+#define _SERF_PRIVATE_H_
+
+/* ### what the hell? why does the APR interface have a "size" ??
+ ### the implication is that, if we bust this limit, we'd need to
+ ### stop, rebuild a pollset, and repopulate it. what suckage. */
+#define MAX_CONN 16
+
+/* Windows does not define IOV_MAX, so we need to ensure it is defined. */
+#ifndef IOV_MAX
+#define IOV_MAX 16
+#endif
+
+#define SERF_IO_CLIENT (1)
+#define SERF_IO_CONN (2)
+#define SERF_IO_LISTENER (3)
+
+typedef struct serf__authn_scheme_t serf__authn_scheme_t;
+
+typedef struct serf_io_baton_t {
+ int type;
+ union {
+ serf_incoming_t *client;
+ serf_connection_t *conn;
+ serf_listener_t *listener;
+ } u;
+} serf_io_baton_t;
+
+/* Holds all the information corresponding to a request/response pair. */
+struct serf_request_t {
+ serf_connection_t *conn;
+
+ apr_pool_t *respool;
+ serf_bucket_alloc_t *allocator;
+
+ /* The bucket corresponding to the request. Will be NULL once the
+ * bucket has been emptied (for delivery into the socket).
+ */
+ serf_bucket_t *req_bkt;
+
+ serf_request_setup_t setup;
+ void *setup_baton;
+
+ serf_response_acceptor_t acceptor;
+ void *acceptor_baton;
+
+ serf_response_handler_t handler;
+ void *handler_baton;
+
+ serf_bucket_t *resp_bkt;
+
+ int written;
+ int priority;
+
+ struct serf_request_t *next;
+};
+
+typedef struct serf_pollset_t {
+ /* the set of connections to poll */
+ apr_pollset_t *pollset;
+} serf_pollset_t;
+
+typedef struct serf__authn_info_t {
+ const char *realm;
+
+ const serf__authn_scheme_t *scheme;
+
+ void *baton;
+} serf__authn_info_t;
+
+struct serf_context_t {
+ /* the pool used for self and for other allocations */
+ apr_pool_t *pool;
+
+ void *pollset_baton;
+ serf_socket_add_t pollset_add;
+ serf_socket_remove_t pollset_rm;
+
+ /* one of our connections has a dirty pollset state. */
+ int dirty_pollset;
+
+ /* the list of active connections */
+ apr_array_header_t *conns;
+#define GET_CONN(ctx, i) (((serf_connection_t **)(ctx)->conns->elts)[i])
+
+ /* Proxy server address */
+ apr_sockaddr_t *proxy_address;
+
+ /* Progress callback */
+ serf_progress_t progress_func;
+ void *progress_baton;
+ apr_off_t progress_read;
+ apr_off_t progress_written;
+
+ /* authentication info for this context, shared by all connections. */
+ serf__authn_info_t authn_info;
+ serf__authn_info_t proxy_authn_info;
+
+ /* List of authn types supported by the client.*/
+ int authn_types;
+ /* Callback function used to get credentials for a realm. */
+ serf_credentials_callback_t cred_cb;
+};
+
+struct serf_listener_t {
+ serf_context_t *ctx;
+ serf_io_baton_t baton;
+ apr_socket_t *skt;
+ apr_pool_t *pool;
+ apr_pollfd_t desc;
+ void *accept_baton;
+ serf_accept_client_t accept_func;
+};
+
+struct serf_incoming_t {
+ serf_context_t *ctx;
+ serf_io_baton_t baton;
+ void *request_baton;
+ serf_incoming_request_cb_t request;
+ apr_socket_t *skt;
+ apr_pollfd_t desc;
+};
+
+/* States for the different stages in the lifecyle of a connection. */
+typedef enum {
+ SERF_CONN_INIT, /* no socket created yet */
+ SERF_CONN_SETUP_SSLTUNNEL, /* ssl tunnel being setup, no requests sent */
+ SERF_CONN_CONNECTED, /* conn is ready to send requests */
+ SERF_CONN_CLOSING, /* conn is closing, no more requests,
+ start a new socket */
+} serf__connection_state_t;
+
+struct serf_connection_t {
+ serf_context_t *ctx;
+
+ apr_status_t status;
+ serf_io_baton_t baton;
+
+ apr_pool_t *pool;
+ serf_bucket_alloc_t *allocator;
+
+ apr_sockaddr_t *address;
+
+ apr_socket_t *skt;
+ apr_pool_t *skt_pool;
+
+ /* the last reqevents we gave to pollset_add */
+ apr_int16_t reqevents;
+
+ /* the events we've seen for this connection in our returned pollset */
+ apr_int16_t seen_in_pollset;
+
+ /* are we a dirty connection that needs its poll status updated? */
+ int dirty_conn;
+
+ /* number of completed requests we've sent */
+ unsigned int completed_requests;
+
+ /* number of completed responses we've got */
+ unsigned int completed_responses;
+
+ /* keepalive */
+ unsigned int probable_keepalive_limit;
+
+ /* Current state of the connection (whether or not it is connected). */
+ serf__connection_state_t state;
+
+ /* This connection may have responses without a request! */
+ int async_responses;
+ serf_bucket_t *current_async_response;
+ serf_response_acceptor_t async_acceptor;
+ void *async_acceptor_baton;
+ serf_response_handler_t async_handler;
+ void *async_handler_baton;
+
+ /* A bucket wrapped around our socket (for reading responses). */
+ serf_bucket_t *stream;
+ /* A reference to the aggregate bucket that provides the boundary between
+ * request level buckets and connection level buckets.
+ */
+ serf_bucket_t *ostream_head;
+ serf_bucket_t *ostream_tail;
+
+ /* Aggregate bucket used to send the CONNECT request. */
+ serf_bucket_t *ssltunnel_ostream;
+
+ /* The list of active requests. */
+ serf_request_t *requests;
+ serf_request_t *requests_tail;
+
+ /* The list of requests we're holding on to because we're going to
+ * reset the connection soon.
+ */
+ serf_request_t *hold_requests;
+ serf_request_t *hold_requests_tail;
+
+ struct iovec vec[IOV_MAX];
+ int vec_len;
+
+ serf_connection_setup_t setup;
+ void *setup_baton;
+ serf_connection_closed_t closed;
+ void *closed_baton;
+
+ /* Max. number of outstanding requests. */
+ unsigned int max_outstanding_requests;
+
+ int hit_eof;
+ /* Host info. */
+ const char *host_url;
+ apr_uri_t host_info;
+
+ /* connection and authentication scheme specific information */
+ void *authn_baton;
+ void *proxy_authn_baton;
+};
+
+/*** Authentication handler declarations ***/
+
+/**
+ * For each authentication scheme we need a handler function of type
+ * serf__auth_handler_func_t. This function will be called when an
+ * authentication challenge is received in a session.
+ */
+typedef apr_status_t
+(*serf__auth_handler_func_t)(int code,
+ serf_request_t *request,
+ serf_bucket_t *response,
+ const char *auth_hdr,
+ const char *auth_attr,
+ void *baton,
+ apr_pool_t *pool);
+
+/**
+ * For each authentication scheme we need an initialization function of type
+ * serf__init_context_func_t. This function will be called the first time
+ * serf tries a specific authentication scheme handler.
+ */
+typedef apr_status_t
+(*serf__init_context_func_t)(int code,
+ serf_context_t *conn,
+ apr_pool_t *pool);
+
+/**
+ * For each authentication scheme we need an initialization function of type
+ * serf__init_conn_func_t. This function will be called when a new
+ * connection is opened.
+ */
+typedef apr_status_t
+(*serf__init_conn_func_t)(int code,
+ serf_connection_t *conn,
+ apr_pool_t *pool);
+
+/**
+ * For each authentication scheme we need a setup_request function of type
+ * serf__setup_request_func_t. This function will be called when a
+ * new serf_request_t object is created and should fill in the correct
+ * authentication headers (if needed).
+ */
+typedef apr_status_t
+(*serf__setup_request_func_t)(int code,
+ serf_connection_t *conn,
+ const char *method,
+ const char *uri,
+ serf_bucket_t *hdrs_bkt);
+
+/**
+ * This function will be called when a response is received, so that the
+ * scheme handler can validate the Authentication related response headers
+ * (if needed).
+ */
+typedef apr_status_t
+(*serf__validate_response_func_t)(int code,
+ serf_connection_t *conn,
+ serf_request_t *request,
+ serf_bucket_t *response,
+ apr_pool_t *pool);
+
+/**
+ * serf__authn_scheme_t: vtable for an authn scheme provider.
+ */
+struct serf__authn_scheme_t {
+ /* The http status code that's handled by this authentication scheme.
+ Normal values are 401 for server authentication and 407 for proxy
+ authentication */
+ int code;
+
+ /* The name of this authentication scheme. This should be a case
+ sensitive match of the string sent in the HTTP authentication header. */
+ const char *name;
+
+ /* Internal code used for this authn type. */
+ int type;
+
+ /* The context initialization function if any; otherwise, NULL */
+ serf__init_context_func_t init_ctx_func;
+
+ /* The connection initialization function if any; otherwise, NULL */
+ serf__init_conn_func_t init_conn_func;
+
+ /* The authentication handler function */
+ serf__auth_handler_func_t handle_func;
+
+ /* Function to set up the authentication header of a request */
+ serf__setup_request_func_t setup_request_func;
+
+ /* Function to validate the authentication header of a response */
+ serf__validate_response_func_t validate_response_func;
+};
+
+/**
+ * Handles a 401 or 407 response, tries the different available authentication
+ * handlers.
+ */
+apr_status_t serf__handle_auth_response(int *consumed_response,
+ serf_request_t *request,
+ serf_bucket_t *response,
+ void *baton,
+ apr_pool_t *pool);
+
+/* fromt context.c */
+void serf__context_progress_delta(void *progress_baton, apr_off_t read,
+ apr_off_t written);
+
+/* from incoming.c */
+apr_status_t serf__process_client(serf_incoming_t *l, apr_int16_t events);
+apr_status_t serf__process_listener(serf_listener_t *l);
+
+/* from outgoing.c */
+apr_status_t serf__open_connections(serf_context_t *ctx);
+apr_status_t serf__process_connection(serf_connection_t *conn,
+ apr_int16_t events);
+apr_status_t serf__conn_update_pollset(serf_connection_t *conn);
+
+/* from ssltunnel.c */
+apr_status_t serf__ssltunnel_connect(serf_connection_t *conn);
+
+#endif