Skip to content
  • NeilBrown's avatar
    NFS: Optimize fallocate by refreshing mapping when needed. · 6ba80d43
    NeilBrown authored
    
    
    posix_fallocate() will allocate space in an NFS file by considering
    the last byte of every 4K block.  If it is before EOF, it will read
    the byte and if it is zero, a zero is written out.  If it is after EOF,
    the zero is unconditionally written.
    
    For the blocks beyond EOF, if NFS believes its cache is valid, it will
    expand these writes to write full pages, and then will merge the pages.
    This results if (typically) 1MB writes.  If NFS believes its cache is
    not valid (particularly if NFS_INO_INVALID_DATA or
    NFS_INO_REVAL_PAGECACHE are set - see nfs_write_pageuptodate()), it will
    send the individual 1-byte writes. This results in (typically) 256 times
    as many RPC requests, and can be substantially slower.
    
    Currently nfs_revalidate_mapping() is only used when reading a file or
    mmapping a file, as these are times when the content needs to be
    up-to-date.  Writes don't generally need the cache to be up-to-date, but
    writes beyond EOF can benefit, particularly in the posix_fallocate()
    case.
    
    So this patch calls nfs_revalidate_mapping() when writing beyond EOF -
    i.e. when there is a gap between the end of the file and the start of
    the write.  If the cache is thought to be out of date (as happens after
    taking a file lock), this will cause a GETATTR, and the two flags
    mentioned above will be cleared.  With this, posix_fallocate() on a
    newly locked file does not generate excessive tiny writes.
    
    Signed-off-by: default avatarNeilBrown <neilb@suse.com>
    Signed-off-by: default avatarAnna Schumaker <Anna.Schumaker@Netapp.com>
    6ba80d43