Print this page
PSARC 2008/290 lofi mount
6384817 Need persistent lofi based mounts and direct mount(1m) support for lofi

Split Close
Expand all
Collapse all
          --- old/usr/src/uts/common/fs/pcfs/pc_vfsops.c
          +++ new/usr/src/uts/common/fs/pcfs/pc_vfsops.c
↓ open down ↓ 11 lines elided ↑ open up ↑
  12   12   *
  13   13   * When distributing Covered Code, include this CDDL HEADER in each
  14   14   * file and include the License file at usr/src/OPENSOLARIS.LICENSE.
  15   15   * If applicable, add the following below this CDDL HEADER, with the
  16   16   * fields enclosed by brackets "[]" replaced with your own identifying
  17   17   * information: Portions Copyright [yyyy] [name of copyright owner]
  18   18   *
  19   19   * CDDL HEADER END
  20   20   */
  21   21  /*
  22      - * Copyright 2007 Sun Microsystems, Inc.  All rights reserved.
       22 + * Copyright 2008 Sun Microsystems, Inc.  All rights reserved.
  23   23   * Use is subject to license terms.
  24   24   */
  25   25  
  26      -#pragma ident   "@(#)pc_vfsops.c        1.104   07/10/25 SMI"
       26 +#pragma ident   "@(#)pc_vfsops.c        1.105   08/05/07 SMI"
  27   27  
  28   28  #include <sys/param.h>
  29   29  #include <sys/systm.h>
  30   30  #include <sys/kmem.h>
  31   31  #include <sys/user.h>
  32   32  #include <sys/proc.h>
  33   33  #include <sys/cred.h>
  34   34  #include <sys/disp.h>
  35   35  #include <sys/buf.h>
  36   36  #include <sys/vfs.h>
↓ open down ↓ 249 lines elided ↑ open up ↑
 286  286  static int
 287  287  pcfs_device_identify(
 288  288          struct vfs *vfsp,
 289  289          struct mounta *uap,
 290  290          struct cred *cr,
 291  291          int *dos_ldrive,
 292  292          dev_t *xdev)
 293  293  {
 294  294          struct pathname special;
 295  295          char *c;
 296      -        struct vnode *bvp;
      296 +        struct vnode *svp = NULL;
      297 +        struct vnode *lvp = NULL;
 297  298          int oflag, aflag;
 298  299          int error;
 299  300  
 300  301          /*
 301  302           * Resolve path name of special file being mounted.
 302  303           */
 303  304          if (error = pn_get(uap->spec, UIO_USERSPACE, &special)) {
 304  305                  return (error);
 305  306          }
 306  307  
 307  308          *dos_ldrive = -1;
 308  309  
 309  310          if (error =
 310      -            lookupname(special.pn_path, UIO_SYSSPACE, FOLLOW, NULLVPP, &bvp)) {
      311 +            lookupname(special.pn_path, UIO_SYSSPACE, FOLLOW, NULLVPP, &svp)) {
 311  312                  /*
 312  313                   * If there's no device node, the name specified most likely
 313  314                   * maps to a PCFS-style "partition specifier" to select a
 314  315                   * harddisk primary/logical partition. Disable floppy-specific
 315  316                   * checks in such cases unless an explicit :A or :B is
 316  317                   * requested.
 317  318                   */
 318  319  
 319  320                  /*
 320  321                   * Split the pathname string at the last ':' separator.
↓ open down ↓ 56 lines elided ↑ open up ↑
 377  378                          }
 378  379                  } else {
 379  380                          /*
 380  381                           * Can't parse this - pass through previous error.
 381  382                           */
 382  383                          goto devlookup_done;
 383  384                  }
 384  385  
 385  386  
 386  387                  error = lookupname(special.pn_path, UIO_SYSSPACE, FOLLOW,
 387      -                    NULLVPP, &bvp);
      388 +                    NULLVPP, &svp);
 388  389          } else {
 389  390                  *dos_ldrive = UNPARTITIONED_DRIVE;
 390  391          }
 391  392  devlookup_done:
 392  393          pn_free(&special);
 393  394          if (error)
 394  395                  return (error);
 395  396  
 396  397          ASSERT(*dos_ldrive >= UNPARTITIONED_DRIVE);
 397  398  
 398      -        *xdev = bvp->v_rdev;
 399      -
 400  399          /*
 401  400           * Verify caller's permission to open the device special file.
 402  401           */
 403  402          if ((vfsp->vfs_flag & VFS_RDONLY) != 0 ||
 404  403              ((uap->flags & MS_RDONLY) != 0)) {
 405  404                  oflag = FREAD;
 406  405                  aflag = VREAD;
 407  406          } else {
 408  407                  oflag = FREAD | FWRITE;
 409  408                  aflag = VREAD | VWRITE;
 410  409          }
 411  410  
 412      -        if (bvp->v_type != VBLK)
 413      -                error = ENOTBLK;
 414      -        else if (getmajor(*xdev) >= devcnt)
 415      -                error = ENXIO;
      411 +        error = vfs_get_lofi(vfsp, &lvp);
 416  412  
 417      -        if ((error != 0) ||
 418      -            (error = VOP_ACCESS(bvp, aflag, 0, cr, NULL)) != 0 ||
 419      -            (error = secpolicy_spec_open(cr, bvp, oflag)) != 0) {
 420      -                VN_RELE(bvp);
 421      -                return (error);
      413 +        if (error > 0) {
      414 +                if (error == ENOENT)
      415 +                        error = ENODEV;
      416 +                goto out;
      417 +        } else if (error == 0) {
      418 +                *xdev = lvp->v_rdev;
      419 +        } else {
      420 +                *xdev = svp->v_rdev;
      421 +
      422 +                if (svp->v_type != VBLK)
      423 +                        error = ENOTBLK;
      424 +
      425 +                if ((error = secpolicy_spec_open(cr, svp, oflag)) != 0)
      426 +                        goto out;
 422  427          }
 423  428  
 424      -        VN_RELE(bvp);
 425      -        return (0);
      429 +        if (getmajor(*xdev) >= devcnt) {
      430 +                error = ENXIO;
      431 +                goto out;
      432 +        }
      433 +
      434 +        if ((error = VOP_ACCESS(svp, aflag, 0, cr, NULL)) != 0)
      435 +                goto out;
      436 +
      437 +out:
      438 +        if (svp != NULL)
      439 +                VN_RELE(svp);
      440 +        if (lvp != NULL)
      441 +                VN_RELE(lvp);
      442 +        return (error);
 426  443  }
 427  444  
 428  445  static int
 429  446  pcfs_device_ismounted(
 430  447          struct vfs *vfsp,
 431  448          int dos_ldrive,
 432  449          dev_t xdev,
 433  450          int *remounting,
 434  451          dev_t *pseudodev)
 435  452  {