summaryrefslogtreecommitdiffstats
path: root/sys/kern/sys_generic.c
diff options
context:
space:
mode:
authorgreen <green@FreeBSD.org>2000-07-02 08:08:09 +0000
committergreen <green@FreeBSD.org>2000-07-02 08:08:09 +0000
commit9707bc34b009d1e09d192ec84d1ddc8e8693006f (patch)
tree176c788b7d732a310aa42a0b4652b645bc735a99 /sys/kern/sys_generic.c
parentc350a86095dd249ad9e0371c7caaf6a5c52a0260 (diff)
downloadFreeBSD-src-9707bc34b009d1e09d192ec84d1ddc8e8693006f.zip
FreeBSD-src-9707bc34b009d1e09d192ec84d1ddc8e8693006f.tar.gz
Modify ktrace's general I/O tracing, ktrgenio(), to use a struct uio *
instead of a struct iovec * array and int len. Get rid of stupidly trying to allocate all of the memory and copyin()ing the entire iovec[], and instead just do the proper VOP_WRITE() in ktrwrite() using a copy of the struct uio that the syscall originally used. This solves the DoS which could easily be performed; to work around the DoS, one could also remove "options KTRACE" from the kernel. This is a very strong MFC candidate for 4.1. Found by: art@OpenBSD.org
Diffstat (limited to 'sys/kern/sys_generic.c')
-rw-r--r--sys/kern/sys_generic.c51
1 files changed, 36 insertions, 15 deletions
diff --git a/sys/kern/sys_generic.c b/sys/kern/sys_generic.c
index bf33a4d..562536a 100644
--- a/sys/kern/sys_generic.c
+++ b/sys/kern/sys_generic.c
@@ -154,6 +154,7 @@ dofileread(p, fp, fd, buf, nbyte, offset, flags)
long cnt, error = 0;
#ifdef KTRACE
struct iovec ktriov;
+ struct uio ktruio;
#endif
aiov.iov_base = (caddr_t)buf;
@@ -171,8 +172,10 @@ dofileread(p, fp, fd, buf, nbyte, offset, flags)
/*
* if tracing, save a copy of iovec
*/
- if (KTRPOINT(p, KTR_GENIO))
+ if (KTRPOINT(p, KTR_GENIO)) {
ktriov = aiov;
+ ktruio = auio;
+ }
#endif
cnt = nbyte;
if ((error = fo_read(fp, &auio, fp->f_cred, flags, p)))
@@ -181,8 +184,11 @@ dofileread(p, fp, fd, buf, nbyte, offset, flags)
error = 0;
cnt -= auio.uio_resid;
#ifdef KTRACE
- if (KTRPOINT(p, KTR_GENIO) && error == 0)
- ktrgenio(p->p_tracep, fd, UIO_READ, &ktriov, cnt, error);
+ if (error == 0 && KTRPOINT(p, KTR_GENIO)) {
+ ktruio.uio_iov = &ktriov;
+ ktruio.uio_resid = cnt;
+ ktrgenio(p->p_tracep, fd, UIO_READ, &ktruio, error);
+ }
#endif
p->p_retval[0] = cnt;
return (error);
@@ -213,6 +219,7 @@ readv(p, uap)
u_int iovlen;
#ifdef KTRACE
struct iovec *ktriov = NULL;
+ struct uio ktruio;
#endif
if ((fp = getfp(fdp, uap->fd, FREAD)) == NULL)
@@ -252,6 +259,7 @@ readv(p, uap)
if (KTRPOINT(p, KTR_GENIO)) {
MALLOC(ktriov, struct iovec *, iovlen, M_TEMP, M_WAITOK);
bcopy((caddr_t)auio.uio_iov, (caddr_t)ktriov, iovlen);
+ ktruio = auio;
}
#endif
cnt = auio.uio_resid;
@@ -262,9 +270,12 @@ readv(p, uap)
cnt -= auio.uio_resid;
#ifdef KTRACE
if (ktriov != NULL) {
- if (error == 0)
- ktrgenio(p->p_tracep, uap->fd, UIO_READ, ktriov,
- cnt, error);
+ if (error == 0) {
+ ktruio.uio_iov = ktriov;
+ ktruio.uio_resid = cnt;
+ ktrgenio(p->p_tracep, uap->fd, UIO_READ, &ktruio,
+ error);
+ }
FREE(ktriov, M_TEMP);
}
#endif
@@ -338,6 +349,7 @@ dofilewrite(p, fp, fd, buf, nbyte, offset, flags)
long cnt, error = 0;
#ifdef KTRACE
struct iovec ktriov;
+ struct uio ktruio;
#endif
aiov.iov_base = (void *)buf;
@@ -353,10 +365,12 @@ dofilewrite(p, fp, fd, buf, nbyte, offset, flags)
auio.uio_procp = p;
#ifdef KTRACE
/*
- * if tracing, save a copy of iovec
+ * if tracing, save a copy of iovec and uio
*/
- if (KTRPOINT(p, KTR_GENIO))
+ if (KTRPOINT(p, KTR_GENIO)) {
ktriov = aiov;
+ ktruio = auio;
+ }
#endif
cnt = nbyte;
if ((error = fo_write(fp, &auio, fp->f_cred, flags, p))) {
@@ -368,9 +382,11 @@ dofilewrite(p, fp, fd, buf, nbyte, offset, flags)
}
cnt -= auio.uio_resid;
#ifdef KTRACE
- if (KTRPOINT(p, KTR_GENIO) && error == 0)
- ktrgenio(p->p_tracep, fd, UIO_WRITE,
- &ktriov, cnt, error);
+ if (error == 0 && KTRPOINT(p, KTR_GENIO)) {
+ ktruio.uio_iov = &ktriov;
+ ktruio.uio_resid = cnt;
+ ktrgenio(p->p_tracep, fd, UIO_WRITE, &ktruio, error);
+ }
#endif
p->p_retval[0] = cnt;
return (error);
@@ -401,6 +417,7 @@ writev(p, uap)
u_int iovlen;
#ifdef KTRACE
struct iovec *ktriov = NULL;
+ struct uio ktruio;
#endif
if ((fp = getfp(fdp, uap->fd, FWRITE)) == NULL)
@@ -439,11 +456,12 @@ writev(p, uap)
}
#ifdef KTRACE
/*
- * if tracing, save a copy of iovec
+ * if tracing, save a copy of iovec and uio
*/
if (KTRPOINT(p, KTR_GENIO)) {
MALLOC(ktriov, struct iovec *, iovlen, M_TEMP, M_WAITOK);
bcopy((caddr_t)auio.uio_iov, (caddr_t)ktriov, iovlen);
+ ktruio = auio;
}
#endif
cnt = auio.uio_resid;
@@ -457,9 +475,12 @@ writev(p, uap)
cnt -= auio.uio_resid;
#ifdef KTRACE
if (ktriov != NULL) {
- if (error == 0)
- ktrgenio(p->p_tracep, uap->fd, UIO_WRITE,
- ktriov, cnt, error);
+ if (error == 0) {
+ ktruio.uio_iov = ktriov;
+ ktruio.uio_resid = cnt;
+ ktrgenio(p->p_tracep, uap->fd, UIO_WRITE, &ktruio,
+ error);
+ }
FREE(ktriov, M_TEMP);
}
#endif
OpenPOWER on IntegriCloud