Reduce hypercalls related to reading to essentially an amalgamation

of readv and preadv.  ditto for writing.  Hypercalls are so seldomly
used that it doesn't justify 3x the calls for syntactic sugar.
This commit is contained in:
pooka 2013-04-29 20:08:48 +00:00
parent c36d22e278
commit 0dc3609e1c
6 changed files with 93 additions and 115 deletions

View File

@ -1,4 +1,4 @@
/* $NetBSD: rumpuser.c,v 1.43 2013/04/29 17:31:05 pooka Exp $ */
/* $NetBSD: rumpuser.c,v 1.44 2013/04/29 20:08:48 pooka Exp $ */
/*
* Copyright (c) 2007-2010 Antti Kantee. All Rights Reserved.
@ -28,7 +28,7 @@
#include "rumpuser_port.h"
#if !defined(lint)
__RCSID("$NetBSD: rumpuser.c,v 1.43 2013/04/29 17:31:05 pooka Exp $");
__RCSID("$NetBSD: rumpuser.c,v 1.44 2013/04/29 20:08:48 pooka Exp $");
#endif /* !lint */
#include <sys/ioctl.h>
@ -319,12 +319,23 @@ rumpuser_close(int fd, int *error)
return 0;
}
/*
* Assume "struct rumpuser_iovec" and "struct iovec" are the same.
* If you encounter POSIX platforms where they aren't, add some
* translation for iovlen > 1.
*/
ssize_t
rumpuser_read(int fd, void *data, size_t size, int *error)
rumpuser_iovread(int fd, struct rumpuser_iovec *ruiov, size_t iovlen,
off_t off, int *error)
{
struct iovec *iov = (struct iovec *)ruiov;
ssize_t rv;
KLOCK_WRAP(rv = read(fd, data, size));
if (off == RUMPUSER_IOV_NOSEEK)
KLOCK_WRAP(rv = readv(fd, iov, iovlen));
else
KLOCK_WRAP(rv = preadv(fd, iov, iovlen, off));
if (rv == -1)
seterror(errno);
@ -332,95 +343,23 @@ rumpuser_read(int fd, void *data, size_t size, int *error)
}
ssize_t
rumpuser_pread(int fd, void *data, size_t size, off_t offset, int *error)
rumpuser_iovwrite(int fd, const struct rumpuser_iovec *ruiov, size_t iovlen,
off_t off, int *error)
{
const struct iovec *iov = (const struct iovec *)ruiov;
ssize_t rv;
KLOCK_WRAP(rv = pread(fd, data, size, offset));
if (off == RUMPUSER_IOV_NOSEEK)
KLOCK_WRAP(rv = writev(fd, iov, iovlen));
else
KLOCK_WRAP(rv = pwritev(fd, iov, iovlen, off));
if (rv == -1)
seterror(errno);
return rv;
}
ssize_t
rumpuser_write(int fd, const void *data, size_t size, int *error)
{
ssize_t rv;
KLOCK_WRAP(rv = write(fd, data, size));
if (rv == -1)
seterror(errno);
return rv;
}
ssize_t
rumpuser_pwrite(int fd, const void *data, size_t size, off_t offset, int *error)
{
ssize_t rv;
KLOCK_WRAP(rv = pwrite(fd, data, size, offset));
if (rv == -1)
seterror(errno);
return rv;
}
ssize_t
rumpuser_readv(int fd, const struct rumpuser_iovec *riov, int iovcnt,
int *error)
{
struct iovec *iovp;
ssize_t rv;
int i;
iovp = malloc(iovcnt * sizeof(struct iovec));
if (iovp == NULL) {
seterror(ENOMEM);
return -1;
}
for (i = 0; i < iovcnt; i++) {
iovp[i].iov_base = riov[i].iov_base;
/*LINTED*/
iovp[i].iov_len = riov[i].iov_len;
}
KLOCK_WRAP(rv = readv(fd, iovp, iovcnt));
if (rv == -1)
seterror(errno);
free(iovp);
return rv;
}
ssize_t
rumpuser_writev(int fd, const struct rumpuser_iovec *riov, int iovcnt,
int *error)
{
struct iovec *iovp;
ssize_t rv;
int i;
iovp = malloc(iovcnt * sizeof(struct iovec));
if (iovp == NULL) {
seterror(ENOMEM);
return -1;
}
for (i = 0; i < iovcnt; i++) {
iovp[i].iov_base = riov[i].iov_base;
/*LINTED*/
iovp[i].iov_len = riov[i].iov_len;
}
KLOCK_WRAP(rv = writev(fd, iovp, iovcnt));
if (rv == -1)
seterror(errno);
free(iovp);
return rv;
}
int
rumpuser_clock_gettime(uint64_t *sec, uint64_t *nsec, enum rumpclock rclk)
{

View File

@ -1,4 +1,4 @@
/* $NetBSD: ugenhc.c,v 1.13 2013/04/28 09:58:11 pooka Exp $ */
/* $NetBSD: ugenhc.c,v 1.14 2013/04/29 20:08:48 pooka Exp $ */
/*
* Copyright (c) 2009, 2010 Antti Kantee. All Rights Reserved.
@ -61,7 +61,7 @@
*/
#include <sys/cdefs.h>
__KERNEL_RCSID(0, "$NetBSD: ugenhc.c,v 1.13 2013/04/28 09:58:11 pooka Exp $");
__KERNEL_RCSID(0, "$NetBSD: ugenhc.c,v 1.14 2013/04/29 20:08:48 pooka Exp $");
#include <sys/param.h>
#include <sys/bus.h>
@ -750,10 +750,14 @@ rumpusb_device_bulk_start(usbd_xfer_handle xfer)
while (RUSB(xfer)->rusb_status == 0) {
if (isread) {
struct rumpuser_iovec iov;
rumpcomp_ugenhc_ioctl(sc->sc_ugenfd[endpt],
USB_SET_SHORT_XFER, &shortval, &error);
n = rumpuser_read(sc->sc_ugenfd[endpt],
buf+done, len-done, &error);
iov.iov_base = buf+done;
iov.iov_len = len-done;
n = rumpuser_iovread(sc->sc_ugenfd[endpt], &iov, 1,
RUMPUSER_IOV_NOSEEK, &error);
if (n == -1) {
n = 0;
if (done == 0) {
@ -767,8 +771,12 @@ rumpusb_device_bulk_start(usbd_xfer_handle xfer)
if (done == len)
break;
} else {
n = rumpuser_write(sc->sc_ugenfd[endpt],
buf, len, &error);
struct rumpuser_iovec iov;
iov.iov_base = buf;
iov.iov_len = len;
n = rumpuser_iovwrite(sc->sc_ugenfd[endpt], &iov, 1,
RUMPUSER_IOV_NOSEEK, &error);
done = n;
if (done == len)
break;

View File

@ -1,4 +1,4 @@
/* $NetBSD: puffs_rumpglue.c,v 1.11 2009/10/14 18:18:53 pooka Exp $ */
/* $NetBSD: puffs_rumpglue.c,v 1.12 2013/04/29 20:08:48 pooka Exp $ */
/*
* Copyright (c) 2008 Antti Kantee. All Rights Reserved.
@ -29,7 +29,7 @@
*/
#include <sys/cdefs.h>
__KERNEL_RCSID(0, "$NetBSD: puffs_rumpglue.c,v 1.11 2009/10/14 18:18:53 pooka Exp $");
__KERNEL_RCSID(0, "$NetBSD: puffs_rumpglue.c,v 1.12 2013/04/29 20:08:48 pooka Exp $");
#include <sys/param.h>
#include <sys/conf.h>
@ -97,7 +97,13 @@ readthread(void *arg)
inited = 1;
while (rv) {
n = rumpuser_write(pap->comfd, buf, rv, &error);
struct rumpuser_iovec iov;
iov.iov_base = buf;
iov.iov_len = rv;
n = rumpuser_iovwrite(pap->comfd, &iov, 1,
RUMPUSER_IOV_NOSEEK, &error);
if (n == -1)
panic("fileread failed: %d", error);
if (n == 0)
@ -135,7 +141,12 @@ writethread(void *arg)
off = 0;
toread = sizeof(struct putter_hdr);
do {
n = rumpuser_read(pap->comfd, buf+off, toread, &error);
struct rumpuser_iovec iov;
iov.iov_base = buf+off;
iov.iov_len = toread;
n = rumpuser_iovread(pap->comfd, &iov, 1,
RUMPUSER_IOV_NOSEEK, &error);
if (n <= 0) {
if (n == 0)
goto out;

View File

@ -1,4 +1,4 @@
/* $NetBSD: rumpuser.h,v 1.96 2013/04/29 17:35:04 pooka Exp $ */
/* $NetBSD: rumpuser.h,v 1.97 2013/04/29 20:08:48 pooka Exp $ */
/*
* Copyright (c) 2007-2013 Antti Kantee. All Rights Reserved.
@ -99,17 +99,20 @@ int rumpuser_getfileinfo(const char *, uint64_t *, int *, int *);
typedef void (*rump_biodone_fn)(void *, size_t, int);
void rumpuser_bio(int, int, void *, size_t, off_t, rump_biodone_fn, void *);
ssize_t rumpuser_read(int, void *, size_t, int *);
ssize_t rumpuser_pread(int, void *, size_t, off_t, int *);
ssize_t rumpuser_write(int, const void *, size_t, int *);
ssize_t rumpuser_pwrite(int, const void *, size_t, off_t, int *);
/*
* Reading and writing. Since hypercalls are relatively uncommon, we don't
* need tons of syntactic sugar; fold everything into two.
*/
/* this one "accidentally" matches the NetBSD kernel ... */
struct rumpuser_iovec {
void *iov_base;
uint64_t iov_len;
size_t iov_len;
};
ssize_t rumpuser_readv(int, const struct rumpuser_iovec *, int, int *);
ssize_t rumpuser_writev(int, const struct rumpuser_iovec *, int, int *);
#define RUMPUSER_IOV_NOSEEK -1
ssize_t rumpuser_iovread(int, struct rumpuser_iovec *, size_t, off_t, int *);
ssize_t rumpuser_iovwrite(int, const struct rumpuser_iovec *, size_t,
off_t, int *);
/*
* clock and zzz

View File

@ -1,4 +1,4 @@
/* $NetBSD: rumpfs.c,v 1.112 2013/04/07 18:42:49 stacktic Exp $ */
/* $NetBSD: rumpfs.c,v 1.113 2013/04/29 20:08:49 pooka Exp $ */
/*
* Copyright (c) 2009, 2010, 2011 Antti Kantee. All Rights Reserved.
@ -26,7 +26,7 @@
*/
#include <sys/cdefs.h>
__KERNEL_RCSID(0, "$NetBSD: rumpfs.c,v 1.112 2013/04/07 18:42:49 stacktic Exp $");
__KERNEL_RCSID(0, "$NetBSD: rumpfs.c,v 1.113 2013/04/29 20:08:49 pooka Exp $");
#include <sys/param.h>
#include <sys/atomic.h>
@ -1338,6 +1338,7 @@ rump_vop_readdir(void *v)
static int
etread(struct rumpfs_node *rn, struct uio *uio)
{
struct rumpuser_iovec iov;
uint8_t *buf;
size_t bufsize;
ssize_t n;
@ -1347,7 +1348,9 @@ etread(struct rumpfs_node *rn, struct uio *uio)
if (bufsize == 0)
return 0;
buf = kmem_alloc(bufsize, KM_SLEEP);
if ((n = rumpuser_pread(rn->rn_readfd, buf, bufsize,
iov.iov_base = buf;
iov.iov_len = bufsize;
if ((n = rumpuser_iovread(rn->rn_readfd, &iov, 1,
uio->uio_offset + rn->rn_offset, &error)) == -1)
goto out;
KASSERT(n <= bufsize);
@ -1399,6 +1402,7 @@ rump_vop_read(void *v)
static int
etwrite(struct rumpfs_node *rn, struct uio *uio)
{
struct rumpuser_iovec iov;
uint8_t *buf;
size_t bufsize;
ssize_t n;
@ -1412,7 +1416,9 @@ etwrite(struct rumpfs_node *rn, struct uio *uio)
if (error)
goto out;
KASSERT(uio->uio_resid == 0);
n = rumpuser_pwrite(rn->rn_writefd, buf, bufsize,
iov.iov_base = buf;
iov.iov_len = bufsize;
n = rumpuser_iovwrite(rn->rn_writefd, &iov, 1,
(uio->uio_offset-bufsize) + rn->rn_offset, &error);
if (n >= 0) {
KASSERT(n <= bufsize);

View File

@ -1,4 +1,4 @@
/* $NetBSD: if_shmem.c,v 1.51 2013/04/29 13:17:32 pooka Exp $ */
/* $NetBSD: if_shmem.c,v 1.52 2013/04/29 20:08:49 pooka Exp $ */
/*
* Copyright (c) 2009, 2010 Antti Kantee. All Rights Reserved.
@ -28,7 +28,7 @@
*/
#include <sys/cdefs.h>
__KERNEL_RCSID(0, "$NetBSD: if_shmem.c,v 1.51 2013/04/29 13:17:32 pooka Exp $");
__KERNEL_RCSID(0, "$NetBSD: if_shmem.c,v 1.52 2013/04/29 20:08:49 pooka Exp $");
#include <sys/param.h>
#include <sys/atomic.h>
@ -109,6 +109,18 @@ static void shmif_rcv(void *);
vmem_t *shmif_units;
static void
dowakeup(struct shmif_sc *sc)
{
struct rumpuser_iovec iov;
uint32_t ver = SHMIF_VERSION;
int error;
iov.iov_base = &ver;
iov.iov_len = sizeof(ver);
rumpuser_iovwrite(sc->sc_memfd, &iov, 1, IFMEM_WAKEUP, &error);
}
/*
* This locking needs work and will misbehave severely if:
* 1) the backing memory has to be paged in
@ -505,7 +517,6 @@ shmif_start(struct ifnet *ifp)
uint32_t pktsize, pktwrote;
bool wrote = false;
bool wrap;
int error;
ifp->if_flags |= IFF_OACTIVE;
@ -562,9 +573,9 @@ shmif_start(struct ifnet *ifp)
ifp->if_flags &= ~IFF_OACTIVE;
/* wakeup? */
if (wrote)
rumpuser_pwrite(sc->sc_memfd,
&busversion, sizeof(busversion), IFMEM_WAKEUP, &error);
if (wrote) {
dowakeup(sc);
}
}
static void
@ -579,9 +590,9 @@ shmif_stop(struct ifnet *ifp, int disable)
* wakeup thread. this will of course wake up all bus
* listeners, but that's life.
*/
if (sc->sc_memfd != -1)
rumpuser_pwrite(sc->sc_memfd,
&busversion, sizeof(busversion), IFMEM_WAKEUP, NULL);
if (sc->sc_memfd != -1) {
dowakeup(sc);
}
}