af_packet: Don't send zero-byte data in packet_sendmsg_spkt().
[platform/kernel/linux-rpi.git] / net / packet / af_packet.c
index ecd9fc2..640d94e 100644 (file)
@@ -270,8 +270,11 @@ static noinline struct sk_buff *nf_hook_direct_egress(struct sk_buff *skb)
 }
 #endif
 
-static int packet_direct_xmit(struct sk_buff *skb)
+static int packet_xmit(const struct packet_sock *po, struct sk_buff *skb)
 {
+       if (!packet_sock_flag(po, PACKET_SOCK_QDISC_BYPASS))
+               return dev_queue_xmit(skb);
+
 #ifdef CONFIG_NETFILTER_EGRESS
        if (nf_hook_egress_active()) {
                skb = nf_hook_direct_egress(skb);
@@ -305,12 +308,6 @@ static void packet_cached_dev_reset(struct packet_sock *po)
        RCU_INIT_POINTER(po->cached_dev, NULL);
 }
 
-static bool packet_use_direct_xmit(const struct packet_sock *po)
-{
-       /* Paired with WRITE_ONCE() in packet_setsockopt() */
-       return READ_ONCE(po->xmit) == packet_direct_xmit;
-}
-
 static u16 packet_pick_tx_queue(struct sk_buff *skb)
 {
        struct net_device *dev = skb->dev;
@@ -340,14 +337,14 @@ static void __register_prot_hook(struct sock *sk)
 {
        struct packet_sock *po = pkt_sk(sk);
 
-       if (!po->running) {
+       if (!packet_sock_flag(po, PACKET_SOCK_RUNNING)) {
                if (po->fanout)
                        __fanout_link(sk, po);
                else
                        dev_add_pack(&po->prot_hook);
 
                sock_hold(sk);
-               po->running = 1;
+               packet_sock_flag_set(po, PACKET_SOCK_RUNNING, 1);
        }
 }
 
@@ -369,7 +366,7 @@ static void __unregister_prot_hook(struct sock *sk, bool sync)
 
        lockdep_assert_held_once(&po->bind_lock);
 
-       po->running = 0;
+       packet_sock_flag_set(po, PACKET_SOCK_RUNNING, 0);
 
        if (po->fanout)
                __fanout_unlink(sk, po);
@@ -389,7 +386,7 @@ static void unregister_prot_hook(struct sock *sk, bool sync)
 {
        struct packet_sock *po = pkt_sk(sk);
 
-       if (po->running)
+       if (packet_sock_flag(po, PACKET_SOCK_RUNNING))
                __unregister_prot_hook(sk, sync);
 }
 
@@ -474,7 +471,7 @@ static __u32 __packet_set_timestamp(struct packet_sock *po, void *frame,
        struct timespec64 ts;
        __u32 ts_status;
 
-       if (!(ts_status = tpacket_get_timestamp(skb, &ts, po->tp_tstamp)))
+       if (!(ts_status = tpacket_get_timestamp(skb, &ts, READ_ONCE(po->tp_tstamp))))
                return 0;
 
        h.raw = frame;
@@ -1307,22 +1304,23 @@ static int __packet_rcv_has_room(const struct packet_sock *po,
 
 static int packet_rcv_has_room(struct packet_sock *po, struct sk_buff *skb)
 {
-       int pressure, ret;
+       bool pressure;
+       int ret;
 
        ret = __packet_rcv_has_room(po, skb);
        pressure = ret != ROOM_NORMAL;
 
-       if (READ_ONCE(po->pressure) != pressure)
-               WRITE_ONCE(po->pressure, pressure);
+       if (packet_sock_flag(po, PACKET_SOCK_PRESSURE) != pressure)
+               packet_sock_flag_set(po, PACKET_SOCK_PRESSURE, pressure);
 
        return ret;
 }
 
 static void packet_rcv_try_clear_pressure(struct packet_sock *po)
 {
-       if (READ_ONCE(po->pressure) &&
+       if (packet_sock_flag(po, PACKET_SOCK_PRESSURE) &&
            __packet_rcv_has_room(po, NULL) == ROOM_NORMAL)
-               WRITE_ONCE(po->pressure,  0);
+               packet_sock_flag_set(po, PACKET_SOCK_PRESSURE, false);
 }
 
 static void packet_sock_destruct(struct sock *sk)
@@ -1409,7 +1407,8 @@ static unsigned int fanout_demux_rollover(struct packet_fanout *f,
        i = j = min_t(int, po->rollover->sock, num - 1);
        do {
                po_next = pkt_sk(rcu_dereference(f->arr[i]));
-               if (po_next != po_skip && !READ_ONCE(po_next->pressure) &&
+               if (po_next != po_skip &&
+                   !packet_sock_flag(po_next, PACKET_SOCK_PRESSURE) &&
                    packet_rcv_has_room(po_next, skb) == ROOM_NORMAL) {
                        if (i != j)
                                po->rollover->sock = i;
@@ -1782,7 +1781,7 @@ static int fanout_add(struct sock *sk, struct fanout_args *args)
        err = -EINVAL;
 
        spin_lock(&po->bind_lock);
-       if (po->running &&
+       if (packet_sock_flag(po, PACKET_SOCK_RUNNING) &&
            match->type == type &&
            match->prot_hook.type == po->prot_hook.type &&
            match->prot_hook.dev == po->prot_hook.dev) {
@@ -2034,7 +2033,7 @@ retry:
                goto retry;
        }
 
-       if (!dev_validate_header(dev, skb->data, len)) {
+       if (!dev_validate_header(dev, skb->data, len) || !skb->len) {
                err = -EINVAL;
                goto out_unlock;
        }
@@ -2091,18 +2090,18 @@ static unsigned int run_filter(struct sk_buff *skb,
 }
 
 static int packet_rcv_vnet(struct msghdr *msg, const struct sk_buff *skb,
-                          size_t *len)
+                          size_t *len, int vnet_hdr_sz)
 {
-       struct virtio_net_hdr vnet_hdr;
+       struct virtio_net_hdr_mrg_rxbuf vnet_hdr = { .num_buffers = 0 };
 
-       if (*len < sizeof(vnet_hdr))
+       if (*len < vnet_hdr_sz)
                return -EINVAL;
-       *len -= sizeof(vnet_hdr);
+       *len -= vnet_hdr_sz;
 
-       if (virtio_net_hdr_from_skb(skb, &vnet_hdr, vio_le(), true, 0))
+       if (virtio_net_hdr_from_skb(skb, (struct virtio_net_hdr *)&vnet_hdr, vio_le(), true, 0))
                return -EINVAL;
 
-       return memcpy_to_msg(msg, (void *)&vnet_hdr, sizeof(vnet_hdr));
+       return memcpy_to_msg(msg, (void *)&vnet_hdr, vnet_hdr_sz);
 }
 
 /*
@@ -2251,7 +2250,7 @@ static int tpacket_rcv(struct sk_buff *skb, struct net_device *dev,
        __u32 ts_status;
        bool is_drop_n_account = false;
        unsigned int slot_id = 0;
-       bool do_vnet = false;
+       int vnet_hdr_sz = 0;
 
        /* struct tpacket{2,3}_hdr is aligned to a multiple of TPACKET_ALIGNMENT.
         * We may add members to them until current aligned size without forcing
@@ -2309,10 +2308,9 @@ static int tpacket_rcv(struct sk_buff *skb, struct net_device *dev,
                netoff = TPACKET_ALIGN(po->tp_hdrlen +
                                       (maclen < 16 ? 16 : maclen)) +
                                       po->tp_reserve;
-               if (po->has_vnet_hdr) {
-                       netoff += sizeof(struct virtio_net_hdr);
-                       do_vnet = true;
-               }
+               vnet_hdr_sz = READ_ONCE(po->vnet_hdr_sz);
+               if (vnet_hdr_sz)
+                       netoff += vnet_hdr_sz;
                macoff = netoff - maclen;
        }
        if (netoff > USHRT_MAX) {
@@ -2338,7 +2336,7 @@ static int tpacket_rcv(struct sk_buff *skb, struct net_device *dev,
                        snaplen = po->rx_ring.frame_size - macoff;
                        if ((int)snaplen < 0) {
                                snaplen = 0;
-                               do_vnet = false;
+                               vnet_hdr_sz = 0;
                        }
                }
        } else if (unlikely(macoff + snaplen >
@@ -2352,7 +2350,7 @@ static int tpacket_rcv(struct sk_buff *skb, struct net_device *dev,
                if (unlikely((int)snaplen < 0)) {
                        snaplen = 0;
                        macoff = GET_PBDQC_FROM_RB(&po->rx_ring)->max_frame_len;
-                       do_vnet = false;
+                       vnet_hdr_sz = 0;
                }
        }
        spin_lock(&sk->sk_receive_queue.lock);
@@ -2368,7 +2366,7 @@ static int tpacket_rcv(struct sk_buff *skb, struct net_device *dev,
                __set_bit(slot_id, po->rx_ring.rx_owner_map);
        }
 
-       if (do_vnet &&
+       if (vnet_hdr_sz &&
            virtio_net_hdr_from_skb(skb, h.raw + macoff -
                                    sizeof(struct virtio_net_hdr),
                                    vio_le(), true, 0)) {
@@ -2403,7 +2401,8 @@ static int tpacket_rcv(struct sk_buff *skb, struct net_device *dev,
         * closer to the time of capture.
         */
        ts_status = tpacket_get_timestamp(skb, &ts,
-                                         po->tp_tstamp | SOF_TIMESTAMPING_SOFTWARE);
+                                         READ_ONCE(po->tp_tstamp) |
+                                         SOF_TIMESTAMPING_SOFTWARE);
        if (!ts_status)
                ktime_get_real_ts64(&ts);
 
@@ -2551,16 +2550,26 @@ static int __packet_snd_vnet_parse(struct virtio_net_hdr *vnet_hdr, size_t len)
 }
 
 static int packet_snd_vnet_parse(struct msghdr *msg, size_t *len,
-                                struct virtio_net_hdr *vnet_hdr)
+                                struct virtio_net_hdr *vnet_hdr, int vnet_hdr_sz)
 {
-       if (*len < sizeof(*vnet_hdr))
+       int ret;
+
+       if (*len < vnet_hdr_sz)
                return -EINVAL;
-       *len -= sizeof(*vnet_hdr);
+       *len -= vnet_hdr_sz;
 
        if (!copy_from_iter_full(vnet_hdr, sizeof(*vnet_hdr), &msg->msg_iter))
                return -EFAULT;
 
-       return __packet_snd_vnet_parse(vnet_hdr, *len);
+       ret = __packet_snd_vnet_parse(vnet_hdr, *len);
+       if (ret)
+               return ret;
+
+       /* move iter to point to the start of mac header */
+       if (vnet_hdr_sz != sizeof(struct virtio_net_hdr))
+               iov_iter_advance(&msg->msg_iter, vnet_hdr_sz - sizeof(struct virtio_net_hdr));
+
+       return 0;
 }
 
 static int tpacket_fill_skb(struct packet_sock *po, struct sk_buff *skb,
@@ -2622,8 +2631,8 @@ static int tpacket_fill_skb(struct packet_sock *po, struct sk_buff *skb,
                nr_frags = skb_shinfo(skb)->nr_frags;
 
                if (unlikely(nr_frags >= MAX_SKB_FRAGS)) {
-                       pr_err("Packet exceed the number of skb frags(%lu)\n",
-                              MAX_SKB_FRAGS);
+                       pr_err("Packet exceed the number of skb frags(%u)\n",
+                              (unsigned int)MAX_SKB_FRAGS);
                        return -EFAULT;
                }
 
@@ -2671,7 +2680,7 @@ static int tpacket_parse_header(struct packet_sock *po, void *frame,
                return -EMSGSIZE;
        }
 
-       if (unlikely(po->tp_tx_has_off)) {
+       if (unlikely(packet_sock_flag(po, PACKET_SOCK_TX_HAS_OFF))) {
                int off_min, off_max;
 
                off_min = po->tp_hdrlen - sizeof(struct sockaddr_ll);
@@ -2722,6 +2731,7 @@ static int tpacket_snd(struct packet_sock *po, struct msghdr *msg)
        void *ph;
        DECLARE_SOCKADDR(struct sockaddr_ll *, saddr, msg->msg_name);
        bool need_wait = !(msg->msg_flags & MSG_DONTWAIT);
+       int vnet_hdr_sz = READ_ONCE(po->vnet_hdr_sz);
        unsigned char *addr = NULL;
        int tp_len, size_max;
        void *data;
@@ -2779,7 +2789,7 @@ static int tpacket_snd(struct packet_sock *po, struct msghdr *msg)
        size_max = po->tx_ring.frame_size
                - (po->tp_hdrlen - sizeof(struct sockaddr_ll));
 
-       if ((size_max > dev->mtu + reserve + VLAN_HLEN) && !po->has_vnet_hdr)
+       if ((size_max > dev->mtu + reserve + VLAN_HLEN) && !vnet_hdr_sz)
                size_max = dev->mtu + reserve + VLAN_HLEN;
 
        reinit_completion(&po->skb_completion);
@@ -2808,10 +2818,10 @@ static int tpacket_snd(struct packet_sock *po, struct msghdr *msg)
                status = TP_STATUS_SEND_REQUEST;
                hlen = LL_RESERVED_SPACE(dev);
                tlen = dev->needed_tailroom;
-               if (po->has_vnet_hdr) {
+               if (vnet_hdr_sz) {
                        vnet_hdr = data;
-                       data += sizeof(*vnet_hdr);
-                       tp_len -= sizeof(*vnet_hdr);
+                       data += vnet_hdr_sz;
+                       tp_len -= vnet_hdr_sz;
                        if (tp_len < 0 ||
                            __packet_snd_vnet_parse(vnet_hdr, tp_len)) {
                                tp_len = -EINVAL;
@@ -2836,13 +2846,13 @@ static int tpacket_snd(struct packet_sock *po, struct msghdr *msg)
                                          addr, hlen, copylen, &sockc);
                if (likely(tp_len >= 0) &&
                    tp_len > dev->mtu + reserve &&
-                   !po->has_vnet_hdr &&
+                   !vnet_hdr_sz &&
                    !packet_extra_vlan_len_allowed(dev, skb))
                        tp_len = -EMSGSIZE;
 
                if (unlikely(tp_len < 0)) {
 tpacket_error:
-                       if (po->tp_loss) {
+                       if (packet_sock_flag(po, PACKET_SOCK_TP_LOSS)) {
                                __packet_set_status(po, ph,
                                                TP_STATUS_AVAILABLE);
                                packet_increment_head(&po->tx_ring);
@@ -2855,7 +2865,7 @@ tpacket_error:
                        }
                }
 
-               if (po->has_vnet_hdr) {
+               if (vnet_hdr_sz) {
                        if (virtio_net_hdr_to_skb(skb, vnet_hdr, vio_le())) {
                                tp_len = -EINVAL;
                                goto tpacket_error;
@@ -2868,8 +2878,7 @@ tpacket_error:
                packet_inc_pending(&po->tx_ring);
 
                status = TP_STATUS_SEND_REQUEST;
-               /* Paired with WRITE_ONCE() in packet_setsockopt() */
-               err = READ_ONCE(po->xmit)(skb);
+               err = packet_xmit(po, skb);
                if (unlikely(err != 0)) {
                        if (err > 0)
                                err = net_xmit_errno(err);
@@ -2946,7 +2955,7 @@ static int packet_snd(struct socket *sock, struct msghdr *msg, size_t len)
        struct virtio_net_hdr vnet_hdr = { 0 };
        int offset = 0;
        struct packet_sock *po = pkt_sk(sk);
-       bool has_vnet_hdr = false;
+       int vnet_hdr_sz = READ_ONCE(po->vnet_hdr_sz);
        int hlen, tlen, linear;
        int extra_len = 0;
 
@@ -2990,11 +2999,10 @@ static int packet_snd(struct socket *sock, struct msghdr *msg, size_t len)
 
        if (sock->type == SOCK_RAW)
                reserve = dev->hard_header_len;
-       if (po->has_vnet_hdr) {
-               err = packet_snd_vnet_parse(msg, &len, &vnet_hdr);
+       if (vnet_hdr_sz) {
+               err = packet_snd_vnet_parse(msg, &len, &vnet_hdr, vnet_hdr_sz);
                if (err)
                        goto out_unlock;
-               has_vnet_hdr = true;
        }
 
        if (unlikely(sock_flag(sk, SOCK_NOFCS))) {
@@ -3064,16 +3072,16 @@ static int packet_snd(struct socket *sock, struct msghdr *msg, size_t len)
 
        packet_parse_headers(skb, sock);
 
-       if (has_vnet_hdr) {
+       if (vnet_hdr_sz) {
                err = virtio_net_hdr_to_skb(skb, &vnet_hdr, vio_le());
                if (err)
                        goto out_free;
-               len += sizeof(vnet_hdr);
+               len += vnet_hdr_sz;
                virtio_net_hdr_set_proto(skb, &vnet_hdr);
        }
 
-       /* Paired with WRITE_ONCE() in packet_setsockopt() */
-       err = READ_ONCE(po->xmit)(skb);
+       err = packet_xmit(po, skb);
+
        if (unlikely(err != 0)) {
                if (err > 0)
                        err = net_xmit_errno(err);
@@ -3220,7 +3228,7 @@ static int packet_do_bind(struct sock *sk, const char *name, int ifindex,
 
        if (need_rehook) {
                dev_hold(dev);
-               if (po->running) {
+               if (packet_sock_flag(po, PACKET_SOCK_RUNNING)) {
                        rcu_read_unlock();
                        /* prevents packet_notifier() from calling
                         * register_prot_hook()
@@ -3233,7 +3241,7 @@ static int packet_do_bind(struct sock *sk, const char *name, int ifindex,
                                                                 dev->ifindex);
                }
 
-               BUG_ON(po->running);
+               BUG_ON(packet_sock_flag(po, PACKET_SOCK_RUNNING));
                WRITE_ONCE(po->num, proto);
                po->prot_hook.type = proto;
 
@@ -3355,7 +3363,6 @@ static int packet_create(struct net *net, struct socket *sock, int protocol,
        init_completion(&po->skb_completion);
        sk->sk_family = PF_PACKET;
        po->num = proto;
-       po->xmit = dev_queue_xmit;
 
        err = packet_alloc_pending(po);
        if (err)
@@ -3409,7 +3416,7 @@ static int packet_recvmsg(struct socket *sock, struct msghdr *msg, size_t len,
        struct sock *sk = sock->sk;
        struct sk_buff *skb;
        int copied, err;
-       int vnet_hdr_len = 0;
+       int vnet_hdr_len = READ_ONCE(pkt_sk(sk)->vnet_hdr_sz);
        unsigned int origlen = 0;
 
        err = -EINVAL;
@@ -3450,11 +3457,10 @@ static int packet_recvmsg(struct socket *sock, struct msghdr *msg, size_t len,
 
        packet_rcv_try_clear_pressure(pkt_sk(sk));
 
-       if (pkt_sk(sk)->has_vnet_hdr) {
-               err = packet_rcv_vnet(msg, skb, &len);
+       if (vnet_hdr_len) {
+               err = packet_rcv_vnet(msg, skb, &len, vnet_hdr_len);
                if (err)
                        goto out_free;
-               vnet_hdr_len = sizeof(struct virtio_net_hdr);
        }
 
        /* You lose any data beyond the buffer you gave. If it worries
@@ -3885,7 +3891,7 @@ packet_setsockopt(struct socket *sock, int level, int optname, sockptr_t optval,
                if (po->rx_ring.pg_vec || po->tx_ring.pg_vec) {
                        ret = -EBUSY;
                } else {
-                       po->tp_loss = !!val;
+                       packet_sock_flag_set(po, PACKET_SOCK_TP_LOSS, val);
                        ret = 0;
                }
                release_sock(sk);
@@ -3916,8 +3922,9 @@ packet_setsockopt(struct socket *sock, int level, int optname, sockptr_t optval,
                return 0;
        }
        case PACKET_VNET_HDR:
+       case PACKET_VNET_HDR_SZ:
        {
-               int val;
+               int val, hdr_len;
 
                if (sock->type != SOCK_RAW)
                        return -EINVAL;
@@ -3926,11 +3933,19 @@ packet_setsockopt(struct socket *sock, int level, int optname, sockptr_t optval,
                if (copy_from_sockptr(&val, optval, sizeof(val)))
                        return -EFAULT;
 
+               if (optname == PACKET_VNET_HDR_SZ) {
+                       if (val && val != sizeof(struct virtio_net_hdr) &&
+                           val != sizeof(struct virtio_net_hdr_mrg_rxbuf))
+                               return -EINVAL;
+                       hdr_len = val;
+               } else {
+                       hdr_len = val ? sizeof(struct virtio_net_hdr) : 0;
+               }
                lock_sock(sk);
                if (po->rx_ring.pg_vec || po->tx_ring.pg_vec) {
                        ret = -EBUSY;
                } else {
-                       po->has_vnet_hdr = !!val;
+                       WRITE_ONCE(po->vnet_hdr_sz, hdr_len);
                        ret = 0;
                }
                release_sock(sk);
@@ -3945,7 +3960,7 @@ packet_setsockopt(struct socket *sock, int level, int optname, sockptr_t optval,
                if (copy_from_sockptr(&val, optval, sizeof(val)))
                        return -EFAULT;
 
-               po->tp_tstamp = val;
+               WRITE_ONCE(po->tp_tstamp, val);
                return 0;
        }
        case PACKET_FANOUT:
@@ -3992,7 +4007,7 @@ packet_setsockopt(struct socket *sock, int level, int optname, sockptr_t optval,
 
                lock_sock(sk);
                if (!po->rx_ring.pg_vec && !po->tx_ring.pg_vec)
-                       po->tp_tx_has_off = !!val;
+                       packet_sock_flag_set(po, PACKET_SOCK_TX_HAS_OFF, val);
 
                release_sock(sk);
                return 0;
@@ -4006,8 +4021,7 @@ packet_setsockopt(struct socket *sock, int level, int optname, sockptr_t optval,
                if (copy_from_sockptr(&val, optval, sizeof(val)))
                        return -EFAULT;
 
-               /* Paired with all lockless reads of po->xmit */
-               WRITE_ONCE(po->xmit, val ? packet_direct_xmit : dev_queue_xmit);
+               packet_sock_flag_set(po, PACKET_SOCK_QDISC_BYPASS, val);
                return 0;
        }
        default:
@@ -4064,7 +4078,10 @@ static int packet_getsockopt(struct socket *sock, int level, int optname,
                val = packet_sock_flag(po, PACKET_SOCK_ORIGDEV);
                break;
        case PACKET_VNET_HDR:
-               val = po->has_vnet_hdr;
+               val = !!READ_ONCE(po->vnet_hdr_sz);
+               break;
+       case PACKET_VNET_HDR_SZ:
+               val = READ_ONCE(po->vnet_hdr_sz);
                break;
        case PACKET_VERSION:
                val = po->tp_version;
@@ -4094,10 +4111,10 @@ static int packet_getsockopt(struct socket *sock, int level, int optname,
                val = po->tp_reserve;
                break;
        case PACKET_LOSS:
-               val = po->tp_loss;
+               val = packet_sock_flag(po, PACKET_SOCK_TP_LOSS);
                break;
        case PACKET_TIMESTAMP:
-               val = po->tp_tstamp;
+               val = READ_ONCE(po->tp_tstamp);
                break;
        case PACKET_FANOUT:
                val = (po->fanout ?
@@ -4119,10 +4136,10 @@ static int packet_getsockopt(struct socket *sock, int level, int optname,
                lv = sizeof(rstats);
                break;
        case PACKET_TX_HAS_OFF:
-               val = po->tp_tx_has_off;
+               val = packet_sock_flag(po, PACKET_SOCK_TX_HAS_OFF);
                break;
        case PACKET_QDISC_BYPASS:
-               val = packet_use_direct_xmit(po);
+               val = packet_sock_flag(po, PACKET_SOCK_QDISC_BYPASS);
                break;
        default:
                return -ENOPROTOOPT;
@@ -4157,7 +4174,7 @@ static int packet_notifier(struct notifier_block *this,
                case NETDEV_DOWN:
                        if (dev->ifindex == po->ifindex) {
                                spin_lock(&po->bind_lock);
-                               if (po->running) {
+                               if (packet_sock_flag(po, PACKET_SOCK_RUNNING)) {
                                        __unregister_prot_hook(sk, false);
                                        sk->sk_err = ENETDOWN;
                                        if (!sock_flag(sk, SOCK_DEAD))
@@ -4468,7 +4485,7 @@ static int packet_set_ring(struct sock *sk, union tpacket_req_u *req_u,
 
        /* Detach socket from network */
        spin_lock(&po->bind_lock);
-       was_running = po->running;
+       was_running = packet_sock_flag(po, PACKET_SOCK_RUNNING);
        num = po->num;
        if (was_running) {
                WRITE_ONCE(po->num, 0);
@@ -4679,7 +4696,7 @@ static int packet_seq_show(struct seq_file *seq, void *v)
                           s->sk_type,
                           ntohs(READ_ONCE(po->num)),
                           READ_ONCE(po->ifindex),
-                          po->running,
+                          packet_sock_flag(po, PACKET_SOCK_RUNNING),
                           atomic_read(&s->sk_rmem_alloc),
                           from_kuid_munged(seq_user_ns(seq), sock_i_uid(s)),
                           sock_i_ino(s));