net: ip: 6lo: Fix corner case with packet format after IPHC

IEEE802154 drivers expect, that a complete 802.15.4 frame fits into a
single net_buf provided in a net_pkt.

There is a corner case with header compression when this could not be
the case. If the IPv6 packet before IPHC exceeded 802.15.4 MTU, it'd
consist of several net_buf's. This was not an issue, if the IPv6 packet
after header compression still required fragmentation, as the
fragmentation module took care of formatting individual net_buf's
properly.

For short range of packet sizes however this was no the case. The IPv6
packet, after header compression, might not require fragmentation any
more. As the IPHC logic only modified the IPv6 header part, by trimming
the buffer in front of the net_buf, such a packet would still consist of
two net_bufs, even though it should fit into a single 15.4 frame. Such
packet was passed to the driver, causing the driver to send only part of
the packet, from the first net_buf.

Fix this, by using net_pkt functions to manipulate the packet, instead
of operating on net_buf directly. net_pkt_pull() will not trim the
buffer in front, but rather move the entire packet content to the front.
On the other hand, net_pkt_compact() will assure that there's no gaps in
the net_bufs. In result, packets that do not require fragmentation,
should be placed into a single net_buf, as expected by drivers.

Signed-off-by: Robert Lubos <robert.lubos@nordicsemi.no>
This commit is contained in:
Robert Lubos 2023-02-16 14:17:55 +01:00 committed by Anas Nashif
parent dc641ceffd
commit a28dba2503

View file

@ -832,7 +832,9 @@ sa_end:
compressed = inline_pos - pkt->buffer->data;
net_buf_pull(pkt->buffer, compressed);
net_pkt_cursor_init(pkt);
net_pkt_pull(pkt, compressed);
net_pkt_compact(pkt);
return compressed;
}