mmlib/mmat: replace some variables by literal constants
[mmondor.git] / tests / bktr_httpd / client.c
CommitLineData
a09176ab 1/* $Id: client.c,v 1.11 2008/09/07 06:21:51 mmondor Exp $ */
ce436d0b
MM
2
3/*
4 * Copyright (c) 2008, Matthew Mondor
5 * ALL RIGHTS RESERVED.
6 */
7
8
9#include <stdlib.h>
e583c3d8 10#include <unistd.h>
ce436d0b 11
c20ad7db 12#include "types.h"
dacf6158 13#include "net.h"
ce436d0b 14#include "client.h"
e583c3d8 15#include "sendq.h"
23ab503c 16#include "recvq.h"
1eece7b6 17#include "http.h"
ce436d0b
MM
18
19
23ab503c
MM
20static bool client_ctor(pnode_t *);
21static void client_dtor(pnode_t *);
e3a154c0 22static inline void client_destroy(client_t *, client_t **);
0ab43060
MM
23
24
e3a154c0 25static pool_t client_pool;
ce436d0b 26
e3a154c0
MM
27list_t client_list;
28static list_t client_destroy_list;
fa6ec601 29
ce436d0b
MM
30
31bool
32client_init(void)
33{
34
23ab503c
MM
35 if (!pool_init(&client_pool, "client_pool", malloc, free,
36 client_ctor, client_dtor,
ce436d0b
MM
37 sizeof(client_t), 65536 / sizeof(client_t), 1, 0))
38 return false;
39
0ab43060
MM
40 DLIST_INIT(&client_list);
41 DLIST_INIT(&client_destroy_list);
42
ce436d0b
MM
43 return true;
44}
45
23ab503c
MM
46static bool
47client_ctor(pnode_t *pn)
48{
49 client_t *c = (client_t *)pn;
50
51 return recvq_alloc(&c->recvq);
52}
53
54static void
55client_dtor(pnode_t *pn)
56{
57 client_t *c = (client_t *)pn;
58
59 recvq_free(&c->recvq);
60}
61
ce436d0b 62client_t *
f37281a9 63client_new(netaddr_t *naddr, int fd, time_t exp)
ce436d0b
MM
64{
65 client_t *c;
66
67 if ((c = (client_t *)pool_alloc(&client_pool, false)) != NULL) {
68 DLIST_INIT(&c->sendq);
23ab503c 69 recvq_init(&c->recvq);
1eece7b6 70 http_init(&c->http);
dacf6158 71 c->netaddr = naddr;
e583c3d8
MM
72 c->fd = fd;
73 c->first = true;
74 c->skip = c->skipcnt = 0;
0ab43060 75 c->todestroy = false;
f37281a9 76 c->expires = exp;
23ab503c 77 c->state = CSTATE_REQUEST;
a09176ab 78 DLIST_APPEND(&client_list, (node_t *)c);
ce436d0b
MM
79 }
80
81 return c;
82}
83
84void
0ab43060
MM
85client_destroy_mark(client_t *c)
86{
87
88 if (c == NULL || c->todestroy)
89 return;
90
91 c->todestroy = true;
92 DLIST_SWAP(&client_destroy_list, &client_list, (node_t *)c, false);
93}
94
95void
96client_destroy_marked(client_t **idx)
97{
98 node_t *n, *next;
99
100 for (n = DLIST_TOP(&client_destroy_list); n != NULL; n = next) {
101 next = DLIST_NEXT(n);
102
103 DLIST_UNLINK(&client_destroy_list, n);
104 client_destroy((client_t *)n, idx);
105 }
106}
107
e3a154c0 108static inline void
0ab43060 109client_destroy(client_t *c, client_t **idx)
ce436d0b
MM
110{
111
0ab43060 112 idx[c->fd] = NULL;
e583c3d8 113 (void) close(c->fd);
e583c3d8 114 sendq_purge(&c->sendq, true);
23ab503c
MM
115 if (c->state == CSTATE_BKTR)
116 c->netaddr->bktr = false;
dacf6158 117 netaddr_destroy(c->netaddr);
ce436d0b
MM
118 (void) pool_free((pnode_t *)c);
119}