[RFC,v2,0/4] virtio/vsock: fix credit update logic

Message ID a7ab414b-5e41-c7b6-250b-e8401f335859@sberdevices.ru
Headers
Series virtio/vsock: fix credit update logic |

Message

Arseniy Krasnov March 5, 2023, 8:04 p.m. UTC
  Hello,

this patchset fixes three things in skbuff handling:
1) Current implementation of 'virtio_transport_dec_rx_pkt()':

   value to update 'rx_bytes' and 'fwd_cnt' is calculated as:

   skb_headroom(skb) - sizeof(struct virtio_vsock_hdr) - skb->len;

   i'm a little bit confused about subtracting 'skb->len'. It is clear,
   that difference between first two components is number of bytes copied
   to user. 'skb_headroom()' is delta between 'data' and 'head'. 'data'
   is incremented on each copy data to user from skb by call 'skb_pull()'
   (at the same moment, 'skb->len' is decremented to the same amount of
   bytes). 'head' points to the header of the packet. But what is purpose
   of 'skb->len' here? For SOCK_STREAM is has no effect because this
   logic is called only when 'skb->len' == 0, but for SOCK_SEQPACKET and
   other future calls i think it is buggy.

2) For SOCK_SEQPACKET all sk_buffs are handled only once - after dequeue
   each sk_buff is removed, so user will never read rest of the data.
   Thus we need to update credit parameters of the socket ('rx_bytes' and
   'fwd_cnt') like whole sk_buff is read - so call 'skb_pull()' for the
   whole buffer.

3) For SOCK_STREAM when 'memcpy_to_msg()' fails it fixes 'rx_bytes'
   update (like in 2)) and frees current skbuff.

Test is also added to vsock_test. It does two attempts to read data from
socket - first attempt to invalid buffer (kernel must drop skb). Second
attempt is performed with valid buffer and MSG_DONTWAIT flag. If socket's
queue will be empty (skbuff was dropped due to 'memcpy_to_msg()' fail
and 'rx_bytes' which controls data waiting set to 0), such call will
return immediately with EAGAIN.

Link to v1 on lore:
https://lore.kernel.org/netdev/c2d3e204-89d9-88e9-8a15-3fe027e56b4b@sberdevices.ru/

Change log:

v1 -> v2:
 - For SOCK_SEQPACKET call 'skb_pull()' also in case of copy failure or
   dropping skbuff (when we just waiting message end).
 - Handle copy failure for SOCK_STREAM in the same manner (plus free
   current skbuff).
 - Replace bug repdroducer with new test in vsock_test.c

Arseniy Krasnov (4):
  virtio/vsock: fix 'rx_bytes'/'fwd_cnt' calculation
  virtio/vsock: remove all data from sk_buff
  virtio/vsock: free skb on data copy failure
  test/vsock: invalid buffer tests

 net/vmw_vsock/virtio_transport_common.c |  10 ++-
 tools/testing/vsock/vsock_test.c        | 106 ++++++++++++++++++++++++
 2 files changed, 113 insertions(+), 3 deletions(-)