[U-Boot] [PATCH 1/2] fs: fat: treat invalid FAT clusters as errors
AKASHI Takahiro
takahiro.akashi at linaro.org
Wed Sep 18 04:37:02 UTC 2019
On Thu, Sep 12, 2019 at 07:19:29PM +0200, Heinrich Schuchardt wrote:
> When hitting an invalid FAT cluster while reading a file always print an
> error message and return an error code.
I don't know what the intention of original author was here.
In general, a cluster's FAT entry points to a next cluster
which composes part of a file and hence a chain of clusters.
The last cluster's FAT is marked with EOC(End of Cluster),
which has a dedicated value, for fat16, one of 0xfff8:0xffff.
As you can see, those values are also detected by CHECK_CLUST() macro.
I'm afraid that, at least initially, this macro might have worked
for detecting a file end correctly (so returned 0?).
Another issue is that CHECK_CLUST() checks against >0xfff0 for fat16
while 0xfff0:0xfff6 are still valid for cluster numbers.
So it will potentially detect a wrong "invalid" FAT entry for
a quite large file.
Thanks,
-Takahiro Akashi
> Signed-off-by: Heinrich Schuchardt <xypron.glpk at gmx.de>
> ---
> fs/fat/fat.c | 30 ++++++++++++++++++++----------
> 1 file changed, 20 insertions(+), 10 deletions(-)
>
> diff --git a/fs/fat/fat.c b/fs/fat/fat.c
> index 73a89fc9e3..b4e8083734 100644
> --- a/fs/fat/fat.c
> +++ b/fs/fat/fat.c
> @@ -301,10 +301,20 @@ get_cluster(fsdata *mydata, __u32 clustnum, __u8 *buffer, unsigned long size)
> return 0;
> }
>
> -/*
> +/**
> + * get_contents() - read from file
> + *
> * Read at most 'maxsize' bytes from 'pos' in the file associated with 'dentptr'
> - * into 'buffer'.
> - * Update the number of bytes read in *gotsize or return -1 on fatal errors.
> + * into 'buffer'. Update the number of bytes read in *gotsize or return -1 on
> + * fatal errors.
> + *
> + * @mydata: file system description
> + * @dentprt: directory entry pointer
> + * @pos: position from where to read
> + * @buffer: buffer into which to read
> + * @maxsize: maximum number of bytes to read
> + * @gotsize: number of bytes actually read
> + * Return: -1 on error, otherwise 0
> */
> static int get_contents(fsdata *mydata, dir_entry *dentptr, loff_t pos,
> __u8 *buffer, loff_t maxsize, loff_t *gotsize)
> @@ -335,8 +345,8 @@ static int get_contents(fsdata *mydata, dir_entry *dentptr, loff_t pos,
> curclust = get_fatent(mydata, curclust);
> if (CHECK_CLUST(curclust, mydata->fatsize)) {
> debug("curclust: 0x%x\n", curclust);
> - debug("Invalid FAT entry\n");
> - return 0;
> + printf("Invalid FAT entry\n");
> + return -1;
> }
> actsize += bytesperclust;
> }
> @@ -374,8 +384,8 @@ static int get_contents(fsdata *mydata, dir_entry *dentptr, loff_t pos,
> curclust = get_fatent(mydata, curclust);
> if (CHECK_CLUST(curclust, mydata->fatsize)) {
> debug("curclust: 0x%x\n", curclust);
> - debug("Invalid FAT entry\n");
> - return 0;
> + printf("Invalid FAT entry\n");
> + return -1;
> }
> }
>
> @@ -390,8 +400,8 @@ static int get_contents(fsdata *mydata, dir_entry *dentptr, loff_t pos,
> goto getit;
> if (CHECK_CLUST(newclust, mydata->fatsize)) {
> debug("curclust: 0x%x\n", newclust);
> - debug("Invalid FAT entry\n");
> - return 0;
> + printf("Invalid FAT entry\n");
> + return -1;
> }
> endclust = newclust;
> actsize += bytesperclust;
> @@ -418,7 +428,7 @@ getit:
> if (CHECK_CLUST(curclust, mydata->fatsize)) {
> debug("curclust: 0x%x\n", curclust);
> printf("Invalid FAT entry\n");
> - return 0;
> + return -1;
> }
> actsize = bytesperclust;
> endclust = curclust;
> --
> 2.23.0
>
More information about the U-Boot
mailing list