devshr: security!
This commit is contained in:
parent
e1318e0bef
commit
b39d5fbbef
|
@ -14,7 +14,9 @@ shr \- global mountpoints
|
||||||
The
|
The
|
||||||
.I shr
|
.I shr
|
||||||
device provides global mountpoints in the form of share directories
|
device provides global mountpoints in the form of share directories
|
||||||
where 9p services can be mounted and unmounted dynamically.
|
where
|
||||||
|
.IR 9P
|
||||||
|
services can be mounted on.
|
||||||
|
|
||||||
Effectively, it is a global mountpoint registry that is separate from
|
Effectively, it is a global mountpoint registry that is separate from
|
||||||
private namespaces.
|
private namespaces.
|
||||||
|
@ -26,7 +28,7 @@ in the mount tree
|
||||||
.BI #σ
|
.BI #σ
|
||||||
are the share mountpoints themselve and in the control tree
|
are the share mountpoints themselve and in the control tree
|
||||||
.BI #σc
|
.BI #σc
|
||||||
share directories can be created or removed.
|
share directories list the service files of the share.
|
||||||
.PP
|
.PP
|
||||||
To create a new share, create the directory
|
To create a new share, create the directory
|
||||||
.B #σc/myshare
|
.B #σc/myshare
|
||||||
|
@ -37,13 +39,26 @@ and then write a text string (suitable for
|
||||||
.IR strtoul ;
|
.IR strtoul ;
|
||||||
see
|
see
|
||||||
.IR atof (2))
|
.IR atof (2))
|
||||||
giving the file descriptor number of an open 9p service. Any process
|
giving the file descriptor number of an open
|
||||||
|
.I 9P
|
||||||
|
service. Any process
|
||||||
with the proper permission may then access
|
with the proper permission may then access
|
||||||
.B #σ/myshare
|
.B #σ/myshare
|
||||||
to use the service.
|
on the mount tree.
|
||||||
.PP
|
.PP
|
||||||
Multiple services can be mounted under a share. New services get
|
The service file can be reopened and passed to
|
||||||
mounted before old ones. Removing the service file from a share
|
.IR mount
|
||||||
removes the service as soon as the last reference goes away.
|
(see
|
||||||
|
.IR bind(2))
|
||||||
|
or added to another share.
|
||||||
|
.PP
|
||||||
|
Multiple services can be mounted under a share forming a union
|
||||||
|
directory. New services get mounted before old ones.
|
||||||
|
Removing the service file unmounts the service from the share.
|
||||||
|
.PP
|
||||||
|
Creating shares and mounts requires read-write access in the share
|
||||||
|
directory. The special user
|
||||||
|
.B none
|
||||||
|
is prohibited from these operations.
|
||||||
.SH SOURCE
|
.SH SOURCE
|
||||||
.B /sys/src/9/port/devshr.c
|
.B /sys/src/9/port/devshr.c
|
||||||
|
|
|
@ -2,7 +2,7 @@
|
||||||
|
|
||||||
if(! bind -a '#u' /dev)
|
if(! bind -a '#u' /dev)
|
||||||
exit
|
exit
|
||||||
mkdir '#σc/usb'
|
mkdir -m 0700 '#σc/usb'
|
||||||
if(! nusb/usbd)
|
if(! nusb/usbd)
|
||||||
exit
|
exit
|
||||||
|
|
||||||
|
|
|
@ -392,6 +392,8 @@ shropen(Chan *c, int omode)
|
||||||
devpermcheck(shr->owner, shr->perm, openmode(omode));
|
devpermcheck(shr->owner, shr->perm, openmode(omode));
|
||||||
break;
|
break;
|
||||||
case Qcmpt:
|
case Qcmpt:
|
||||||
|
if(omode&OTRUNC)
|
||||||
|
error(Eexist);
|
||||||
shr = sch->shr;
|
shr = sch->shr;
|
||||||
mpt = sch->mpt;
|
mpt = sch->mpt;
|
||||||
devpermcheck(mpt->owner, mpt->perm, openmode(omode));
|
devpermcheck(mpt->owner, mpt->perm, openmode(omode));
|
||||||
|
@ -429,6 +431,12 @@ shrcreate(Chan *c, char *name, int omode, ulong perm)
|
||||||
switch(sch->level){
|
switch(sch->level){
|
||||||
default:
|
default:
|
||||||
error(Enocreate);
|
error(Enocreate);
|
||||||
|
case Qcroot:
|
||||||
|
case Qcshr:
|
||||||
|
if(strcmp(up->user, "none") == 0)
|
||||||
|
error(Eperm);
|
||||||
|
}
|
||||||
|
switch(sch->level){
|
||||||
case Qcroot:
|
case Qcroot:
|
||||||
if((perm & DMDIR) == 0 || openmode(omode) != OREAD)
|
if((perm & DMDIR) == 0 || openmode(omode) != OREAD)
|
||||||
error(Eperm);
|
error(Eperm);
|
||||||
|
@ -461,11 +469,14 @@ shrcreate(Chan *c, char *name, int omode, ulong perm)
|
||||||
sch->shr = shr;
|
sch->shr = shr;
|
||||||
break;
|
break;
|
||||||
case Qcshr:
|
case Qcshr:
|
||||||
shr = sch->shr;
|
|
||||||
devpermcheck(shr->owner, shr->perm, ORDWR);
|
|
||||||
if((perm & DMDIR) || openmode(omode) != OWRITE)
|
if((perm & DMDIR) || openmode(omode) != OWRITE)
|
||||||
error(Eperm);
|
error(Eperm);
|
||||||
|
|
||||||
|
shr = sch->shr;
|
||||||
|
if(strcmp(shr->owner, eve) == 0 && !iseve())
|
||||||
|
error(Eperm);
|
||||||
|
devpermcheck(shr->owner, shr->perm, ORDWR);
|
||||||
|
|
||||||
h = &shr->umh;
|
h = &shr->umh;
|
||||||
wlock(&h->lock);
|
wlock(&h->lock);
|
||||||
if(waserror()){
|
if(waserror()){
|
||||||
|
@ -520,8 +531,16 @@ shrremove(Chan *c)
|
||||||
default:
|
default:
|
||||||
error(Eperm);
|
error(Eperm);
|
||||||
case Qcshr:
|
case Qcshr:
|
||||||
|
case Qcmpt:
|
||||||
shr = sch->shr;
|
shr = sch->shr;
|
||||||
|
if(!iseve()){
|
||||||
|
if(strcmp(shr->owner, eve) == 0)
|
||||||
|
error(Eperm);
|
||||||
devpermcheck(shr->owner, shr->perm, ORDWR);
|
devpermcheck(shr->owner, shr->perm, ORDWR);
|
||||||
|
}
|
||||||
|
}
|
||||||
|
switch(sch->level){
|
||||||
|
case Qcshr:
|
||||||
h = &shr->umh;
|
h = &shr->umh;
|
||||||
qlock(&shrslk);
|
qlock(&shrslk);
|
||||||
rlock(&h->lock);
|
rlock(&h->lock);
|
||||||
|
@ -541,8 +560,6 @@ shrremove(Chan *c)
|
||||||
qunlock(&shrslk);
|
qunlock(&shrslk);
|
||||||
break;
|
break;
|
||||||
case Qcmpt:
|
case Qcmpt:
|
||||||
shr = sch->shr;
|
|
||||||
devpermcheck(shr->owner, shr->perm, ORDWR);
|
|
||||||
mpt = sch->mpt;
|
mpt = sch->mpt;
|
||||||
m = &mpt->m;
|
m = &mpt->m;
|
||||||
h = &shr->umh;
|
h = &shr->umh;
|
||||||
|
@ -630,7 +647,6 @@ shrwstat(Chan *c, uchar *dp, int n)
|
||||||
wunlock(&h->lock);
|
wunlock(&h->lock);
|
||||||
break;
|
break;
|
||||||
}
|
}
|
||||||
|
|
||||||
return n;
|
return n;
|
||||||
}
|
}
|
||||||
|
|
||||||
|
|
Loading…
Reference in a new issue