1 | /* Copyright 2002-2004 Justin Erenkrantz and Greg Stein
|
---|
2 | *
|
---|
3 | * Licensed under the Apache License, Version 2.0 (the "License");
|
---|
4 | * you may not use this file except in compliance with the License.
|
---|
5 | * You may obtain a copy of the License at
|
---|
6 | *
|
---|
7 | * http://www.apache.org/licenses/LICENSE-2.0
|
---|
8 | *
|
---|
9 | * Unless required by applicable law or agreed to in writing, software
|
---|
10 | * distributed under the License is distributed on an "AS IS" BASIS,
|
---|
11 | * WITHOUT WARRANTIES OR CONDITIONS OF ANY KIND, either express or implied.
|
---|
12 | * See the License for the specific language governing permissions and
|
---|
13 | * limitations under the License.
|
---|
14 | */
|
---|
15 |
|
---|
16 | #ifndef SERF_H
|
---|
17 | #define SERF_H
|
---|
18 |
|
---|
19 | /**
|
---|
20 | * @file serf.h
|
---|
21 | * @brief Main serf header file
|
---|
22 | */
|
---|
23 |
|
---|
24 | #include <apr.h>
|
---|
25 | #include <apr_errno.h>
|
---|
26 | #include <apr_allocator.h>
|
---|
27 | #include <apr_pools.h>
|
---|
28 | #include <apr_network_io.h>
|
---|
29 | #include <apr_time.h>
|
---|
30 | #include <apr_poll.h>
|
---|
31 | #include <apr_uri.h>
|
---|
32 |
|
---|
33 | #ifdef __cplusplus
|
---|
34 | extern "C" {
|
---|
35 | #endif
|
---|
36 |
|
---|
37 | /* Forward declare some structures */
|
---|
38 | typedef struct serf_context_t serf_context_t;
|
---|
39 |
|
---|
40 | typedef struct serf_bucket_t serf_bucket_t;
|
---|
41 | typedef struct serf_bucket_type_t serf_bucket_type_t;
|
---|
42 | typedef struct serf_bucket_alloc_t serf_bucket_alloc_t;
|
---|
43 |
|
---|
44 | typedef struct serf_connection_t serf_connection_t;
|
---|
45 | typedef struct serf_listener_t serf_listener_t;
|
---|
46 | typedef struct serf_incoming_t serf_incoming_t;
|
---|
47 | typedef struct serf_incoming_request_t serf_incoming_request_t;
|
---|
48 |
|
---|
49 | typedef struct serf_request_t serf_request_t;
|
---|
50 |
|
---|
51 |
|
---|
52 | /**
|
---|
53 | * @defgroup serf high-level constructs
|
---|
54 | * @ingroup serf
|
---|
55 | * @{
|
---|
56 | */
|
---|
57 |
|
---|
58 | /**
|
---|
59 | * Serf-specific error codes
|
---|
60 | */
|
---|
61 | #define SERF_ERROR_RANGE 100
|
---|
62 |
|
---|
63 | /* This code is for when this is the last response on this connection:
|
---|
64 | * i.e. do not send any more requests on this connection or expect
|
---|
65 | * any more responses.
|
---|
66 | */
|
---|
67 | #define SERF_ERROR_CLOSING (APR_OS_START_USERERR + SERF_ERROR_RANGE + 1)
|
---|
68 | /* This code is for when the connection terminated before the request
|
---|
69 | * could be processed on the other side.
|
---|
70 | */
|
---|
71 | #define SERF_ERROR_REQUEST_LOST (APR_OS_START_USERERR + SERF_ERROR_RANGE + 2)
|
---|
72 | /* This code is for when the connection is blocked - we can not proceed
|
---|
73 | * until something happens - generally due to SSL negotiation-like behavior
|
---|
74 | * where a write() is blocked until a read() is processed.
|
---|
75 | */
|
---|
76 | #define SERF_ERROR_WAIT_CONN (APR_OS_START_USERERR + SERF_ERROR_RANGE + 3)
|
---|
77 | /* This code is for when something went wrong during deflating compressed
|
---|
78 | * data e.g. a CRC error. */
|
---|
79 | #define SERF_ERROR_DECOMPRESSION_FAILED (APR_OS_START_USERERR + \
|
---|
80 | SERF_ERROR_RANGE + 4)
|
---|
81 | /* This code is for when a response received from a http server is not in
|
---|
82 | * http-compliant syntax. */
|
---|
83 | #define SERF_ERROR_BAD_HTTP_RESPONSE (APR_OS_START_USERERR + \
|
---|
84 | SERF_ERROR_RANGE + 5)
|
---|
85 |
|
---|
86 | /* General authentication related errors */
|
---|
87 | #define SERF_ERROR_AUTHN_FAILED (APR_OS_START_USERERR + SERF_ERROR_RANGE + 90)
|
---|
88 |
|
---|
89 | /* None of the available authn mechanisms for the request are supported */
|
---|
90 | #define SERF_ERROR_AUTHN_NOT_SUPPORTED (APR_OS_START_USERERR + SERF_ERROR_RANGE + 91)
|
---|
91 |
|
---|
92 | /* Authn was requested by the server but the header lacked some attribute */
|
---|
93 | #define SERF_ERROR_AUTHN_MISSING_ATTRIBUTE (APR_OS_START_USERERR + SERF_ERROR_RANGE + 92)
|
---|
94 |
|
---|
95 | /* Authentication handler initialization related errors */
|
---|
96 | #define SERF_ERROR_AUTHN_INITALIZATION_FAILED (APR_OS_START_USERERR +\
|
---|
97 | SERF_ERROR_RANGE + 93)
|
---|
98 |
|
---|
99 | /* This macro groups errors potentially raised when reading a http response. */
|
---|
100 | #define SERF_BAD_RESPONSE_ERROR(status) ((status) \
|
---|
101 | && ((SERF_ERROR_DECOMPRESSION_FAILED == (status)) \
|
---|
102 | ||(SERF_ERROR_BAD_HTTP_RESPONSE == (status))))
|
---|
103 |
|
---|
104 | /**
|
---|
105 | * Return a string that describes the specified error code.
|
---|
106 | *
|
---|
107 | * If the error code is not one of the above Serf error codes, then
|
---|
108 | * NULL will be returned.
|
---|
109 | *
|
---|
110 | * Note regarding lifetime: the string is a statically-allocated constant
|
---|
111 | */
|
---|
112 | const char *serf_error_string(apr_status_t errcode);
|
---|
113 |
|
---|
114 |
|
---|
115 | /**
|
---|
116 | * Create a new context for serf operations.
|
---|
117 | *
|
---|
118 | * A serf context defines a control loop which processes multiple
|
---|
119 | * connections simultaneously.
|
---|
120 | *
|
---|
121 | * The context will be allocated within @a pool.
|
---|
122 | */
|
---|
123 | serf_context_t *serf_context_create(
|
---|
124 | apr_pool_t *pool);
|
---|
125 |
|
---|
126 | /**
|
---|
127 | * Callback function. Add a socket to the externally managed poll set.
|
---|
128 | *
|
---|
129 | * Both @a pfd and @a serf_baton should be used when calling serf_event_trigger
|
---|
130 | * later.
|
---|
131 | */
|
---|
132 | typedef apr_status_t (*serf_socket_add_t)(
|
---|
133 | void *user_baton,
|
---|
134 | apr_pollfd_t *pfd,
|
---|
135 | void *serf_baton);
|
---|
136 |
|
---|
137 | /**
|
---|
138 | * Callback function. Remove the socket, identified by both @a pfd and
|
---|
139 | * @a serf_baton from the externally managed poll set.
|
---|
140 | */
|
---|
141 | typedef apr_status_t (*serf_socket_remove_t)(
|
---|
142 | void *user_baton,
|
---|
143 | apr_pollfd_t *pfd,
|
---|
144 | void *serf_baton);
|
---|
145 |
|
---|
146 | /* Create a new context for serf operations.
|
---|
147 | *
|
---|
148 | * Use this function to make serf not use its internal control loop, but
|
---|
149 | * instead rely on an external event loop. Serf will use the @a addf and @a rmf
|
---|
150 | * callbacks to notify of any event on a connection. The @a user_baton will be
|
---|
151 | * passed through the addf and rmf callbacks.
|
---|
152 | *
|
---|
153 | * The context will be allocated within @a pool.
|
---|
154 | */
|
---|
155 | serf_context_t *serf_context_create_ex(
|
---|
156 | void *user_baton,
|
---|
157 | serf_socket_add_t addf,
|
---|
158 | serf_socket_remove_t rmf,
|
---|
159 | apr_pool_t *pool);
|
---|
160 |
|
---|
161 | /**
|
---|
162 | * Make serf process events on a connection, identified by both @a pfd and
|
---|
163 | * @a serf_baton.
|
---|
164 | *
|
---|
165 | * Any outbound data is delivered, and incoming data is made available to
|
---|
166 | * the associated response handlers and their buckets.
|
---|
167 | *
|
---|
168 | * If any data is processed (incoming or outgoing), then this function will
|
---|
169 | * return with APR_SUCCESS.
|
---|
170 | */
|
---|
171 | apr_status_t serf_event_trigger(
|
---|
172 | serf_context_t *s,
|
---|
173 | void *serf_baton,
|
---|
174 | const apr_pollfd_t *pfd);
|
---|
175 |
|
---|
176 | /** @see serf_context_run should not block at all. */
|
---|
177 | #define SERF_DURATION_NOBLOCK 0
|
---|
178 | /** @see serf_context_run should run for (nearly) "forever". */
|
---|
179 | #define SERF_DURATION_FOREVER 2000000000 /* approx 1^31 */
|
---|
180 |
|
---|
181 | /**
|
---|
182 | * Run the main networking control loop.
|
---|
183 | *
|
---|
184 | * The set of connections defined by the serf context @a ctx are processed.
|
---|
185 | * Any outbound data is delivered, and incoming data is made available to
|
---|
186 | * the associated response handlers and their buckets. This function will
|
---|
187 | * block on the network for no longer than @a duration microseconds.
|
---|
188 | *
|
---|
189 | * If any data is processed (incoming or outgoing), then this function will
|
---|
190 | * return with APR_SUCCESS. Typically, the caller will just want to call it
|
---|
191 | * again to continue processing data.
|
---|
192 | *
|
---|
193 | * If no activity occurs within the specified timeout duration, then
|
---|
194 | * APR_TIMEUP is returned.
|
---|
195 | *
|
---|
196 | * All temporary allocations will be made in @a pool.
|
---|
197 | */
|
---|
198 | apr_status_t serf_context_run(
|
---|
199 | serf_context_t *ctx,
|
---|
200 | apr_short_interval_time_t duration,
|
---|
201 | apr_pool_t *pool);
|
---|
202 |
|
---|
203 |
|
---|
204 | apr_status_t serf_context_prerun(
|
---|
205 | serf_context_t *ctx);
|
---|
206 |
|
---|
207 | /**
|
---|
208 | * Callback function for progress information. @a progress indicates cumulative
|
---|
209 | * number of bytes read or written, for the whole context.
|
---|
210 | */
|
---|
211 | typedef void (*serf_progress_t)(
|
---|
212 | void *progress_baton,
|
---|
213 | apr_off_t read,
|
---|
214 | apr_off_t write);
|
---|
215 |
|
---|
216 | /**
|
---|
217 | * Sets the progress callback function. @a progress_func will be called every
|
---|
218 | * time bytes are read of or written on a socket.
|
---|
219 | */
|
---|
220 | void serf_context_set_progress_cb(
|
---|
221 | serf_context_t *ctx,
|
---|
222 | const serf_progress_t progress_func,
|
---|
223 | void *progress_baton);
|
---|
224 |
|
---|
225 | /** @} */
|
---|
226 |
|
---|
227 | /**
|
---|
228 | * @defgroup serf connections and requests
|
---|
229 | * @ingroup serf
|
---|
230 | * @{
|
---|
231 | */
|
---|
232 |
|
---|
233 | /**
|
---|
234 | * When a connection is established, the application needs to wrap some
|
---|
235 | * buckets around @a skt to enable serf to process incoming responses. This
|
---|
236 | * is the control point for assembling connection-level processing logic
|
---|
237 | * around the given socket.
|
---|
238 | *
|
---|
239 | * The @a setup_baton is the baton established at connection creation time.
|
---|
240 | *
|
---|
241 | * This callback corresponds to reading from the server. Since this is an
|
---|
242 | * on-demand activity, we use a callback. The corresponding write operation
|
---|
243 | * is based on the @see serf_request_deliver function, where the application
|
---|
244 | * can assemble the appropriate bucket(s) before delivery.
|
---|
245 | *
|
---|
246 | * The returned bucket should live at least as long as the connection itself.
|
---|
247 | * It is assumed that an appropriate allocator is passed in @a setup_baton.
|
---|
248 | * ### we may want to create a connection-level allocator and pass that
|
---|
249 | * ### along. however, that allocator would *only* be used for this
|
---|
250 | * ### callback. it may be wasteful to create a per-conn allocator, so this
|
---|
251 | * ### baton-based, app-responsible form might be best.
|
---|
252 | *
|
---|
253 | * Responsibility for the buckets is passed to the serf library. They will be
|
---|
254 | * destroyed when the connection is closed.
|
---|
255 | *
|
---|
256 | * All temporary allocations should be made in @a pool.
|
---|
257 | */
|
---|
258 | typedef apr_status_t (*serf_connection_setup_t)(
|
---|
259 | apr_socket_t *skt,
|
---|
260 | serf_bucket_t **read_bkt,
|
---|
261 | serf_bucket_t **write_bkt,
|
---|
262 | void *setup_baton,
|
---|
263 | apr_pool_t *pool);
|
---|
264 |
|
---|
265 | /**
|
---|
266 | * ### need to update docco w.r.t socket. became "stream" recently.
|
---|
267 | * ### the stream does not have a barrier, this callback should generally
|
---|
268 | * ### add a barrier around the stream before incorporating it into a
|
---|
269 | * ### response bucket stack.
|
---|
270 | * ### should serf add the barrier automatically to protect its data
|
---|
271 | * ### structure? i.e. the passed bucket becomes owned rather than
|
---|
272 | * ### borrowed. that might suit overall semantics better.
|
---|
273 | * Accept an incoming response for @a request, and its @a socket. A bucket
|
---|
274 | * for the response should be constructed and returned. This is the control
|
---|
275 | * point for assembling the appropriate wrapper buckets around the socket to
|
---|
276 | * enable processing of the incoming response.
|
---|
277 | *
|
---|
278 | * The @a acceptor_baton is the baton provided when the specified request
|
---|
279 | * was created.
|
---|
280 | *
|
---|
281 | * The request's pool and bucket allocator should be used for any allocations
|
---|
282 | * that need to live for the duration of the response. Care should be taken
|
---|
283 | * to bound the amount of memory stored in this pool -- to ensure that
|
---|
284 | * allocations are not proportional to the amount of data in the response.
|
---|
285 | *
|
---|
286 | * Responsibility for the bucket is passed to the serf library. It will be
|
---|
287 | * destroyed when the response has been fully read (the bucket returns an
|
---|
288 | * APR_EOF status from its read functions).
|
---|
289 | *
|
---|
290 | * All temporary allocations should be made in @a pool.
|
---|
291 | */
|
---|
292 | /* ### do we need to return an error? */
|
---|
293 | typedef serf_bucket_t * (*serf_response_acceptor_t)(
|
---|
294 | serf_request_t *request,
|
---|
295 | serf_bucket_t *stream,
|
---|
296 | void *acceptor_baton,
|
---|
297 | apr_pool_t *pool);
|
---|
298 |
|
---|
299 | /**
|
---|
300 | * Notification callback for when a connection closes.
|
---|
301 | *
|
---|
302 | * This callback is used to inform an application that the @a conn
|
---|
303 | * connection has been (abnormally) closed. The @a closed_baton is the
|
---|
304 | * baton provided when the connection was first opened. The reason for
|
---|
305 | * closure is given in @a why, and will be APR_SUCCESS if the application
|
---|
306 | * requested closure (by clearing the pool used to allocate this
|
---|
307 | * connection or calling serf_connection_close).
|
---|
308 | *
|
---|
309 | * All temporary allocations should be made in @a pool.
|
---|
310 | */
|
---|
311 | typedef void (*serf_connection_closed_t)(
|
---|
312 | serf_connection_t *conn,
|
---|
313 | void *closed_baton,
|
---|
314 | apr_status_t why,
|
---|
315 | apr_pool_t *pool);
|
---|
316 |
|
---|
317 | /**
|
---|
318 | * Response data has arrived and should be processed.
|
---|
319 | *
|
---|
320 | * Whenever response data for @a request arrives (initially, or continued data
|
---|
321 | * arrival), this handler is invoked. The response data is available in the
|
---|
322 | * @a response bucket. The @a handler_baton is passed along from the baton
|
---|
323 | * provided by the request setup callback (@see serf_request_setup_t).
|
---|
324 | *
|
---|
325 | * The handler MUST process data from the @a response bucket until the
|
---|
326 | * bucket's read function states it would block (see APR_STATUS_IS_EAGAIN).
|
---|
327 | * The handler is invoked only when new data arrives. If no further data
|
---|
328 | * arrives, and the handler does not process all available data, then the
|
---|
329 | * system can result in a deadlock around the unprocessed, but read, data.
|
---|
330 | *
|
---|
331 | * The handler should return APR_EOF when the response has been fully read.
|
---|
332 | * If calling the handler again would block, APR_EAGAIN should be returned.
|
---|
333 | * If the handler should be invoked again, simply return APR_SUCCESS.
|
---|
334 | *
|
---|
335 | * Note: if the connection closed (at the request of the application, or
|
---|
336 | * because of an (abnormal) termination) while a request is being delivered,
|
---|
337 | * or before a response arrives, then @a response will be NULL. This is the
|
---|
338 | * signal that the request was not delivered properly, and no further
|
---|
339 | * response should be expected (this callback will not be invoked again).
|
---|
340 | * If a request is injected into the connection (during this callback's
|
---|
341 | * execution, or otherwise), then the connection will be reopened.
|
---|
342 | *
|
---|
343 | * All temporary allocations should be made in @a pool.
|
---|
344 | */
|
---|
345 | typedef apr_status_t (*serf_response_handler_t)(
|
---|
346 | serf_request_t *request,
|
---|
347 | serf_bucket_t *response,
|
---|
348 | void *handler_baton,
|
---|
349 | apr_pool_t *pool);
|
---|
350 |
|
---|
351 | /**
|
---|
352 | * Callback function to be implemented by the application, so that serf
|
---|
353 | * can handle server and proxy authentication.
|
---|
354 | * code = 401 (server) or 407 (proxy).
|
---|
355 | * baton = the baton passed to serf_context_run.
|
---|
356 | * authn_type = one of "Basic", "Digest".
|
---|
357 | */
|
---|
358 | typedef apr_status_t (*serf_credentials_callback_t)(
|
---|
359 | char **username,
|
---|
360 | char **password,
|
---|
361 | serf_request_t *request, void *baton,
|
---|
362 | int code, const char *authn_type,
|
---|
363 | const char *realm,
|
---|
364 | apr_pool_t *pool);
|
---|
365 |
|
---|
366 | /**
|
---|
367 | * Create a new connection associated with the @a ctx serf context.
|
---|
368 | *
|
---|
369 | * A connection will be created to (eventually) connect to the address
|
---|
370 | * specified by @a address. The address must live at least as long as
|
---|
371 | * @a pool (thus, as long as the connection object).
|
---|
372 | *
|
---|
373 | * The connection object will be allocated within @a pool. Clearing or
|
---|
374 | * destroying this pool will close the connection, and terminate any
|
---|
375 | * outstanding requests or responses.
|
---|
376 | *
|
---|
377 | * When the connection is closed (upon request or because of an error),
|
---|
378 | * then the @a closed callback is invoked, and @a closed_baton is passed.
|
---|
379 | *
|
---|
380 | * ### doc on setup(_baton). tweak below comment re: acceptor.
|
---|
381 | * NULL may be passed for @a acceptor and @a closed; default implementations
|
---|
382 | * will be used.
|
---|
383 | *
|
---|
384 | * Note: the connection is not made immediately. It will be opened on
|
---|
385 | * the next call to @see serf_context_run.
|
---|
386 | */
|
---|
387 | serf_connection_t *serf_connection_create(
|
---|
388 | serf_context_t *ctx,
|
---|
389 | apr_sockaddr_t *address,
|
---|
390 | serf_connection_setup_t setup,
|
---|
391 | void *setup_baton,
|
---|
392 | serf_connection_closed_t closed,
|
---|
393 | void *closed_baton,
|
---|
394 | apr_pool_t *pool);
|
---|
395 |
|
---|
396 | /**
|
---|
397 | * Create a new connection associated with the @a ctx serf context.
|
---|
398 | *
|
---|
399 | * A connection will be created to (eventually) connect to the address
|
---|
400 | * specified by @a address. The address must live at least as long as
|
---|
401 | * @a pool (thus, as long as the connection object).
|
---|
402 | *
|
---|
403 | * The host address will be looked up based on the hostname in @a host_info.
|
---|
404 | *
|
---|
405 | * The connection object will be allocated within @a pool. Clearing or
|
---|
406 | * destroying this pool will close the connection, and terminate any
|
---|
407 | * outstanding requests or responses.
|
---|
408 | *
|
---|
409 | * When the connection is closed (upon request or because of an error),
|
---|
410 | * then the @a closed callback is invoked, and @a closed_baton is passed.
|
---|
411 | *
|
---|
412 | * ### doc on setup(_baton). tweak below comment re: acceptor.
|
---|
413 | * NULL may be passed for @a acceptor and @a closed; default implementations
|
---|
414 | * will be used.
|
---|
415 | *
|
---|
416 | * Note: the connection is not made immediately. It will be opened on
|
---|
417 | * the next call to @see serf_context_run.
|
---|
418 | */
|
---|
419 | apr_status_t serf_connection_create2(
|
---|
420 | serf_connection_t **conn,
|
---|
421 | serf_context_t *ctx,
|
---|
422 | apr_uri_t host_info,
|
---|
423 | serf_connection_setup_t setup,
|
---|
424 | void *setup_baton,
|
---|
425 | serf_connection_closed_t closed,
|
---|
426 | void *closed_baton,
|
---|
427 | apr_pool_t *pool);
|
---|
428 |
|
---|
429 |
|
---|
430 | typedef apr_status_t (*serf_accept_client_t)(
|
---|
431 | serf_context_t *ctx,
|
---|
432 | serf_listener_t *l,
|
---|
433 | void *accept_baton,
|
---|
434 | apr_socket_t *insock,
|
---|
435 | apr_pool_t *pool);
|
---|
436 |
|
---|
437 | apr_status_t serf_listener_create(
|
---|
438 | serf_listener_t **listener,
|
---|
439 | serf_context_t *ctx,
|
---|
440 | const char *host,
|
---|
441 | apr_uint16_t port,
|
---|
442 | void *accept_baton,
|
---|
443 | serf_accept_client_t accept_func,
|
---|
444 | apr_pool_t *pool);
|
---|
445 |
|
---|
446 | typedef apr_status_t (*serf_incoming_request_cb_t)(
|
---|
447 | serf_context_t *ctx,
|
---|
448 | serf_incoming_request_t *req,
|
---|
449 | void *request_baton,
|
---|
450 | apr_pool_t *pool);
|
---|
451 |
|
---|
452 | apr_status_t serf_incoming_create(
|
---|
453 | serf_incoming_t **client,
|
---|
454 | serf_context_t *ctx,
|
---|
455 | apr_socket_t *insock,
|
---|
456 | void *request_baton,
|
---|
457 | serf_incoming_request_cb_t request,
|
---|
458 | apr_pool_t *pool);
|
---|
459 |
|
---|
460 |
|
---|
461 |
|
---|
462 |
|
---|
463 | /**
|
---|
464 | * Reset the connection, but re-open the socket again.
|
---|
465 | */
|
---|
466 | apr_status_t serf_connection_reset(
|
---|
467 | serf_connection_t *conn);
|
---|
468 |
|
---|
469 | /**
|
---|
470 | * Close the connection associated with @a conn and cancel all pending requests.
|
---|
471 | *
|
---|
472 | * The closed callback passed to serf_connection_create() will be invoked
|
---|
473 | * with APR_SUCCESS.
|
---|
474 | */
|
---|
475 | apr_status_t serf_connection_close(
|
---|
476 | serf_connection_t *conn);
|
---|
477 |
|
---|
478 | /**
|
---|
479 | * Sets the maximum number of outstanding requests @a max_requests on the
|
---|
480 | * connection @a conn. Setting max_requests to 0 means unlimited (the default).
|
---|
481 | * Ex.: setting max_requests to 1 means a request is sent when a response on the
|
---|
482 | * previous request was received and handled.
|
---|
483 | */
|
---|
484 | void serf_connection_set_max_outstanding_requests(
|
---|
485 | serf_connection_t *conn,
|
---|
486 | unsigned int max_requests);
|
---|
487 |
|
---|
488 | void serf_connection_set_async_responses(
|
---|
489 | serf_connection_t *conn,
|
---|
490 | serf_response_acceptor_t acceptor,
|
---|
491 | void *acceptor_baton,
|
---|
492 | serf_response_handler_t handler,
|
---|
493 | void *handler_baton);
|
---|
494 |
|
---|
495 | /**
|
---|
496 | * Setup the @a request for delivery on its connection.
|
---|
497 | *
|
---|
498 | * Right before this is invoked, @a pool will be built within the
|
---|
499 | * connection's pool for the request to use. The associated response will
|
---|
500 | * be allocated within that subpool. An associated bucket allocator will
|
---|
501 | * be built. These items may be fetched from the request object through
|
---|
502 | * @see serf_request_get_pool or @see serf_request_get_alloc.
|
---|
503 | *
|
---|
504 | * The content of the request is specified by the @a req_bkt bucket. When
|
---|
505 | * a response arrives, the @a acceptor callback will be invoked (along with
|
---|
506 | * the @a acceptor_baton) to produce a response bucket. That bucket will then
|
---|
507 | * be passed to @a handler, along with the @a handler_baton.
|
---|
508 | *
|
---|
509 | * The responsibility for the request bucket is passed to the request
|
---|
510 | * object. When the request is done with the bucket, it will be destroyed.
|
---|
511 | */
|
---|
512 | typedef apr_status_t (*serf_request_setup_t)(
|
---|
513 | serf_request_t *request,
|
---|
514 | void *setup_baton,
|
---|
515 | serf_bucket_t **req_bkt,
|
---|
516 | serf_response_acceptor_t *acceptor,
|
---|
517 | void **acceptor_baton,
|
---|
518 | serf_response_handler_t *handler,
|
---|
519 | void **handler_baton,
|
---|
520 | apr_pool_t *pool);
|
---|
521 |
|
---|
522 | /**
|
---|
523 | * Construct a request object for the @a conn connection.
|
---|
524 | *
|
---|
525 | * When it is time to deliver the request, the @a setup callback will
|
---|
526 | * be invoked with the @a setup_baton passed into it to complete the
|
---|
527 | * construction of the request object.
|
---|
528 | *
|
---|
529 | * If the request has not (yet) been delivered, then it may be canceled
|
---|
530 | * with @see serf_request_cancel.
|
---|
531 | *
|
---|
532 | * Invoking any calls other than @see serf_request_cancel before the setup
|
---|
533 | * callback executes is not supported.
|
---|
534 | */
|
---|
535 | serf_request_t *serf_connection_request_create(
|
---|
536 | serf_connection_t *conn,
|
---|
537 | serf_request_setup_t setup,
|
---|
538 | void *setup_baton);
|
---|
539 |
|
---|
540 | /**
|
---|
541 | * Construct a request object for the @a conn connection, add it in the
|
---|
542 | * list as the next to-be-written request before all unwritten requests.
|
---|
543 | *
|
---|
544 | * When it is time to deliver the request, the @a setup callback will
|
---|
545 | * be invoked with the @a setup_baton passed into it to complete the
|
---|
546 | * construction of the request object.
|
---|
547 | *
|
---|
548 | * If the request has not (yet) been delivered, then it may be canceled
|
---|
549 | * with @see serf_request_cancel.
|
---|
550 | *
|
---|
551 | * Invoking any calls other than @see serf_request_cancel before the setup
|
---|
552 | * callback executes is not supported.
|
---|
553 | */
|
---|
554 | serf_request_t *serf_connection_priority_request_create(
|
---|
555 | serf_connection_t *conn,
|
---|
556 | serf_request_setup_t setup,
|
---|
557 | void *setup_baton);
|
---|
558 |
|
---|
559 | /**
|
---|
560 | * Cancel the request specified by the @a request object.
|
---|
561 | *
|
---|
562 | * If the request has been scheduled for delivery, then its response
|
---|
563 | * handler will be run, passing NULL for the response bucket.
|
---|
564 | *
|
---|
565 | * If the request has already been (partially or fully) delivered, then
|
---|
566 | * APR_EBUSY is returned and the request is *NOT* canceled. To properly
|
---|
567 | * cancel the request, the connection must be closed (by clearing or
|
---|
568 | * destroying its associated pool).
|
---|
569 | */
|
---|
570 | apr_status_t serf_request_cancel(
|
---|
571 | serf_request_t *request);
|
---|
572 |
|
---|
573 | /**
|
---|
574 | * Return the pool associated with @a request.
|
---|
575 | *
|
---|
576 | * WARNING: be very careful about the kinds of things placed into this
|
---|
577 | * pool. In particular, all allocation should be bounded in size, rather
|
---|
578 | * than proportional to any data stream.
|
---|
579 | */
|
---|
580 | apr_pool_t *serf_request_get_pool(
|
---|
581 | const serf_request_t *request);
|
---|
582 |
|
---|
583 | /**
|
---|
584 | * Return the bucket allocator associated with @a request.
|
---|
585 | */
|
---|
586 | serf_bucket_alloc_t *serf_request_get_alloc(
|
---|
587 | const serf_request_t *request);
|
---|
588 |
|
---|
589 | /**
|
---|
590 | * Return the connection associated with @a request.
|
---|
591 | */
|
---|
592 | serf_connection_t *serf_request_get_conn(
|
---|
593 | const serf_request_t *request);
|
---|
594 |
|
---|
595 | /**
|
---|
596 | * Update the @a handler and @a handler_baton for this @a request.
|
---|
597 | *
|
---|
598 | * This can be called after the request has started processing -
|
---|
599 | * subsequent data will be delivered to this new handler.
|
---|
600 | */
|
---|
601 | void serf_request_set_handler(
|
---|
602 | serf_request_t *request,
|
---|
603 | const serf_response_handler_t handler,
|
---|
604 | const void **handler_baton);
|
---|
605 |
|
---|
606 | /**
|
---|
607 | * Configure proxy server settings, to be used by all connections associated
|
---|
608 | * with the @a ctx serf context.
|
---|
609 | *
|
---|
610 | * The next connection will be created to connect to the proxy server
|
---|
611 | * specified by @a address. The address must live at least as long as the
|
---|
612 | * serf context.
|
---|
613 | */
|
---|
614 | void serf_config_proxy(
|
---|
615 | serf_context_t *ctx,
|
---|
616 | apr_sockaddr_t *address);
|
---|
617 |
|
---|
618 | /* Supported authentication types. */
|
---|
619 | #define SERF_AUTHN_NONE 0x00
|
---|
620 | #define SERF_AUTHN_BASIC 0x01
|
---|
621 | #define SERF_AUTHN_DIGEST 0x02
|
---|
622 | #define SERF_AUTHN_NTLM 0x04
|
---|
623 | #define SERF_AUTHN_NEGOTIATE 0x08
|
---|
624 | #define SERF_AUTHN_ALL 0xFF
|
---|
625 |
|
---|
626 | /**
|
---|
627 | * Define the authentication handlers that serf will try on incoming requests.
|
---|
628 | */
|
---|
629 | void serf_config_authn_types(
|
---|
630 | serf_context_t *ctx,
|
---|
631 | int authn_types);
|
---|
632 |
|
---|
633 | /**
|
---|
634 | * Set the credentials callback handler.
|
---|
635 | */
|
---|
636 | void serf_config_credentials_callback(
|
---|
637 | serf_context_t *ctx,
|
---|
638 | serf_credentials_callback_t cred_cb);
|
---|
639 |
|
---|
640 | /* ### maybe some connection control functions for flood? */
|
---|
641 |
|
---|
642 | /*** Special bucket creation functions ***/
|
---|
643 |
|
---|
644 | /**
|
---|
645 | * Create a bucket of type 'socket bucket'.
|
---|
646 | * This is basically a wrapper around @a serf_bucket_socket_create, which
|
---|
647 | * initializes the bucket using connection and/or context specific settings.
|
---|
648 | */
|
---|
649 | serf_bucket_t *serf_context_bucket_socket_create(
|
---|
650 | serf_context_t *ctx,
|
---|
651 | apr_socket_t *skt,
|
---|
652 | serf_bucket_alloc_t *allocator);
|
---|
653 |
|
---|
654 | /**
|
---|
655 | * Create a bucket of type 'request bucket'.
|
---|
656 | * This is basically a wrapper around @a serf_bucket_request_create, which
|
---|
657 | * initializes the bucket using request, connection and/or context specific
|
---|
658 | * settings.
|
---|
659 | *
|
---|
660 | * This function will set following header(s):
|
---|
661 | * - Host: if the connection was created with @a serf_connection_create2.
|
---|
662 | */
|
---|
663 | serf_bucket_t *serf_request_bucket_request_create(
|
---|
664 | serf_request_t *request,
|
---|
665 | const char *method,
|
---|
666 | const char *uri,
|
---|
667 | serf_bucket_t *body,
|
---|
668 | serf_bucket_alloc_t *allocator);
|
---|
669 |
|
---|
670 | /** @} */
|
---|
671 |
|
---|
672 |
|
---|
673 | /**
|
---|
674 | * @defgroup serf buckets
|
---|
675 | * @ingroup serf
|
---|
676 | * @{
|
---|
677 | */
|
---|
678 |
|
---|
679 | /** Pass as REQUESTED to the read function of a bucket to read, consume,
|
---|
680 | * and return all available data.
|
---|
681 | */
|
---|
682 | #define SERF_READ_ALL_AVAIL ((apr_size_t)-1)
|
---|
683 |
|
---|
684 | /** Acceptable newline types for bucket->readline(). */
|
---|
685 | #define SERF_NEWLINE_CR 0x0001
|
---|
686 | #define SERF_NEWLINE_CRLF 0x0002
|
---|
687 | #define SERF_NEWLINE_LF 0x0004
|
---|
688 | #define SERF_NEWLINE_ANY 0x0007
|
---|
689 |
|
---|
690 | /** Used to indicate that a newline is not present in the data buffer. */
|
---|
691 | /* ### should we make this zero? */
|
---|
692 | #define SERF_NEWLINE_NONE 0x0008
|
---|
693 |
|
---|
694 | /** Used to indicate that a CR was found at the end of a buffer, and CRLF
|
---|
695 | * was acceptable. It may be that the LF is present, but it needs to be
|
---|
696 | * read first.
|
---|
697 | *
|
---|
698 | * Note: an alternative to using this symbol would be for callers to see
|
---|
699 | * the SERF_NEWLINE_CR return value, and know that some "end of buffer" was
|
---|
700 | * reached. While this works well for @see serf_util_readline, it does not
|
---|
701 | * necessary work as well for buckets (there is no obvious "end of buffer",
|
---|
702 | * although there is an "end of bucket"). The other problem with that
|
---|
703 | * alternative is that developers might miss the condition. This symbol
|
---|
704 | * calls out the possibility and ensures that callers will watch for it.
|
---|
705 | */
|
---|
706 | #define SERF_NEWLINE_CRLF_SPLIT 0x0010
|
---|
707 |
|
---|
708 |
|
---|
709 | struct serf_bucket_type_t {
|
---|
710 |
|
---|
711 | /** name of this bucket type */
|
---|
712 | const char *name;
|
---|
713 |
|
---|
714 | /**
|
---|
715 | * Read (and consume) up to @a requested bytes from @a bucket.
|
---|
716 | *
|
---|
717 | * A pointer to the data will be returned in @a data, and its length
|
---|
718 | * is specified by @a len.
|
---|
719 | *
|
---|
720 | * The data will exist until one of two conditions occur:
|
---|
721 | *
|
---|
722 | * 1) this bucket is destroyed
|
---|
723 | * 2) another call to any read function or to peek()
|
---|
724 | *
|
---|
725 | * If an application needs the data to exist for a longer duration,
|
---|
726 | * then it must make a copy.
|
---|
727 | */
|
---|
728 | apr_status_t (*read)(serf_bucket_t *bucket, apr_size_t requested,
|
---|
729 | const char **data, apr_size_t *len);
|
---|
730 |
|
---|
731 | /**
|
---|
732 | * Read (and consume) a line of data from @a bucket.
|
---|
733 | *
|
---|
734 | * The acceptable forms of a newline are given by @a acceptable, and
|
---|
735 | * the type found is returned in @a found. If a newline is not present
|
---|
736 | * in the returned data, then SERF_NEWLINE_NONE is stored into @a found.
|
---|
737 | *
|
---|
738 | * A pointer to the data is returned in @a data, and its length is
|
---|
739 | * specified by @a len. The data will include the newline, if present.
|
---|
740 | *
|
---|
741 | * Note that there is no way to limit the amount of data returned
|
---|
742 | * by this function.
|
---|
743 | *
|
---|
744 | * The lifetime of the data is the same as that of the @see read
|
---|
745 | * function above.
|
---|
746 | */
|
---|
747 | apr_status_t (*readline)(serf_bucket_t *bucket, int acceptable,
|
---|
748 | int *found,
|
---|
749 | const char **data, apr_size_t *len);
|
---|
750 |
|
---|
751 | /**
|
---|
752 | * Read a set of pointer/length pairs from the bucket.
|
---|
753 | *
|
---|
754 | * The size of the @a vecs array is specified by @a vecs_size. The
|
---|
755 | * bucket should fill in elements of the array, and return the number
|
---|
756 | * used in @a vecs_used.
|
---|
757 | *
|
---|
758 | * Each element of @a vecs should specify a pointer to a block of
|
---|
759 | * data and a length of that data.
|
---|
760 | *
|
---|
761 | * The total length of all data elements should not exceed the
|
---|
762 | * amount specified in @a requested.
|
---|
763 | *
|
---|
764 | * The lifetime of the data is the same as that of the @see read
|
---|
765 | * function above.
|
---|
766 | */
|
---|
767 | apr_status_t (*read_iovec)(serf_bucket_t *bucket, apr_size_t requested,
|
---|
768 | int vecs_size, struct iovec *vecs,
|
---|
769 | int *vecs_used);
|
---|
770 |
|
---|
771 | /**
|
---|
772 | * Read data from the bucket in a form suitable for apr_socket_sendfile()
|
---|
773 | *
|
---|
774 | * On input, hdtr->numheaders and hdtr->numtrailers specify the size
|
---|
775 | * of the hdtr->headers and hdtr->trailers arrays, respectively. The
|
---|
776 | * bucket should fill in the headers and trailers, up to the specified
|
---|
777 | * limits, and set numheaders and numtrailers to the number of iovecs
|
---|
778 | * filled in for each item.
|
---|
779 | *
|
---|
780 | * @a file should be filled in with a file that can be read. If a file
|
---|
781 | * is not available or appropriate, then NULL should be stored. The
|
---|
782 | * file offset for the data should be stored in @a offset, and the
|
---|
783 | * length of that data should be stored in @a len. If a file is not
|
---|
784 | * returned, then @a offset and @a len should be ignored.
|
---|
785 | *
|
---|
786 | * The file position is not required to correspond to @a offset, and
|
---|
787 | * the caller may manipulate it at will.
|
---|
788 | *
|
---|
789 | * The total length of all data elements, and the portion of the
|
---|
790 | * file should not exceed the amount specified in @a requested.
|
---|
791 | *
|
---|
792 | * The lifetime of the data is the same as that of the @see read
|
---|
793 | * function above.
|
---|
794 | */
|
---|
795 | apr_status_t (*read_for_sendfile)(serf_bucket_t *bucket,
|
---|
796 | apr_size_t requested, apr_hdtr_t *hdtr,
|
---|
797 | apr_file_t **file, apr_off_t *offset,
|
---|
798 | apr_size_t *len);
|
---|
799 |
|
---|
800 | /**
|
---|
801 | * Look within @a bucket for a bucket of the given @a type. The bucket
|
---|
802 | * must be the "initial" data because it will be consumed by this
|
---|
803 | * function. If the given bucket type is available, then read and consume
|
---|
804 | * it, and return it to the caller.
|
---|
805 | *
|
---|
806 | * This function is usually used by readers that have custom handling
|
---|
807 | * for specific bucket types (e.g. looking for a file bucket to pass
|
---|
808 | * to apr_socket_sendfile).
|
---|
809 | *
|
---|
810 | * If a bucket of the given type is not found, then NULL is returned.
|
---|
811 | *
|
---|
812 | * The returned bucket becomes the responsibility of the caller. When
|
---|
813 | * the caller is done with the bucket, it should be destroyed.
|
---|
814 | */
|
---|
815 | serf_bucket_t * (*read_bucket)(serf_bucket_t *bucket,
|
---|
816 | const serf_bucket_type_t *type);
|
---|
817 |
|
---|
818 | /**
|
---|
819 | * Peek, but don't consume, the data in @a bucket.
|
---|
820 | *
|
---|
821 | * Since this function is non-destructive, the implicit read size is
|
---|
822 | * SERF_READ_ALL_AVAIL. The caller can then use whatever amount is
|
---|
823 | * appropriate.
|
---|
824 | *
|
---|
825 | * The @a data parameter will point to the data, and @a len will
|
---|
826 | * specify how much data is available. The lifetime of the data follows
|
---|
827 | * the same rules as the @see read function above.
|
---|
828 | *
|
---|
829 | * Note: if the peek does not return enough data for your particular
|
---|
830 | * use, then you must read/consume some first, then peek again.
|
---|
831 | *
|
---|
832 | * If the returned data represents all available data, then APR_EOF
|
---|
833 | * will be returned. Since this function does not consume data, it
|
---|
834 | * can return the same data repeatedly rather than blocking; thus,
|
---|
835 | * APR_EAGAIN will never be returned.
|
---|
836 | */
|
---|
837 | apr_status_t (*peek)(serf_bucket_t *bucket,
|
---|
838 | const char **data, apr_size_t *len);
|
---|
839 |
|
---|
840 | /**
|
---|
841 | * Destroy @a bucket, along with any associated resources.
|
---|
842 | */
|
---|
843 | void (*destroy)(serf_bucket_t *bucket);
|
---|
844 |
|
---|
845 | /* ### apr buckets have 'copy', 'split', and 'setaside' functions.
|
---|
846 | ### not sure whether those will be needed in this bucket model.
|
---|
847 | */
|
---|
848 | };
|
---|
849 |
|
---|
850 | /**
|
---|
851 | * Should the use and lifecycle of buckets be tracked?
|
---|
852 | *
|
---|
853 | * When tracking, the system will ensure several semantic requirements
|
---|
854 | * of bucket use:
|
---|
855 | *
|
---|
856 | * - if a bucket returns APR_EAGAIN, one of its read functions should
|
---|
857 | * not be called immediately. the context's run loop should be called.
|
---|
858 | * ### and for APR_EOF, too?
|
---|
859 | * - all buckets must be drained of input before returning to the
|
---|
860 | * context's run loop.
|
---|
861 | * - buckets should not be destroyed before they return APR_EOF unless
|
---|
862 | * the connection is closed for some reason.
|
---|
863 | *
|
---|
864 | * Undefine this symbol to avoid the tracking (and a performance gain).
|
---|
865 | *
|
---|
866 | * ### we may want to examine when/how we provide this. should it always
|
---|
867 | * ### be compiled in? and apps select it before including this header?
|
---|
868 | */
|
---|
869 | /* #define SERF_DEBUG_BUCKET_USE */
|
---|
870 |
|
---|
871 |
|
---|
872 | /* Internal macros for tracking bucket use. */
|
---|
873 | #ifdef SERF_DEBUG_BUCKET_USE
|
---|
874 | #define SERF__RECREAD(b,s) serf_debug__record_read(b,s)
|
---|
875 | #else
|
---|
876 | #define SERF__RECREAD(b,s) (s)
|
---|
877 | #endif
|
---|
878 |
|
---|
879 | #define serf_bucket_read(b,r,d,l) SERF__RECREAD(b, (b)->type->read(b,r,d,l))
|
---|
880 | #define serf_bucket_readline(b,a,f,d,l) \
|
---|
881 | SERF__RECREAD(b, (b)->type->readline(b,a,f,d,l))
|
---|
882 | #define serf_bucket_read_iovec(b,r,s,v,u) \
|
---|
883 | SERF__RECREAD(b, (b)->type->read_iovec(b,r,s,v,u))
|
---|
884 | #define serf_bucket_read_for_sendfile(b,r,h,f,o,l) \
|
---|
885 | SERF__RECREAD(b, (b)->type->read_for_sendfile(b,r,h,f,o,l))
|
---|
886 | #define serf_bucket_read_bucket(b,t) ((b)->type->read_bucket(b,t))
|
---|
887 | #define serf_bucket_peek(b,d,l) ((b)->type->peek(b,d,l))
|
---|
888 | #define serf_bucket_destroy(b) ((b)->type->destroy(b))
|
---|
889 |
|
---|
890 | /**
|
---|
891 | * Check whether a real error occurred. Note that bucket read functions
|
---|
892 | * can return EOF and EAGAIN as part of their "normal" operation, so they
|
---|
893 | * should not be considered an error.
|
---|
894 | */
|
---|
895 | #define SERF_BUCKET_READ_ERROR(status) ((status) \
|
---|
896 | && !APR_STATUS_IS_EOF(status) \
|
---|
897 | && !APR_STATUS_IS_EAGAIN(status) \
|
---|
898 | && (SERF_ERROR_WAIT_CONN != status))
|
---|
899 |
|
---|
900 |
|
---|
901 | struct serf_bucket_t {
|
---|
902 |
|
---|
903 | /** the type of this bucket */
|
---|
904 | const serf_bucket_type_t *type;
|
---|
905 |
|
---|
906 | /** bucket-private data */
|
---|
907 | void *data;
|
---|
908 |
|
---|
909 | /** the allocator used for this bucket (needed at destroy time) */
|
---|
910 | serf_bucket_alloc_t *allocator;
|
---|
911 | };
|
---|
912 |
|
---|
913 |
|
---|
914 | /**
|
---|
915 | * Generic macro to construct "is TYPE" macros.
|
---|
916 | */
|
---|
917 | #define SERF_BUCKET_CHECK(b, btype) ((b)->type == &serf_bucket_type_ ## btype)
|
---|
918 |
|
---|
919 |
|
---|
920 | /**
|
---|
921 | * Notification callback for a block that was not returned to the bucket
|
---|
922 | * allocator when its pool was destroyed.
|
---|
923 | *
|
---|
924 | * The block of memory is given by @a block. The baton provided when the
|
---|
925 | * allocator was constructed is passed as @a unfreed_baton.
|
---|
926 | */
|
---|
927 | typedef void (*serf_unfreed_func_t)(
|
---|
928 | void *unfreed_baton,
|
---|
929 | void *block);
|
---|
930 |
|
---|
931 | /**
|
---|
932 | * Create a new allocator for buckets.
|
---|
933 | *
|
---|
934 | * All buckets are associated with a serf bucket allocator. This allocator
|
---|
935 | * will be created within @a pool and will be destroyed when that pool is
|
---|
936 | * cleared or destroyed.
|
---|
937 | *
|
---|
938 | * When the allocator is destroyed, if any allocations were not explicitly
|
---|
939 | * returned (by calling serf_bucket_mem_free), then the @a unfreed callback
|
---|
940 | * will be invoked for each block. @a unfreed_baton will be passed to the
|
---|
941 | * callback.
|
---|
942 | *
|
---|
943 | * If @a unfreed is NULL, then the library will invoke the abort() stdlib
|
---|
944 | * call. Any failure to return memory is a bug in the application, and an
|
---|
945 | * abort can assist with determining what kinds of memory were not freed.
|
---|
946 | */
|
---|
947 | serf_bucket_alloc_t *serf_bucket_allocator_create(
|
---|
948 | apr_pool_t *pool,
|
---|
949 | serf_unfreed_func_t unfreed,
|
---|
950 | void *unfreed_baton);
|
---|
951 |
|
---|
952 | /**
|
---|
953 | * Return the pool that was used for this @a allocator.
|
---|
954 | *
|
---|
955 | * WARNING: the use of this pool for allocations requires a very
|
---|
956 | * detailed understanding of pool behaviors, the bucket system,
|
---|
957 | * and knowledge of the bucket's use within the overall pattern
|
---|
958 | * of request/response behavior.
|
---|
959 | *
|
---|
960 | * See design-guide.txt for more information about pool usage.
|
---|
961 | */
|
---|
962 | apr_pool_t *serf_bucket_allocator_get_pool(
|
---|
963 | const serf_bucket_alloc_t *allocator);
|
---|
964 |
|
---|
965 |
|
---|
966 | /**
|
---|
967 | * Utility structure for reading a complete line of input from a bucket.
|
---|
968 | *
|
---|
969 | * Since it is entirely possible for a line to be broken by APR_EAGAIN,
|
---|
970 | * this structure can be used to accumulate the data until a complete line
|
---|
971 | * has been read from a bucket.
|
---|
972 | */
|
---|
973 |
|
---|
974 | /* This limit applies to the line buffer functions. If an application needs
|
---|
975 | * longer lines, then they will need to manually handle line buffering.
|
---|
976 | */
|
---|
977 | #define SERF_LINEBUF_LIMIT 8000
|
---|
978 |
|
---|
979 | typedef struct {
|
---|
980 |
|
---|
981 | /* Current state of the buffer. */
|
---|
982 | enum {
|
---|
983 | SERF_LINEBUF_EMPTY,
|
---|
984 | SERF_LINEBUF_READY,
|
---|
985 | SERF_LINEBUF_PARTIAL,
|
---|
986 | SERF_LINEBUF_CRLF_SPLIT
|
---|
987 | } state;
|
---|
988 |
|
---|
989 | /* How much of the buffer have we used? */
|
---|
990 | apr_size_t used;
|
---|
991 |
|
---|
992 | /* The line is read into this buffer, minus CR/LF */
|
---|
993 | char line[SERF_LINEBUF_LIMIT];
|
---|
994 |
|
---|
995 | } serf_linebuf_t;
|
---|
996 |
|
---|
997 | /**
|
---|
998 | * Initialize the @a linebuf structure.
|
---|
999 | */
|
---|
1000 | void serf_linebuf_init(serf_linebuf_t *linebuf);
|
---|
1001 |
|
---|
1002 | /**
|
---|
1003 | * Fetch a line of text from @a bucket, accumulating the line into
|
---|
1004 | * @a linebuf. @a acceptable specifies the types of newlines which are
|
---|
1005 | * acceptable for this fetch.
|
---|
1006 | *
|
---|
1007 | * ### we should return a data/len pair so that we can avoid a copy,
|
---|
1008 | * ### rather than having callers look into our state and line buffer.
|
---|
1009 | */
|
---|
1010 | apr_status_t serf_linebuf_fetch(
|
---|
1011 | serf_linebuf_t *linebuf,
|
---|
1012 | serf_bucket_t *bucket,
|
---|
1013 | int acceptable);
|
---|
1014 |
|
---|
1015 | /** @} */
|
---|
1016 |
|
---|
1017 |
|
---|
1018 | /* Internal functions for bucket use and lifecycle tracking */
|
---|
1019 | apr_status_t serf_debug__record_read(
|
---|
1020 | const serf_bucket_t *bucket,
|
---|
1021 | apr_status_t status);
|
---|
1022 | void serf_debug__entered_loop(
|
---|
1023 | serf_bucket_alloc_t *allocator);
|
---|
1024 | void serf_debug__closed_conn(
|
---|
1025 | serf_bucket_alloc_t *allocator);
|
---|
1026 | void serf_debug__bucket_destroy(
|
---|
1027 | const serf_bucket_t *bucket);
|
---|
1028 | void serf_debug__bucket_alloc_check(
|
---|
1029 | serf_bucket_alloc_t *allocator);
|
---|
1030 |
|
---|
1031 | /* Version info */
|
---|
1032 | #define SERF_MAJOR_VERSION 1
|
---|
1033 | #define SERF_MINOR_VERSION 1
|
---|
1034 | #define SERF_PATCH_VERSION 0
|
---|
1035 |
|
---|
1036 | /* Version number string */
|
---|
1037 | #define SERF_VERSION_STRING APR_STRINGIFY(SERF_MAJOR_VERSION) "." \
|
---|
1038 | APR_STRINGIFY(SERF_MINOR_VERSION) "." \
|
---|
1039 | APR_STRINGIFY(SERF_PATCH_VERSION)
|
---|
1040 |
|
---|
1041 | /**
|
---|
1042 | * Check at compile time if the Serf version is at least a certain
|
---|
1043 | * level.
|
---|
1044 | * @param major The major version component of the version checked
|
---|
1045 | * for (e.g., the "1" of "1.3.0").
|
---|
1046 | * @param minor The minor version component of the version checked
|
---|
1047 | * for (e.g., the "3" of "1.3.0").
|
---|
1048 | * @param patch The patch level component of the version checked
|
---|
1049 | * for (e.g., the "0" of "1.3.0").
|
---|
1050 | */
|
---|
1051 | #define SERF_VERSION_AT_LEAST(major,minor,patch) \
|
---|
1052 | (((major) < SERF_MAJOR_VERSION) \
|
---|
1053 | || ((major) == SERF_MAJOR_VERSION && (minor) < SERF_MINOR_VERSION) \
|
---|
1054 | || ((major) == SERF_MAJOR_VERSION && (minor) == SERF_MINOR_VERSION && \
|
---|
1055 | (patch) <= SERF_PATCH_VERSION))
|
---|
1056 |
|
---|
1057 |
|
---|
1058 | /**
|
---|
1059 | * Returns the version of the library the application has linked/loaded.
|
---|
1060 | * Values are returned in @a major, @a minor, and @a patch.
|
---|
1061 | *
|
---|
1062 | * Applications will want to use this function to verify compatibility,
|
---|
1063 | * expecially while serf has not reached a 1.0 milestone. APIs and
|
---|
1064 | * semantics may change drastically until the library hits 1.0.
|
---|
1065 | */
|
---|
1066 | void serf_lib_version(
|
---|
1067 | int *major,
|
---|
1068 | int *minor,
|
---|
1069 | int *patch);
|
---|
1070 |
|
---|
1071 |
|
---|
1072 | #ifdef __cplusplus
|
---|
1073 | }
|
---|
1074 | #endif
|
---|
1075 |
|
---|
1076 |
|
---|
1077 | /*
|
---|
1078 | * Every user of serf will want to deal with our various bucket types.
|
---|
1079 | * Go ahead and include that header right now.
|
---|
1080 | *
|
---|
1081 | * Note: make sure this occurs outside of the C++ namespace block
|
---|
1082 | */
|
---|
1083 | #include "serf_bucket_types.h"
|
---|
1084 |
|
---|
1085 |
|
---|
1086 | #endif /* !SERF_H */
|
---|