DiskThreadsDiskFile.cc
Go to the documentation of this file.
1/*
2 * Copyright (C) 1996-2023 The Squid Software Foundation and contributors
3 *
4 * Squid software is distributed under GPLv2+ license and includes
5 * contributions from numerous individuals and organizations.
6 * Please see the COPYING and CONTRIBUTORS files for details.
7 */
8
9/* DEBUG: section 79 Disk IO Routines */
10
11#include "squid.h"
12#include "comm.h"
13#include "DiskIO/IORequestor.h"
14#include "DiskIO/ReadRequest.h"
15#include "DiskIO/WriteRequest.h"
16#include "DiskThreadsDiskFile.h"
17#include "fd.h"
18#include "fs_io.h"
19#include "Generic.h"
20#include "globals.h"
21#include "StatCounters.h"
22#include "Store.h"
23
24#include <cerrno>
25
26/* === PUBLIC =========================================================== */
27
29
31{
32 assert(aPath);
33 debugs(79, 3, "UFSFile::UFSFile: " << aPath);
34 path_ = xstrdup(aPath);
35}
36
38{
40 doClose();
41}
42
43void
45{
47#if !ASYNC_OPEN
48
49 fd = file_open(path_, flags);
50
51 if (fd < 0) {
52 debugs(79, 3, "DiskThreadsDiskFile::open: got failure (" << errno << ")");
53 errorOccured = true;
54 return;
55 }
56
57#endif
58 ++Opening_FD;
59
60 ioRequestor = callback;
61
63
64#if ASYNC_OPEN
65
66 aioOpen(path_, flags, mode, DiskThreadsDiskFile::OpenDone, this);
67
68#else
69
70 openDone(fd, nullptr, fd, 0);
71
72#endif
73}
74
75void
77{
78 debugs(79, 3, "DiskThreadsDiskFile::read: " << this << ", size " << request->len);
79 assert (fd > -1);
83#if ASYNC_READ
84
85 aioRead(fd, request->offset, request->len, ReadDone, new IoResult<ReadRequest>(this, request));
86#else
87
88 file_read(fd, request->buf, request->len, request->offset, ReadDone, new IoResult<ReadRequest>(this, request));
89#endif
90}
91
92void
94{
96#if !ASYNC_CREATE
97
98 int fd = file_open(path_, flags);
99
100 if (fd < 0) {
101 debugs(79, 3, "DiskThreadsDiskFile::create: got failure (" << errno << ")");
102 errorOccured = true;
103 return;
104 }
105
106#endif
107 ++Opening_FD;
108
109 ioRequestor = callback;
110
112
113#if ASYNC_CREATE
114
115 aioOpen(path_, flags, mode, DiskThreadsDiskFile::OpenDone, this);
116
117#else
118
119 openDone (fd, nullptr, fd, 0);
120
121#endif
122}
123
124bool
126{
127 return errorOccured;
128}
129
130void
131DiskThreadsDiskFile::OpenDone(int fd, void *cbdata, const char *buf, int aio_return, int aio_errno)
132{
133 DiskThreadsDiskFile *myFile = static_cast<DiskThreadsDiskFile *>(cbdata);
134 myFile->openDone (fd, buf, aio_return, aio_errno);
135}
136
137void
138DiskThreadsDiskFile::openDone(int, const char *, int anFD, int errflag)
139{
140 debugs(79, 3, "DiskThreadsDiskFile::openDone: FD " << anFD << ", errflag " << errflag);
141 --Opening_FD;
142
143 fd = anFD;
144
145 if (errflag || fd < 0) {
146 debugs(79, DBG_CRITICAL, MYNAME << xstrerr(errflag));
147 debugs(79, DBG_IMPORTANT, "\t" << path_);
148 errorOccured = true;
149 } else {
153 }
154
158
159 debugs(79, 3, "DiskThreadsDiskFile::openDone: exiting");
160}
161
163{
164 if (fd > -1) {
166#if ASYNC_CLOSE
167
168 aioClose(fd);
169 fd_close(fd);
170#else
171
172 aioCancel(fd);
173 file_close(fd);
174#endif
175
177 fd = -1;
178 }
179}
180
181void
183{
184 debugs(79, 3, "DiskThreadsDiskFile::close: " << this << " closing for " << ioRequestor.getRaw());
185
186 if (!ioInProgress()) {
187 doClose();
188 assert (ioRequestor != nullptr);
190 return;
191 } else {
192 debugs(79, DBG_CRITICAL, "DiskThreadsDiskFile::close: " <<
193 "did NOT close because ioInProgress() is true. now what?");
194 }
195}
196
197bool
199{
200 debugs(79, 3, "DiskThreadsDiskFile::canRead: fd is " << fd);
201 return fd > -1;
202}
203
204void
206{
207 debugs(79, 3, "DiskThreadsDiskFile::write: FD " << fd);
210#if ASYNC_WRITE
211
212 aioWrite(fd, writeRequest->offset, (char *)writeRequest->buf, writeRequest->len, WriteDone, new IoResult<WriteRequest>(this, writeRequest),
213 writeRequest->free_func);
214#else
215
216 file_write(fd, writeRequest->offset, (char *)writeRequest->buf, writeRequest->len, WriteDone, new IoResult<WriteRequest>(this, writeRequest),
217 writeRequest->free_func);
218#endif
219}
220
221bool
223{
224 return fd > -1;
225}
226
227bool
229{
230 return inProgressIOs > 0;
231}
232
233/* === STATIC =========================================================== */
234
235#if ASYNC_READ
236void
237DiskThreadsDiskFile::ReadDone(int fd, void *my_data, const char *buf, int len, int errflag)
238#else
239void
240DiskThreadsDiskFile::ReadDone(int fd, const char *buf, int len, int errflag, void *my_data)
241#endif
242{
243 IoResult<ReadRequest> * result = static_cast<IoResult<ReadRequest> *>(my_data);
244 assert (result);
245 result->file->readDone(fd, buf, len, errflag, result->request);
246 delete result;
247}
248
249void
250DiskThreadsDiskFile::readDone(int rvfd, const char *buf, int len, int errflag, RefCount<ReadRequest> request)
251{
252 debugs(79, 3, "DiskThreadsDiskFile::readDone: FD " << rvfd);
253 assert (fd == rvfd);
254
255 ssize_t rlen;
256
257 if (errflag) {
258 debugs(79, 3, "DiskThreadsDiskFile::readDone: got failure (" << errflag << ")");
259 rlen = -1;
260 } else {
261 rlen = (ssize_t) len;
262 }
263
264#if ASYNC_READ
265 /* translate errflag from errno to Squid disk error */
266 errno = errflag;
267
268 if (errflag)
269 errflag = DISK_ERROR;
270 else
271 errflag = DISK_OK;
272
273#else
274
275 if (errflag == DISK_EOF)
276 errflag = DISK_OK; /* EOF is signalled by len == 0, not errors... */
277
278#endif
279
281
282 ioRequestor->readCompleted(buf, rlen, errflag, request);
283}
284
285void
287#if ASYNC_WRITE
288WriteDone(int fd, void *my_data, const char *buf, int len, int errflag)
289#else
290WriteDone(int fd, int errflag, size_t len, void *my_data)
291#endif
292{
293 IoResult<WriteRequest> * result = static_cast<IoResult<WriteRequest> *>(my_data);
294 assert (result);
295 result->file->writeDone(fd, errflag, len, result->request);
296 delete result;
297}
298
299void
300DiskThreadsDiskFile::writeDone(int rvfd, int errflag, size_t len, RefCount<WriteRequest> request)
301{
302 assert (rvfd == fd);
303 static int loop_detect = 0;
304
305#if ASYNC_WRITE
306 /* Translate from errno to Squid disk error */
307
308 if (errflag)
309 errflag = errflag == ENOSPC ? DISK_NO_SPACE_LEFT : DISK_ERROR;
310 else
311 errflag = DISK_OK;
312
313#endif
314
315 debugs(79, 3, "DiskThreadsDiskFile::writeDone: FD " << fd << ", len " << len << ", err=" << errflag);
316
317 ++loop_detect;
318 assert(loop_detect < 10);
319
321
322 ioRequestor->writeCompleted(errflag, len, request);
323
324 --loop_detect;
325}
326
328template <class RT>
CBDATA_CLASS_INIT(DiskThreadsDiskFile)
StatCounters statCounter
Definition: StatCounters.cc:12
#define assert(EX)
Definition: assert.h:17
void aioOpen(const char *path, int oflag, mode_t mode, AIOCB *callback, void *callback_data)
Definition: async_io.cc:29
void aioRead(int fd, off_t offset, size_t len, AIOCB *callback, void *callback_data)
Definition: async_io.cc:135
void aioClose(int fd)
Definition: async_io.cc:47
void aioCancel(int fd)
Definition: async_io.cc:66
void aioWrite(int fd, off_t offset, char *bufp, size_t len, AIOCB *callback, void *callback_data, FREE *free_func)
Definition: async_io.cc:107
static const cbdata_type CBDATA_UNKNOWN
Definition: cbdata.h:196
int cbdata_type
Definition: cbdata.h:195
void openDone(int fd, const char *buf, int aio_return, int aio_errno)
bool ioInProgress() const override
void create(int flags, mode_t mode, RefCount< IORequestor > callback) override
void writeDone(int fd, int errflag, size_t len, RefCount< WriteRequest > request)
void open(int flags, mode_t mode, RefCount< IORequestor > callback) override
bool canRead() const override
bool error() const override
DiskThreadsDiskFile(char const *path)
void readDone(int fd, const char *buf, int len, int errflag, RefCount< ReadRequest > request)
bool canWrite() const override
RefCount< IORequestor > ioRequestor
void write(WriteRequest *) override
void read(ReadRequest *) override
virtual void closeCompleted()=0
virtual void readCompleted(const char *buf, int len, int errflag, RefCount< ReadRequest >)=0
virtual void ioCompletedNotification()=0
virtual void writeCompleted(int errflag, size_t len, RefCount< WriteRequest >)=0
RefCount< DiskThreadsDiskFile > file
RefCount< RT > request
size_t len
Definition: ReadRequest.h:26
off_t offset
Definition: ReadRequest.h:25
char * buf
Definition: ReadRequest.h:24
C * getRaw() const
Definition: RefCount.h:89
struct StatCounters::@130 syscalls
struct StatCounters::@130::@134 disk
FREE * free_func
Definition: WriteRequest.h:28
char const * buf
Definition: WriteRequest.h:25
Definition: cbdata.cc:38
void fd_open(const int fd, unsigned int, const char *description)
Definition: minimal.cc:14
void fd_close(const int fd)
Definition: minimal.cc:20
void commSetCloseOnExec(int fd)
Definition: comm.cc:1127
#define MYNAME
Definition: Stream.h:236
#define DBG_IMPORTANT
Definition: Stream.h:38
#define debugs(SECTION, LEVEL, CONTENT)
Definition: Stream.h:194
#define DBG_CRITICAL
Definition: Stream.h:37
#define DISK_EOF
Definition: defines.h:29
#define DISK_NO_SPACE_LEFT
Definition: defines.h:30
#define DISK_ERROR
Definition: defines.h:28
#define DISK_OK
Definition: defines.h:27
@ FD_FILE
Definition: enums.h:15
int file_open(const char *path, int mode)
Definition: fs_io.cc:45
void file_read(int fd, char *buf, int req_len, off_t offset, DRCB *handler, void *client_data)
Definition: fs_io.cc:453
void file_close(int fd)
Definition: fs_io.cc:73
void file_write(int fd, off_t file_offset, void const *ptr_to_buf, int len, DWCB *handle, void *handle_data, FREE *free_func)
Definition: fs_io.cc:326
int Opening_FD
int store_open_disk_fd
#define xstrdup
unsigned short mode_t
Definition: types.h:129
#define safe_free(x)
Definition: xalloc.h:73
const char * xstrerr(int error)
Definition: xstrerror.cc:83

 

Introduction

Documentation

Support

Miscellaneous

Web Site Translations

Mirrors