static int zpl_get_link_common(struct dentry *dentry, struct inode *ip, char **link) { fstrans_cookie_t cookie; cred_t *cr = CRED(); struct iovec iov; uio_t uio; int error; crhold(cr); *link = NULL; iov.iov_len = MAXPATHLEN; iov.iov_base = kmem_zalloc(MAXPATHLEN, KM_SLEEP); uio.uio_iov = &iov; uio.uio_iovcnt = 1; uio.uio_skip = 0; uio.uio_resid = (MAXPATHLEN - 1); uio.uio_segflg = UIO_SYSSPACE; cookie = spl_fstrans_mark(); error = -zfs_readlink(ip, &uio, cr); spl_fstrans_unmark(cookie); crfree(cr); if (error) kmem_free(iov.iov_base, MAXPATHLEN); else *link = iov.iov_base; return (error); }
static void * zpl_follow_link(struct dentry *dentry, struct nameidata *nd) { cred_t *cr = CRED(); struct inode *ip = dentry->d_inode; struct iovec iov; uio_t uio; char *link; int error; crhold(cr); iov.iov_len = MAXPATHLEN; iov.iov_base = link = kmem_zalloc(MAXPATHLEN, KM_SLEEP); uio.uio_iov = &iov; uio.uio_iovcnt = 1; uio.uio_resid = (MAXPATHLEN - 1); uio.uio_segflg = UIO_SYSSPACE; error = -zfs_readlink(ip, &uio, cr); if (error) { kmem_free(link, MAXPATHLEN); nd_set_link(nd, ERR_PTR(error)); } else { nd_set_link(nd, link); } crfree(cr); return (NULL); }
const char * zpl_follow_link(struct dentry *dentry, void **symlink_cookie) #endif { cred_t *cr = CRED(); struct inode *ip = dentry->d_inode; struct iovec iov; uio_t uio; char *link; int error; fstrans_cookie_t cookie; crhold(cr); iov.iov_len = MAXPATHLEN; iov.iov_base = link = kmem_zalloc(MAXPATHLEN, KM_SLEEP); uio.uio_iov = &iov; uio.uio_iovcnt = 1; uio.uio_skip = 0; uio.uio_resid = (MAXPATHLEN - 1); uio.uio_segflg = UIO_SYSSPACE; cookie = spl_fstrans_mark(); error = -zfs_readlink(ip, &uio, cr); spl_fstrans_unmark(cookie); if (error) kmem_free(link, MAXPATHLEN); crfree(cr); #ifdef HAVE_FOLLOW_LINK_NAMEIDATA if (error) nd_set_link(nd, ERR_PTR(error)); else nd_set_link(nd, link); return (NULL); #else if (error) return (ERR_PTR(error)); else return (*symlink_cookie = link); #endif }