static void *
kobj_open_file_vnode(const char *file)
{
	struct thread *td = curthread;
	struct filedesc *fd;
	struct nameidata nd;
	int error, flags, vfslocked;

	fd = td->td_proc->p_fd;
	FILEDESC_XLOCK(fd);
	if (fd->fd_rdir == NULL) {
		fd->fd_rdir = rootvnode;
		vref(fd->fd_rdir);
	}
	if (fd->fd_cdir == NULL) {
		fd->fd_cdir = rootvnode;
		vref(fd->fd_cdir);
	}
	FILEDESC_XUNLOCK(fd);

	flags = FREAD | O_NOFOLLOW;
	NDINIT(&nd, LOOKUP, MPSAFE, UIO_SYSSPACE, file, td);
	error = vn_open_cred(&nd, &flags, 0, 0, curthread->td_ucred, NULL);
	if (error != 0)
		return (NULL);
	vfslocked = NDHASGIANT(&nd);
	NDFREE(&nd, NDF_ONLY_PNBUF);
	/* We just unlock so we hold a reference. */
	VOP_UNLOCK(nd.ni_vp, 0);
	VFS_UNLOCK_GIANT(vfslocked);
	return (nd.ni_vp);
}
Beispiel #2
0
int
alq_open_flags(struct alq **alqp, const char *file, struct ucred *cred, int cmode,
               int size, int flags)
{
    struct thread *td;
    struct nameidata nd;
    struct alq *alq;
    int oflags;
    int error;
    int vfslocked;

    KASSERT((size > 0), ("%s: size <= 0", __func__));

    *alqp = NULL;
    td = curthread;

    NDINIT(&nd, LOOKUP, NOFOLLOW | MPSAFE, UIO_SYSSPACE, file, td);
    oflags = FWRITE | O_NOFOLLOW | O_CREAT;

    error = vn_open_cred(&nd, &oflags, cmode, 0, cred, NULL);
    if (error)
        return (error);

    vfslocked = NDHASGIANT(&nd);
    NDFREE(&nd, NDF_ONLY_PNBUF);
    /* We just unlock so we hold a reference */
    VOP_UNLOCK(nd.ni_vp, 0);
    VFS_UNLOCK_GIANT(vfslocked);

    alq = bsd_malloc(sizeof(*alq), M_ALD, M_WAITOK|M_ZERO);
    alq->aq_vp = nd.ni_vp;
    alq->aq_cred = crhold(cred);

    mtx_init(&alq->aq_mtx, "ALD Queue", NULL, MTX_SPIN|MTX_QUIET);

    alq->aq_buflen = size;
    alq->aq_entmax = 0;
    alq->aq_entlen = 0;

    alq->aq_freebytes = alq->aq_buflen;
    alq->aq_entbuf = bsd_malloc(alq->aq_buflen, M_ALD, M_WAITOK|M_ZERO);
    alq->aq_writehead = alq->aq_writetail = 0;
    if (flags & ALQ_ORDERED)
        alq->aq_flags |= AQ_ORDERED;

    if ((error = ald_add(alq)) != 0) {
        alq_destroy(alq);
        return (error);
    }

    *alqp = alq;

    return (0);
}
Beispiel #3
0
static void *
kobj_open_file_vnode(const char *file)
{
	struct thread *td = curthread;
	struct nameidata nd;
	int error, flags;

	pwd_ensure_dirs();

	flags = FREAD | O_NOFOLLOW;
	NDINIT(&nd, LOOKUP, 0, UIO_SYSSPACE, file, td);
	error = vn_open_cred(&nd, &flags, 0, 0, curthread->td_ucred, NULL);
	if (error != 0)
		return (NULL);
	NDFREE(&nd, NDF_ONLY_PNBUF);
	/* We just unlock so we hold a reference. */
	VOP_UNLOCK(nd.ni_vp, 0);
	return (nd.ni_vp);
}
Beispiel #4
0
	/*
	 * Open the lock fifo.  If for any reason we don't find the fifo, it
	 * means that the lock daemon isn't running.  Translate any missing
	 * file error message for the user, otherwise the application will
	 * complain that the user's file is missing, which isn't the case.
	 * Note that we use proc0's cred, so the fifo is opened as root.
	 *
	 * XXX: Note that this behavior is relative to the root directory
	 * of the current process, and this may result in a variety of
	 * {functional, security} problems in chroot() environments.
	 */
	NDINIT(&nd, LOOKUP, FOLLOW, UIO_SYSSPACE, _PATH_LCKFIFO, td);

	fmode = FFLAGS(O_WRONLY);
	error = vn_open_cred(&nd, &fmode, 0, thread0.td_ucred);
	if (error != 0) {
		return (error == ENOENT ? EOPNOTSUPP : error);
	}
	wvp = nd.ni_vp;
	VOP_UNLOCK(wvp, 0, td);		/* vn_open leaves it locked */


	ioflg = IO_UNIT | IO_NOMACCHECK;
	for (;;) {
		VOP_LEASE(wvp, td, thread0.td_ucred, LEASE_WRITE);

		error = vn_rdwr(UIO_WRITE, wvp, (caddr_t)&msg, sizeof(msg), 0,
		    UIO_SYSSPACE, ioflg, thread0.td_ucred, NOCRED, NULL, td);

		if (error && (((ioflg & IO_NDELAY) == 0) || error != EAGAIN)) {
/*
 * Create the queue data structure, allocate the buffer, and open the file.
 */
int
alq_open(struct alq **alqp, const char *file, struct ucred *cred, int cmode,
    int size, int count)
{
	struct thread *td;
	struct nameidata nd;
	struct ale *ale;
	struct ale *alp;
	struct alq *alq;
	char *bufp;
	int flags;
	int error;
	int i, vfslocked;

	*alqp = NULL;
	td = curthread;

	NDINIT(&nd, LOOKUP, NOFOLLOW | MPSAFE, UIO_SYSSPACE, file, td);
	flags = FWRITE | O_NOFOLLOW | O_CREAT;

	error = vn_open_cred(&nd, &flags, cmode, 0, cred, NULL);
	if (error)
		return (error);

	vfslocked = NDHASGIANT(&nd);
	NDFREE(&nd, NDF_ONLY_PNBUF);
	/* We just unlock so we hold a reference */
	VOP_UNLOCK(nd.ni_vp, 0);
	VFS_UNLOCK_GIANT(vfslocked);

	alq = malloc(sizeof(*alq), M_ALD, M_WAITOK|M_ZERO);
	alq->aq_entbuf = malloc(count * size, M_ALD, M_WAITOK|M_ZERO);
	alq->aq_first = malloc(sizeof(*ale) * count, M_ALD, M_WAITOK|M_ZERO);
	alq->aq_vp = nd.ni_vp;
	alq->aq_cred = crhold(cred);
	alq->aq_entmax = count;
	alq->aq_entlen = size;
	alq->aq_entfree = alq->aq_first;

	mtx_init(&alq->aq_mtx, "ALD Queue", NULL, MTX_SPIN|MTX_QUIET);

	bufp = alq->aq_entbuf;
	ale = alq->aq_first;
	alp = NULL;

	/* Match up entries with buffers */
	for (i = 0; i < count; i++) {
		if (alp)
			alp->ae_next = ale;
		ale->ae_data = bufp;
		alp = ale;
		ale++;
		bufp += size;
	}

	alp->ae_next = alq->aq_first;

	if ((error = ald_add(alq)) != 0)
		return (error);
	*alqp = alq;

	return (0);
}