]> git.ipfire.org Git - thirdparty/squid.git/blob - src/DiskIO/DiskThreads/async_io.cc
Cleanup: zap CVS Id tags
[thirdparty/squid.git] / src / DiskIO / DiskThreads / async_io.cc
1
2 /*
3 * $Id$
4 *
5 * DEBUG: section 32 Asynchronous Disk I/O
6 * AUTHOR: Pete Bentley <pete@demon.net>
7 * AUTHOR: Stewart Forster <slf@connect.com.au>
8 *
9 * SQUID Web Proxy Cache http://www.squid-cache.org/
10 * ----------------------------------------------------------
11 *
12 * Squid is the result of efforts by numerous individuals from
13 * the Internet community; see the CONTRIBUTORS file for full
14 * details. Many organizations have provided support for Squid's
15 * development; see the SPONSORS file for full details. Squid is
16 * Copyrighted (C) 2001 by the Regents of the University of
17 * California; see the COPYRIGHT file for full details. Squid
18 * incorporates software developed and/or copyrighted by other
19 * sources; see the CREDITS file for full details.
20 *
21 * This program is free software; you can redistribute it and/or modify
22 * it under the terms of the GNU General Public License as published by
23 * the Free Software Foundation; either version 2 of the License, or
24 * (at your option) any later version.
25 *
26 * This program is distributed in the hope that it will be useful,
27 * but WITHOUT ANY WARRANTY; without even the implied warranty of
28 * MERCHANTABILITY or FITNESS FOR A PARTICULAR PURPOSE. See the
29 * GNU General Public License for more details.
30 *
31 * You should have received a copy of the GNU General Public License
32 * along with this program; if not, write to the Free Software
33 * Foundation, Inc., 59 Temple Place, Suite 330, Boston, MA 02111, USA.
34 *
35 */
36
37 #include "squid.h"
38 #include "DiskThreads.h"
39 #include "Store.h"
40 #include "fde.h"
41 #include "DiskThreadsIOStrategy.h"
42 #include "Generic.h"
43
44 AIOCounts squidaio_counts;
45
46 typedef struct squidaio_unlinkq_t {
47 char *path;
48
49 struct squidaio_unlinkq_t *next;
50 } squidaio_unlinkq_t;
51
52 dlink_list used_list;
53
54 void
55 aioOpen(const char *path, int oflag, mode_t mode, AIOCB * callback, void *callback_data)
56 {
57 squidaio_ctrl_t *ctrlp;
58
59 assert(DiskThreadsIOStrategy::Instance.initialised);
60 squidaio_counts.open_start++;
61 ctrlp = (squidaio_ctrl_t *)DiskThreadsIOStrategy::Instance.squidaio_ctrl_pool->alloc();
62 ctrlp->fd = -2;
63 ctrlp->done_handler = callback;
64 ctrlp->done_handler_data = cbdataReference(callback_data);
65 ctrlp->operation = _AIO_OPEN;
66 ctrlp->result.data = ctrlp;
67 squidaio_open(path, oflag, mode, &ctrlp->result);
68 dlinkAdd(ctrlp, &ctrlp->node, &used_list);
69 return;
70 }
71
72 void
73 aioClose(int fd)
74 {
75 squidaio_ctrl_t *ctrlp;
76
77 assert(DiskThreadsIOStrategy::Instance.initialised);
78 squidaio_counts.close_start++;
79 aioCancel(fd);
80 ctrlp = (squidaio_ctrl_t *)DiskThreadsIOStrategy::Instance.squidaio_ctrl_pool->alloc();
81 ctrlp->fd = fd;
82 ctrlp->done_handler = NULL;
83 ctrlp->done_handler_data = NULL;
84 ctrlp->operation = _AIO_CLOSE;
85 ctrlp->result.data = ctrlp;
86 squidaio_close(fd, &ctrlp->result);
87 dlinkAdd(ctrlp, &ctrlp->node, &used_list);
88 return;
89 }
90
91 void
92 aioCancel(int fd)
93 {
94 squidaio_ctrl_t *ctrlp;
95 dlink_node *m, *next;
96
97 assert(DiskThreadsIOStrategy::Instance.initialised);
98 squidaio_counts.cancel++;
99
100 for (m = used_list.head; m; m = next) {
101 next = m->next;
102 ctrlp = (squidaio_ctrl_t *)m->data;
103
104 if (ctrlp->fd != fd)
105 continue;
106
107 squidaio_cancel(&ctrlp->result);
108
109 if (ctrlp->done_handler) {
110 AIOCB *callback = ctrlp->done_handler;
111 void *cbdata;
112 ctrlp->done_handler = NULL;
113 debugs(32, 1, "this be aioCancel. Danger ahead!");
114
115 if (cbdataReferenceValidDone(ctrlp->done_handler_data, &cbdata))
116 callback(fd, cbdata, NULL, -2, -2);
117
118 /* free data if requested to aioWrite() */
119 if (ctrlp->free_func)
120 ctrlp->free_func(ctrlp->bufp);
121
122 /* free temporary read buffer */
123 if (ctrlp->operation == _AIO_READ)
124 squidaio_xfree(ctrlp->bufp, ctrlp->len);
125 }
126
127 dlinkDelete(m, &used_list);
128 DiskThreadsIOStrategy::Instance.squidaio_ctrl_pool->free(ctrlp);
129 }
130 }
131
132
133 void
134 aioWrite(int fd, off_t offset, char *bufp, size_t len, AIOCB * callback, void *callback_data, FREE * free_func)
135 {
136 squidaio_ctrl_t *ctrlp;
137 int seekmode;
138
139 assert(DiskThreadsIOStrategy::Instance.initialised);
140 squidaio_counts.write_start++;
141 ctrlp = (squidaio_ctrl_t *)DiskThreadsIOStrategy::Instance.squidaio_ctrl_pool->alloc();
142 ctrlp->fd = fd;
143 ctrlp->done_handler = callback;
144 ctrlp->done_handler_data = cbdataReference(callback_data);
145 ctrlp->operation = _AIO_WRITE;
146 ctrlp->bufp = bufp;
147 ctrlp->free_func = free_func;
148
149 if (offset >= 0)
150 seekmode = SEEK_SET;
151 else {
152 seekmode = SEEK_END;
153 offset = 0;
154 }
155
156 ctrlp->result.data = ctrlp;
157 squidaio_write(fd, bufp, len, offset, seekmode, &ctrlp->result);
158 dlinkAdd(ctrlp, &ctrlp->node, &used_list);
159 } /* aioWrite */
160
161
162 void
163 aioRead(int fd, off_t offset, size_t len, AIOCB * callback, void *callback_data)
164 {
165 squidaio_ctrl_t *ctrlp;
166 int seekmode;
167
168 assert(DiskThreadsIOStrategy::Instance.initialised);
169 squidaio_counts.read_start++;
170 ctrlp = (squidaio_ctrl_t *)DiskThreadsIOStrategy::Instance.squidaio_ctrl_pool->alloc();
171 ctrlp->fd = fd;
172 ctrlp->done_handler = callback;
173 ctrlp->done_handler_data = cbdataReference(callback_data);
174 ctrlp->operation = _AIO_READ;
175 ctrlp->len = len;
176 ctrlp->bufp = (char *)squidaio_xmalloc(len);
177
178 if (offset >= 0)
179 seekmode = SEEK_SET;
180 else {
181 seekmode = SEEK_CUR;
182 offset = 0;
183 }
184
185 ctrlp->result.data = ctrlp;
186 squidaio_read(fd, ctrlp->bufp, len, offset, seekmode, &ctrlp->result);
187 dlinkAdd(ctrlp, &ctrlp->node, &used_list);
188 return;
189 } /* aioRead */
190
191 void
192
193 aioStat(char *path, struct stat *sb, AIOCB * callback, void *callback_data)
194 {
195 squidaio_ctrl_t *ctrlp;
196
197 assert(DiskThreadsIOStrategy::Instance.initialised);
198 squidaio_counts.stat_start++;
199 ctrlp = (squidaio_ctrl_t *)DiskThreadsIOStrategy::Instance.squidaio_ctrl_pool->alloc();
200 ctrlp->fd = -2;
201 ctrlp->done_handler = callback;
202 ctrlp->done_handler_data = cbdataReference(callback_data);
203 ctrlp->operation = _AIO_STAT;
204 ctrlp->result.data = ctrlp;
205 squidaio_stat(path, sb, &ctrlp->result);
206 dlinkAdd(ctrlp, &ctrlp->node, &used_list);
207 return;
208 } /* aioStat */
209
210 void
211 aioUnlink(const char *path, AIOCB * callback, void *callback_data)
212 {
213 squidaio_ctrl_t *ctrlp;
214 assert(DiskThreadsIOStrategy::Instance.initialised);
215 squidaio_counts.unlink_start++;
216 ctrlp = (squidaio_ctrl_t *)DiskThreadsIOStrategy::Instance.squidaio_ctrl_pool->alloc();
217 ctrlp->fd = -2;
218 ctrlp->done_handler = callback;
219 ctrlp->done_handler_data = cbdataReference(callback_data);
220 ctrlp->operation = _AIO_UNLINK;
221 ctrlp->result.data = ctrlp;
222 squidaio_unlink(path, &ctrlp->result);
223 dlinkAdd(ctrlp, &ctrlp->node, &used_list);
224 } /* aioUnlink */
225
226 int
227 aioQueueSize(void)
228 {
229 return DiskThreadsIOStrategy::Instance.squidaio_ctrl_pool->inUseCount();
230 }