From 0851b001640ad0f7bf556f50826ee6718bc8218a Mon Sep 17 00:00:00 2001 From: Greg Kroah-Hartman Date: Wed, 14 Jun 2023 16:15:55 +0000 Subject: [PATCH] Revert "bpf, sockmap: Incorrectly handling copied_seq" This reverts commit fe735073a50eaa71aceb2e990827fe26f33cddd6. It breaks the Android KABI and will be brought back at a later time when it is safe to do so. Bug: 161946584 Change-Id: Iff834f7a4fde71e5c43d477cb9e2adbebd92d389 Signed-off-by: Greg Kroah-Hartman --- include/net/tcp.h | 10 ---------- net/core/skmsg.c | 15 ++++++++------- net/ipv4/tcp.c | 10 +++++++++- net/ipv4/tcp_bpf.c | 28 +--------------------------- 4 files changed, 18 insertions(+), 45 deletions(-) diff --git a/include/net/tcp.h b/include/net/tcp.h index 0744717f5caa..5b70b241ce71 100644 --- a/include/net/tcp.h +++ b/include/net/tcp.h @@ -1467,8 +1467,6 @@ static inline void tcp_adjust_rcv_ssthresh(struct sock *sk) } void tcp_cleanup_rbuf(struct sock *sk, int copied); -void __tcp_cleanup_rbuf(struct sock *sk, int copied); - /* We provision sk_rcvbuf around 200% of sk_rcvlowat. * If 87.5 % (7/8) of the space has been consumed, we want to override @@ -2293,14 +2291,6 @@ int tcp_bpf_update_proto(struct sock *sk, struct sk_psock *psock, bool restore); void tcp_bpf_clone(const struct sock *sk, struct sock *newsk); #endif /* CONFIG_BPF_SYSCALL */ -#ifdef CONFIG_INET -void tcp_eat_skb(struct sock *sk, struct sk_buff *skb); -#else -static inline void tcp_eat_skb(struct sock *sk, struct sk_buff *skb) -{ -} -#endif - int tcp_bpf_sendmsg_redir(struct sock *sk, bool ingress, struct sk_msg *msg, u32 bytes, int flags); #endif /* CONFIG_NET_SOCK_MSG */ diff --git a/net/core/skmsg.c b/net/core/skmsg.c index 9e0f69451563..062612ee508c 100644 --- a/net/core/skmsg.c +++ b/net/core/skmsg.c @@ -978,8 +978,10 @@ static int sk_psock_verdict_apply(struct sk_psock *psock, struct sk_buff *skb, err = -EIO; sk_other = psock->sk; if (sock_flag(sk_other, SOCK_DEAD) || - !sk_psock_test_state(psock, SK_PSOCK_TX_ENABLED)) + !sk_psock_test_state(psock, SK_PSOCK_TX_ENABLED)) { + skb_bpf_redirect_clear(skb); goto out_free; + } skb_bpf_set_ingress(skb); @@ -1008,19 +1010,18 @@ static int sk_psock_verdict_apply(struct sk_psock *psock, struct sk_buff *skb, err = 0; } spin_unlock_bh(&psock->ingress_lock); - if (err < 0) + if (err < 0) { + skb_bpf_redirect_clear(skb); goto out_free; + } } break; case __SK_REDIRECT: - tcp_eat_skb(psock->sk, skb); err = sk_psock_skb_redirect(psock, skb); break; case __SK_DROP: default: out_free: - skb_bpf_redirect_clear(skb); - tcp_eat_skb(psock->sk, skb); sock_drop(psock->sk, skb); } @@ -1065,7 +1066,8 @@ static void sk_psock_strp_read(struct strparser *strp, struct sk_buff *skb) skb_dst_drop(skb); skb_bpf_redirect_clear(skb); ret = bpf_prog_run_pin_on_cpu(prog, skb); - skb_bpf_set_strparser(skb); + if (ret == SK_PASS) + skb_bpf_set_strparser(skb); ret = sk_psock_map_verd(ret, skb_bpf_redirect_fetch(skb)); skb->sk = NULL; } @@ -1171,7 +1173,6 @@ static int sk_psock_verdict_recv(struct sock *sk, struct sk_buff *skb) psock = sk_psock(sk); if (unlikely(!psock)) { len = 0; - tcp_eat_skb(sk, skb); sock_drop(sk, skb); goto out; } diff --git a/net/ipv4/tcp.c b/net/ipv4/tcp.c index 3a856354d42c..849ef44f5043 100644 --- a/net/ipv4/tcp.c +++ b/net/ipv4/tcp.c @@ -1570,7 +1570,7 @@ static int tcp_peek_sndq(struct sock *sk, struct msghdr *msg, int len) * calculation of whether or not we must ACK for the sake of * a window update. */ -void __tcp_cleanup_rbuf(struct sock *sk, int copied) +static void __tcp_cleanup_rbuf(struct sock *sk, int copied) { struct tcp_sock *tp = tcp_sk(sk); bool time_to_ack = false; @@ -1785,6 +1785,14 @@ int tcp_read_skb(struct sock *sk, skb_read_actor_t recv_actor) break; } } + WRITE_ONCE(tp->copied_seq, seq); + + tcp_rcv_space_adjust(sk); + + /* Clean up data we have read: This will do ACK frames. */ + if (copied > 0) + __tcp_cleanup_rbuf(sk, copied); + return copied; } EXPORT_SYMBOL(tcp_read_skb); diff --git a/net/ipv4/tcp_bpf.c b/net/ipv4/tcp_bpf.c index 5f93918c063c..01dd76be1a58 100644 --- a/net/ipv4/tcp_bpf.c +++ b/net/ipv4/tcp_bpf.c @@ -11,24 +11,6 @@ #include #include -void tcp_eat_skb(struct sock *sk, struct sk_buff *skb) -{ - struct tcp_sock *tcp; - int copied; - - if (!skb || !skb->len || !sk_is_tcp(sk)) - return; - - if (skb_bpf_strparser(skb)) - return; - - tcp = tcp_sk(sk); - copied = tcp->copied_seq + skb->len; - WRITE_ONCE(tcp->copied_seq, copied); - tcp_rcv_space_adjust(sk); - __tcp_cleanup_rbuf(sk, skb->len); -} - static int bpf_tcp_ingress(struct sock *sk, struct sk_psock *psock, struct sk_msg *msg, u32 apply_bytes, int flags) { @@ -216,10 +198,8 @@ static int tcp_bpf_recvmsg_parser(struct sock *sk, int flags, int *addr_len) { - struct tcp_sock *tcp = tcp_sk(sk); - u32 seq = tcp->copied_seq; struct sk_psock *psock; - int copied = 0; + int copied; if (unlikely(flags & MSG_ERRQUEUE)) return inet_recv_error(sk, msg, len, addr_len); @@ -264,11 +244,9 @@ msg_bytes_ready: if (is_fin) { copied = 0; - seq++; goto out; } } - seq += copied; if (!copied) { long timeo; int data; @@ -306,10 +284,6 @@ msg_bytes_ready: copied = -EAGAIN; } out: - WRITE_ONCE(tcp->copied_seq, seq); - tcp_rcv_space_adjust(sk); - if (copied > 0) - __tcp_cleanup_rbuf(sk, copied); release_sock(sk); sk_psock_put(sk, psock); return copied;