tftp: roll over block counter to prevent timeouts with data packets

The block number is a 16-bit counter which only allows to fetch
files no bigger than 65535 * blksize. To avoid this limit, the
counter is rolled over. This behavior isn't defined in RFC 1350
but is handled by many TFTP servers and it's what GRUB was doing
before implicitly due an overflow.

Closes-Bug: #1938559

Signed-off-by: Jiping Ma <jiping.ma2@windriver.com>
Change-Id: I4a0c04cf15b87f6f40c7a979d20fb3c57657cefd
This commit is contained in:
Jiping Ma 2021-08-31 20:07:04 -07:00
parent 0a6dd52d96
commit 572cd24c49
3 changed files with 69 additions and 0 deletions

View File

@ -0,0 +1,23 @@
From cff7cf7787b4619a7cbbe5ccbbfeced54999ad70 Mon Sep 17 00:00:00 2001
From: jma1 <jma1@opendev.org>
Date: Mon, 30 Aug 2021 06:27:13 +0000
Subject: [PATCH] tftp: roll over block counter to prevent timeouts with data
Signed-off-by: Jiping Ma <jiping.ma2@windriver.com>
---
grub.patches | 1 +
1 file changed, 1 insertion(+)
diff --git a/grub.patches b/grub.patches
index 678ba4b..ece014a 100644
--- a/SOURCES/grub.patches
+++ b/SOURCES/grub.patches
@@ -335,4 +335,5 @@ Patch0334: 0334-linux-Fix-integer-overflows-in-initrd-size-handling.patch
Patch1000: 1000_linux-mktitle-de-brand-the-grub.cfg-menu.patch
Patch1001: 1001-add-tboot.patch
Patch1002: 1002-Don-t-write-trailing-colon-when-populating-MAC-strin.patch
+Patch1003: 1003-tftp-roll-over-block-counter-to-prevent-timeouts-wit.patch
--
2.29.2

View File

@ -9,3 +9,4 @@
0010-grub2-add-tboot.patch
0011-grub2-fix-str-for-6B-macs.patch
0012-grub2-Don-t-strip-img-files-from-non-EFI-build.patch
0013-tftp-roll-over-block-counter-to-prevent-timeouts-wit.patch

View File

@ -0,0 +1,45 @@
From 250304ce7a6f31e3999d128183fe299b99ec95aa Mon Sep 17 00:00:00 2001
From: Javier Martinez Canillas <javierm@redhat.com>
Date: Mon, 24 Aug 2020 14:46:27 +0200
Subject: [PATCH] tftp: roll over block counter to prevent timeouts with data
packets
The block number is a 16-bit counter which only allows to fetch
files no bigger than 65535 * blksize. To avoid this limit, the
counter is rolled over. This behavior isn't defined in RFC 1350
but is handled by many TFTP servers and it's what GRUB was doing
before implicitly due an overflow.
Suggested-by: Peter Jones <pjones@redhat.com>
Signed-off-by: Javier Martinez Canillas <javierm@redhat.com>
Signed-off-by: Jiping Ma <jiping.ma2@windriver.com>
---
grub-core/net/tftp.c | 12 ++++++++++--
1 file changed, 10 insertions(+), 2 deletions(-)
diff --git a/grub-core/net/tftp.c b/grub-core/net/tftp.c
index 79c16f9..eab9ab7 100644
--- a/grub-core/net/tftp.c
+++ b/grub-core/net/tftp.c
@@ -183,8 +183,16 @@ tftp_receive (grub_net_udp_socket_t sock __attribute__ ((unused)),
return GRUB_ERR_NONE;
}
- /* Ack old/retransmitted block. */
- if (grub_be_to_cpu16 (tftph->u.data.block) < data->block + 1)
+ /*
+ * Ack old/retransmitted block.
+ *
+ * The block number is a 16-bit counter which only allows to fetch
+ * files no bigger than 65535 * blksize. To avoid this limit, the
+ * counter is rolled over. This behavior isn't defined in RFC 1350
+ * but is handled by many TFTP servers and it's what GRUB was doing
+ * before implicitly due an overflow.
+ */
+ if (grub_be_to_cpu16 (tftph->u.data.block) < ((data->block + 1) & 0xffffu))
ack (data, grub_be_to_cpu16 (tftph->u.data.block));
/* Ignore unexpected block. */
else if (grub_be_to_cpu16 (tftph->u.data.block) > data->block + 1)
--
2.31.1