An overflow can occur in a situation where src.centiseconds
takes the value of 255. This situation is unlikely, but there
is no validation check anywere in the code.
Found by Linux Verification Center (linuxtesting.org) with Svace.
Suggested-by: Jan Kara <[email protected]>
Signed-off-by: Roman Smirnov <[email protected]>
---
fs/udf/udftime.c | 11 ++++++++---
1 file changed, 8 insertions(+), 3 deletions(-)
diff --git a/fs/udf/udftime.c b/fs/udf/udftime.c
index 758163af39c2..3113785af3cf 100644
--- a/fs/udf/udftime.c
+++ b/fs/udf/udftime.c
@@ -46,13 +46,18 @@ udf_disk_stamp_to_time(struct timespec64 *dest, struct timestamp src)
dest->tv_sec = mktime64(year, src.month, src.day, src.hour, src.minute,
src.second);
dest->tv_sec -= offset * 60;
- dest->tv_nsec = 1000 * (src.centiseconds * 10000 +
- src.hundredsOfMicroseconds * 100 + src.microseconds);
+
/*
* Sanitize nanosecond field since reportedly some filesystems are
* recorded with bogus sub-second values.
*/
- dest->tv_nsec %= NSEC_PER_SEC;
+ if (src.centiseconds < 100 && src.hundredsOfMicroseconds < 100 &&
+ src.microseconds < 100) {
+ dest->tv_nsec = 1000 * (src.centiseconds * 10000 +
+ src.hundredsOfMicroseconds * 100 + src.microseconds);
+ } else {
+ desk->tv_nsec = 0;
+ }
}
void
--
2.34.1
On 3/27/24 4:27 PM, Roman Smirnov wrote:
> An overflow can occur in a situation where src.centiseconds
> takes the value of 255. This situation is unlikely, but there
> is no validation check anywere in the code.
>
> Found by Linux Verification Center (linuxtesting.org) with Svace.
>
> Suggested-by: Jan Kara <[email protected]>
> Signed-off-by: Roman Smirnov <[email protected]>
Reviewed-by: Sergey Shtylyov <[email protected]>
[...]
MBR, Sergey
On Wed 27-03-24 16:27:55, Roman Smirnov wrote:
> An overflow can occur in a situation where src.centiseconds
> takes the value of 255. This situation is unlikely, but there
> is no validation check anywere in the code.
>
> Found by Linux Verification Center (linuxtesting.org) with Svace.
>
> Suggested-by: Jan Kara <[email protected]>
> Signed-off-by: Roman Smirnov <[email protected]>
Thanks! I've added the patch to my tree.
Honza
> ---
> fs/udf/udftime.c | 11 ++++++++---
> 1 file changed, 8 insertions(+), 3 deletions(-)
>
> diff --git a/fs/udf/udftime.c b/fs/udf/udftime.c
> index 758163af39c2..3113785af3cf 100644
> --- a/fs/udf/udftime.c
> +++ b/fs/udf/udftime.c
> @@ -46,13 +46,18 @@ udf_disk_stamp_to_time(struct timespec64 *dest, struct timestamp src)
> dest->tv_sec = mktime64(year, src.month, src.day, src.hour, src.minute,
> src.second);
> dest->tv_sec -= offset * 60;
> - dest->tv_nsec = 1000 * (src.centiseconds * 10000 +
> - src.hundredsOfMicroseconds * 100 + src.microseconds);
> +
> /*
> * Sanitize nanosecond field since reportedly some filesystems are
> * recorded with bogus sub-second values.
> */
> - dest->tv_nsec %= NSEC_PER_SEC;
> + if (src.centiseconds < 100 && src.hundredsOfMicroseconds < 100 &&
> + src.microseconds < 100) {
> + dest->tv_nsec = 1000 * (src.centiseconds * 10000 +
> + src.hundredsOfMicroseconds * 100 + src.microseconds);
> + } else {
> + desk->tv_nsec = 0;
> + }
> }
>
> void
> --
> 2.34.1
>
--
Jan Kara <[email protected]>
SUSE Labs, CR
On Wed 10-04-24 13:04:06, Jan Kara wrote:
> On Wed 27-03-24 16:27:55, Roman Smirnov wrote:
> > An overflow can occur in a situation where src.centiseconds
> > takes the value of 255. This situation is unlikely, but there
> > is no validation check anywere in the code.
> >
> > Found by Linux Verification Center (linuxtesting.org) with Svace.
> >
> > Suggested-by: Jan Kara <[email protected]>
> > Signed-off-by: Roman Smirnov <[email protected]>
>
> Thanks! I've added the patch to my tree.
Actually, there's a small typo that needed fixing up. Corrected on commit.
> > diff --git a/fs/udf/udftime.c b/fs/udf/udftime.c
> > index 758163af39c2..3113785af3cf 100644
> > --- a/fs/udf/udftime.c
> > +++ b/fs/udf/udftime.c
> > @@ -46,13 +46,18 @@ udf_disk_stamp_to_time(struct timespec64 *dest, struct timestamp src)
> > dest->tv_sec = mktime64(year, src.month, src.day, src.hour, src.minute,
> > src.second);
> > dest->tv_sec -= offset * 60;
> > - dest->tv_nsec = 1000 * (src.centiseconds * 10000 +
> > - src.hundredsOfMicroseconds * 100 + src.microseconds);
> > +
> > /*
> > * Sanitize nanosecond field since reportedly some filesystems are
> > * recorded with bogus sub-second values.
> > */
> > - dest->tv_nsec %= NSEC_PER_SEC;
> > + if (src.centiseconds < 100 && src.hundredsOfMicroseconds < 100 &&
> > + src.microseconds < 100) {
> > + dest->tv_nsec = 1000 * (src.centiseconds * 10000 +
> > + src.hundredsOfMicroseconds * 100 + src.microseconds);
> > + } else {
> > + desk->tv_nsec = 0;
^^^^ Here
> > + }
> > }
Honza
--
Jan Kara <[email protected]>
SUSE Labs, CR