Commit 8160385b authored by Jukka Rissanen's avatar Jukka Rissanen
Browse files

net: pkt: Fix removal of empty buffers in net_pkt_pull()



If we have removed first net_buf, then we must not restore the
original cursor as that will point to wrong head net_buf.
Add also unit test to check that the packets are removed
properly.
Clarify the documentation that we are removing data from
beginning of the function, also document that the cursor
is reset after this call.

Signed-off-by: default avatarJukka Rissanen <jukka.rissanen@linux.intel.com>
parent 0bac2f35
Loading
Loading
Loading
Loading
+1 −0
Original line number Diff line number Diff line
@@ -1805,6 +1805,7 @@ int net_pkt_update_length(struct net_pkt *pkt, size_t length);
 *
 * @details net_pkt's cursor should be properly initialized and,
 *          eventually, properly positioned using net_pkt_skip/read/write.
 *          Note that net_pkt's cursor is reset by this function.
 *
 * @param pkt    Network packet
 * @param length Number of bytes to be removed
+3 −10
Original line number Diff line number Diff line
@@ -1872,13 +1872,6 @@ int net_pkt_update_length(struct net_pkt *pkt, size_t length)
int net_pkt_pull(struct net_pkt *pkt, size_t length)
{
	struct net_pkt_cursor *c_op = &pkt->cursor;
	struct net_pkt_cursor backup;

	if (!pkt->buffer) {
		return -ENOBUFS;
	}

	net_pkt_cursor_backup(pkt, &backup);

	while (length) {
		size_t left, rem;
@@ -1910,15 +1903,15 @@ int net_pkt_pull(struct net_pkt *pkt, size_t length)
				pkt->buffer = buf->frags;
				buf->frags = NULL;
				net_buf_unref(buf);
			}

			net_pkt_cursor_init(pkt);
		}
		}

		length -= rem;
	}

	net_pkt_cursor_restore(pkt, &backup);
	net_pkt_cursor_init(pkt);

	if (length) {
		NET_DBG("Still some length to go %zu", length);
+28 −0
Original line number Diff line number Diff line
@@ -638,6 +638,7 @@ void test_net_pkt_pull(void)
	struct net_pkt *dummy_pkt;
	static u8_t pkt_data[PULL_TEST_PKT_DATA_SIZE];
	static u8_t pkt_data_readback[PULL_TEST_PKT_DATA_SIZE];
	size_t len;
	int i, ret;

	for (i = 0; i < PULL_TEST_PKT_DATA_SIZE; ++i) {
@@ -715,6 +716,33 @@ void test_net_pkt_pull(void)
		      net_pkt_get_len(dummy_pkt));

	net_pkt_unref(dummy_pkt);

	dummy_pkt = net_pkt_alloc_with_buffer(eth_if,
					      PULL_TEST_PKT_DATA_SIZE,
					      AF_UNSPEC,
					      0,
					      K_NO_WAIT);
	zassert_true(dummy_pkt != NULL, "Pkt not allocated");

	zassert_true(net_pkt_write(dummy_pkt,
				   pkt_data,
				   PULL_TEST_PKT_DATA_SIZE) == 0,
		     "Write packet failed");

	net_pkt_cursor_init(dummy_pkt);
	len = net_pkt_get_len(dummy_pkt);

	for (i = 0; i < len; i++) {
		ret = net_pkt_pull(dummy_pkt, 1);
		zassert_equal(ret, 0, "Did return error");
	}

	ret = net_pkt_pull(dummy_pkt, 1);
	zassert_equal(ret, -ENOBUFS, "Did not return error");

	zassert_equal(dummy_pkt->buffer, NULL, "buffer list not empty");

	net_pkt_unref(dummy_pkt);
}

void test_net_pkt_clone(void)