NAK.

I do not see why this is needed.  Not all sparse warnings need fixing.

What is so bad about a variable length array that we need to incur kmalloc 
overhead on each call?  I would have thought the CPU overhead of the kmalloc is 
a lot larger than any CPU overhead of a variable length array...

The array size is tiny - basically on all volumes mft_record_size is 1024 and 
blocksize is either 512 or 1024 thus the array size is either 1 or 2 pointers.  
The reason it is dynamic is just in case Microsoft change their mind and 
increase the mft_record_size in a future NTFS/Windows version to something 
bigger than 1024 bytes, the current code would still cope fine.

Note mft_record_size is the "on disk inode size" thus it will never be much 
bigger and unlikely to ever change from the 1024 really.  A very long time ago 
when NTFS was being developed Microsoft used 2048 bytes but quickly changed it 
to 1024 as most inodes do not need anywhere near that much space for an inode.

Best regards,

        Anton

On 27 Apr 2014, at 11:12, Fabian Frederick <f...@skynet.be> wrote:

> fs/ntfs/mft.c:471:33: warning: Variable length array is used.
> fs/ntfs/mft.c:676:33: warning: Variable length array is used.
> 
> This is untested.
> 
> Cc: Anton Altaparmakov <an...@tuxera.com>
> Cc: Andrew Morton <a...@linux-foundation.org>
> Signed-off-by: Fabian Frederick <f...@skynet.be>
> ---
> fs/ntfs/mft.c | 17 ++++++++++++-----
> 1 file changed, 12 insertions(+), 5 deletions(-)
> 
> diff --git a/fs/ntfs/mft.c b/fs/ntfs/mft.c
> index 3014a36..eddb739 100644
> --- a/fs/ntfs/mft.c
> +++ b/fs/ntfs/mft.c
> @@ -468,7 +468,7 @@ int ntfs_sync_mft_mirror(ntfs_volume *vol, const unsigned 
> long mft_no,
>       struct page *page;
>       unsigned int blocksize = vol->sb->s_blocksize;
>       int max_bhs = vol->mft_record_size / blocksize;
> -     struct buffer_head *bhs[max_bhs];
> +     struct buffer_head **bhs;
>       struct buffer_head *bh, *head;
>       u8 *kmirr;
>       runlist_element *rl;
> @@ -478,11 +478,14 @@ int ntfs_sync_mft_mirror(ntfs_volume *vol, const 
> unsigned long mft_no,
> 
>       ntfs_debug("Entering for inode 0x%lx.", mft_no);
>       BUG_ON(!max_bhs);
> -     if (unlikely(!vol->mftmirr_ino)) {
> +     bhs = kmalloc(max_bhs * sizeof(struct buffer_head *), GFP_NOFS);
> +     if (unlikely(!bhs || !vol->mftmirr_ino)) {
>               /* This could happen during umount... */
>               err = ntfs_sync_mft_mirror_umount(vol, mft_no, m);
> -             if (likely(!err))
> +             if (likely(!err)) {
> +                     kfree(bhs);
>                       return err;
> +             }
>               goto err_out;
>       }
>       /* Get the page containing the mirror copy of the mft record @m. */
> @@ -632,6 +635,7 @@ err_out:
>                               "after umounting to correct this.", -err);
>               NVolSetErrors(vol);
>       }
> +     kfree(bhs);
>       return err;
> }
> 
> @@ -673,7 +677,7 @@ int write_mft_record_nolock(ntfs_inode *ni, MFT_RECORD 
> *m, int sync)
>       unsigned int blocksize = vol->sb->s_blocksize;
>       unsigned char blocksize_bits = vol->sb->s_blocksize_bits;
>       int max_bhs = vol->mft_record_size / blocksize;
> -     struct buffer_head *bhs[max_bhs];
> +     struct buffer_head **bhs;
>       struct buffer_head *bh, *head;
>       runlist_element *rl;
>       unsigned int block_start, block_end, m_start, m_end;
> @@ -689,7 +693,8 @@ int write_mft_record_nolock(ntfs_inode *ni, MFT_RECORD 
> *m, int sync)
>        * There is no danger of races since the caller is holding the locks
>        * for the mft record @m and the page it is in.
>        */
> -     if (!NInoTestClearDirty(ni))
> +     bhs = kmalloc(max_bhs * sizeof(struct buffer_head *), GFP_NOFS);
> +     if (!bhs || !NInoTestClearDirty(ni))
>               goto done;
>       bh = head = page_buffers(page);
>       BUG_ON(!bh);
> @@ -820,6 +825,7 @@ int write_mft_record_nolock(ntfs_inode *ni, MFT_RECORD 
> *m, int sync)
>               goto err_out;
>       }
> done:
> +     kfree(bhs);
>       ntfs_debug("Done.");
>       return 0;
> cleanup_out:
> @@ -840,6 +846,7 @@ err_out:
>               err = 0;
>       } else
>               NVolSetErrors(vol);
> +     kfree(bhs);
>       return err;
> }
--
To unsubscribe from this list: send the line "unsubscribe linux-kernel" in
the body of a message to majord...@vger.kernel.org
More majordomo info at  http://vger.kernel.org/majordomo-info.html
Please read the FAQ at  http://www.tux.org/lkml/

Reply via email to