Print this page
8368 remove warlock leftovers from usr/src/uts


 282                 }
 283         }
 284 
 285         return (0);
 286 }
 287 
 288 /* ARGSUSED */
 289 static int32_t
 290 udf_read(
 291         struct vnode *vp,
 292         struct uio *uiop,
 293         int32_t ioflag,
 294         struct cred *cr,
 295         caller_context_t *ct)
 296 {
 297         struct ud_inode *ip = VTOI(vp);
 298         int32_t error;
 299 
 300         ud_printf("udf_read\n");
 301 
 302 #ifdef  __lock_lint
 303         rw_enter(&ip->i_rwlock, RW_READER);
 304 #endif
 305 
 306         ASSERT(RW_READ_HELD(&ip->i_rwlock));
 307 
 308         if (MANDLOCK(vp, ip->i_char)) {
 309                 /*
 310                  * udf_getattr ends up being called by chklock
 311                  */
 312                 error = chklock(vp, FREAD, uiop->uio_loffset,
 313                     uiop->uio_resid, uiop->uio_fmode, ct);
 314                 if (error) {
 315                         goto end;
 316                 }
 317         }
 318 
 319         rw_enter(&ip->i_contents, RW_READER);
 320         error = ud_rdip(ip, uiop, ioflag, cr);
 321         rw_exit(&ip->i_contents);
 322 
 323 end:
 324 #ifdef  __lock_lint
 325         rw_exit(&ip->i_rwlock);
 326 #endif
 327 
 328         return (error);
 329 }
 330 
 331 
 332 int32_t ud_WRITES = 1;
 333 int32_t ud_HW = 96 * 1024;
 334 int32_t ud_LW = 64 * 1024;
 335 int32_t ud_throttles = 0;
 336 
 337 /* ARGSUSED */
 338 static int32_t
 339 udf_write(
 340         struct vnode *vp,
 341         struct uio *uiop,
 342         int32_t ioflag,
 343         struct cred *cr,
 344         caller_context_t *ct)
 345 {
 346         struct ud_inode *ip = VTOI(vp);
 347         int32_t error = 0;
 348 
 349         ud_printf("udf_write\n");
 350 
 351 #ifdef  __lock_lint
 352         rw_enter(&ip->i_rwlock, RW_WRITER);
 353 #endif
 354 
 355         ASSERT(RW_WRITE_HELD(&ip->i_rwlock));
 356 
 357         if (MANDLOCK(vp, ip->i_char)) {
 358                 /*
 359                  * ud_getattr ends up being called by chklock
 360                  */
 361                 error = chklock(vp, FWRITE, uiop->uio_loffset,
 362                     uiop->uio_resid, uiop->uio_fmode, ct);
 363                 if (error) {
 364                         goto end;
 365                 }
 366         }
 367         /*
 368          * Throttle writes.
 369          */
 370         mutex_enter(&ip->i_tlock);
 371         if (ud_WRITES && (ip->i_writes > ud_HW)) {
 372                 while (ip->i_writes > ud_HW) {
 373                         ud_throttles++;
 374                         cv_wait(&ip->i_wrcv, &ip->i_tlock);
 375                 }
 376         }
 377         mutex_exit(&ip->i_tlock);
 378 
 379         /*
 380          * Write to the file
 381          */
 382         rw_enter(&ip->i_contents, RW_WRITER);
 383         if ((ioflag & FAPPEND) != 0 && (ip->i_type == VREG)) {
 384                 /*
 385                  * In append mode start at end of file.
 386                  */
 387                 uiop->uio_loffset = ip->i_size;
 388         }
 389         error = ud_wrip(ip, uiop, ioflag, cr);
 390         rw_exit(&ip->i_contents);
 391 
 392 end:
 393 #ifdef  __lock_lint
 394         rw_exit(&ip->i_rwlock);
 395 #endif
 396 
 397         return (error);
 398 }
 399 
 400 /* ARGSUSED */
 401 static int32_t
 402 udf_ioctl(
 403         struct vnode *vp,
 404         int32_t cmd,
 405         intptr_t arg,
 406         int32_t flag,
 407         struct cred *cr,
 408         int32_t *rvalp,
 409         caller_context_t *ct)
 410 {
 411         return (ENOTTY);
 412 }
 413 
 414 /* ARGSUSED */
 415 static int32_t
 416 udf_getattr(


 728         if ((vap->va_mode & VSVTX) && secpolicy_vnode_stky_modify(cr) != 0)
 729                 vap->va_mode &= ~VSVTX;
 730 
 731         if (*name == '\0') {
 732                 /*
 733                  * Null component name refers to the directory itself.
 734                  */
 735                 VN_HOLD(dvp);
 736                 ITIMES(ip);
 737                 error = EEXIST;
 738         } else {
 739                 xip = NULL;
 740                 rw_enter(&ip->i_rwlock, RW_WRITER);
 741                 error = ud_direnter(ip, name, DE_CREATE,
 742                     (struct ud_inode *)0, (struct ud_inode *)0,
 743                     vap, &xip, cr, ct);
 744                 rw_exit(&ip->i_rwlock);
 745                 ITIMES(ip);
 746                 ip = xip;
 747         }
 748 #ifdef  __lock_lint
 749         rw_enter(&ip->i_contents, RW_WRITER);
 750 #else
 751         if (ip != NULL) {
 752                 rw_enter(&ip->i_contents, RW_WRITER);
 753         }
 754 #endif
 755 
 756         /*
 757          * If the file already exists and this is a non-exclusive create,
 758          * check permissions and allow access for non-directories.
 759          * Read-only create of an existing directory is also allowed.
 760          * We fail an exclusive create of anything which already exists.
 761          */
 762         if (error == EEXIST) {
 763                 if (excl == NONEXCL) {
 764                         if ((ip->i_type == VDIR) && (mode & VWRITE)) {
 765                                 error = EISDIR;
 766                         } else if (mode) {
 767                                 error = ud_iaccess(ip,
 768                                     UD_UPERM2DPERM(mode), cr, 0);
 769                         } else {
 770                                 error = 0;
 771                         }
 772                 }
 773                 if (error) {
 774                         rw_exit(&ip->i_contents);


 783                          * bmap we would do this).
 784                          * Must get the locks in the correct order.
 785                          */
 786                         if (ip->i_size == 0) {
 787                                 ip->i_flag |= ICHG | IUPD;
 788                         } else {
 789                                 rw_exit(&ip->i_contents);
 790                                 rw_enter(&ip->i_rwlock, RW_WRITER);
 791                                 rw_enter(&ip->i_contents, RW_WRITER);
 792                                 (void) ud_itrunc(ip, 0, 0, cr);
 793                                 rw_exit(&ip->i_rwlock);
 794                         }
 795                         vnevent_create(ITOV(ip), ct);
 796                 }
 797         }
 798 
 799         if (error == 0) {
 800                 *vpp = ITOV(ip);
 801                 ITIMES(ip);
 802         }
 803 #ifdef  __lock_lint
 804         rw_exit(&ip->i_contents);
 805 #else
 806         if (ip != NULL) {
 807                 rw_exit(&ip->i_contents);
 808         }
 809 #endif
 810         if (error) {
 811                 goto out;
 812         }
 813 
 814         /*
 815          * If vnode is a device return special vnode instead.
 816          */
 817         if (!error && IS_DEVVP(*vpp)) {
 818                 struct vnode *newvp;
 819 
 820                 newvp = specvp(*vpp, (*vpp)->v_rdev, (*vpp)->v_type, cr);
 821                 VN_RELE(*vpp);
 822                 if (newvp == NULL) {
 823                         error = ENOSYS;
 824                         goto out;
 825                 }
 826                 *vpp = newvp;
 827         }
 828 out:
 829         return (error);


1553         udfidp->udfid_prn = ip->i_icb_prn;
1554         udfidp->udfid_icb_lbn = ip->i_icb_block;
1555         rw_exit(&ip->i_contents);
1556 
1557         return (0);
1558 }
1559 
1560 /* ARGSUSED2 */
1561 static int
1562 udf_rwlock(struct vnode *vp, int32_t write_lock, caller_context_t *ctp)
1563 {
1564         struct ud_inode *ip = VTOI(vp);
1565 
1566         ud_printf("udf_rwlock\n");
1567 
1568         if (write_lock) {
1569                 rw_enter(&ip->i_rwlock, RW_WRITER);
1570         } else {
1571                 rw_enter(&ip->i_rwlock, RW_READER);
1572         }
1573 #ifdef  __lock_lint
1574         rw_exit(&ip->i_rwlock);
1575 #endif
1576         return (write_lock);
1577 }
1578 
1579 /* ARGSUSED */
1580 static void
1581 udf_rwunlock(struct vnode *vp, int32_t write_lock, caller_context_t *ctp)
1582 {
1583         struct ud_inode *ip = VTOI(vp);
1584 
1585         ud_printf("udf_rwunlock\n");
1586 
1587 #ifdef  __lock_lint
1588         rw_enter(&ip->i_rwlock, RW_WRITER);
1589 #endif
1590 
1591         rw_exit(&ip->i_rwlock);
1592 
1593 }
1594 
1595 /* ARGSUSED */
1596 static int32_t
1597 udf_seek(struct vnode *vp, offset_t ooff, offset_t *noffp, caller_context_t *ct)
1598 {
1599         return ((*noffp < 0 || *noffp > MAXOFFSET_T) ? EINVAL : 0);
1600 }
1601 
1602 static int32_t
1603 udf_frlock(
1604         struct vnode *vp,
1605         int32_t cmd,
1606         struct flock64 *bfp,
1607         int32_t flag,
1608         offset_t offset,
1609         struct flk_callback *flk_cbp,
1610         cred_t *cr,


1677         struct udf_vfs *udf_vfsp = ip->i_udf;
1678         page_t **pl;
1679         u_offset_t pgoff, eoff, uoff;
1680         krw_t rwtype;
1681         caddr_t pgaddr;
1682 
1683         ud_printf("udf_getpage\n");
1684 
1685         uoff = (u_offset_t)off; /* type conversion */
1686         if (protp) {
1687                 *protp = PROT_ALL;
1688         }
1689         if (vp->v_flag & VNOMAP) {
1690                 return (ENOSYS);
1691         }
1692         seqmode = ip->i_nextr == uoff && rw != S_CREATE;
1693 
1694         rwtype = RW_READER;
1695         dolock = (rw_owner(&ip->i_contents) != curthread);
1696 retrylock:
1697 #ifdef  __lock_lint
1698         rw_enter(&ip->i_contents, rwtype);
1699 #else
1700         if (dolock) {
1701                 rw_enter(&ip->i_contents, rwtype);
1702         }
1703 #endif
1704 
1705         /*
1706          * We may be getting called as a side effect of a bmap using
1707          * fbread() when the blocks might be being allocated and the
1708          * size has not yet been up'ed.  In this case we want to be
1709          * able to return zero pages if we get back UDF_HOLE from
1710          * calling bmap for a non write case here.  We also might have
1711          * to read some frags from the disk into a page if we are
1712          * extending the number of frags for a given lbn in bmap().
1713          */
1714         beyond_eof = uoff + len > ip->i_size + PAGEOFFSET;
1715         if (beyond_eof && seg != segkmap) {
1716 #ifdef  __lock_lint
1717                 rw_exit(&ip->i_contents);
1718 #else
1719                 if (dolock) {
1720                         rw_exit(&ip->i_contents);
1721                 }
1722 #endif
1723                 return (EFAULT);
1724         }
1725 
1726         /*
1727          * Must hold i_contents lock throughout the call to pvn_getpages
1728          * since locked pages are returned from each call to ud_getapage.
1729          * Must *not* return locked pages and then try for contents lock
1730          * due to lock ordering requirements (inode > page)
1731          */
1732 
1733         has_holes = ud_bmap_has_holes(ip);
1734 
1735         if ((rw == S_WRITE || rw == S_CREATE) && (has_holes || beyond_eof)) {
1736                 int32_t blk_size, count;
1737                 u_offset_t offset;
1738 
1739                 /*
1740                  * We must acquire the RW_WRITER lock in order to
1741                  * call bmap_write().
1742                  */


1766                          * causes a compiler "loop"
1767                          */
1768 
1769                         blk_size = udf_vfsp->udf_lbsize;
1770                         if ((offset + blk_size) > ip->i_size) {
1771                                 count = ip->i_size - offset;
1772                         } else {
1773                                 count = blk_size;
1774                         }
1775                         error = ud_bmap_write(ip, offset, count, 0, cr);
1776                         if (error) {
1777                                 goto update_inode;
1778                         }
1779                         offset += count; /* XXX - make this contig */
1780                 }
1781         }
1782 
1783         /*
1784          * Can be a reader from now on.
1785          */
1786 #ifdef  __lock_lint
1787         if (rwtype == RW_WRITER) {
1788                 rw_downgrade(&ip->i_contents);
1789         }
1790 #else
1791         if (dolock && rwtype == RW_WRITER) {
1792                 rw_downgrade(&ip->i_contents);
1793         }
1794 #endif
1795 
1796         /*
1797          * We remove PROT_WRITE in cases when the file has UDF holes
1798          * because we don't  want to call bmap_read() to check each
1799          * page if it is backed with a disk block.
1800          */
1801         if (protp && has_holes && rw != S_WRITE && rw != S_CREATE) {
1802                 *protp &= ~PROT_WRITE;
1803         }
1804 
1805         error = 0;
1806 
1807         /*
1808          * The loop looks up pages in the range <off, off + len).
1809          * For each page, we first check if we should initiate an asynchronous
1810          * read ahead before we call page_lookup (we may sleep in page_lookup
1811          * for a previously initiated disk read).
1812          */
1813         eoff = (uoff + len);
1814         for (pgoff = uoff, pgaddr = addr, pl = plarr;


1894                         plsz -= pgsize;
1895                 }
1896         }
1897 
1898         if (plarr)
1899                 *pl = NULL;                     /* Terminate page list */
1900         ip->i_nextr = pgoff;
1901 
1902 error_out:
1903         if (error && plarr) {
1904                 /*
1905                  * Release any pages we have locked.
1906                  */
1907                 while (pl > &plarr[0])
1908                         page_unlock(*--pl);
1909 
1910                 plarr[0] = NULL;
1911         }
1912 
1913 update_inode:
1914 #ifdef  __lock_lint
1915         rw_exit(&ip->i_contents);
1916 #else
1917         if (dolock) {
1918                 rw_exit(&ip->i_contents);
1919         }
1920 #endif
1921 
1922         /*
1923          * If the inode is not already marked for IACC (in rwip() for read)
1924          * and the inode is not marked for no access time update (in rwip()
1925          * for write) then update the inode access time and mod time now.
1926          */
1927         mutex_enter(&ip->i_tlock);
1928         if ((ip->i_flag & (IACC | INOACC)) == 0) {
1929                 if ((rw != S_OTHER) && (ip->i_type != VDIR)) {
1930                         ip->i_flag |= IACC;
1931                 }
1932                 if (rw == S_WRITE) {
1933                         ip->i_flag |= IUPD;
1934                 }
1935                 ITIMES_NOLOCK(ip);
1936         }
1937         mutex_exit(&ip->i_tlock);
1938 
1939         return (error);
1940 }
1941 
1942 int32_t ud_delay = 1;
1943 
1944 /* ARGSUSED */
1945 static int32_t
1946 udf_putpage(
1947         struct vnode *vp,
1948         offset_t off,
1949         size_t len,
1950         int32_t flags,
1951         struct cred *cr,
1952         caller_context_t *ct)
1953 {
1954         struct ud_inode *ip;
1955         int32_t error = 0;
1956 
1957         ud_printf("udf_putpage\n");
1958 
1959         ip = VTOI(vp);
1960 #ifdef  __lock_lint
1961         rw_enter(&ip->i_contents, RW_WRITER);
1962 #endif
1963 
1964         if (vp->v_count == 0) {
1965                 cmn_err(CE_WARN, "ud_putpage : bad v_count");
1966                 error = EINVAL;
1967                 goto out;
1968         }
1969 
1970         if (vp->v_flag & VNOMAP) {
1971                 error = ENOSYS;
1972                 goto out;
1973         }
1974 
1975         if (flags & B_ASYNC) {
1976                 if (ud_delay && len &&
1977                     (flags & ~(B_ASYNC|B_DONTNEED|B_FREE)) == 0) {
1978                         mutex_enter(&ip->i_tlock);
1979 
1980                         /*
1981                          * If nobody stalled, start a new cluster.
1982                          */


2006                                 goto out;
2007                         }
2008 
2009                         /*
2010                          * There is something there, it's not full, and
2011                          * it is contig.
2012                          */
2013                         ip->i_delaylen += len;
2014                         mutex_exit(&ip->i_tlock);
2015                         goto out;
2016                 }
2017 
2018                 /*
2019                  * Must have weird flags or we are not clustering.
2020                  */
2021         }
2022 
2023         error = ud_putpages(vp, off, len, flags, cr);
2024 
2025 out:
2026 #ifdef  __lock_lint
2027         rw_exit(&ip->i_contents);
2028 #endif
2029         return (error);
2030 }
2031 
2032 /* ARGSUSED */
2033 static int32_t
2034 udf_map(
2035         struct vnode *vp,
2036         offset_t off,
2037         struct as *as,
2038         caddr_t *addrp,
2039         size_t len,
2040         uint8_t prot,
2041         uint8_t maxprot,
2042         uint32_t flags,
2043         struct cred *cr,
2044         caller_context_t *ct)
2045 {
2046         struct segvn_crargs vn_a;
2047         int32_t error = 0;
2048 


2170         if (cmd == _PC_FILESIZEBITS) {
2171                 /*
2172                  * udf supports 64 bits as file size
2173                  * but there are several other restrictions
2174                  * it only supports 32-bit block numbers and
2175                  * daddr32_t is only and int32_t so taking these
2176                  * into account we can stay just as where ufs is
2177                  */
2178                 *valp = 41;
2179         } else if (cmd == _PC_TIMESTAMP_RESOLUTION) {
2180                 /* nanosecond timestamp resolution */
2181                 *valp = 1L;
2182         } else {
2183                 error = fs_pathconf(vp, cmd, valp, cr, ct);
2184         }
2185 
2186         return (error);
2187 }
2188 
2189 uint32_t ud_pageio_reads = 0, ud_pageio_writes = 0;
2190 #ifndef __lint
2191 _NOTE(SCHEME_PROTECTS_DATA("safe sharing", ud_pageio_reads))
2192 _NOTE(SCHEME_PROTECTS_DATA("safe sharing", ud_pageio_writes))
2193 #endif
2194 /*
2195  * Assumption is that there will not be a pageio request
2196  * to a enbedded file
2197  */
2198 /* ARGSUSED */
2199 static int32_t
2200 udf_pageio(
2201         struct vnode *vp,
2202         struct page *pp,
2203         u_offset_t io_off,
2204         size_t io_len,
2205         int32_t flags,
2206         struct cred *cr,
2207         caller_context_t *ct)
2208 {
2209         daddr_t bn;
2210         struct buf *bp;
2211         struct ud_inode *ip = VTOI(vp);
2212         int32_t dolock, error = 0, contig, multi_io;
2213         size_t done_len = 0, cur_len = 0;
2214         page_t *npp = NULL, *opp = NULL, *cpp = pp;
2215 
2216         if (pp == NULL) {
2217                 return (EINVAL);
2218         }
2219 
2220         dolock = (rw_owner(&ip->i_contents) != curthread);
2221 
2222         /*
2223          * We need a better check.  Ideally, we would use another
2224          * vnodeops so that hlocked and forcibly unmounted file
2225          * systems would return EIO where appropriate and w/o the
2226          * need for these checks.
2227          */
2228         if (ip->i_udf == NULL) {
2229                 return (EIO);
2230         }
2231 
2232 #ifdef  __lock_lint
2233         rw_enter(&ip->i_contents, RW_READER);
2234 #else
2235         if (dolock) {
2236                 rw_enter(&ip->i_contents, RW_READER);
2237         }
2238 #endif
2239 
2240         /*
2241          * Break the io request into chunks, one for each contiguous
2242          * stretch of disk blocks in the target file.
2243          */
2244         while (done_len < io_len) {
2245                 ASSERT(cpp);
2246                 bp = NULL;
2247                 contig = 0;
2248                 if (error = ud_bmap_read(ip, (u_offset_t)(io_off + done_len),
2249                     &bn, &contig)) {
2250                         break;
2251                 }
2252 
2253                 if (bn == UDF_HOLE) {   /* No holey swapfiles */
2254                         cmn_err(CE_WARN, "SWAP file has HOLES");
2255                         error = EINVAL;
2256                         break;
2257                 }
2258 


2322                 done_len += cur_len;
2323         }
2324 
2325         ASSERT(error || (cpp == NULL && npp == NULL && done_len == io_len));
2326         if (error) {
2327                 if (flags & B_ASYNC) {
2328                         /* Cleanup unprocessed parts of list */
2329                         page_list_concat(&cpp, &npp);
2330                         if (flags & B_READ) {
2331                                 pvn_read_done(cpp, B_ERROR);
2332                         } else {
2333                                 pvn_write_done(cpp, B_ERROR);
2334                         }
2335                 } else {
2336                         /* Re-assemble list and let caller clean up */
2337                         page_list_concat(&opp, &cpp);
2338                         page_list_concat(&opp, &npp);
2339                 }
2340         }
2341 
2342 #ifdef  __lock_lint
2343         rw_exit(&ip->i_contents);
2344 #else
2345         if (dolock) {
2346                 rw_exit(&ip->i_contents);
2347         }
2348 #endif
2349         return (error);
2350 }
2351 
2352 
2353 
2354 
2355 /* -------------------- local functions --------------------------- */
2356 
2357 
2358 
2359 int32_t
2360 ud_rdwri(enum uio_rw rw, int32_t ioflag,
2361         struct ud_inode *ip, caddr_t base, int32_t len,
2362         offset_t offset, enum uio_seg seg, int32_t *aresid, struct cred *cr)
2363 {
2364         int32_t error;
2365         struct uio auio;
2366         struct iovec aiov;
2367 
2368         ud_printf("ud_rdwri\n");


2665 
2666         ud_printf("ud_putpages\n");
2667 
2668         if (vp->v_count == 0) {
2669                 cmn_err(CE_WARN, "ud_putpages: bad v_count");
2670                 return (EINVAL);
2671         }
2672 
2673         ip = VTOI(vp);
2674 
2675         /*
2676          * Acquire the readers/write inode lock before locking
2677          * any pages in this inode.
2678          * The inode lock is held during i/o.
2679          */
2680         if (len == 0) {
2681                 mutex_enter(&ip->i_tlock);
2682                 ip->i_delayoff = ip->i_delaylen = 0;
2683                 mutex_exit(&ip->i_tlock);
2684         }
2685 #ifdef  __lock_lint
2686         rw_enter(&ip->i_contents, RW_READER);
2687 #else
2688         dolock = (rw_owner(&ip->i_contents) != curthread);
2689         if (dolock) {
2690                 rw_enter(&ip->i_contents, RW_READER);
2691         }
2692 #endif
2693 
2694         if (!vn_has_cached_data(vp)) {
2695 #ifdef  __lock_lint
2696                 rw_exit(&ip->i_contents);
2697 #else
2698                 if (dolock) {
2699                         rw_exit(&ip->i_contents);
2700                 }
2701 #endif
2702                 return (0);
2703         }
2704 
2705         if (len == 0) {
2706                 /*
2707                  * Search the entire vp list for pages >= off.
2708                  */
2709                 err = pvn_vplist_dirty(vp, (u_offset_t)off, ud_putapage,
2710                     flags, cr);
2711         } else {
2712                 /*
2713                  * Loop over all offsets in the range looking for
2714                  * pages to deal with.
2715                  */
2716                 if ((eoff = blkroundup(ip->i_udf, ip->i_size)) != 0) {
2717                         eoff = MIN(off + len, eoff);
2718                 } else {
2719                         eoff = off + len;
2720                 }
2721 


2746                                 }
2747                                 /*
2748                                  * "io_off" and "io_len" are returned as
2749                                  * the range of pages we actually wrote.
2750                                  * This allows us to skip ahead more quickly
2751                                  * since several pages may've been dealt
2752                                  * with by this iteration of the loop.
2753                                  */
2754                         }
2755                 }
2756         }
2757         if (err == 0 && off == 0 && (len == 0 || len >= ip->i_size)) {
2758                 /*
2759                  * We have just sync'ed back all the pages on
2760                  * the inode, turn off the IMODTIME flag.
2761                  */
2762                 mutex_enter(&ip->i_tlock);
2763                 ip->i_flag &= ~IMODTIME;
2764                 mutex_exit(&ip->i_tlock);
2765         }
2766 #ifdef  __lock_lint
2767         rw_exit(&ip->i_contents);
2768 #else
2769         if (dolock) {
2770                 rw_exit(&ip->i_contents);
2771         }
2772 #endif
2773         return (err);
2774 }
2775 
2776 /* ARGSUSED */
2777 int32_t
2778 ud_putapage(struct vnode *vp,
2779         page_t *pp, u_offset_t *offp,
2780         size_t *lenp, int32_t flags, struct cred *cr)
2781 {
2782         daddr_t bn;
2783         size_t io_len;
2784         struct ud_inode *ip;
2785         int32_t error = 0, contig, multi_io = 0;
2786         struct udf_vfs *udf_vfsp;
2787         u_offset_t off, io_off;
2788         caddr_t kaddr, caddr;
2789         struct buf *bp = NULL;
2790         int32_t lbmask;
2791         uint64_t isize;
2792         uint16_t crc_len;


3038                 offset_t diff;
3039                 u_offset_t uoff = uio->uio_loffset;
3040                 off = uoff & (offset_t)MAXBMASK;
3041                 mapon = (int)(uoff & (offset_t)MAXBOFFSET);
3042                 on = (int)blkoff(udf_vfsp, uoff);
3043                 n = (int)MIN(udf_vfsp->udf_lbsize - on, uio->uio_resid);
3044 
3045                 diff = ip->i_size - uoff;
3046 
3047                 if (diff <= (offset_t)0) {
3048                         error = 0;
3049                         goto out;
3050                 }
3051                 if (diff < (offset_t)n) {
3052                         n = (int)diff;
3053                 }
3054                 dofree = ud_freebehind &&
3055                     ip->i_nextr == (off & PAGEMASK) &&
3056                     off > ud_smallfile;
3057 
3058 #ifndef __lock_lint
3059                 if (rwtype == RW_READER) {
3060                         rw_exit(&ip->i_contents);
3061                 }
3062 #endif
3063 
3064                 base = segmap_getmapflt(segkmap, vp, (off + mapon),
3065                     (uint32_t)n, 1, S_READ);
3066                 error = uiomove(base + mapon, (long)n, UIO_READ, uio);
3067 
3068                 flags = 0;
3069                 if (!error) {
3070                         /*
3071                          * If read a whole block, or read to eof,
3072                          * won't need this buffer again soon.
3073                          */
3074                         if (n + on == MAXBSIZE && ud_freebehind && dofree &&
3075                             freemem < lotsfree + pages_before_pager) {
3076                                 flags = SM_FREE | SM_DONTNEED |SM_ASYNC;
3077                         }
3078                         /*
3079                          * In POSIX SYNC (FSYNC and FDSYNC) read mode,
3080                          * we want to make sure that the page which has
3081                          * been read, is written on disk if it is dirty.
3082                          * And corresponding indirect blocks should also
3083                          * be flushed out.
3084                          */
3085                         if ((ioflag & FRSYNC) && (ioflag & (FSYNC|FDSYNC))) {
3086                                 flags &= ~SM_ASYNC;
3087                                 flags |= SM_WRITE;
3088                         }
3089                         error = segmap_release(segkmap, base, flags);
3090                 } else    {
3091                         (void) segmap_release(segkmap, base, flags);
3092                 }
3093 
3094 #ifndef __lock_lint
3095                 if (rwtype == RW_READER) {
3096                         rw_enter(&ip->i_contents, rwtype);
3097                 }
3098 #endif
3099         } while (error == 0 && uio->uio_resid > 0 && n != 0);
3100 out:
3101         /*
3102          * Inode is updated according to this table if FRSYNC is set.
3103          *
3104          *      FSYNC   FDSYNC(posix.4)
3105          *      --------------------------
3106          *      always  IATTCHG|IBDWRITE
3107          */
3108         if (ioflag & FRSYNC) {
3109                 if ((ioflag & FSYNC) ||
3110                     ((ioflag & FDSYNC) &&
3111                     (ip->i_flag & (IATTCHG|IBDWRITE)))) {
3112                 rw_exit(&ip->i_contents);
3113                 rw_enter(&ip->i_contents, RW_WRITER);
3114                 ud_iupdat(ip, 1);
3115                 }
3116         }
3117         /*
3118          * If we've already done a partial read, terminate




 282                 }
 283         }
 284 
 285         return (0);
 286 }
 287 
 288 /* ARGSUSED */
 289 static int32_t
 290 udf_read(
 291         struct vnode *vp,
 292         struct uio *uiop,
 293         int32_t ioflag,
 294         struct cred *cr,
 295         caller_context_t *ct)
 296 {
 297         struct ud_inode *ip = VTOI(vp);
 298         int32_t error;
 299 
 300         ud_printf("udf_read\n");
 301 




 302         ASSERT(RW_READ_HELD(&ip->i_rwlock));
 303 
 304         if (MANDLOCK(vp, ip->i_char)) {
 305                 /*
 306                  * udf_getattr ends up being called by chklock
 307                  */
 308                 error = chklock(vp, FREAD, uiop->uio_loffset,
 309                     uiop->uio_resid, uiop->uio_fmode, ct);
 310                 if (error) {
 311                         goto end;
 312                 }
 313         }
 314 
 315         rw_enter(&ip->i_contents, RW_READER);
 316         error = ud_rdip(ip, uiop, ioflag, cr);
 317         rw_exit(&ip->i_contents);
 318 
 319 end:




 320         return (error);
 321 }
 322 
 323 
 324 int32_t ud_WRITES = 1;
 325 int32_t ud_HW = 96 * 1024;
 326 int32_t ud_LW = 64 * 1024;
 327 int32_t ud_throttles = 0;
 328 
 329 /* ARGSUSED */
 330 static int32_t
 331 udf_write(
 332         struct vnode *vp,
 333         struct uio *uiop,
 334         int32_t ioflag,
 335         struct cred *cr,
 336         caller_context_t *ct)
 337 {
 338         struct ud_inode *ip = VTOI(vp);
 339         int32_t error = 0;
 340 
 341         ud_printf("udf_write\n");
 342 




 343         ASSERT(RW_WRITE_HELD(&ip->i_rwlock));
 344 
 345         if (MANDLOCK(vp, ip->i_char)) {
 346                 /*
 347                  * ud_getattr ends up being called by chklock
 348                  */
 349                 error = chklock(vp, FWRITE, uiop->uio_loffset,
 350                     uiop->uio_resid, uiop->uio_fmode, ct);
 351                 if (error) {
 352                         goto end;
 353                 }
 354         }
 355         /*
 356          * Throttle writes.
 357          */
 358         mutex_enter(&ip->i_tlock);
 359         if (ud_WRITES && (ip->i_writes > ud_HW)) {
 360                 while (ip->i_writes > ud_HW) {
 361                         ud_throttles++;
 362                         cv_wait(&ip->i_wrcv, &ip->i_tlock);
 363                 }
 364         }
 365         mutex_exit(&ip->i_tlock);
 366 
 367         /*
 368          * Write to the file
 369          */
 370         rw_enter(&ip->i_contents, RW_WRITER);
 371         if ((ioflag & FAPPEND) != 0 && (ip->i_type == VREG)) {
 372                 /*
 373                  * In append mode start at end of file.
 374                  */
 375                 uiop->uio_loffset = ip->i_size;
 376         }
 377         error = ud_wrip(ip, uiop, ioflag, cr);
 378         rw_exit(&ip->i_contents);
 379 
 380 end:




 381         return (error);
 382 }
 383 
 384 /* ARGSUSED */
 385 static int32_t
 386 udf_ioctl(
 387         struct vnode *vp,
 388         int32_t cmd,
 389         intptr_t arg,
 390         int32_t flag,
 391         struct cred *cr,
 392         int32_t *rvalp,
 393         caller_context_t *ct)
 394 {
 395         return (ENOTTY);
 396 }
 397 
 398 /* ARGSUSED */
 399 static int32_t
 400 udf_getattr(


 712         if ((vap->va_mode & VSVTX) && secpolicy_vnode_stky_modify(cr) != 0)
 713                 vap->va_mode &= ~VSVTX;
 714 
 715         if (*name == '\0') {
 716                 /*
 717                  * Null component name refers to the directory itself.
 718                  */
 719                 VN_HOLD(dvp);
 720                 ITIMES(ip);
 721                 error = EEXIST;
 722         } else {
 723                 xip = NULL;
 724                 rw_enter(&ip->i_rwlock, RW_WRITER);
 725                 error = ud_direnter(ip, name, DE_CREATE,
 726                     (struct ud_inode *)0, (struct ud_inode *)0,
 727                     vap, &xip, cr, ct);
 728                 rw_exit(&ip->i_rwlock);
 729                 ITIMES(ip);
 730                 ip = xip;
 731         }



 732         if (ip != NULL) {
 733                 rw_enter(&ip->i_contents, RW_WRITER);
 734         }

 735 
 736         /*
 737          * If the file already exists and this is a non-exclusive create,
 738          * check permissions and allow access for non-directories.
 739          * Read-only create of an existing directory is also allowed.
 740          * We fail an exclusive create of anything which already exists.
 741          */
 742         if (error == EEXIST) {
 743                 if (excl == NONEXCL) {
 744                         if ((ip->i_type == VDIR) && (mode & VWRITE)) {
 745                                 error = EISDIR;
 746                         } else if (mode) {
 747                                 error = ud_iaccess(ip,
 748                                     UD_UPERM2DPERM(mode), cr, 0);
 749                         } else {
 750                                 error = 0;
 751                         }
 752                 }
 753                 if (error) {
 754                         rw_exit(&ip->i_contents);


 763                          * bmap we would do this).
 764                          * Must get the locks in the correct order.
 765                          */
 766                         if (ip->i_size == 0) {
 767                                 ip->i_flag |= ICHG | IUPD;
 768                         } else {
 769                                 rw_exit(&ip->i_contents);
 770                                 rw_enter(&ip->i_rwlock, RW_WRITER);
 771                                 rw_enter(&ip->i_contents, RW_WRITER);
 772                                 (void) ud_itrunc(ip, 0, 0, cr);
 773                                 rw_exit(&ip->i_rwlock);
 774                         }
 775                         vnevent_create(ITOV(ip), ct);
 776                 }
 777         }
 778 
 779         if (error == 0) {
 780                 *vpp = ITOV(ip);
 781                 ITIMES(ip);
 782         }



 783         if (ip != NULL) {
 784                 rw_exit(&ip->i_contents);
 785         }

 786         if (error) {
 787                 goto out;
 788         }
 789 
 790         /*
 791          * If vnode is a device return special vnode instead.
 792          */
 793         if (!error && IS_DEVVP(*vpp)) {
 794                 struct vnode *newvp;
 795 
 796                 newvp = specvp(*vpp, (*vpp)->v_rdev, (*vpp)->v_type, cr);
 797                 VN_RELE(*vpp);
 798                 if (newvp == NULL) {
 799                         error = ENOSYS;
 800                         goto out;
 801                 }
 802                 *vpp = newvp;
 803         }
 804 out:
 805         return (error);


1529         udfidp->udfid_prn = ip->i_icb_prn;
1530         udfidp->udfid_icb_lbn = ip->i_icb_block;
1531         rw_exit(&ip->i_contents);
1532 
1533         return (0);
1534 }
1535 
1536 /* ARGSUSED2 */
1537 static int
1538 udf_rwlock(struct vnode *vp, int32_t write_lock, caller_context_t *ctp)
1539 {
1540         struct ud_inode *ip = VTOI(vp);
1541 
1542         ud_printf("udf_rwlock\n");
1543 
1544         if (write_lock) {
1545                 rw_enter(&ip->i_rwlock, RW_WRITER);
1546         } else {
1547                 rw_enter(&ip->i_rwlock, RW_READER);
1548         }



1549         return (write_lock);
1550 }
1551 
1552 /* ARGSUSED */
1553 static void
1554 udf_rwunlock(struct vnode *vp, int32_t write_lock, caller_context_t *ctp)
1555 {
1556         struct ud_inode *ip = VTOI(vp);
1557 
1558         ud_printf("udf_rwunlock\n");
1559 




1560         rw_exit(&ip->i_rwlock);
1561 
1562 }
1563 
1564 /* ARGSUSED */
1565 static int32_t
1566 udf_seek(struct vnode *vp, offset_t ooff, offset_t *noffp, caller_context_t *ct)
1567 {
1568         return ((*noffp < 0 || *noffp > MAXOFFSET_T) ? EINVAL : 0);
1569 }
1570 
1571 static int32_t
1572 udf_frlock(
1573         struct vnode *vp,
1574         int32_t cmd,
1575         struct flock64 *bfp,
1576         int32_t flag,
1577         offset_t offset,
1578         struct flk_callback *flk_cbp,
1579         cred_t *cr,


1646         struct udf_vfs *udf_vfsp = ip->i_udf;
1647         page_t **pl;
1648         u_offset_t pgoff, eoff, uoff;
1649         krw_t rwtype;
1650         caddr_t pgaddr;
1651 
1652         ud_printf("udf_getpage\n");
1653 
1654         uoff = (u_offset_t)off; /* type conversion */
1655         if (protp) {
1656                 *protp = PROT_ALL;
1657         }
1658         if (vp->v_flag & VNOMAP) {
1659                 return (ENOSYS);
1660         }
1661         seqmode = ip->i_nextr == uoff && rw != S_CREATE;
1662 
1663         rwtype = RW_READER;
1664         dolock = (rw_owner(&ip->i_contents) != curthread);
1665 retrylock:



1666         if (dolock) {
1667                 rw_enter(&ip->i_contents, rwtype);
1668         }

1669 
1670         /*
1671          * We may be getting called as a side effect of a bmap using
1672          * fbread() when the blocks might be being allocated and the
1673          * size has not yet been up'ed.  In this case we want to be
1674          * able to return zero pages if we get back UDF_HOLE from
1675          * calling bmap for a non write case here.  We also might have
1676          * to read some frags from the disk into a page if we are
1677          * extending the number of frags for a given lbn in bmap().
1678          */
1679         beyond_eof = uoff + len > ip->i_size + PAGEOFFSET;
1680         if (beyond_eof && seg != segkmap) {



1681                 if (dolock) {
1682                         rw_exit(&ip->i_contents);
1683                 }

1684                 return (EFAULT);
1685         }
1686 
1687         /*
1688          * Must hold i_contents lock throughout the call to pvn_getpages
1689          * since locked pages are returned from each call to ud_getapage.
1690          * Must *not* return locked pages and then try for contents lock
1691          * due to lock ordering requirements (inode > page)
1692          */
1693 
1694         has_holes = ud_bmap_has_holes(ip);
1695 
1696         if ((rw == S_WRITE || rw == S_CREATE) && (has_holes || beyond_eof)) {
1697                 int32_t blk_size, count;
1698                 u_offset_t offset;
1699 
1700                 /*
1701                  * We must acquire the RW_WRITER lock in order to
1702                  * call bmap_write().
1703                  */


1727                          * causes a compiler "loop"
1728                          */
1729 
1730                         blk_size = udf_vfsp->udf_lbsize;
1731                         if ((offset + blk_size) > ip->i_size) {
1732                                 count = ip->i_size - offset;
1733                         } else {
1734                                 count = blk_size;
1735                         }
1736                         error = ud_bmap_write(ip, offset, count, 0, cr);
1737                         if (error) {
1738                                 goto update_inode;
1739                         }
1740                         offset += count; /* XXX - make this contig */
1741                 }
1742         }
1743 
1744         /*
1745          * Can be a reader from now on.
1746          */





1747         if (dolock && rwtype == RW_WRITER) {
1748                 rw_downgrade(&ip->i_contents);
1749         }

1750 
1751         /*
1752          * We remove PROT_WRITE in cases when the file has UDF holes
1753          * because we don't  want to call bmap_read() to check each
1754          * page if it is backed with a disk block.
1755          */
1756         if (protp && has_holes && rw != S_WRITE && rw != S_CREATE) {
1757                 *protp &= ~PROT_WRITE;
1758         }
1759 
1760         error = 0;
1761 
1762         /*
1763          * The loop looks up pages in the range <off, off + len).
1764          * For each page, we first check if we should initiate an asynchronous
1765          * read ahead before we call page_lookup (we may sleep in page_lookup
1766          * for a previously initiated disk read).
1767          */
1768         eoff = (uoff + len);
1769         for (pgoff = uoff, pgaddr = addr, pl = plarr;


1849                         plsz -= pgsize;
1850                 }
1851         }
1852 
1853         if (plarr)
1854                 *pl = NULL;                     /* Terminate page list */
1855         ip->i_nextr = pgoff;
1856 
1857 error_out:
1858         if (error && plarr) {
1859                 /*
1860                  * Release any pages we have locked.
1861                  */
1862                 while (pl > &plarr[0])
1863                         page_unlock(*--pl);
1864 
1865                 plarr[0] = NULL;
1866         }
1867 
1868 update_inode:



1869         if (dolock) {
1870                 rw_exit(&ip->i_contents);
1871         }

1872 
1873         /*
1874          * If the inode is not already marked for IACC (in rwip() for read)
1875          * and the inode is not marked for no access time update (in rwip()
1876          * for write) then update the inode access time and mod time now.
1877          */
1878         mutex_enter(&ip->i_tlock);
1879         if ((ip->i_flag & (IACC | INOACC)) == 0) {
1880                 if ((rw != S_OTHER) && (ip->i_type != VDIR)) {
1881                         ip->i_flag |= IACC;
1882                 }
1883                 if (rw == S_WRITE) {
1884                         ip->i_flag |= IUPD;
1885                 }
1886                 ITIMES_NOLOCK(ip);
1887         }
1888         mutex_exit(&ip->i_tlock);
1889 
1890         return (error);
1891 }
1892 
1893 int32_t ud_delay = 1;
1894 
1895 /* ARGSUSED */
1896 static int32_t
1897 udf_putpage(
1898         struct vnode *vp,
1899         offset_t off,
1900         size_t len,
1901         int32_t flags,
1902         struct cred *cr,
1903         caller_context_t *ct)
1904 {
1905         struct ud_inode *ip;
1906         int32_t error = 0;
1907 
1908         ud_printf("udf_putpage\n");
1909 
1910         ip = VTOI(vp);



1911 
1912         if (vp->v_count == 0) {
1913                 cmn_err(CE_WARN, "ud_putpage : bad v_count");
1914                 error = EINVAL;
1915                 goto out;
1916         }
1917 
1918         if (vp->v_flag & VNOMAP) {
1919                 error = ENOSYS;
1920                 goto out;
1921         }
1922 
1923         if (flags & B_ASYNC) {
1924                 if (ud_delay && len &&
1925                     (flags & ~(B_ASYNC|B_DONTNEED|B_FREE)) == 0) {
1926                         mutex_enter(&ip->i_tlock);
1927 
1928                         /*
1929                          * If nobody stalled, start a new cluster.
1930                          */


1954                                 goto out;
1955                         }
1956 
1957                         /*
1958                          * There is something there, it's not full, and
1959                          * it is contig.
1960                          */
1961                         ip->i_delaylen += len;
1962                         mutex_exit(&ip->i_tlock);
1963                         goto out;
1964                 }
1965 
1966                 /*
1967                  * Must have weird flags or we are not clustering.
1968                  */
1969         }
1970 
1971         error = ud_putpages(vp, off, len, flags, cr);
1972 
1973 out:



1974         return (error);
1975 }
1976 
1977 /* ARGSUSED */
1978 static int32_t
1979 udf_map(
1980         struct vnode *vp,
1981         offset_t off,
1982         struct as *as,
1983         caddr_t *addrp,
1984         size_t len,
1985         uint8_t prot,
1986         uint8_t maxprot,
1987         uint32_t flags,
1988         struct cred *cr,
1989         caller_context_t *ct)
1990 {
1991         struct segvn_crargs vn_a;
1992         int32_t error = 0;
1993 


2115         if (cmd == _PC_FILESIZEBITS) {
2116                 /*
2117                  * udf supports 64 bits as file size
2118                  * but there are several other restrictions
2119                  * it only supports 32-bit block numbers and
2120                  * daddr32_t is only and int32_t so taking these
2121                  * into account we can stay just as where ufs is
2122                  */
2123                 *valp = 41;
2124         } else if (cmd == _PC_TIMESTAMP_RESOLUTION) {
2125                 /* nanosecond timestamp resolution */
2126                 *valp = 1L;
2127         } else {
2128                 error = fs_pathconf(vp, cmd, valp, cr, ct);
2129         }
2130 
2131         return (error);
2132 }
2133 
2134 uint32_t ud_pageio_reads = 0, ud_pageio_writes = 0;
2135 



2136 /*
2137  * Assumption is that there will not be a pageio request
2138  * to a enbedded file
2139  */
2140 /* ARGSUSED */
2141 static int32_t
2142 udf_pageio(
2143         struct vnode *vp,
2144         struct page *pp,
2145         u_offset_t io_off,
2146         size_t io_len,
2147         int32_t flags,
2148         struct cred *cr,
2149         caller_context_t *ct)
2150 {
2151         daddr_t bn;
2152         struct buf *bp;
2153         struct ud_inode *ip = VTOI(vp);
2154         int32_t dolock, error = 0, contig, multi_io;
2155         size_t done_len = 0, cur_len = 0;
2156         page_t *npp = NULL, *opp = NULL, *cpp = pp;
2157 
2158         if (pp == NULL) {
2159                 return (EINVAL);
2160         }
2161 
2162         dolock = (rw_owner(&ip->i_contents) != curthread);
2163 
2164         /*
2165          * We need a better check.  Ideally, we would use another
2166          * vnodeops so that hlocked and forcibly unmounted file
2167          * systems would return EIO where appropriate and w/o the
2168          * need for these checks.
2169          */
2170         if (ip->i_udf == NULL) {
2171                 return (EIO);
2172         }
2173 



2174         if (dolock) {
2175                 rw_enter(&ip->i_contents, RW_READER);
2176         }

2177 
2178         /*
2179          * Break the io request into chunks, one for each contiguous
2180          * stretch of disk blocks in the target file.
2181          */
2182         while (done_len < io_len) {
2183                 ASSERT(cpp);
2184                 bp = NULL;
2185                 contig = 0;
2186                 if (error = ud_bmap_read(ip, (u_offset_t)(io_off + done_len),
2187                     &bn, &contig)) {
2188                         break;
2189                 }
2190 
2191                 if (bn == UDF_HOLE) {   /* No holey swapfiles */
2192                         cmn_err(CE_WARN, "SWAP file has HOLES");
2193                         error = EINVAL;
2194                         break;
2195                 }
2196 


2260                 done_len += cur_len;
2261         }
2262 
2263         ASSERT(error || (cpp == NULL && npp == NULL && done_len == io_len));
2264         if (error) {
2265                 if (flags & B_ASYNC) {
2266                         /* Cleanup unprocessed parts of list */
2267                         page_list_concat(&cpp, &npp);
2268                         if (flags & B_READ) {
2269                                 pvn_read_done(cpp, B_ERROR);
2270                         } else {
2271                                 pvn_write_done(cpp, B_ERROR);
2272                         }
2273                 } else {
2274                         /* Re-assemble list and let caller clean up */
2275                         page_list_concat(&opp, &cpp);
2276                         page_list_concat(&opp, &npp);
2277                 }
2278         }
2279 



2280         if (dolock) {
2281                 rw_exit(&ip->i_contents);
2282         }
2283 
2284         return (error);
2285 }
2286 
2287 
2288 
2289 
2290 /* -------------------- local functions --------------------------- */
2291 
2292 
2293 
2294 int32_t
2295 ud_rdwri(enum uio_rw rw, int32_t ioflag,
2296         struct ud_inode *ip, caddr_t base, int32_t len,
2297         offset_t offset, enum uio_seg seg, int32_t *aresid, struct cred *cr)
2298 {
2299         int32_t error;
2300         struct uio auio;
2301         struct iovec aiov;
2302 
2303         ud_printf("ud_rdwri\n");


2600 
2601         ud_printf("ud_putpages\n");
2602 
2603         if (vp->v_count == 0) {
2604                 cmn_err(CE_WARN, "ud_putpages: bad v_count");
2605                 return (EINVAL);
2606         }
2607 
2608         ip = VTOI(vp);
2609 
2610         /*
2611          * Acquire the readers/write inode lock before locking
2612          * any pages in this inode.
2613          * The inode lock is held during i/o.
2614          */
2615         if (len == 0) {
2616                 mutex_enter(&ip->i_tlock);
2617                 ip->i_delayoff = ip->i_delaylen = 0;
2618                 mutex_exit(&ip->i_tlock);
2619         }



2620         dolock = (rw_owner(&ip->i_contents) != curthread);
2621         if (dolock) {
2622                 rw_enter(&ip->i_contents, RW_READER);
2623         }

2624 
2625         if (!vn_has_cached_data(vp)) {



2626                 if (dolock) {
2627                         rw_exit(&ip->i_contents);
2628                 }

2629                 return (0);
2630         }
2631 
2632         if (len == 0) {
2633                 /*
2634                  * Search the entire vp list for pages >= off.
2635                  */
2636                 err = pvn_vplist_dirty(vp, (u_offset_t)off, ud_putapage,
2637                     flags, cr);
2638         } else {
2639                 /*
2640                  * Loop over all offsets in the range looking for
2641                  * pages to deal with.
2642                  */
2643                 if ((eoff = blkroundup(ip->i_udf, ip->i_size)) != 0) {
2644                         eoff = MIN(off + len, eoff);
2645                 } else {
2646                         eoff = off + len;
2647                 }
2648 


2673                                 }
2674                                 /*
2675                                  * "io_off" and "io_len" are returned as
2676                                  * the range of pages we actually wrote.
2677                                  * This allows us to skip ahead more quickly
2678                                  * since several pages may've been dealt
2679                                  * with by this iteration of the loop.
2680                                  */
2681                         }
2682                 }
2683         }
2684         if (err == 0 && off == 0 && (len == 0 || len >= ip->i_size)) {
2685                 /*
2686                  * We have just sync'ed back all the pages on
2687                  * the inode, turn off the IMODTIME flag.
2688                  */
2689                 mutex_enter(&ip->i_tlock);
2690                 ip->i_flag &= ~IMODTIME;
2691                 mutex_exit(&ip->i_tlock);
2692         }



2693         if (dolock) {
2694                 rw_exit(&ip->i_contents);
2695         }

2696         return (err);
2697 }
2698 
2699 /* ARGSUSED */
2700 int32_t
2701 ud_putapage(struct vnode *vp,
2702         page_t *pp, u_offset_t *offp,
2703         size_t *lenp, int32_t flags, struct cred *cr)
2704 {
2705         daddr_t bn;
2706         size_t io_len;
2707         struct ud_inode *ip;
2708         int32_t error = 0, contig, multi_io = 0;
2709         struct udf_vfs *udf_vfsp;
2710         u_offset_t off, io_off;
2711         caddr_t kaddr, caddr;
2712         struct buf *bp = NULL;
2713         int32_t lbmask;
2714         uint64_t isize;
2715         uint16_t crc_len;


2961                 offset_t diff;
2962                 u_offset_t uoff = uio->uio_loffset;
2963                 off = uoff & (offset_t)MAXBMASK;
2964                 mapon = (int)(uoff & (offset_t)MAXBOFFSET);
2965                 on = (int)blkoff(udf_vfsp, uoff);
2966                 n = (int)MIN(udf_vfsp->udf_lbsize - on, uio->uio_resid);
2967 
2968                 diff = ip->i_size - uoff;
2969 
2970                 if (diff <= (offset_t)0) {
2971                         error = 0;
2972                         goto out;
2973                 }
2974                 if (diff < (offset_t)n) {
2975                         n = (int)diff;
2976                 }
2977                 dofree = ud_freebehind &&
2978                     ip->i_nextr == (off & PAGEMASK) &&
2979                     off > ud_smallfile;
2980 

2981                 if (rwtype == RW_READER) {
2982                         rw_exit(&ip->i_contents);
2983                 }

2984 
2985                 base = segmap_getmapflt(segkmap, vp, (off + mapon),
2986                     (uint32_t)n, 1, S_READ);
2987                 error = uiomove(base + mapon, (long)n, UIO_READ, uio);
2988 
2989                 flags = 0;
2990                 if (!error) {
2991                         /*
2992                          * If read a whole block, or read to eof,
2993                          * won't need this buffer again soon.
2994                          */
2995                         if (n + on == MAXBSIZE && ud_freebehind && dofree &&
2996                             freemem < lotsfree + pages_before_pager) {
2997                                 flags = SM_FREE | SM_DONTNEED |SM_ASYNC;
2998                         }
2999                         /*
3000                          * In POSIX SYNC (FSYNC and FDSYNC) read mode,
3001                          * we want to make sure that the page which has
3002                          * been read, is written on disk if it is dirty.
3003                          * And corresponding indirect blocks should also
3004                          * be flushed out.
3005                          */
3006                         if ((ioflag & FRSYNC) && (ioflag & (FSYNC|FDSYNC))) {
3007                                 flags &= ~SM_ASYNC;
3008                                 flags |= SM_WRITE;
3009                         }
3010                         error = segmap_release(segkmap, base, flags);
3011                 } else    {
3012                         (void) segmap_release(segkmap, base, flags);
3013                 }
3014 

3015                 if (rwtype == RW_READER) {
3016                         rw_enter(&ip->i_contents, rwtype);
3017                 }

3018         } while (error == 0 && uio->uio_resid > 0 && n != 0);
3019 out:
3020         /*
3021          * Inode is updated according to this table if FRSYNC is set.
3022          *
3023          *      FSYNC   FDSYNC(posix.4)
3024          *      --------------------------
3025          *      always  IATTCHG|IBDWRITE
3026          */
3027         if (ioflag & FRSYNC) {
3028                 if ((ioflag & FSYNC) ||
3029                     ((ioflag & FDSYNC) &&
3030                     (ip->i_flag & (IATTCHG|IBDWRITE)))) {
3031                 rw_exit(&ip->i_contents);
3032                 rw_enter(&ip->i_contents, RW_WRITER);
3033                 ud_iupdat(ip, 1);
3034                 }
3035         }
3036         /*
3037          * If we've already done a partial read, terminate