struct xfs_inode        *ip = XFS_I(inode);
        struct xfs_mount        *mp = ip->i_mount;
        ssize_t                 count = i_blocksize(inode);
-       xfs_fileoff_t           offset_fsb = XFS_B_TO_FSBT(mp, offset), end_fsb;
+       xfs_fileoff_t           offset_fsb, end_fsb;
        struct xfs_bmbt_irec    imap;
        int                     whichfork = XFS_DATA_FORK;
+       struct xfs_iext_cursor  icur;
        int                     error = 0;
        int                     nimaps = 1;
 
               (ip->i_df.if_flags & XFS_IFEXTENTS));
        ASSERT(offset <= mp->m_super->s_maxbytes);
 
+       if (offset > mp->m_super->s_maxbytes - count)
+               count = mp->m_super->s_maxbytes - offset;
+       end_fsb = XFS_B_TO_FSB(mp, (xfs_ufsize_t)offset + count);
+       offset_fsb = XFS_B_TO_FSBT(mp, offset);
+
+       /*
+        * Check if this is offset is covered by a COW extents, and if yes use
+        * it directly instead of looking up anything in the data fork.
+        */
        if (xfs_is_reflink_inode(ip) &&
-           xfs_reflink_find_cow_mapping(ip, offset, &imap)) {
+           xfs_iext_lookup_extent(ip, ip->i_cowfp, offset_fsb, &icur, &imap) &&
+           imap.br_startoff <= offset_fsb) {
                xfs_iunlock(ip, XFS_ILOCK_SHARED);
                /*
                 * Truncate can race with writeback since writeback doesn't
         * offset.  This will convert delayed allocations (including COW ones)
         * into real extents.
         */
-       if (offset > mp->m_super->s_maxbytes - count)
-               count = mp->m_super->s_maxbytes - offset;
-       end_fsb = XFS_B_TO_FSB(mp, (xfs_ufsize_t)offset + count);
-       offset_fsb = XFS_B_TO_FSBT(mp, offset);
        error = xfs_bmapi_read(ip, offset_fsb, end_fsb - offset_fsb,
                                &imap, &nimaps, XFS_BMAPI_ENTIRE);
        xfs_iunlock(ip, XFS_ILOCK_SHARED);
 
        return error;
 }
 
-/*
- * Find the CoW reservation for a given byte offset of a file.
- */
-bool
-xfs_reflink_find_cow_mapping(
-       struct xfs_inode                *ip,
-       xfs_off_t                       offset,
-       struct xfs_bmbt_irec            *imap)
-{
-       struct xfs_ifork                *ifp = XFS_IFORK_PTR(ip, XFS_COW_FORK);
-       xfs_fileoff_t                   offset_fsb;
-       struct xfs_bmbt_irec            got;
-       struct xfs_iext_cursor          icur;
-
-       ASSERT(xfs_isilocked(ip, XFS_ILOCK_EXCL | XFS_ILOCK_SHARED));
-
-       if (!xfs_is_reflink_inode(ip))
-               return false;
-       offset_fsb = XFS_B_TO_FSBT(ip->i_mount, offset);
-       if (!xfs_iext_lookup_extent(ip, ifp, offset_fsb, &icur, &got))
-               return false;
-       if (got.br_startoff > offset_fsb)
-               return false;
-
-       trace_xfs_reflink_find_cow_mapping(ip, offset, 1, XFS_IO_OVERWRITE,
-                       &got);
-       *imap = got;
-       return true;
-}
-
 /*
  * Cancel CoW reservations for some block range of an inode.
  *
 
                struct xfs_bmbt_irec *imap, bool *shared, uint *lockmode);
 extern int xfs_reflink_convert_cow(struct xfs_inode *ip, xfs_off_t offset,
                xfs_off_t count);
-extern bool xfs_reflink_find_cow_mapping(struct xfs_inode *ip, xfs_off_t offset,
-               struct xfs_bmbt_irec *imap);
 
 extern int xfs_reflink_cancel_cow_blocks(struct xfs_inode *ip,
                struct xfs_trans **tpp, xfs_fileoff_t offset_fsb,