[BACK]Return to xfs_vfsops-bsd.c CVS log [TXT][DIR] Up to [local] / sys / xfs

Annotation of sys/xfs/xfs_vfsops-bsd.c, Revision 1.1.1.1

1.1       nbrk        1: /*
                      2:  * Copyright (c) 1995 - 2002 Kungliga Tekniska Högskolan
                      3:  * (Royal Institute of Technology, Stockholm, Sweden).
                      4:  * All rights reserved.
                      5:  *
                      6:  * Redistribution and use in source and binary forms, with or without
                      7:  * modification, are permitted provided that the following conditions
                      8:  * are met:
                      9:  *
                     10:  * 1. Redistributions of source code must retain the above copyright
                     11:  *    notice, this list of conditions and the following disclaimer.
                     12:  *
                     13:  * 2. Redistributions in binary form must reproduce the above copyright
                     14:  *    notice, this list of conditions and the following disclaimer in the
                     15:  *    documentation and/or other materials provided with the distribution.
                     16:  *
                     17:  * 3. Neither the name of the Institute nor the names of its contributors
                     18:  *    may be used to endorse or promote products derived from this software
                     19:  *    without specific prior written permission.
                     20:  *
                     21:  * THIS SOFTWARE IS PROVIDED BY THE INSTITUTE AND CONTRIBUTORS ``AS IS'' AND
                     22:  * ANY EXPRESS OR IMPLIED WARRANTIES, INCLUDING, BUT NOT LIMITED TO, THE
                     23:  * IMPLIED WARRANTIES OF MERCHANTABILITY AND FITNESS FOR A PARTICULAR PURPOSE
                     24:  * ARE DISCLAIMED.  IN NO EVENT SHALL THE INSTITUTE OR CONTRIBUTORS BE LIABLE
                     25:  * FOR ANY DIRECT, INDIRECT, INCIDENTAL, SPECIAL, EXEMPLARY, OR CONSEQUENTIAL
                     26:  * DAMAGES (INCLUDING, BUT NOT LIMITED TO, PROCUREMENT OF SUBSTITUTE GOODS
                     27:  * OR SERVICES; LOSS OF USE, DATA, OR PROFITS; OR BUSINESS INTERRUPTION)
                     28:  * HOWEVER CAUSED AND ON ANY THEORY OF LIABILITY, WHETHER IN CONTRACT, STRICT
                     29:  * LIABILITY, OR TORT (INCLUDING NEGLIGENCE OR OTHERWISE) ARISING IN ANY WAY
                     30:  * OUT OF THE USE OF THIS SOFTWARE, EVEN IF ADVISED OF THE POSSIBILITY OF
                     31:  * SUCH DAMAGE.
                     32:  */
                     33:
                     34: #include <xfs/xfs_locl.h>
                     35:
                     36: RCSID("$arla: xfs_vfsops-bsd.c,v 1.72 2002/12/19 10:30:17 lha Exp $");
                     37:
                     38: /*
                     39:  * NNPFS vfs operations.
                     40:  */
                     41:
                     42: #include <xfs/xfs_common.h>
                     43: #include <xfs/xfs_message.h>
                     44: #include <xfs/xfs_fs.h>
                     45: #include <xfs/xfs_dev.h>
                     46: #include <xfs/xfs_deb.h>
                     47: #include <xfs/xfs_vfsops.h>
                     48: #include <xfs/xfs_vfsops-bsd.h>
                     49: #include <xfs/xfs_vnodeops.h>
                     50:
                     51: int
                     52: xfs_mount_caddr(struct mount *mp,
                     53:                const char *user_path,
                     54:                caddr_t user_data,
                     55:                struct nameidata *ndp,
                     56:                d_thread_t *p)
                     57: {
                     58:     return xfs_mount_common(mp, user_path, user_data, ndp, p);
                     59: }
                     60:
                     61: int
                     62: xfs_start(struct mount * mp, int flags, d_thread_t * p)
                     63: {
                     64:     NNPFSDEB(XDEBVFOPS, ("xfs_start mp = %lx, flags = %d, proc = %lx\n",
                     65:                       (unsigned long)mp, flags, (unsigned long)p));
                     66:     return 0;
                     67: }
                     68:
                     69:
                     70: int
                     71: xfs_unmount(struct mount * mp, int mntflags, d_thread_t *p)
                     72: {
                     73:     NNPFSDEB(XDEBVFOPS, ("xfs_umount: mp = %lx, mntflags = %d, proc = %lx\n",
                     74:                       (unsigned long)mp, mntflags, (unsigned long)p));
                     75:     return xfs_unmount_common(mp, mntflags);
                     76: }
                     77:
                     78: int
                     79: xfs_root(struct mount *mp, struct vnode **vpp)
                     80: {
                     81:     NNPFSDEB(XDEBVFOPS, ("xfs_root mp = %lx\n", (unsigned long)mp));
                     82: #ifdef HAVE_FREEBSD_THREAD
                     83:     return xfs_root_common(mp, vpp, xfs_curthread(), xfs_curthread()->td_proc->p_ucred);
                     84: #else
                     85:     return xfs_root_common(mp, vpp, xfs_curproc(), xfs_curproc()->p_ucred);
                     86: #endif
                     87: }
                     88:
                     89: int
                     90: xfs_quotactl(struct mount *mp, int cmd, uid_t uid, caddr_t arg, d_thread_t *p)
                     91: {
                     92:     NNPFSDEB(XDEBVFOPS, ("xfs_quotactl: mp = %lx, cmd = %d, uid = %u, "
                     93:                       "arg = %lx, proc = %lx\n",
                     94:                       (unsigned long)mp, cmd, uid,
                     95:                       (unsigned long)arg, (unsigned long)p));
                     96:     return EOPNOTSUPP;
                     97: }
                     98:
                     99: int
                    100: xfs_statfs(struct mount *mp, struct statfs *sbp, d_thread_t *p)
                    101: {
                    102:     NNPFSDEB(XDEBVFOPS, ("xfs_statfs: mp = %lx, sbp = %lx, proc = %lx\n",
                    103:                       (unsigned long)mp,
                    104:                       (unsigned long)sbp,
                    105:                       (unsigned long)p));
                    106:     bcopy(&mp->mnt_stat, sbp, sizeof(*sbp));
                    107:     return 0;
                    108: }
                    109:
                    110: int
                    111: xfs_sync(struct mount *mp, int waitfor, struct ucred *cred, d_thread_t *p)
                    112: {
                    113:     NNPFSDEB(XDEBVFOPS, ("xfs_sync: mp = %lx, waitfor = %d, "
                    114:                       "cred = %lx, proc = %lx\n",
                    115:                       (unsigned long)mp,
                    116:                       waitfor,
                    117:                       (unsigned long)cred,
                    118:                       (unsigned long)p));
                    119:     return 0;
                    120: }
                    121:
                    122: int
                    123: xfs_vget(struct mount * mp,
                    124: #ifdef __APPLE__
                    125:         void *ino,
                    126: #else
                    127:         ino_t ino,
                    128: #endif
                    129:         struct vnode ** vpp)
                    130: {
                    131:     NNPFSDEB(XDEBVFOPS, ("xfs_vget\n"));
                    132:     return EOPNOTSUPP;
                    133: }
                    134:
                    135: static int
                    136: common_fhtovp(struct mount * mp,
                    137:           struct fid * fhp,
                    138:           struct vnode ** vpp)
                    139: {
                    140: #ifdef ARLA_KNFS
                    141:     struct netcred *np = NULL;
                    142:     struct xfs_node *xn;
                    143:     struct vnode *vp;
                    144:     xfs_handle handle;
                    145:     int error;
                    146:
                    147:     NNPFSDEB(XDEBVFOPS, ("xfs_fhtovp\n"));
                    148:
                    149:     if (fhp->fid_len != 16) {
                    150:        printf("xfs_fhtovp: *PANIC* got a invalid length of a fid\n");
                    151:        return EINVAL;
                    152:     }
                    153:
                    154:     memcpy(&handle, fhp->fid_data, sizeof(handle));
                    155:     NNPFSDEB(XDEBVFOPS, ("xfs_fhtovp: fid: %d.%d.%d.%d\n",
                    156:                       handle.a, handle.d, handle.c, handle.d));
                    157:
                    158:     NNPFSDEB(XDEBVFOPS, ("xfs_fhtovp: xfs_vnode_find\n"));
                    159:     xn = xfs_node_find(&xfs[0].nodehead, &handle);
                    160:
                    161:     if (xn == NULL) {
                    162:        struct xfs_message_getattr msg;
                    163:
                    164:         error = xfs_getnewvnode(xfs[0].mp, &vp, &handle);
                    165:         if (error)
                    166:             return error;
                    167:
                    168:        xfs_do_vget(vp, 0, curproc);
                    169:
                    170:     } else {
                    171:        /* XXX access ? */
                    172:        vp = XNODE_TO_VNODE(xn);
                    173:
                    174:        /* XXX wrong ? (we tell arla below) */
                    175:         if (vp->v_usecount <= 0)
                    176:            xfs_do_vget(vp, 0, curproc);
                    177:        else
                    178:            VREF(vp);
                    179:        error = 0;
                    180:     }
                    181:
                    182:     *vpp = vp;
                    183:
                    184:     if (error == 0) {
                    185:        NNPFSDEB(XDEBVFOPS, ("xfs_fhtovp done\n"));
                    186:
                    187:        /*
                    188:         * XXX tell arla about this node is hold by nfsd.
                    189:         * There need to be code in xfs_write too.
                    190:         */
                    191:     } else
                    192:        NNPFSDEB(XDEBVFOPS, ("xfs_fhtovp failed (%d)\n", error));
                    193:
                    194:     return error;
                    195: #else /* !ARLA_KNFS */
                    196:     return EOPNOTSUPP;
                    197: #endif /* !ARLA_KNFS */
                    198: }
                    199:
                    200: /* new style fhtovp */
                    201:
                    202: #ifdef HAVE_STRUCT_VFSOPS_VFS_CHECKEXP
                    203: int
                    204: xfs_fhtovp(struct mount * mp,
                    205:           struct fid * fhp,
                    206:           struct vnode ** vpp)
                    207: {
                    208:     return common_fhtovp (mp, fhp, vpp);
                    209: }
                    210:
                    211: #else /* !HAVE_STRUCT_VFSOPS_VFS_CHECKEXP */
                    212:
                    213: /* old style fhtovp */
                    214:
                    215: int
                    216: xfs_fhtovp(struct mount * mp,
                    217:           struct fid * fhp,
                    218:           struct mbuf * nam,
                    219:           struct vnode ** vpp,
                    220:           int *exflagsp,
                    221:           struct ucred ** credanonp)
                    222: {
                    223:     static struct ucred fhtovpcred;
                    224:     int error;
                    225:
                    226:     /* XXX: Should see if we is exported to this client */
                    227: #if 0
                    228:     np = vfs_export_lookup(mp, &ump->um_export, nam);
                    229:     if (np == NULL)
                    230:        return EACCES;
                    231: #endif
                    232:     error = common_fhtovp(mp, fhp, vpp);
                    233:     if (error == 0) {
                    234:        fhtovpcred.cr_uid = 0;
                    235:        fhtovpcred.cr_gid = 0;
                    236:        fhtovpcred.cr_ngroups = 0;
                    237:
                    238: #ifdef MNT_EXPUBLIC
                    239:        *exflagsp = MNT_EXPUBLIC;
                    240: #else
                    241:        *exflagsp = 0;
                    242: #endif
                    243:        *credanonp = &fhtovpcred;
                    244:     }
                    245:     return error;
                    246: }
                    247: #endif /* !HAVE_STRUCT_VFSOPS_VFS_CHECKEXP */
                    248:
                    249: int
                    250: xfs_checkexp (struct mount *mp,
                    251: #ifdef __FreeBSD__
                    252:              struct sockaddr *nam,
                    253: #else
                    254:              struct mbuf *nam,
                    255: #endif
                    256:              int *exflagsp,
                    257:              struct ucred **credanonp)
                    258: {
                    259:     NNPFSDEB(XDEBVFOPS, ("xfs_checkexp\n"));
                    260:
                    261: #if 0
                    262:     np = vfs_export_lookup(mp, &ump->um_export, nam);
                    263:     if (np == NULL)
                    264:        return EACCES;
                    265: #endif
                    266:     return 0;
                    267: }
                    268:
                    269: int
                    270: xfs_vptofh(struct vnode * vp,
                    271:           struct fid * fhp)
                    272: {
                    273: #ifdef ARLA_KNFS
                    274:     struct xfs_node *xn;
                    275:     NNPFSDEB(XDEBVFOPS, ("xfs_vptofh\n"));
                    276:
                    277:     if (MAXFIDSZ < 16)
                    278:        return EOPNOTSUPP;
                    279:
                    280:     xn = VNODE_TO_XNODE(vp);
                    281:
                    282:     if (xn == NULL)
                    283:        return EINVAL;
                    284:
                    285:     fhp->fid_len = 16;
                    286:     memcpy(fhp->fid_data, &xn->handle,  16);
                    287:
                    288:     return 0;
                    289: #else
                    290:     NNPFSDEB(XDEBVFOPS, ("xfs_vptofh\n"));
                    291:     return EOPNOTSUPP;
                    292: #endif
                    293: }
                    294:
                    295: /*
                    296:  * xfs complete dead vnodes implementation.
                    297:  *
                    298:  * this is because the dead_vnodeops_p is _not_ filesystem, but rather
                    299:  * a part of the vfs-layer.
                    300:  */
                    301:
                    302: int
                    303: xfs_dead_lookup(struct vop_lookup_args * ap)
                    304:      /* struct vop_lookup_args {
                    305:        struct vnodeop_desc *a_desc;
                    306:        struct vnode *a_dvp;
                    307:        struct vnode **a_vpp;
                    308:        struct componentname *a_cnp;
                    309: }; */
                    310: {
                    311:     *ap->a_vpp = NULL;
                    312:     return ENOTDIR;
                    313: }
                    314:
                    315: /*
                    316:  * Given `fsid', `fileid', and `gen', return in `vpp' a locked and
                    317:  * ref'ed vnode from that file system with that id and generation.
                    318:  * All is done in the context of `proc'.  Returns 0 if successful, and
                    319:  * error otherwise.
                    320:  */
                    321:
                    322: int
                    323: xfs_fhlookup (d_thread_t *proc,
                    324:              struct xfs_fhandle_t *fhp,
                    325:              struct vnode **vpp)
                    326: {
                    327:     int error;
                    328:     struct mount *mp;
                    329: #if !(defined(HAVE_GETFH) && defined(HAVE_FHOPEN))
                    330:     struct ucred *cred = proc->p_ucred;
                    331:     struct vattr vattr;
                    332:     fsid_t fsid;
                    333:     struct xfs_fh_args *fh_args = (struct xfs_fh_args *)fhp->fhdata;
                    334:
                    335:     NNPFSDEB(XDEBVFOPS, ("xfs_fhlookup (xfs)\n"));
                    336:
                    337:     error = xfs_suser (proc);
                    338:     if (error)
                    339:        return EPERM;
                    340:
                    341:     if (fhp->len < sizeof(struct xfs_fh_args))
                    342:        return EINVAL;
                    343:
                    344:     fsid = SCARG(fh_args, fsid);
                    345:
                    346:     mp = xfs_vfs_getvfs (&fsid);
                    347:     if (mp == NULL)
                    348:        return ENXIO;
                    349:
                    350: #ifdef __APPLE__
                    351:     {
                    352:        uint32_t ino = SCARG(fh_args, fileid);
                    353:        error = VFS_VGET(mp, &ino, vpp);
                    354:     }
                    355: #else
                    356:     error = VFS_VGET(mp, SCARG(fh_args, fileid), vpp);
                    357: #endif
                    358:
                    359:     if (error)
                    360:        return error;
                    361:
                    362:     if (*vpp == NULL)
                    363:        return ENOENT;
                    364:
                    365:     error = VOP_GETATTR(*vpp, &vattr, cred, proc);
                    366:     if (error) {
                    367:        vput(*vpp);
                    368:        return error;
                    369:     }
                    370:
                    371:     if (vattr.va_gen != SCARG(fh_args, gen)) {
                    372:        vput(*vpp);
                    373:        return ENOENT;
                    374:     }
                    375: #else /* HAVE_GETFH && HAVE_FHOPEN */
                    376:     {
                    377:        fhandle_t *fh = (fhandle_t *) fhp;
                    378:
                    379:        NNPFSDEB(XDEBVFOPS, ("xfs_fhlookup (native)\n"));
                    380:
                    381:        mp = xfs_vfs_getvfs (&fh->fh_fsid);
                    382:        if (mp == NULL)
                    383:            return ESTALE;
                    384:
                    385:        if ((error = VFS_FHTOVP(mp, &fh->fh_fid, vpp)) != 0) {
                    386:            *vpp = NULL;
                    387:            return error;
                    388:        }
                    389:     }
                    390: #endif  /* HAVE_GETFH && HAVE_FHOPEN */
                    391:
                    392: #ifdef HAVE_KERNEL_VFS_OBJECT_CREATE
                    393:     if ((*vpp)->v_type == VREG && (*vpp)->v_object == NULL)
                    394: #ifdef HAVE_FREEBSD_THREAD
                    395:        xfs_vfs_object_create (*vpp, proc, proc->td_proc->p_ucred);
                    396: #else
                    397:        xfs_vfs_object_create (*vpp, proc, proc->p_ucred);
                    398: #endif
                    399: #elif __APPLE__
                    400:     if ((*vpp)->v_type == VREG && (!UBCINFOEXISTS(*vpp))) {
                    401:         ubc_info_init(*vpp);
                    402:     }
                    403:     ubc_hold(*vpp);
                    404: #endif
                    405:     return 0;
                    406: }
                    407:
                    408:
                    409:
                    410: /*
                    411:  * Perform an open operation on the vnode identified by a `xfs_fhandle_t'
                    412:  * (see xfs_fhlookup) with flags `user_flags'.  Returns 0 or
                    413:  * error.  If successful, the file descriptor is returned in `retval'.
                    414:  */
                    415:
                    416: extern struct fileops vnops;   /* sometimes declared in <file.h> */
                    417:
                    418: int
                    419: xfs_fhopen (d_thread_t *proc,
                    420:            struct xfs_fhandle_t *fhp,
                    421:            int user_flags,
                    422:            register_t *retval)
                    423: {
                    424:     int error;
                    425:     struct vnode *vp;
                    426: #ifdef HAVE_FREEBSD_THREAD
                    427:     struct ucred *cred = proc->td_proc->p_ucred;
                    428: #else
                    429:     struct ucred *cred = proc->p_ucred;
                    430: #endif
                    431:     int flags = FFLAGS(user_flags);
                    432:     int index;
                    433:     struct file *fp;
                    434:     int mode;
                    435:     struct xfs_fhandle_t fh;
                    436:
                    437:     NNPFSDEB(XDEBVFOPS, ("xfs_fhopen: flags = %d\n", user_flags));
                    438:
                    439:     error = copyin (fhp, &fh, sizeof(fh));
                    440:     if (error)
                    441:        return error;
                    442:
                    443:     error = xfs_fhlookup (proc, &fh, &vp);
                    444:     NNPFSDEB(XDEBVFOPS, ("xfs_fhlookup returned %d\n", error));
                    445:     if (error)
                    446:        return error;
                    447:
                    448:     switch (vp->v_type) {
                    449:     case VDIR :
                    450:     case VREG :
                    451:        break;
                    452:     case VLNK :
                    453:        error = EMLINK;
                    454:        goto out;
                    455:     default :
                    456:        error = EOPNOTSUPP;
                    457:        goto out;
                    458:     }
                    459:
                    460:     mode = 0;
                    461:     if (flags & FWRITE) {
                    462:        switch (vp->v_type) {
                    463:        case VREG :
                    464:            break;
                    465:        case VDIR :
                    466:            error = EISDIR;
                    467:            goto out;
                    468:        default :
                    469:            error = EOPNOTSUPP;
                    470:            goto out;
                    471:        }
                    472:
                    473:        error = vn_writechk (vp);
                    474:        if (error)
                    475:            goto out;
                    476:
                    477:        mode |= VWRITE;
                    478:     }
                    479:     if (flags & FREAD)
                    480:        mode |= VREAD;
                    481:
                    482:     if (mode) {
                    483:        error = VOP_ACCESS(vp, mode, cred, proc);
                    484:        if (error)
                    485:            goto out;
                    486:     }
                    487:
                    488:     error = VOP_OPEN(vp, flags, cred, proc);
                    489:     if (error)
                    490:        goto out;
                    491:
                    492:     error = falloc(proc, &fp, &index);
                    493:     if (error)
                    494:        goto out;
                    495:
                    496:     if (flags & FWRITE)
                    497:         vp->v_writecount++;
                    498:
                    499: #if defined(__FreeBSD_version) && __FreeBSD_version >= 300000
                    500:     if (vp->v_type == VREG) {
                    501: #ifdef HAVE_FREEBSD_THREAD
                    502:        error = xfs_vfs_object_create(vp, proc, proc->td_proc->p_ucred);
                    503: #else
                    504:        error = xfs_vfs_object_create(vp, proc, proc->p_ucred);
                    505: #endif
                    506:        if (error)
                    507:            goto out;
                    508:     }
                    509: #endif
                    510:
                    511:     fp->f_flag = flags & FMASK;
                    512:     fp->f_type = DTYPE_VNODE;
                    513:     fp->f_ops  = &vnops;
                    514:     fp->f_data = (caddr_t)vp;
                    515:     xfs_vfs_unlock(vp, proc);
                    516:     *retval = index;
                    517: #ifdef FILE_UNUSE
                    518:     FILE_UNUSE(fp, proc);
                    519: #endif
                    520: #ifdef __APPLE__
                    521:     *fdflags(proc, index) &= ~UF_RESERVED;
                    522: #endif
                    523:     return 0;
                    524: out:
                    525:     NNPFSDEB(XDEBVFOPS, ("xfs_fhopen: error = %d\n", error));
                    526:     vput(vp);
                    527:     return error;
                    528: }

CVSweb