diff options
author | pjd <pjd@FreeBSD.org> | 2005-04-08 09:28:08 +0000 |
---|---|---|
committer | pjd <pjd@FreeBSD.org> | 2005-04-08 09:28:08 +0000 |
commit | a2b6f806840b15fedd7fb6d52c4487302428cab1 (patch) | |
tree | 8acab262fa713782c7fa028f1a361d812832fa3e /sys/geom | |
parent | 231b2a9d26a93ce449e72c361ed1ada2b7bebf00 (diff) | |
download | FreeBSD-src-a2b6f806840b15fedd7fb6d52c4487302428cab1.zip FreeBSD-src-a2b6f806840b15fedd7fb6d52c4487302428cab1.tar.gz |
Fix a long-standing bug. Error string has to be copyied from the user
process context.
Approved by: phk
MFC after: 3 days
Diffstat (limited to 'sys/geom')
-rw-r--r-- | sys/geom/geom_ctl.c | 14 |
1 files changed, 9 insertions, 5 deletions
diff --git a/sys/geom/geom_ctl.c b/sys/geom/geom_ctl.c index 51008a3..a60e4cd 100644 --- a/sys/geom/geom_ctl.c +++ b/sys/geom/geom_ctl.c @@ -98,6 +98,10 @@ gctl_error(struct gctl_req *req, const char *fmt, ...) return (EINVAL); /* We only record the first error */ + if (sbuf_done(req->serror)) { + if (!req->nerror) + req->nerror = EEXIST; + } if (req->nerror) return (req->nerror); @@ -107,11 +111,7 @@ gctl_error(struct gctl_req *req, const char *fmt, ...) sbuf_finish(req->serror); if (g_debugflags & G_F_CTLDUMP) printf("gctl %p error \"%s\"\n", req, sbuf_data(req->serror)); - req->nerror = copyout(sbuf_data(req->serror), req->error, - imin(req->lerror, sbuf_len(req->serror) + 1)); - if (!req->nerror) - req->nerror = EINVAL; - return (req->nerror); + return (0); } /* @@ -468,6 +468,10 @@ g_ctl_ioctl_ctl(struct cdev *dev, u_long cmd, caddr_t data, int fflag, struct th g_waitfor_event(g_ctl_req, req, M_WAITOK, NULL); gctl_copyout(req); } + if (sbuf_done(req->serror)) { + req->nerror = copyout(sbuf_data(req->serror), req->error, + imin(req->lerror, sbuf_len(req->serror) + 1)); + } nerror = req->nerror; gctl_free(req); |