diff --git a/sys/fs/pseudofs/pseudofs.h b/sys/fs/pseudofs/pseudofs.h index 2432748fe4f0..ba0a93b11e69 100644 --- a/sys/fs/pseudofs/pseudofs.h +++ b/sys/fs/pseudofs/pseudofs.h @@ -132,6 +132,18 @@ typedef int (*pfs_vis_t)(PFS_VIS_ARGS); int name(PFS_IOCTL_ARGS); typedef int (*pfs_ioctl_t)(PFS_IOCTL_ARGS); +/* + * Getextattr callback + */ +#define PFS_GETEXTATTR_ARGS \ + struct thread *td, struct proc *p, struct pfs_node *pn, \ + int attrnamespace, const char *name, struct uio *uio, \ + struct ucred *cred +#define PFS_GETEXTATTR_PROTO(name) \ + int name(PFS_GETEXTATTR_ARGS); +struct ucred; +typedef int (*pfs_getextattr_t)(PFS_GETEXTATTR_ARGS); + /* * Last-close callback */ @@ -172,6 +184,7 @@ struct pfs_node { pfs_close_t pn_close; pfs_attr_t pn_attr; pfs_vis_t pn_vis; + pfs_getextattr_t pn_getextattr; void *pn_data; int pn_flags; diff --git a/sys/fs/pseudofs/pseudofs_vnops.c b/sys/fs/pseudofs/pseudofs_vnops.c index 4c869b2e8fb5..e7741b87311d 100644 --- a/sys/fs/pseudofs/pseudofs_vnops.c +++ b/sys/fs/pseudofs/pseudofs_vnops.c @@ -250,6 +250,47 @@ pfs_ioctl(struct vop_ioctl_args *va) PFS_RETURN (error); } +/* + * Perform getextattr + */ +static int +pfs_getextattr(struct vop_getextattr_args *va) +{ + struct vnode *vn = va->a_vp; + struct pfs_vdata *pvd = (struct pfs_vdata *)vn->v_data; + struct pfs_node *pn = pvd->pvd_pn; + struct proc *proc = NULL; + int error; + + PFS_TRACE((pd->pn_name)); + + if (pn->pn_getextattr == NULL) + PFS_RETURN (EOPNOTSUPP); + + /* + * This is necessary because either process' privileges may + * have changed since the open() call. + */ + if (!pfs_visible(curthread, pn, pvd->pvd_pid)) + PFS_RETURN (EIO); + + /* XXX duplicates bits of pfs_visible() */ + if (pvd->pvd_pid != NO_PID) { + if ((proc = pfind(pvd->pvd_pid)) == NULL) + PFS_RETURN (EIO); + _PHOLD(proc); + PROC_UNLOCK(proc); + } + + error = (pn->pn_getextattr)(curthread, proc, pn, va->a_attrnamespace, + va->a_name, va->a_uio, va->a_cred); + + if (proc != NULL) + PRELE(proc); + + PFS_RETURN (error); +} + /* * Look up a file or directory */ @@ -748,6 +789,7 @@ static struct vnodeopv_entry_desc pfs_vnodeop_entries[] = { { &vop_close_desc, (vop_t *)pfs_close }, { &vop_create_desc, (vop_t *)pfs_badop }, { &vop_getattr_desc, (vop_t *)pfs_getattr }, + { &vop_getextattr_desc, (vop_t *)pfs_getextattr }, { &vop_ioctl_desc, (vop_t *)pfs_ioctl }, { &vop_link_desc, (vop_t *)pfs_badop }, { &vop_lookup_desc, (vop_t *)pfs_lookup },