Added method vfs_asynchronous_write_pages(), which, unsurprisingly,
writes the given page iovecs asynchronously. The new class AsyncIOCallback is used to inform the caller when the request has been finished. git-svn-id: file:///srv/svn/repos/haiku/haiku/trunk@27055 a95241bf-73f2-0310-859d-f6bbb57e9c96
This commit is contained in:
parent
80048d7de3
commit
663948966c
@ -251,10 +251,44 @@ extern status_t _user_socketpair(int family, int type, int protocol,
|
||||
extern status_t _user_get_next_socket_stat(int family, uint32 *cookie,
|
||||
struct net_stat *stat);
|
||||
|
||||
/* vfs entry points... */
|
||||
|
||||
#ifdef __cplusplus
|
||||
}
|
||||
#endif
|
||||
|
||||
|
||||
#ifdef __cplusplus
|
||||
|
||||
class AsyncIOCallback {
|
||||
public:
|
||||
virtual ~AsyncIOCallback();
|
||||
|
||||
virtual void IOFinished(status_t status,
|
||||
bool partialTransfer,
|
||||
size_t bytesTransferred) = 0;
|
||||
|
||||
void operator delete(void* address, size_t size);
|
||||
|
||||
static status_t IORequestCallback(void* data,
|
||||
io_request* request, status_t status,
|
||||
bool partialTransfer,
|
||||
size_t transferEndOffset);
|
||||
};
|
||||
|
||||
|
||||
class StackableAsyncIOCallback : public AsyncIOCallback {
|
||||
public:
|
||||
StackableAsyncIOCallback(AsyncIOCallback* next);
|
||||
|
||||
protected:
|
||||
AsyncIOCallback* fNextCallback;
|
||||
};
|
||||
|
||||
|
||||
status_t vfs_asynchronous_write_pages(struct vnode* vnode, void* cookie,
|
||||
off_t pos, const iovec* vecs, size_t count, size_t numBytes,
|
||||
uint32 flags, AsyncIOCallback* callback);
|
||||
|
||||
|
||||
#endif // __cplusplus
|
||||
|
||||
#endif /* _KERNEL_VFS_H */
|
||||
|
@ -14,6 +14,44 @@
|
||||
#endif
|
||||
|
||||
|
||||
// #pragma mark - AsyncIOCallback
|
||||
|
||||
|
||||
AsyncIOCallback::~AsyncIOCallback()
|
||||
{
|
||||
}
|
||||
|
||||
|
||||
void
|
||||
AsyncIOCallback::operator delete(void* address, size_t size)
|
||||
{
|
||||
io_request_free(address);
|
||||
}
|
||||
|
||||
|
||||
/* static */ status_t
|
||||
AsyncIOCallback::IORequestCallback(void* data, io_request* request,
|
||||
status_t status, bool partialTransfer, size_t transferEndOffset)
|
||||
{
|
||||
((AsyncIOCallback*)data)->IOFinished(status, partialTransfer,
|
||||
transferEndOffset);
|
||||
return B_OK;
|
||||
}
|
||||
|
||||
|
||||
// #pragma mark - StackableAsyncIOCallback
|
||||
|
||||
|
||||
StackableAsyncIOCallback::StackableAsyncIOCallback(AsyncIOCallback* next)
|
||||
:
|
||||
fNextCallback(next)
|
||||
{
|
||||
}
|
||||
|
||||
|
||||
// #pragma mark -
|
||||
|
||||
|
||||
struct iterative_io_cookie {
|
||||
struct vnode* vnode;
|
||||
file_descriptor* descriptor;
|
||||
@ -379,6 +417,32 @@ vfs_synchronous_io(io_request* request,
|
||||
}
|
||||
|
||||
|
||||
status_t
|
||||
vfs_asynchronous_write_pages(struct vnode* vnode, void* cookie, off_t pos,
|
||||
const iovec* vecs, size_t count, size_t numBytes, uint32 flags,
|
||||
AsyncIOCallback* callback)
|
||||
{
|
||||
IORequest* request = IORequest::Create((flags & B_VIP_IO_REQUEST) != 0);
|
||||
if (request == NULL) {
|
||||
callback->IOFinished(B_NO_MEMORY, true, 0);
|
||||
return B_NO_MEMORY;
|
||||
}
|
||||
|
||||
status_t status = request->Init(pos, vecs, count, numBytes, true,
|
||||
flags | B_DELETE_IO_REQUEST);
|
||||
if (status != B_OK) {
|
||||
delete request;
|
||||
callback->IOFinished(status, true, 0);
|
||||
return status;
|
||||
}
|
||||
|
||||
request->SetFinishedCallback(&AsyncIOCallback::IORequestCallback,
|
||||
callback);
|
||||
|
||||
return vfs_vnode_io(vnode, cookie, request);
|
||||
}
|
||||
|
||||
|
||||
// #pragma mark - public API
|
||||
|
||||
|
||||
|
Loading…
Reference in New Issue
Block a user