|
@@ -632,6 +632,7 @@ static void init_prb_bdqc(struct packet_sock *po,
|
|
|
p1->tov_in_jiffies = msecs_to_jiffies(p1->retire_blk_tov);
|
|
|
p1->blk_sizeof_priv = req_u->req3.tp_sizeof_priv;
|
|
|
|
|
|
+ p1->max_frame_len = p1->kblk_size - BLK_PLUS_PRIV(p1->blk_sizeof_priv);
|
|
|
prb_init_ft_ops(p1, req_u);
|
|
|
prb_setup_retire_blk_timer(po, tx_ring);
|
|
|
prb_open_block(p1, pbd);
|
|
@@ -1942,6 +1943,18 @@ static int tpacket_rcv(struct sk_buff *skb, struct net_device *dev,
|
|
|
if ((int)snaplen < 0)
|
|
|
snaplen = 0;
|
|
|
}
|
|
|
+ } else if (unlikely(macoff + snaplen >
|
|
|
+ GET_PBDQC_FROM_RB(&po->rx_ring)->max_frame_len)) {
|
|
|
+ u32 nval;
|
|
|
+
|
|
|
+ nval = GET_PBDQC_FROM_RB(&po->rx_ring)->max_frame_len - macoff;
|
|
|
+ pr_err_once("tpacket_rcv: packet too big, clamped from %u to %u. macoff=%u\n",
|
|
|
+ snaplen, nval, macoff);
|
|
|
+ snaplen = nval;
|
|
|
+ if (unlikely((int)snaplen < 0)) {
|
|
|
+ snaplen = 0;
|
|
|
+ macoff = GET_PBDQC_FROM_RB(&po->rx_ring)->max_frame_len;
|
|
|
+ }
|
|
|
}
|
|
|
spin_lock(&sk->sk_receive_queue.lock);
|
|
|
h.raw = packet_current_rx_frame(po, skb,
|
|
@@ -3783,6 +3796,10 @@ static int packet_set_ring(struct sock *sk, union tpacket_req_u *req_u,
|
|
|
goto out;
|
|
|
if (unlikely(req->tp_block_size & (PAGE_SIZE - 1)))
|
|
|
goto out;
|
|
|
+ if (po->tp_version >= TPACKET_V3 &&
|
|
|
+ (int)(req->tp_block_size -
|
|
|
+ BLK_PLUS_PRIV(req_u->req3.tp_sizeof_priv)) <= 0)
|
|
|
+ goto out;
|
|
|
if (unlikely(req->tp_frame_size < po->tp_hdrlen +
|
|
|
po->tp_reserve))
|
|
|
goto out;
|