summaryrefslogtreecommitdiff
path: root/src
diff options
context:
space:
mode:
authorZixun LI <[email protected]>2026-07-05 13:22:58 +0200
committerGitHub <[email protected]>2026-07-05 13:22:58 +0200
commit6fc114c8271e25160390c0ac5ea798c2f7cee315 (patch)
treefa84588379eb3c7fa1e6662e1b4b23f0c1e69498 /src
parent7bc2e7d129eac0b83ef29b8f6b68defd10613ad5 (diff)
parent2d5f5c0cf2ae992234fff826f95c3a24daff223a (diff)
Merge pull request #3741 from dxbjavid/ncm-ndp-length-bound
bound ndp16 wLength against received ntb in recv_validate_datagram
Diffstat (limited to 'src')
-rw-r--r--src/class/net/ncm_device.c8
1 files changed, 7 insertions, 1 deletions
diff --git a/src/class/net/ncm_device.c b/src/class/net/ncm_device.c
index d828ab97c..84a524f49 100644
--- a/src/class/net/ncm_device.c
+++ b/src/class/net/ncm_device.c
@@ -602,7 +602,7 @@ static bool recv_validate_datagram(const recv_ntb_t *ntb, uint32_t len) {
TU_LOG_DRV("(EE) ill block length2: %d > %d\n", nth16->wBlockLength, CFG_TUD_NCM_OUT_NTB_MAX_SIZE);
return false;
}
- if (nth16->wNdpIndex < sizeof(nth16) || nth16->wNdpIndex > len - (sizeof(ndp16_t) + 2 * sizeof(ndp16_datagram_t))) {
+ if (nth16->wNdpIndex < sizeof(nth16_t) || nth16->wNdpIndex > len - (sizeof(ndp16_t) + 2 * sizeof(ndp16_datagram_t))) {
TU_LOG_DRV("(EE) ill position of first ndp: %d (%lu)\n", nth16->wNdpIndex, len);
return false;
}
@@ -614,6 +614,12 @@ static bool recv_validate_datagram(const recv_ntb_t *ntb, uint32_t len) {
TU_LOG_DRV("(EE) ill ndp16 length: %d\n", ndp16->wLength);
return false;
}
+ // the NDP block (wLength bytes from wNdpIndex) must fit within the received NTB, otherwise the
+ // datagram pointer array walked below (max_ndx is derived from wLength) runs past ntb->data
+ if ((uint32_t) nth16->wNdpIndex + ndp16->wLength > len) {
+ TU_LOG_DRV("(EE) ill ndp16 length: %d (%lu)\n", ndp16->wLength, len);
+ return false;
+ }
if (ndp16->dwSignature != NDP16_SIGNATURE_NCM0 && ndp16->dwSignature != NDP16_SIGNATURE_NCM1) {
TU_LOG_DRV("(EE) ill signature: 0x%08x\n", (unsigned) ndp16->dwSignature);
return false;