Hi Oscar,

On 2026-10-27T13:18:37, Oscar Deschamps <[email protected]> wrote:
> lib: date: reject out-of-range month in rtc_calc_weekday()
>
> rtc_calc_weekday() indexes the 12-entry month_offset[] array with
> tm->tm_mon - 1 but never checks that tm_mon is in 1..12. A caller that
> derives the month from untrusted data can pass a larger value, causing an
> out-of-bounds read of month_offset[].
>
> fs/fat reaches this with on-disk data: fat_readdir() calls fat2rtc() on
> each directory entry's cdate/date/adate fields, and fat2rtc() does
>
>     tm->tm_mon = (date & 0x1e0) >> 5;
>
> The month is a 4-bit field, so it can be 0..15. A directory-entry date
> word with a month of 13..15 (which a compliant filesystem never writes,
> but a crafted or corrupted image can contain) makes rtc_calc_weekday()
> read past month_offset[]. This happens while merely listing a FAT volume
> (fatls / ls), i.e. on attacker-controlled media before it is validated.

Month 0 is more common and needs no crafted image. The creation and
access dates are optional in FAT and many implementations leave them
as zero, so a zero date word gives tm_mon = 0 and reads
month_offset[-1] on an ordinary volume. Please can you mention this,
since the patch fixes it too. Also, fat_readdir() only calls fat2rtc()
when EFI_LOADER is enabled, so it would be worth saying that.

> Found with a libFuzzer harness over the FAT parser (test/fuzz/fat.c).

There is no test/fuzz/fat.c in the tree - are you planning to send the
harness too? A small unit test for rtc_calc_weekday() with months 0
and 13 would be good, perhaps as a follow-up.

>
> The impact is limited to an out-of-bounds read (a wrong weekday, or on a
> sanitizer build an abort); there is no write. Reject an out-of-range
> [...]
>
>  lib/date.c | 2 ++
>  1 file changed, 2 insertions(+)

In any case:
Reviewed-by: Simon Glass <[email protected]>

Regards,
Simon

Reply via email to