Pull networking fixes from Paolo Abeni: "Including fixes from netfilter. Current release - regressions: - revert "net: fix cpu_max_bits_warn() usage in netif_attrmask_next{,_and}" - revert "net: sched: fq_codel: remove redundant resource cleanup in fq_codel_init()" - dsa: uninitialized variable in dsa_slave_netdevice_event() - eth: sunhme: uninitialized variable in happy_meal_init() Current release - new code bugs: - eth: octeontx2: fix resource not freed after malloc Previous releases - regressions: - sched: fix return value of qdisc ingress handling on success - sched: fix race condition in qdisc_graft() - udp: update reuse->has_conns under reuseport_lock. - tls: strp: make sure the TCP skbs do not have overlapping data - hsr: avoid possible NULL deref in skb_clone() - tipc: fix an information leak in tipc_topsrv_kern_subscr - phylink: add mac_managed_pm in phylink_config structure - eth: i40e: fix DMA mappings leak - eth: hyperv: fix a RX-path warning - eth: mtk: fix memory leaks Previous releases - always broken: - sched: cake: fix null pointer access issue when cake_init() fails" * tag 'net-6.1-rc2' of git://git.kernel.org/pub/scm/linux/kernel/git/netdev/net: (43 commits) net: phy: dp83822: disable MDI crossover status change interrupt net: sched: fix race condition in qdisc_graft() net: hns: fix possible memory leak in hnae_ae_register() wwan_hwsim: fix possible memory leak in wwan_hwsim_dev_new() sfc: include vport_id in filter spec hash and equal() genetlink: fix kdoc warnings selftests: add selftest for chaining of tc ingress handling to egress net: Fix return value of qdisc ingress handling on success net: sched: sfb: fix null pointer access issue when sfb_init() fails Revert "net: sched: fq_codel: remove redundant resource cleanup in fq_codel_init()" net: sched: cake: fix null pointer access issue when cake_init() fails ethernet: marvell: octeontx2 Fix resource not freed after malloc netfilter: nf_tables: relax NFTA_SET_ELEM_KEY_END set flags requirements netfilter: rpfilter/fib: Set ->flowic_uid correctly for user namespaces. ionic: catch NULL pointer issue on reconfig net: hsr: avoid possible NULL deref in skb_clone() bnxt_en: fix memory leak in bnxt_nvm_test() ip6mr: fix UAF issue in ip6mr_sk_done() when addrconf_init_net() failed udp: Update reuse->has_conns under reuseport_lock. net: ethernet: mediatek: ppe: Remove the unused function mtk_foe_entry_usable() ...
Unified · Split
| @@ -8,7 +8,6 @@ title: Samsung S3FWRN5 NCI NFC Controller · 7 unmodified lines | ||
| 8 | 8 | |
| 9 | 9 | maintainers: |
| 10 | 10 | - Krzysztof Kozlowski <krzk@kernel.org> |
| 11 | − - Krzysztof Opasiak <k.opasiak@samsung.com> | |
| 12 | 11 | |
| 13 | 12 | properties: |
| 14 | 13 | compatible: |
| @@ -18215,7 +18215,6 @@ F: include/media/drv-intf/s3c_camif.h · 18214 unmodified lines | ||
| 18215 | 18215 | |
| 18216 | 18216 | SAMSUNG S3FWRN5 NFC DRIVER |
| 18217 | 18217 | M: Krzysztof Kozlowski <krzysztof.kozlowski@linaro.org> |
| 18218 | −M: Krzysztof Opasiak <k.opasiak@samsung.com> | |
| 18219 | 18218 | L: linux-nfc@lists.01.org (subscribers-only) |
| 18220 | 18219 | S: Maintained |
| 18221 | 18220 | F: Documentation/devicetree/bindings/net/nfc/samsung,s3fwrn5.yaml |
| @@ -21297,7 +21296,7 @@ L: linux-usb@vger.kernel.org · 3075 unmodified lines | ||
| 21297 | 21296 | L: netdev@vger.kernel.org |
| 21298 | 21297 | S: Maintained |
| 21299 | 21298 | W: https://github.com/petkan/pegasus |
| 21300 | −T: git git://github.com/petkan/pegasus.git | |
| 21299 | +T: git https://github.com/petkan/pegasus.git | |
| 21301 | 21300 | F: drivers/net/usb/pegasus.* |
| 21302 | 21301 | |
| 21303 | 21302 | USB PHY LAYER |
| @@ -21334,7 +21333,7 @@ L: linux-usb@vger.kernel.org · 30 unmodified lines | ||
| 21334 | 21333 | L: netdev@vger.kernel.org |
| 21335 | 21334 | S: Maintained |
| 21336 | 21335 | W: https://github.com/petkan/rtl8150 |
| 21337 | −T: git git://github.com/petkan/rtl8150.git | |
| 21336 | +T: git https://github.com/petkan/rtl8150.git | |
| 21338 | 21337 | F: drivers/net/usb/rtl8150.c |
| 21339 | 21338 | |
| 21340 | 21339 | USB SERIAL SUBSYSTEM |
| @@ -137,27 +137,42 @@ static void qca8k_rw_reg_ack_handler(struct dsa_switch *ds, struct sk_buff *skb) · 136 unmodified lines | ||
| 137 | 137 | struct qca8k_mgmt_eth_data *mgmt_eth_data; |
| 138 | 138 | struct qca8k_priv *priv = ds->priv; |
| 139 | 139 | struct qca_mgmt_ethhdr *mgmt_ethhdr; |
| 140 | + u32 command; | |
| 140 | 141 | u8 len, cmd; |
| 142 | + int i; | |
| 141 | 143 | |
| 142 | 144 | mgmt_ethhdr = (struct qca_mgmt_ethhdr *)skb_mac_header(skb); |
| 143 | 145 | mgmt_eth_data = &priv->mgmt_eth_data; |
| 144 | 146 | |
| 145 | − cmd = FIELD_GET(QCA_HDR_MGMT_CMD, mgmt_ethhdr->command); | |
| 146 | − len = FIELD_GET(QCA_HDR_MGMT_LENGTH, mgmt_ethhdr->command); | |
| 147 | + command = get_unaligned_le32(&mgmt_ethhdr->command); | |
| 148 | + cmd = FIELD_GET(QCA_HDR_MGMT_CMD, command); | |
| 149 | + len = FIELD_GET(QCA_HDR_MGMT_LENGTH, command); | |
| 147 | 150 | |
| 148 | 151 | /* Make sure the seq match the requested packet */ |
| 149 | − if (mgmt_ethhdr->seq == mgmt_eth_data->seq) | |
| 152 | + if (get_unaligned_le32(&mgmt_ethhdr->seq) == mgmt_eth_data->seq) | |
| 150 | 153 | mgmt_eth_data->ack = true; |
| 151 | 154 | |
| 152 | 155 | if (cmd == MDIO_READ) { |
| 153 | − mgmt_eth_data->data[0] = mgmt_ethhdr->mdio_data; | |
| 156 | + u32 *val = mgmt_eth_data->data; | |
| 157 | + | |
| 158 | + *val = get_unaligned_le32(&mgmt_ethhdr->mdio_data); | |
| 154 | 159 | |
| 155 | 160 | /* Get the rest of the 12 byte of data. |
| 156 | 161 | * The read/write function will extract the requested data. |
| 157 | 162 | */ |
| 158 | − if (len > QCA_HDR_MGMT_DATA1_LEN) | |
| 159 | − memcpy(mgmt_eth_data->data + 1, skb->data, | |
| 160 | − QCA_HDR_MGMT_DATA2_LEN); | |
| 163 | + if (len > QCA_HDR_MGMT_DATA1_LEN) { | |
| 164 | + __le32 *data2 = (__le32 *)skb->data; | |
| 165 | + int data_len = min_t(int, QCA_HDR_MGMT_DATA2_LEN, | |
| 166 | + len - QCA_HDR_MGMT_DATA1_LEN); | |
| 167 | + | |
| 168 | + val++; | |
| 169 | + | |
| 170 | + for (i = sizeof(u32); i <= data_len; i += sizeof(u32)) { | |
| 171 | + *val = get_unaligned_le32(data2); | |
| 172 | + val++; | |
| 173 | + data2++; | |
| 174 | + } | |
| 175 | + } | |
| 161 | 176 | } |
| 162 | 177 | |
| 163 | 178 | complete(&mgmt_eth_data->rw_done); |
| @@ -169,8 +184,10 @@ static struct sk_buff *qca8k_alloc_mdio_header(enum mdio_cmd cmd, u32 reg, u32 * · 5 unmodified lines | ||
| 169 | 184 | struct qca_mgmt_ethhdr *mgmt_ethhdr; |
| 170 | 185 | unsigned int real_len; |
| 171 | 186 | struct sk_buff *skb; |
| 172 | − u32 *data2; | |
| 187 | + __le32 *data2; | |
| 188 | + u32 command; | |
| 173 | 189 | u16 hdr; |
| 190 | + int i; | |
| 174 | 191 | |
| 175 | 192 | skb = dev_alloc_skb(QCA_HDR_MGMT_PKT_LEN); |
| 176 | 193 | if (!skb) |
| @@ -199,20 +216,32 @@ static struct sk_buff *qca8k_alloc_mdio_header(enum mdio_cmd cmd, u32 reg, u32 * · 22 unmodified lines | ||
| 199 | 216 | hdr |= FIELD_PREP(QCA_HDR_XMIT_DP_BIT, BIT(0)); |
| 200 | 217 | hdr |= FIELD_PREP(QCA_HDR_XMIT_CONTROL, QCA_HDR_XMIT_TYPE_RW_REG); |
| 201 | 218 | |
| 202 | − mgmt_ethhdr->command = FIELD_PREP(QCA_HDR_MGMT_ADDR, reg); | |
| 203 | − mgmt_ethhdr->command |= FIELD_PREP(QCA_HDR_MGMT_LENGTH, real_len); | |
| 204 | − mgmt_ethhdr->command |= FIELD_PREP(QCA_HDR_MGMT_CMD, cmd); | |
| 205 | − mgmt_ethhdr->command |= FIELD_PREP(QCA_HDR_MGMT_CHECK_CODE, | |
| 219 | + command = FIELD_PREP(QCA_HDR_MGMT_ADDR, reg); | |
| 220 | + command |= FIELD_PREP(QCA_HDR_MGMT_LENGTH, real_len); | |
| 221 | + command |= FIELD_PREP(QCA_HDR_MGMT_CMD, cmd); | |
| 222 | + command |= FIELD_PREP(QCA_HDR_MGMT_CHECK_CODE, | |
| 206 | 223 | QCA_HDR_MGMT_CHECK_CODE_VAL); |
| 207 | 224 | |
| 225 | + put_unaligned_le32(command, &mgmt_ethhdr->command); | |
| 226 | + | |
| 208 | 227 | if (cmd == MDIO_WRITE) |
| 209 | − mgmt_ethhdr->mdio_data = *val; | |
| 228 | + put_unaligned_le32(*val, &mgmt_ethhdr->mdio_data); | |
| 210 | 229 | |
| 211 | 230 | mgmt_ethhdr->hdr = htons(hdr); |
| 212 | 231 | |
| 213 | 232 | data2 = skb_put_zero(skb, QCA_HDR_MGMT_DATA2_LEN + QCA_HDR_MGMT_PADDING_LEN); |
| 214 | − if (cmd == MDIO_WRITE && len > QCA_HDR_MGMT_DATA1_LEN) | |
| 215 | − memcpy(data2, val + 1, len - QCA_HDR_MGMT_DATA1_LEN); | |
| 233 | + if (cmd == MDIO_WRITE && len > QCA_HDR_MGMT_DATA1_LEN) { | |
| 234 | + int data_len = min_t(int, QCA_HDR_MGMT_DATA2_LEN, | |
| 235 | + len - QCA_HDR_MGMT_DATA1_LEN); | |
| 236 | + | |
| 237 | + val++; | |
| 238 | + | |
| 239 | + for (i = sizeof(u32); i <= data_len; i += sizeof(u32)) { | |
| 240 | + put_unaligned_le32(*val, data2); | |
| 241 | + data2++; | |
| 242 | + val++; | |
| 243 | + } | |
| 244 | + } | |
| 216 | 245 | |
| 217 | 246 | return skb; |
| 218 | 247 | } |
| @@ -220,9 +249,11 @@ static struct sk_buff *qca8k_alloc_mdio_header(enum mdio_cmd cmd, u32 reg, u32 * · 1 unmodified line | ||
| 220 | 249 | static void qca8k_mdio_header_fill_seq_num(struct sk_buff *skb, u32 seq_num) |
| 221 | 250 | { |
| 222 | 251 | struct qca_mgmt_ethhdr *mgmt_ethhdr; |
| 252 | + u32 seq; | |
| 223 | 253 | |
| 254 | + seq = FIELD_PREP(QCA_HDR_MGMT_SEQ_NUM, seq_num); | |
| 224 | 255 | mgmt_ethhdr = (struct qca_mgmt_ethhdr *)skb->data; |
| 225 | − mgmt_ethhdr->seq = FIELD_PREP(QCA_HDR_MGMT_SEQ_NUM, seq_num); | |
| 256 | + put_unaligned_le32(seq, &mgmt_ethhdr->seq); | |
| 226 | 257 | } |
| 227 | 258 | |
| 228 | 259 | static int qca8k_read_eth(struct qca8k_priv *priv, u32 reg, u32 *val, int len) |
| @@ -1487,9 +1518,9 @@ static void qca8k_mib_autocast_handler(struct dsa_switch *ds, struct sk_buff *sk · 1258 unmodified lines | ||
| 1487 | 1518 | struct qca8k_priv *priv = ds->priv; |
| 1488 | 1519 | const struct qca8k_mib_desc *mib; |
| 1489 | 1520 | struct mib_ethhdr *mib_ethhdr; |
| 1490 | − int i, mib_len, offset = 0; | |
| 1491 | − u64 *data; | |
| 1521 | + __le32 *data2; | |
| 1492 | 1522 | u8 port; |
| 1523 | + int i; | |
| 1493 | 1524 | |
| 1494 | 1525 | mib_ethhdr = (struct mib_ethhdr *)skb_mac_header(skb); |
| 1495 | 1526 | mib_eth_data = &priv->mib_eth_data; |
| @@ -1501,28 +1532,24 @@ static void qca8k_mib_autocast_handler(struct dsa_switch *ds, struct sk_buff *sk · 5 unmodified lines | ||
| 1501 | 1532 | if (port != mib_eth_data->req_port) |
| 1502 | 1533 | goto exit; |
| 1503 | 1534 | |
| 1504 | − data = mib_eth_data->data; | |
| 1535 | + data2 = (__le32 *)skb->data; | |
| 1505 | 1536 | |
| 1506 | 1537 | for (i = 0; i < priv->info->mib_count; i++) { |
| 1507 | 1538 | mib = &ar8327_mib[i]; |
| 1508 | 1539 | |
| 1509 | 1540 | /* First 3 mib are present in the skb head */ |
| 1510 | 1541 | if (i < 3) { |
| 1511 | − data[i] = mib_ethhdr->data[i]; | |
| 1542 | + mib_eth_data->data[i] = get_unaligned_le32(mib_ethhdr->data + i); | |
| 1512 | 1543 | continue; |
| 1513 | 1544 | } |
| 1514 | 1545 | |
| 1515 | − mib_len = sizeof(uint32_t); | |
| 1516 | − | |
| 1517 | 1546 | /* Some mib are 64 bit wide */ |
| 1518 | 1547 | if (mib->size == 2) |
| 1519 | − mib_len = sizeof(uint64_t); | |
| 1520 | − | |
| 1521 | − /* Copy the mib value from packet to the */ | |
| 1522 | − memcpy(data + i, skb->data + offset, mib_len); | |
| 1548 | + mib_eth_data->data[i] = get_unaligned_le64((__le64 *)data2); | |
| 1549 | + else | |
| 1550 | + mib_eth_data->data[i] = get_unaligned_le32(data2); | |
| 1523 | 1551 | |
| 1524 | − /* Set the offset for the next mib */ | |
| 1525 | − offset += mib_len; | |
| 1552 | + data2 += mib->size; | |
| 1526 | 1553 | } |
| 1527 | 1554 | |
| 1528 | 1555 | exit: |
| @@ -613,6 +613,7 @@ static int bnxt_dl_reload_up(struct devlink *dl, enum devlink_reload_action acti · 612 unmodified lines | ||
| 613 | 613 | |
| 614 | 614 | static bool bnxt_nvm_test(struct bnxt *bp, struct netlink_ext_ack *extack) |
| 615 | 615 | { |
| 616 | + bool rc = false; | |
| 616 | 617 | u32 datalen; |
| 617 | 618 | u16 index; |
| 618 | 619 | u8 *buf; |
| @@ -632,20 +633,20 @@ static bool bnxt_nvm_test(struct bnxt *bp, struct netlink_ext_ack *extack) · 13 unmodified lines | ||
| 632 | 633 | |
| 633 | 634 | if (bnxt_get_nvram_item(bp->dev, index, 0, datalen, buf)) { |
| 634 | 635 | NL_SET_ERR_MSG_MOD(extack, "nvm test vpd read error"); |
| 635 | − goto err; | |
| 636 | + goto done; | |
| 636 | 637 | } |
| 637 | 638 | |
| 638 | 639 | if (bnxt_flash_nvram(bp->dev, BNX_DIR_TYPE_VPD, BNX_DIR_ORDINAL_FIRST, |
| 639 | 640 | BNX_DIR_EXT_NONE, 0, 0, buf, datalen)) { |
| 640 | 641 | NL_SET_ERR_MSG_MOD(extack, "nvm test vpd write error"); |
| 641 | − goto err; | |
| 642 | + goto done; | |
| 642 | 643 | } |
| 643 | 644 | |
| 644 | − return true; | |
| 645 | + rc = true; | |
| 645 | 646 | |
| 646 | −err: | |
| 647 | +done: | |
| 647 | 648 | kfree(buf); |
| 648 | − return false; | |
| 649 | + return rc; | |
| 649 | 650 | } |
| 650 | 651 | |
| 651 | 652 | static bool bnxt_dl_selftest_check(struct devlink *dl, unsigned int id, |
| @@ -419,8 +419,10 @@ int hnae_ae_register(struct hnae_ae_dev *hdev, struct module *owner) · 418 unmodified lines | ||
| 419 | 419 | hdev->cls_dev.release = hnae_release; |
| 420 | 420 | (void)dev_set_name(&hdev->cls_dev, "hnae%d", hdev->id); |
| 421 | 421 | ret = device_register(&hdev->cls_dev); |
| 422 | − if (ret) | |
| 422 | + if (ret) { | |
| 423 | + put_device(&hdev->cls_dev); | |
| 423 | 424 | return ret; |
| 425 | + } | |
| 424 | 426 | |
| 425 | 427 | __module_get(THIS_MODULE); |
| 426 | 428 | |
| @@ -2181,9 +2181,6 @@ static int i40e_set_ringparam(struct net_device *netdev, · 2180 unmodified lines | ||
| 2181 | 2181 | */ |
| 2182 | 2182 | rx_rings[i].tail = hw->hw_addr + I40E_PRTGEN_STATUS; |
| 2183 | 2183 | err = i40e_setup_rx_descriptors(&rx_rings[i]); |
| 2184 | − if (err) | |
| 2185 | − goto rx_unwind; | |
| 2186 | − err = i40e_alloc_rx_bi(&rx_rings[i]); | |
| 2187 | 2184 | if (err) |
| 2188 | 2185 | goto rx_unwind; |
| 2189 | 2186 | |
| @@ -3566,12 +3566,8 @@ static int i40e_configure_rx_ring(struct i40e_ring *ring) · 3565 unmodified lines | ||
| 3566 | 3566 | if (ring->vsi->type == I40E_VSI_MAIN) |
| 3567 | 3567 | xdp_rxq_info_unreg_mem_model(&ring->xdp_rxq); |
| 3568 | 3568 | |
| 3569 | − kfree(ring->rx_bi); | |
| 3570 | 3569 | ring->xsk_pool = i40e_xsk_pool(ring); |
| 3571 | 3570 | if (ring->xsk_pool) { |
| 3572 | − ret = i40e_alloc_rx_bi_zc(ring); | |
| 3573 | − if (ret) | |
| 3574 | − return ret; | |
| 3575 | 3571 | ring->rx_buf_len = |
| 3576 | 3572 | xsk_pool_get_rx_frame_size(ring->xsk_pool); |
| 3577 | 3573 | /* For AF_XDP ZC, we disallow packets to span on |
| @@ -3589,9 +3585,6 @@ static int i40e_configure_rx_ring(struct i40e_ring *ring) · 11 unmodified lines | ||
| 3589 | 3585 | ring->queue_index); |
| 3590 | 3586 | |
| 3591 | 3587 | } else { |
| 3592 | − ret = i40e_alloc_rx_bi(ring); | |
| 3593 | − if (ret) | |
| 3594 | − return ret; | |
| 3595 | 3588 | ring->rx_buf_len = vsi->rx_buf_len; |
| 3596 | 3589 | if (ring->vsi->type == I40E_VSI_MAIN) { |
| 3597 | 3590 | ret = xdp_rxq_info_reg_mem_model(&ring->xdp_rxq, |
| @@ -13296,6 +13289,14 @@ static int i40e_xdp_setup(struct i40e_vsi *vsi, struct bpf_prog *prog, · 9698 unmodified lines | ||
| 13296 | 13289 | i40e_reset_and_rebuild(pf, true, true); |
| 13297 | 13290 | } |
| 13298 | 13291 | |
| 13292 | + if (!i40e_enabled_xdp_vsi(vsi) && prog) { | |
| 13293 | + if (i40e_realloc_rx_bi_zc(vsi, true)) | |
| 13294 | + return -ENOMEM; | |
| 13295 | + } else if (i40e_enabled_xdp_vsi(vsi) && !prog) { | |
| 13296 | + if (i40e_realloc_rx_bi_zc(vsi, false)) | |
| 13297 | + return -ENOMEM; | |
| 13298 | + } | |
| 13299 | + | |
| 13299 | 13300 | for (i = 0; i < vsi->num_queue_pairs; i++) |
| 13300 | 13301 | WRITE_ONCE(vsi->rx_rings[i]->xdp_prog, vsi->xdp_prog); |
| 13301 | 13302 | |
| @@ -13528,6 +13529,7 @@ int i40e_queue_pair_disable(struct i40e_vsi *vsi, int queue_pair) · 226 unmodified lines | ||
| 13528 | 13529 | |
| 13529 | 13530 | i40e_queue_pair_disable_irq(vsi, queue_pair); |
| 13530 | 13531 | err = i40e_queue_pair_toggle_rings(vsi, queue_pair, false /* off */); |
| 13532 | + i40e_clean_rx_ring(vsi->rx_rings[queue_pair]); | |
| 13531 | 13533 | i40e_queue_pair_toggle_napi(vsi, queue_pair, false /* off */); |
| 13532 | 13534 | i40e_queue_pair_clean_rings(vsi, queue_pair); |
| 13533 | 13535 | i40e_queue_pair_reset_stats(vsi, queue_pair); |
| @@ -1457,14 +1457,6 @@ err: · 1456 unmodified lines | ||
| 1457 | 1457 | return -ENOMEM; |
| 1458 | 1458 | } |
| 1459 | 1459 | |
| 1460 | −int i40e_alloc_rx_bi(struct i40e_ring *rx_ring) | |
| 1461 | −{ | |
| 1462 | − unsigned long sz = sizeof(*rx_ring->rx_bi) * rx_ring->count; | |
| 1463 | − | |
| 1464 | − rx_ring->rx_bi = kzalloc(sz, GFP_KERNEL); | |
| 1465 | − return rx_ring->rx_bi ? 0 : -ENOMEM; | |
| 1466 | −} | |
| 1467 | − | |
| 1468 | 1460 | static void i40e_clear_rx_bi(struct i40e_ring *rx_ring) |
| 1469 | 1461 | { |
| 1470 | 1462 | memset(rx_ring->rx_bi, 0, sizeof(*rx_ring->rx_bi) * rx_ring->count); |
| @@ -1593,6 +1585,11 @@ int i40e_setup_rx_descriptors(struct i40e_ring *rx_ring) · 122 unmodified lines | ||
| 1593 | 1585 | |
| 1594 | 1586 | rx_ring->xdp_prog = rx_ring->vsi->xdp_prog; |
| 1595 | 1587 | |
| 1588 | + rx_ring->rx_bi = | |
| 1589 | + kcalloc(rx_ring->count, sizeof(*rx_ring->rx_bi), GFP_KERNEL); | |
| 1590 | + if (!rx_ring->rx_bi) | |
| 1591 | + return -ENOMEM; | |
| 1592 | + | |
| 1596 | 1593 | return 0; |
| 1597 | 1594 | } |
| 1598 | 1595 | |
| @@ -469,7 +469,6 @@ int __i40e_maybe_stop_tx(struct i40e_ring *tx_ring, int size); · 468 unmodified lines | ||
| 469 | 469 | bool __i40e_chk_linearize(struct sk_buff *skb); |
| 470 | 470 | int i40e_xdp_xmit(struct net_device *dev, int n, struct xdp_frame **frames, |
| 471 | 471 | u32 flags); |
| 472 | −int i40e_alloc_rx_bi(struct i40e_ring *rx_ring); | |
| 473 | 472 | |
| 474 | 473 | /** |
| 475 | 474 | * i40e_get_head - Retrieve head from head writeback |
| @@ -10,14 +10,6 @@ · 9 unmodified lines | ||
| 10 | 10 | #include "i40e_txrx_common.h" |
| 11 | 11 | #include "i40e_xsk.h" |
| 12 | 12 | |
| 13 | −int i40e_alloc_rx_bi_zc(struct i40e_ring *rx_ring) | |
| 14 | −{ | |
| 15 | − unsigned long sz = sizeof(*rx_ring->rx_bi_zc) * rx_ring->count; | |
| 16 | − | |
| 17 | − rx_ring->rx_bi_zc = kzalloc(sz, GFP_KERNEL); | |
| 18 | − return rx_ring->rx_bi_zc ? 0 : -ENOMEM; | |
| 19 | −} | |
| 20 | − | |
| 21 | 13 | void i40e_clear_rx_bi_zc(struct i40e_ring *rx_ring) |
| 22 | 14 | { |
| 23 | 15 | memset(rx_ring->rx_bi_zc, 0, |
| @@ -29,6 +21,58 @@ static struct xdp_buff **i40e_rx_bi(struct i40e_ring *rx_ring, u32 idx) · 5 unmodified lines | ||
| 29 | 21 | return &rx_ring->rx_bi_zc[idx]; |
| 30 | 22 | } |
| 31 | 23 | |
| 24 | +/** | |
| 25 | + * i40e_realloc_rx_xdp_bi - reallocate SW ring for either XSK or normal buffer | |
| 26 | + * @rx_ring: Current rx ring | |
| 27 | + * @pool_present: is pool for XSK present | |
| 28 | + * | |
| 29 | + * Try allocating memory and return ENOMEM, if failed to allocate. | |
| 30 | + * If allocation was successful, substitute buffer with allocated one. | |
| 31 | + * Returns 0 on success, negative on failure | |
| 32 | + */ | |
| 33 | +static int i40e_realloc_rx_xdp_bi(struct i40e_ring *rx_ring, bool pool_present) | |
| 34 | +{ | |
| 35 | + size_t elem_size = pool_present ? sizeof(*rx_ring->rx_bi_zc) : | |
| 36 | + sizeof(*rx_ring->rx_bi); | |
| 37 | + void *sw_ring = kcalloc(rx_ring->count, elem_size, GFP_KERNEL); | |
| 38 | + | |
| 39 | + if (!sw_ring) | |
| 40 | + return -ENOMEM; | |
| 41 | + | |
| 42 | + if (pool_present) { | |
| 43 | + kfree(rx_ring->rx_bi); | |
| 44 | + rx_ring->rx_bi = NULL; | |
| 45 | + rx_ring->rx_bi_zc = sw_ring; | |
| 46 | + } else { | |
| 47 | + kfree(rx_ring->rx_bi_zc); | |
| 48 | + rx_ring->rx_bi_zc = NULL; | |
| 49 | + rx_ring->rx_bi = sw_ring; | |
| 50 | + } | |
| 51 | + return 0; | |
| 52 | +} | |
| 53 | + | |
| 54 | +/** | |
| 55 | + * i40e_realloc_rx_bi_zc - reallocate rx SW rings | |
| 56 | + * @vsi: Current VSI | |
| 57 | + * @zc: is zero copy set | |
| 58 | + * | |
| 59 | + * Reallocate buffer for rx_rings that might be used by XSK. | |
| 60 | + * XDP requires more memory, than rx_buf provides. | |
| 61 | + * Returns 0 on success, negative on failure | |
| 62 | + */ | |
| 63 | +int i40e_realloc_rx_bi_zc(struct i40e_vsi *vsi, bool zc) | |
| 64 | +{ | |
| 65 | + struct i40e_ring *rx_ring; | |
| 66 | + unsigned long q; | |
| 67 | + | |
| 68 | + for_each_set_bit(q, vsi->af_xdp_zc_qps, vsi->alloc_queue_pairs) { | |
| 69 | + rx_ring = vsi->rx_rings[q]; | |
| 70 | + if (i40e_realloc_rx_xdp_bi(rx_ring, zc)) | |
| 71 | + return -ENOMEM; | |
| 72 | + } | |
| 73 | + return 0; | |
| 74 | +} | |
| 75 | + | |
| 32 | 76 | /** |
| 33 | 77 | * i40e_xsk_pool_enable - Enable/associate an AF_XDP buffer pool to a |
| 34 | 78 | * certain ring/qid |
| @@ -69,6 +113,10 @@ static int i40e_xsk_pool_enable(struct i40e_vsi *vsi, · 34 unmodified lines | ||
| 69 | 113 | if (err) |
| 70 | 114 | return err; |
| 71 | 115 | |
| 116 | + err = i40e_realloc_rx_xdp_bi(vsi->rx_rings[qid], true); | |
| 117 | + if (err) | |
| 118 | + return err; | |
| 119 | + | |
| 72 | 120 | err = i40e_queue_pair_enable(vsi, qid); |
| 73 | 121 | if (err) |
| 74 | 122 | return err; |
| @@ -113,6 +161,9 @@ static int i40e_xsk_pool_disable(struct i40e_vsi *vsi, u16 qid) · 38 unmodified lines | ||
| 113 | 161 | xsk_pool_dma_unmap(pool, I40E_RX_DMA_ATTR); |
| 114 | 162 | |
| 115 | 163 | if (if_running) { |
| 164 | + err = i40e_realloc_rx_xdp_bi(vsi->rx_rings[qid], false); | |
| 165 | + if (err) | |
| 166 | + return err; | |
| 116 | 167 | err = i40e_queue_pair_enable(vsi, qid); |
| 117 | 168 | if (err) |
| 118 | 169 | return err; |
| @@ -32,7 +32,7 @@ int i40e_clean_rx_irq_zc(struct i40e_ring *rx_ring, int budget); · 31 unmodified lines | ||
| 32 | 32 | |
| 33 | 33 | bool i40e_clean_xdp_tx_irq(struct i40e_vsi *vsi, struct i40e_ring *tx_ring); |
| 34 | 34 | int i40e_xsk_wakeup(struct net_device *dev, u32 queue_id, u32 flags); |
| 35 | −int i40e_alloc_rx_bi_zc(struct i40e_ring *rx_ring); | |
| 35 | +int i40e_realloc_rx_bi_zc(struct i40e_vsi *vsi, bool zc); | |
| 36 | 36 | void i40e_clear_rx_bi_zc(struct i40e_ring *rx_ring); |
| 37 | 37 | |
| 38 | 38 | #endif /* _I40E_XSK_H_ */ |
| @@ -815,6 +815,7 @@ free_flowid: · 814 unmodified lines | ||
| 815 | 815 | cn10k_mcs_free_rsrc(pfvf, MCS_TX, MCS_RSRC_TYPE_FLOWID, |
| 816 | 816 | txsc->hw_flow_id, false); |
| 817 | 817 | fail: |
| 818 | + kfree(txsc); | |
| 818 | 819 | return ERR_PTR(ret); |
| 819 | 820 | } |
| 820 | 821 | |
| @@ -870,6 +871,7 @@ free_flowid: · 49 unmodified lines | ||
| 870 | 871 | cn10k_mcs_free_rsrc(pfvf, MCS_RX, MCS_RSRC_TYPE_FLOWID, |
| 871 | 872 | rxsc->hw_flow_id, false); |
| 872 | 873 | fail: |
| 874 | + kfree(rxsc); | |
| 873 | 875 | return ERR_PTR(ret); |
| 874 | 876 | } |
| 875 | 877 | |
| @@ -4060,19 +4060,23 @@ static int mtk_probe(struct platform_device *pdev) · 4059 unmodified lines | ||
| 4060 | 4060 | eth->irq[i] = platform_get_irq(pdev, i); |
| 4061 | 4061 | if (eth->irq[i] < 0) { |
| 4062 | 4062 | dev_err(&pdev->dev, "no IRQ%d resource found\n", i); |
| 4063 | − return -ENXIO; | |
| 4063 | + err = -ENXIO; | |
| 4064 | + goto err_wed_exit; | |
| 4064 | 4065 | } |
| 4065 | 4066 | } |
| 4066 | 4067 | for (i = 0; i < ARRAY_SIZE(eth->clks); i++) { |
| 4067 | 4068 | eth->clks[i] = devm_clk_get(eth->dev, |
| 4068 | 4069 | mtk_clks_source_name[i]); |
| 4069 | 4070 | if (IS_ERR(eth->clks[i])) { |
| 4070 | − if (PTR_ERR(eth->clks[i]) == -EPROBE_DEFER) | |
| 4071 | − return -EPROBE_DEFER; | |
| 4071 | + if (PTR_ERR(eth->clks[i]) == -EPROBE_DEFER) { | |
| 4072 | + err = -EPROBE_DEFER; | |
| 4073 | + goto err_wed_exit; | |
| 4074 | + } | |
| 4072 | 4075 | if (eth->soc->required_clks & BIT(i)) { |
| 4073 | 4076 | dev_err(&pdev->dev, "clock %s not found\n", |
| 4074 | 4077 | mtk_clks_source_name[i]); |
| 4075 | − return -EINVAL; | |
| 4078 | + err = -EINVAL; | |
| 4079 | + goto err_wed_exit; | |
| 4076 | 4080 | } |
| 4077 | 4081 | eth->clks[i] = NULL; |
| 4078 | 4082 | } |
| @@ -4083,7 +4087,7 @@ static int mtk_probe(struct platform_device *pdev) · 4 unmodified lines | ||
| 4083 | 4087 | |
| 4084 | 4088 | err = mtk_hw_init(eth); |
| 4085 | 4089 | if (err) |
| 4086 | − return err; | |
| 4090 | + goto err_wed_exit; | |
| 4087 | 4091 | |
| 4088 | 4092 | eth->hwlro = MTK_HAS_CAPS(eth->soc->caps, MTK_HWLRO); |
| 4089 | 4093 | |
| @@ -4179,6 +4183,8 @@ err_free_dev: · 89 unmodified lines | ||
| 4179 | 4183 | mtk_free_dev(eth); |
| 4180 | 4184 | err_deinit_hw: |
| 4181 | 4185 | mtk_hw_deinit(eth); |
| 4186 | +err_wed_exit: | |
| 4187 | + mtk_wed_exit(); | |
| 4182 | 4188 | |
| 4183 | 4189 | return err; |
| 4184 | 4190 | } |
| @@ -4198,6 +4204,7 @@ static int mtk_remove(struct platform_device *pdev) · 13 unmodified lines | ||
| 4198 | 4204 | phylink_disconnect_phy(mac->phylink); |
| 4199 | 4205 | } |
| 4200 | 4206 | |
| 4207 | + mtk_wed_exit(); | |
| 4201 | 4208 | mtk_hw_deinit(eth); |
| 4202 | 4209 | |
| 4203 | 4210 | netif_napi_del(ð->tx_napi); |
| @@ -397,12 +397,6 @@ int mtk_foe_entry_set_wdma(struct mtk_eth *eth, struct mtk_foe_entry *entry, · 396 unmodified lines | ||
| 397 | 397 | return 0; |
| 398 | 398 | } |
| 399 | 399 | |
| 400 | −static inline bool mtk_foe_entry_usable(struct mtk_foe_entry *entry) | |
| 401 | −{ | |
| 402 | − return !(entry->ib1 & MTK_FOE_IB1_STATIC) && | |
| 403 | − FIELD_GET(MTK_FOE_IB1_STATE, entry->ib1) != MTK_FOE_STATE_BIND; | |
| 404 | −} | |
| 405 | − | |
| 406 | 400 | static bool |
| 407 | 401 | mtk_flow_entry_match(struct mtk_eth *eth, struct mtk_flow_entry *entry, |
| 408 | 402 | struct mtk_foe_entry *data) |
| @@ -1072,16 +1072,16 @@ void mtk_wed_add_hw(struct device_node *np, struct mtk_eth *eth, · 1071 unmodified lines | ||
| 1072 | 1072 | |
| 1073 | 1073 | pdev = of_find_device_by_node(np); |
| 1074 | 1074 | if (!pdev) |
| 1075 | − return; | |
| 1075 | + goto err_of_node_put; | |
| 1076 | 1076 | |
| 1077 | 1077 | get_device(&pdev->dev); |
| 1078 | 1078 | irq = platform_get_irq(pdev, 0); |
| 1079 | 1079 | if (irq < 0) |
| 1080 | − return; | |
| 1080 | + goto err_put_device; | |
| 1081 | 1081 | |
| 1082 | 1082 | regs = syscon_regmap_lookup_by_phandle(np, NULL); |
| 1083 | 1083 | if (IS_ERR(regs)) |
| 1084 | − return; | |
| 1084 | + goto err_put_device; | |
| 1085 | 1085 | |
| 1086 | 1086 | rcu_assign_pointer(mtk_soc_wed_ops, &wed_ops); |
| 1087 | 1087 | |
| @@ -1124,8 +1124,16 @@ void mtk_wed_add_hw(struct device_node *np, struct mtk_eth *eth, · 36 unmodified lines | ||
| 1124 | 1124 | |
| 1125 | 1125 | hw_list[index] = hw; |
| 1126 | 1126 | |
| 1127 | + mutex_unlock(&hw_lock); | |
| 1128 | + | |
| 1129 | + return; | |
| 1130 | + | |
| 1127 | 1131 | unlock: |
| 1128 | 1132 | mutex_unlock(&hw_lock); |
| 1133 | +err_put_device: | |
| 1134 | + put_device(&pdev->dev); | |
| 1135 | +err_of_node_put: | |
| 1136 | + of_node_put(np); | |
| 1129 | 1137 | } |
| 1130 | 1138 | |
| 1131 | 1139 | void mtk_wed_exit(void) |
| @@ -1146,6 +1154,7 @@ void mtk_wed_exit(void) · 14 unmodified lines | ||
| 1146 | 1154 | hw_list[i] = NULL; |
| 1147 | 1155 | debugfs_remove(hw->debugfs_dir); |
| 1148 | 1156 | put_device(hw->dev); |
| 1157 | + of_node_put(hw->node); | |
| 1149 | 1158 | kfree(hw); |
| 1150 | 1159 | } |
| 1151 | 1160 | } |
| @@ -2817,11 +2817,15 @@ err_out: · 2816 unmodified lines | ||
| 2817 | 2817 | * than the full array, but leave the qcq shells in place |
| 2818 | 2818 | */ |
| 2819 | 2819 | for (i = lif->nxqs; i < lif->ionic->ntxqs_per_lif; i++) { |
| 2820 | − lif->txqcqs[i]->flags &= ~IONIC_QCQ_F_INTR; | |
| 2821 | − ionic_qcq_free(lif, lif->txqcqs[i]); | |
| 2820 | + if (lif->txqcqs && lif->txqcqs[i]) { | |
| 2821 | + lif->txqcqs[i]->flags &= ~IONIC_QCQ_F_INTR; | |
| 2822 | + ionic_qcq_free(lif, lif->txqcqs[i]); | |
| 2823 | + } | |
| 2822 | 2824 | |
| 2823 | − lif->rxqcqs[i]->flags &= ~IONIC_QCQ_F_INTR; | |
| 2824 | − ionic_qcq_free(lif, lif->rxqcqs[i]); | |
| 2825 | + if (lif->rxqcqs && lif->rxqcqs[i]) { | |
| 2826 | + lif->rxqcqs[i]->flags &= ~IONIC_QCQ_F_INTR; | |
| 2827 | + ionic_qcq_free(lif, lif->rxqcqs[i]); | |
| 2828 | + } | |
| 2825 | 2829 | } |
| 2826 | 2830 | |
| 2827 | 2831 | if (err) |
| @@ -3277,6 +3277,30 @@ static int efx_ef10_set_mac_address(struct efx_nic *efx) · 3276 unmodified lines | ||
| 3277 | 3277 | bool was_enabled = efx->port_enabled; |
| 3278 | 3278 | int rc; |
| 3279 | 3279 | |
| 3280 | +#ifdef CONFIG_SFC_SRIOV | |
| 3281 | + /* If this function is a VF and we have access to the parent PF, | |
| 3282 | + * then use the PF control path to attempt to change the VF MAC address. | |
| 3283 | + */ | |
| 3284 | + if (efx->pci_dev->is_virtfn && efx->pci_dev->physfn) { | |
| 3285 | + struct efx_nic *efx_pf = pci_get_drvdata(efx->pci_dev->physfn); | |
| 3286 | + struct efx_ef10_nic_data *nic_data = efx->nic_data; | |
| 3287 | + u8 mac[ETH_ALEN]; | |
| 3288 | + | |
| 3289 | + /* net_dev->dev_addr can be zeroed by efx_net_stop in | |
| 3290 | + * efx_ef10_sriov_set_vf_mac, so pass in a copy. | |
| 3291 | + */ | |
| 3292 | + ether_addr_copy(mac, efx->net_dev->dev_addr); | |
| 3293 | + | |
| 3294 | + rc = efx_ef10_sriov_set_vf_mac(efx_pf, nic_data->vf_index, mac); | |
| 3295 | + if (!rc) | |
| 3296 | + return 0; | |
| 3297 | + | |
| 3298 | + netif_dbg(efx, drv, efx->net_dev, | |
| 3299 | + "Updating VF mac via PF failed (%d), setting directly\n", | |
| 3300 | + rc); | |
| 3301 | + } | |
| 3302 | +#endif | |
| 3303 | + | |
| 3280 | 3304 | efx_device_detach_sync(efx); |
| 3281 | 3305 | efx_net_stop(efx->net_dev); |
| 3282 | 3306 | |
| @@ -3297,40 +3321,6 @@ static int efx_ef10_set_mac_address(struct efx_nic *efx) · 14 unmodified lines | ||
| 3297 | 3321 | efx_net_open(efx->net_dev); |
| 3298 | 3322 | efx_device_attach_if_not_resetting(efx); |
| 3299 | 3323 | |
| 3300 | −#ifdef CONFIG_SFC_SRIOV | |
| 3301 | − if (efx->pci_dev->is_virtfn && efx->pci_dev->physfn) { | |
| 3302 | − struct efx_ef10_nic_data *nic_data = efx->nic_data; | |
| 3303 | − struct pci_dev *pci_dev_pf = efx->pci_dev->physfn; | |
| 3304 | − | |
| 3305 | − if (rc == -EPERM) { | |
| 3306 | − struct efx_nic *efx_pf; | |
| 3307 | − | |
| 3308 | − /* Switch to PF and change MAC address on vport */ | |
| 3309 | − efx_pf = pci_get_drvdata(pci_dev_pf); | |
| 3310 | − | |
| 3311 | − rc = efx_ef10_sriov_set_vf_mac(efx_pf, | |
| 3312 | − nic_data->vf_index, | |
| 3313 | − efx->net_dev->dev_addr); | |
| 3314 | − } else if (!rc) { | |
| 3315 | − struct efx_nic *efx_pf = pci_get_drvdata(pci_dev_pf); | |
| 3316 | − struct efx_ef10_nic_data *nic_data = efx_pf->nic_data; | |
| 3317 | − unsigned int i; | |
| 3318 | − | |
| 3319 | − /* MAC address successfully changed by VF (with MAC | |
| 3320 | − * spoofing) so update the parent PF if possible. | |
| 3321 | − */ | |
| 3322 | − for (i = 0; i < efx_pf->vf_count; ++i) { | |
| 3323 | − struct ef10_vf *vf = nic_data->vf + i; | |
| 3324 | − | |
| 3325 | − if (vf->efx == efx) { | |
| 3326 | − ether_addr_copy(vf->mac, | |
| 3327 | − efx->net_dev->dev_addr); | |
| 3328 | − return 0; | |
| 3329 | − } | |
| 3330 | − } | |
| 3331 | − } | |
| 3332 | − } else | |
| 3333 | −#endif | |
| 3334 | 3324 | if (rc == -EPERM) { |
| 3335 | 3325 | netif_err(efx, drv, efx->net_dev, |
| 3336 | 3326 | "Cannot change MAC address; use sfboot to enable" |
| @@ -162,9 +162,9 @@ struct efx_filter_spec { · 161 unmodified lines | ||
| 162 | 162 | u32 priority:2; |
| 163 | 163 | u32 flags:6; |
| 164 | 164 | u32 dmaq_id:12; |
| 165 | − u32 vport_id; | |
| 166 | 165 | u32 rss_context; |
| 167 | − __be16 outer_vid __aligned(4); /* allow jhash2() of match values */ | |
| 166 | + u32 vport_id; | |
| 167 | + __be16 outer_vid; | |
| 168 | 168 | __be16 inner_vid; |
| 169 | 169 | u8 loc_mac[ETH_ALEN]; |
| 170 | 170 | u8 rem_mac[ETH_ALEN]; |
| @@ -660,17 +660,17 @@ bool efx_filter_spec_equal(const struct efx_filter_spec *left, · 659 unmodified lines | ||
| 660 | 660 | (EFX_FILTER_FLAG_RX | EFX_FILTER_FLAG_TX))) |
| 661 | 661 | return false; |
| 662 | 662 | |
| 663 | − return memcmp(&left->outer_vid, &right->outer_vid, | |
| 663 | + return memcmp(&left->vport_id, &right->vport_id, | |
| 664 | 664 | sizeof(struct efx_filter_spec) - |
| 665 | − offsetof(struct efx_filter_spec, outer_vid)) == 0; | |
| 665 | + offsetof(struct efx_filter_spec, vport_id)) == 0; | |
| 666 | 666 | } |
| 667 | 667 | |
| 668 | 668 | u32 efx_filter_spec_hash(const struct efx_filter_spec *spec) |
| 669 | 669 | { |
| 670 | − BUILD_BUG_ON(offsetof(struct efx_filter_spec, outer_vid) & 3); | |
| 671 | − return jhash2((const u32 *)&spec->outer_vid, | |
| 670 | + BUILD_BUG_ON(offsetof(struct efx_filter_spec, vport_id) & 3); | |
| 671 | + return jhash2((const u32 *)&spec->vport_id, | |
| 672 | 672 | (sizeof(struct efx_filter_spec) - |
| 673 | − offsetof(struct efx_filter_spec, outer_vid)) / 4, | |
| 673 | + offsetof(struct efx_filter_spec, vport_id)) / 4, | |
| 674 | 674 | 0); |
| 675 | 675 | } |
| 676 | 676 | |
| @@ -1214,6 +1214,7 @@ static int stmmac_phy_setup(struct stmmac_priv *priv) · 1213 unmodified lines | ||
| 1214 | 1214 | if (priv->plat->tx_queues_to_use > 1) |
| 1215 | 1215 | priv->phylink_config.mac_capabilities &= |
| 1216 | 1216 | ~(MAC_10HD | MAC_100HD | MAC_1000HD); |
| 1217 | + priv->phylink_config.mac_managed_pm = true; | |
| 1217 | 1218 | |
| 1218 | 1219 | phylink = phylink_create(&priv->phylink_config, fwnode, |
| 1219 | 1220 | mode, &stmmac_phylink_mac_ops); |
| @@ -1328,7 +1328,7 @@ static int happy_meal_init(struct happy_meal *hp) · 1327 unmodified lines | ||
| 1328 | 1328 | void __iomem *erxregs = hp->erxregs; |
| 1329 | 1329 | void __iomem *bregs = hp->bigmacregs; |
| 1330 | 1330 | void __iomem *tregs = hp->tcvregs; |
| 1331 | − const char *bursts; | |
| 1331 | + const char *bursts = "64"; | |
| 1332 | 1332 | u32 regtmp, rxcfg; |
| 1333 | 1333 | |
| 1334 | 1334 | /* If auto-negotiation timer is running, kill it. */ |
| @@ -20,6 +20,7 @@ · 19 unmodified lines | ||
| 20 | 20 | #include <linux/vmalloc.h> |
| 21 | 21 | #include <linux/rtnetlink.h> |
| 22 | 22 | #include <linux/ucs2_string.h> |
| 23 | +#include <linux/string.h> | |
| 23 | 24 | |
| 24 | 25 | #include "hyperv_net.h" |
| 25 | 26 | #include "netvsc_trace.h" |
| @@ -335,9 +336,10 @@ static void rndis_filter_receive_response(struct net_device *ndev, · 309 unmodified lines | ||
| 335 | 336 | if (resp->msg_len <= |
| 336 | 337 | sizeof(struct rndis_message) + RNDIS_EXT_LEN) { |
| 337 | 338 | memcpy(&request->response_msg, resp, RNDIS_HEADER_SIZE + sizeof(*req_id)); |
| 338 | − memcpy((void *)&request->response_msg + RNDIS_HEADER_SIZE + sizeof(*req_id), | |
| 339 | + unsafe_memcpy((void *)&request->response_msg + RNDIS_HEADER_SIZE + sizeof(*req_id), | |
| 339 | 340 | data + RNDIS_HEADER_SIZE + sizeof(*req_id), |
| 340 | − resp->msg_len - RNDIS_HEADER_SIZE - sizeof(*req_id)); | |
| 341 | + resp->msg_len - RNDIS_HEADER_SIZE - sizeof(*req_id), | |
| 342 | + "request->response_msg is followed by a padding of RNDIS_EXT_LEN inside rndis_request"); | |
| 341 | 343 | if (request->request_msg.ndis_msg_type == |
| 342 | 344 | RNDIS_MSG_QUERY && request->request_msg.msg. |
| 343 | 345 | query_req.oid == RNDIS_OID_GEN_MEDIA_CONNECT_STATUS) |
| @@ -361,7 +361,7 @@ static void macvlan_broadcast_enqueue(struct macvlan_port *port, · 360 unmodified lines | ||
| 361 | 361 | } |
| 362 | 362 | spin_unlock(&port->bc_queue.lock); |
| 363 | 363 | |
| 364 | − schedule_work(&port->bc_work); | |
| 364 | + queue_work(system_unbound_wq, &port->bc_work); | |
| 365 | 365 | |
| 366 | 366 | if (err) |
| 367 | 367 | goto free_nskb; |
| @@ -254,8 +254,7 @@ static int dp83822_config_intr(struct phy_device *phydev) · 253 unmodified lines | ||
| 254 | 254 | DP83822_EEE_ERROR_CHANGE_INT_EN); |
| 255 | 255 | |
| 256 | 256 | if (!dp83822->fx_enabled) |
| 257 | − misr_status |= DP83822_MDI_XOVER_INT_EN | | |
| 258 | − DP83822_ANEG_ERR_INT_EN | | |
| 257 | + misr_status |= DP83822_ANEG_ERR_INT_EN | | |
| 259 | 258 | DP83822_WOL_PKT_INT_EN; |
| 260 | 259 | |
| 261 | 260 | err = phy_write(phydev, MII_DP83822_MISR2, misr_status); |
| @@ -853,6 +853,14 @@ static int dp83867_config_init(struct phy_device *phydev) · 852 unmodified lines | ||
| 853 | 853 | else |
| 854 | 854 | val &= ~DP83867_SGMII_TYPE; |
| 855 | 855 | phy_write_mmd(phydev, DP83867_DEVADDR, DP83867_SGMIICTL, val); |
| 856 | + | |
| 857 | + /* This is a SW workaround for link instability if RX_CTRL is | |
| 858 | + * not strapped to mode 3 or 4 in HW. This is required for SGMII | |
| 859 | + * in addition to clearing bit 7, handled above. | |
| 860 | + */ | |
| 861 | + if (dp83867->rxctrl_strap_quirk) | |
| 862 | + phy_set_bits_mmd(phydev, DP83867_DEVADDR, DP83867_CFG4, | |
| 863 | + BIT(8)); | |
| 856 | 864 | } |
| 857 | 865 | |
| 858 | 866 | val = phy_read(phydev, DP83867_CFG3); |
| @@ -1661,6 +1661,9 @@ static int phylink_bringup_phy(struct phylink *pl, struct phy_device *phy, · 1660 unmodified lines | ||
| 1661 | 1661 | if (phy_interrupt_is_valid(phy)) |
| 1662 | 1662 | phy_request_interrupt(phy); |
| 1663 | 1663 | |
| 1664 | + if (pl->config->mac_managed_pm) | |
| 1665 | + phy->mac_managed_pm = true; | |
| 1666 | + | |
| 1664 | 1667 | return 0; |
| 1665 | 1668 | } |
| 1666 | 1669 | |
| @@ -311,7 +311,7 @@ err_unreg_dev: · 310 unmodified lines | ||
| 311 | 311 | return ERR_PTR(err); |
| 312 | 312 | |
| 313 | 313 | err_free_dev: |
| 314 | − kfree(dev); | |
| 314 | + put_device(&dev->dev); | |
| 315 | 315 | |
| 316 | 316 | return ERR_PTR(err); |
| 317 | 317 | } |
| @@ -61,9 +61,9 @@ struct sk_buff; · 60 unmodified lines | ||
| 61 | 61 | |
| 62 | 62 | /* Special struct emulating a Ethernet header */ |
| 63 | 63 | struct qca_mgmt_ethhdr { |
| 64 | − u32 command; /* command bit 31:0 */ | |
| 65 | − u32 seq; /* seq 63:32 */ | |
| 66 | − u32 mdio_data; /* first 4byte mdio */ | |
| 64 | + __le32 command; /* command bit 31:0 */ | |
| 65 | + __le32 seq; /* seq 63:32 */ | |
| 66 | + __le32 mdio_data; /* first 4byte mdio */ | |
| 67 | 67 | __be16 hdr; /* qca hdr */ |
| 68 | 68 | } __packed; |
| 69 | 69 | |
| @@ -73,7 +73,7 @@ enum mdio_cmd { · 3 unmodified lines | ||
| 73 | 73 | }; |
| 74 | 74 | |
| 75 | 75 | struct mib_ethhdr { |
| 76 | − u32 data[3]; /* first 3 mib counter */ | |
| 76 | + __le32 data[3]; /* first 3 mib counter */ | |
| 77 | 77 | __be16 hdr; /* qca hdr */ |
| 78 | 78 | } __packed; |
| 79 | 79 | |
| @@ -3663,8 +3663,9 @@ static inline bool netif_attr_test_online(unsigned long j, · 3662 unmodified lines | ||
| 3663 | 3663 | static inline unsigned int netif_attrmask_next(int n, const unsigned long *srcp, |
| 3664 | 3664 | unsigned int nr_bits) |
| 3665 | 3665 | { |
| 3666 | − /* n is a prior cpu */ | |
| 3667 | − cpu_max_bits_warn(n + 1, nr_bits); | |
| 3666 | + /* -1 is a legal arg here. */ | |
| 3667 | + if (n != -1) | |
| 3668 | + cpu_max_bits_warn(n, nr_bits); | |
| 3668 | 3669 | |
| 3669 | 3670 | if (srcp) |
| 3670 | 3671 | return find_next_bit(srcp, nr_bits, n + 1); |
| @@ -3685,8 +3686,9 @@ static inline int netif_attrmask_next_and(int n, const unsigned long *src1p, · 14 unmodified lines | ||
| 3685 | 3686 | const unsigned long *src2p, |
| 3686 | 3687 | unsigned int nr_bits) |
| 3687 | 3688 | { |
| 3688 | − /* n is a prior cpu */ | |
| 3689 | − cpu_max_bits_warn(n + 1, nr_bits); | |
| 3689 | + /* -1 is a legal arg here. */ | |
| 3690 | + if (n != -1) | |
| 3691 | + cpu_max_bits_warn(n, nr_bits); | |
| 3690 | 3692 | |
| 3691 | 3693 | if (src1p && src2p) |
| 3692 | 3694 | return find_next_and_bit(src1p, src2p, nr_bits, n + 1); |
| @@ -122,6 +122,7 @@ enum phylink_op_type { · 121 unmodified lines | ||
| 122 | 122 | * (See commit 7cceb599d15d ("net: phylink: avoid mac_config calls") |
| 123 | 123 | * @poll_fixed_state: if true, starts link_poll, |
| 124 | 124 | * if MAC link is at %MLO_AN_FIXED mode. |
| 125 | + * @mac_managed_pm: if true, indicate the MAC driver is responsible for PHY PM. | |
| 125 | 126 | * @ovr_an_inband: if true, override PCS to MLO_AN_INBAND |
| 126 | 127 | * @get_fixed_state: callback to execute to determine the fixed link state, |
| 127 | 128 | * if MAC link is at %MLO_AN_FIXED mode. |
| @@ -134,6 +135,7 @@ struct phylink_config { · 6 unmodified lines | ||
| 134 | 135 | enum phylink_op_type type; |
| 135 | 136 | bool legacy_pre_march2020; |
| 136 | 137 | bool poll_fixed_state; |
| 138 | + bool mac_managed_pm; | |
| 137 | 139 | bool ovr_an_inband; |
| 138 | 140 | void (*get_fixed_state)(struct phylink_config *config, |
| 139 | 141 | struct phylink_link_state *state); |
| @@ -37,6 +37,7 @@ struct genl_info; · 36 unmodified lines | ||
| 37 | 37 | * do additional, common, filtering and return an error |
| 38 | 38 | * @post_doit: called after an operation's doit callback, it may |
| 39 | 39 | * undo operations done by pre_doit, for example release locks |
| 40 | + * @module: pointer to the owning module (set to THIS_MODULE) | |
| 40 | 41 | * @mcgrps: multicast groups used by this family |
| 41 | 42 | * @n_mcgrps: number of multicast groups |
| 42 | 43 | * @resv_start_op: first operation for which reserved fields of the header |
| @@ -173,9 +174,9 @@ struct genl_ops { · 130 unmodified lines | ||
| 173 | 174 | }; |
| 174 | 175 | |
| 175 | 176 | /** |
| 176 | − * struct genl_info - info that is available during dumpit op call | |
| 177 | + * struct genl_dumpit_info - info that is available during dumpit op call | |
| 177 | 178 | * @family: generic netlink family - for internal genl code usage |
| 178 | − * @ops: generic netlink ops - for internal genl code usage | |
| 179 | + * @op: generic netlink ops - for internal genl code usage | |
| 179 | 180 | * @attrs: netlink attributes |
| 180 | 181 | */ |
| 181 | 182 | struct genl_dumpit_info { |
| @@ -354,6 +355,7 @@ int genlmsg_multicast_allns(const struct genl_family *family, · 172 unmodified lines | ||
| 354 | 355 | |
| 355 | 356 | /** |
| 356 | 357 | * genlmsg_unicast - unicast a netlink message |
| 358 | + * @net: network namespace to look up @portid in | |
| 357 | 359 | * @skb: netlink message as socket buffer |
| 358 | 360 | * @portid: netlink portid of the destination socket |
| 359 | 361 | */ |
| @@ -373,7 +375,7 @@ static inline int genlmsg_reply(struct sk_buff *skb, struct genl_info *info) · 13 unmodified lines | ||
| 373 | 375 | } |
| 374 | 376 | |
| 375 | 377 | /** |
| 376 | − * gennlmsg_data - head of message payload | |
| 378 | + * genlmsg_data - head of message payload | |
| 377 | 379 | * @gnlh: genetlink message header |
| 378 | 380 | */ |
| 379 | 381 | static inline void *genlmsg_data(const struct genlmsghdr *gnlh) |
| @@ -43,21 +43,20 @@ struct sock *reuseport_migrate_sock(struct sock *sk, · 42 unmodified lines | ||
| 43 | 43 | extern int reuseport_attach_prog(struct sock *sk, struct bpf_prog *prog); |
| 44 | 44 | extern int reuseport_detach_prog(struct sock *sk); |
| 45 | 45 | |
| 46 | −static inline bool reuseport_has_conns(struct sock *sk, bool set) | |
| 46 | +static inline bool reuseport_has_conns(struct sock *sk) | |
| 47 | 47 | { |
| 48 | 48 | struct sock_reuseport *reuse; |
| 49 | 49 | bool ret = false; |
| 50 | 50 | |
| 51 | 51 | rcu_read_lock(); |
| 52 | 52 | reuse = rcu_dereference(sk->sk_reuseport_cb); |
| 53 | − if (reuse) { | |
| 54 | − if (set) | |
| 55 | − reuse->has_conns = 1; | |
| 56 | − ret = reuse->has_conns; | |
| 57 | − } | |
| 53 | + if (reuse && reuse->has_conns) | |
| 54 | + ret = true; | |
| 58 | 55 | rcu_read_unlock(); |
| 59 | 56 | |
| 60 | 57 | return ret; |
| 61 | 58 | } |
| 62 | 59 | |
| 60 | +void reuseport_has_conns_set(struct sock *sk); | |
| 61 | + | |
| 63 | 62 | #endif /* _SOCK_REUSEPORT_H */ |
| @@ -219,11 +219,12 @@ static ssize_t proc_mpc_write(struct file *file, const char __user *buff, · 218 unmodified lines | ||
| 219 | 219 | if (!page) |
| 220 | 220 | return -ENOMEM; |
| 221 | 221 | |
| 222 | − for (p = page, len = 0; len < nbytes; p++, len++) { | |
| 222 | + for (p = page, len = 0; len < nbytes; p++) { | |
| 223 | 223 | if (get_user(*p, buff++)) { |
| 224 | 224 | free_page((unsigned long)page); |
| 225 | 225 | return -EFAULT; |
| 226 | 226 | } |
| 227 | + len += 1; | |
| 227 | 228 | if (*p == '\0' || *p == '\n') |
| 228 | 229 | break; |
| 229 | 230 | } |
| @@ -5136,11 +5136,13 @@ sch_handle_ingress(struct sk_buff *skb, struct packet_type **pt_prev, int *ret, · 5135 unmodified lines | ||
| 5136 | 5136 | case TC_ACT_SHOT: |
| 5137 | 5137 | mini_qdisc_qstats_cpu_drop(miniq); |
| 5138 | 5138 | kfree_skb_reason(skb, SKB_DROP_REASON_TC_INGRESS); |
| 5139 | + *ret = NET_RX_DROP; | |
| 5139 | 5140 | return NULL; |
| 5140 | 5141 | case TC_ACT_STOLEN: |
| 5141 | 5142 | case TC_ACT_QUEUED: |
| 5142 | 5143 | case TC_ACT_TRAP: |
| 5143 | 5144 | consume_skb(skb); |
| 5145 | + *ret = NET_RX_SUCCESS; | |
| 5144 | 5146 | return NULL; |
| 5145 | 5147 | case TC_ACT_REDIRECT: |
| 5146 | 5148 | /* skb_mac_header check was done by cls/act_bpf, so |
| @@ -5153,8 +5155,10 @@ sch_handle_ingress(struct sk_buff *skb, struct packet_type **pt_prev, int *ret, · 6 unmodified lines | ||
| 5153 | 5155 | *another = true; |
| 5154 | 5156 | break; |
| 5155 | 5157 | } |
| 5158 | + *ret = NET_RX_SUCCESS; | |
| 5156 | 5159 | return NULL; |
| 5157 | 5160 | case TC_ACT_CONSUMED: |
| 5161 | + *ret = NET_RX_SUCCESS; | |
| 5158 | 5162 | return NULL; |
| 5159 | 5163 | default: |
| 5160 | 5164 | break; |
| @@ -500,11 +500,11 @@ bool sk_msg_is_readable(struct sock *sk) · 499 unmodified lines | ||
| 500 | 500 | } |
| 501 | 501 | EXPORT_SYMBOL_GPL(sk_msg_is_readable); |
| 502 | 502 | |
| 503 | −static struct sk_msg *alloc_sk_msg(void) | |
| 503 | +static struct sk_msg *alloc_sk_msg(gfp_t gfp) | |
| 504 | 504 | { |
| 505 | 505 | struct sk_msg *msg; |
| 506 | 506 | |
| 507 | − msg = kzalloc(sizeof(*msg), __GFP_NOWARN | GFP_KERNEL); | |
| 507 | + msg = kzalloc(sizeof(*msg), gfp | __GFP_NOWARN); | |
| 508 | 508 | if (unlikely(!msg)) |
| 509 | 509 | return NULL; |
| 510 | 510 | sg_init_marker(msg->sg.data, NR_MSG_FRAG_IDS); |
| @@ -520,7 +520,7 @@ static struct sk_msg *sk_psock_create_ingress_msg(struct sock *sk, · 9 unmodified lines | ||
| 520 | 520 | if (!sk_rmem_schedule(sk, skb, skb->truesize)) |
| 521 | 521 | return NULL; |
| 522 | 522 | |
| 523 | − return alloc_sk_msg(); | |
| 523 | + return alloc_sk_msg(GFP_KERNEL); | |
| 524 | 524 | } |
| 525 | 525 | |
| 526 | 526 | static int sk_psock_skb_ingress_enqueue(struct sk_buff *skb, |
| @@ -597,7 +597,7 @@ static int sk_psock_skb_ingress(struct sk_psock *psock, struct sk_buff *skb, · 70 unmodified lines | ||
| 597 | 597 | static int sk_psock_skb_ingress_self(struct sk_psock *psock, struct sk_buff *skb, |
| 598 | 598 | u32 off, u32 len) |
| 599 | 599 | { |
| 600 | − struct sk_msg *msg = alloc_sk_msg(); | |
| 600 | + struct sk_msg *msg = alloc_sk_msg(GFP_ATOMIC); | |
| 601 | 601 | struct sock *sk = psock->sk; |
| 602 | 602 | int err; |
| 603 | 603 | |
| @@ -21,6 +21,22 @@ static DEFINE_IDA(reuseport_ida); · 20 unmodified lines | ||
| 21 | 21 | static int reuseport_resurrect(struct sock *sk, struct sock_reuseport *old_reuse, |
| 22 | 22 | struct sock_reuseport *reuse, bool bind_inany); |
| 23 | 23 | |
| 24 | +void reuseport_has_conns_set(struct sock *sk) | |
| 25 | +{ | |
| 26 | + struct sock_reuseport *reuse; | |
| 27 | + | |
| 28 | + if (!rcu_access_pointer(sk->sk_reuseport_cb)) | |
| 29 | + return; | |
| 30 | + | |
| 31 | + spin_lock_bh(&reuseport_lock); | |
| 32 | + reuse = rcu_dereference_protected(sk->sk_reuseport_cb, | |
| 33 | + lockdep_is_held(&reuseport_lock)); | |
| 34 | + if (likely(reuse)) | |
| 35 | + reuse->has_conns = 1; | |
| 36 | + spin_unlock_bh(&reuseport_lock); | |
| 37 | +} | |
| 38 | +EXPORT_SYMBOL(reuseport_has_conns_set); | |
| 39 | + | |
| 24 | 40 | static int reuseport_sock_index(struct sock *sk, |
| 25 | 41 | const struct sock_reuseport *reuse, |
| 26 | 42 | bool closed) |
| @@ -3145,7 +3145,7 @@ static int dsa_slave_netdevice_event(struct notifier_block *nb, · 3144 unmodified lines | ||
| 3145 | 3145 | case NETDEV_CHANGELOWERSTATE: { |
| 3146 | 3146 | struct netdev_notifier_changelowerstate_info *info = ptr; |
| 3147 | 3147 | struct dsa_port *dp; |
| 3148 | − int err; | |
| 3148 | + int err = 0; | |
| 3149 | 3149 | |
| 3150 | 3150 | if (dsa_slave_dev_check(dev)) { |
| 3151 | 3151 | dp = dsa_slave_to_port(dev); |
| @@ -150,15 +150,15 @@ struct sk_buff *hsr_get_untagged_frame(struct hsr_frame_info *frame, · 149 unmodified lines | ||
| 150 | 150 | struct hsr_port *port) |
| 151 | 151 | { |
| 152 | 152 | if (!frame->skb_std) { |
| 153 | − if (frame->skb_hsr) { | |
| 153 | + if (frame->skb_hsr) | |
| 154 | 154 | frame->skb_std = |
| 155 | 155 | create_stripped_skb_hsr(frame->skb_hsr, frame); |
| 156 | − } else { | |
| 157 | − /* Unexpected */ | |
| 158 | − WARN_ONCE(1, "%s:%d: Unexpected frame received (port_src %s)\n", | |
| 159 | − __FILE__, __LINE__, port->dev->name); | |
| 156 | + else | |
| 157 | + netdev_warn_once(port->dev, | |
| 158 | + "Unexpected frame received in hsr_get_untagged_frame()\n"); | |
| 159 | + | |
| 160 | + if (!frame->skb_std) | |
| 160 | 161 | return NULL; |
| 161 | − } | |
| 162 | 162 | } |
| 163 | 163 | |
| 164 | 164 | return skb_clone(frame->skb_std, GFP_ATOMIC); |
| @@ -70,7 +70,7 @@ int __ip4_datagram_connect(struct sock *sk, struct sockaddr *uaddr, int addr_len · 69 unmodified lines | ||
| 70 | 70 | } |
| 71 | 71 | inet->inet_daddr = fl4->daddr; |
| 72 | 72 | inet->inet_dport = usin->sin_port; |
| 73 | − reuseport_has_conns(sk, true); | |
| 73 | + reuseport_has_conns_set(sk); | |
| 74 | 74 | sk->sk_state = TCP_ESTABLISHED; |
| 75 | 75 | sk_set_txhash(sk); |
| 76 | 76 | inet->inet_id = get_random_u16(); |
| @@ -78,6 +78,7 @@ static bool rpfilter_mt(const struct sk_buff *skb, struct xt_action_param *par) · 77 unmodified lines | ||
| 78 | 78 | flow.flowi4_tos = iph->tos & IPTOS_RT_MASK; |
| 79 | 79 | flow.flowi4_scope = RT_SCOPE_UNIVERSE; |
| 80 | 80 | flow.flowi4_l3mdev = l3mdev_master_ifindex_rcu(xt_in(par)); |
| 81 | + flow.flowi4_uid = sock_net_uid(xt_net(par), NULL); | |
| 81 | 82 | |
| 82 | 83 | return rpfilter_lookup_reverse(xt_net(par), &flow, xt_in(par), info->flags) ^ invert; |
| 83 | 84 | } |
| @@ -65,6 +65,7 @@ void nft_fib4_eval(const struct nft_expr *expr, struct nft_regs *regs, · 64 unmodified lines | ||
| 65 | 65 | struct flowi4 fl4 = { |
| 66 | 66 | .flowi4_scope = RT_SCOPE_UNIVERSE, |
| 67 | 67 | .flowi4_iif = LOOPBACK_IFINDEX, |
| 68 | + .flowi4_uid = sock_net_uid(nft_net(pkt), NULL), | |
| 68 | 69 | }; |
| 69 | 70 | const struct net_device *oif; |
| 70 | 71 | const struct net_device *found; |
| @@ -448,7 +448,7 @@ static struct sock *udp4_lib_lookup2(struct net *net, · 447 unmodified lines | ||
| 448 | 448 | result = lookup_reuseport(net, sk, skb, |
| 449 | 449 | saddr, sport, daddr, hnum); |
| 450 | 450 | /* Fall back to scoring if group has connections */ |
| 451 | − if (result && !reuseport_has_conns(sk, false)) | |
| 451 | + if (result && !reuseport_has_conns(sk)) | |
| 452 | 452 | return result; |
| 453 | 453 | |
| 454 | 454 | result = result ? : sk; |
| @@ -7214,9 +7214,11 @@ err_reg_dflt: · 7213 unmodified lines | ||
| 7214 | 7214 | __addrconf_sysctl_unregister(net, all, NETCONFA_IFINDEX_ALL); |
| 7215 | 7215 | err_reg_all: |
| 7216 | 7216 | kfree(dflt); |
| 7217 | + net->ipv6.devconf_dflt = NULL; | |
| 7217 | 7218 | #endif |
| 7218 | 7219 | err_alloc_dflt: |
| 7219 | 7220 | kfree(all); |
| 7221 | + net->ipv6.devconf_all = NULL; | |
| 7220 | 7222 | err_alloc_all: |
| 7221 | 7223 | kfree(net->ipv6.inet6_addr_lst); |
| 7222 | 7224 | err_alloc_addr: |
| @@ -256,7 +256,7 @@ ipv4_connected: · 255 unmodified lines | ||
| 256 | 256 | goto out; |
| 257 | 257 | } |
| 258 | 258 | |
| 259 | − reuseport_has_conns(sk, true); | |
| 259 | + reuseport_has_conns_set(sk); | |
| 260 | 260 | sk->sk_state = TCP_ESTABLISHED; |
| 261 | 261 | sk_set_txhash(sk); |
| 262 | 262 | out: |
| @@ -40,6 +40,7 @@ static bool rpfilter_lookup_reverse6(struct net *net, const struct sk_buff *skb, · 39 unmodified lines | ||
| 40 | 40 | .flowi6_l3mdev = l3mdev_master_ifindex_rcu(dev), |
| 41 | 41 | .flowlabel = (* (__be32 *) iph) & IPV6_FLOWINFO_MASK, |
| 42 | 42 | .flowi6_proto = iph->nexthdr, |
| 43 | + .flowi6_uid = sock_net_uid(net, NULL), | |
| 43 | 44 | .daddr = iph->saddr, |
| 44 | 45 | }; |
| 45 | 46 | int lookup_flags; |
| @@ -66,6 +66,7 @@ static u32 __nft_fib6_eval_type(const struct nft_fib *priv, · 65 unmodified lines | ||
| 66 | 66 | struct flowi6 fl6 = { |
| 67 | 67 | .flowi6_iif = LOOPBACK_IFINDEX, |
| 68 | 68 | .flowi6_proto = pkt->tprot, |
| 69 | + .flowi6_uid = sock_net_uid(nft_net(pkt), NULL), | |
| 69 | 70 | }; |
| 70 | 71 | u32 ret = 0; |
| 71 | 72 | |
| @@ -163,6 +164,7 @@ void nft_fib6_eval(const struct nft_expr *expr, struct nft_regs *regs, · 91 unmodified lines | ||
| 163 | 164 | struct flowi6 fl6 = { |
| 164 | 165 | .flowi6_iif = LOOPBACK_IFINDEX, |
| 165 | 166 | .flowi6_proto = pkt->tprot, |
| 167 | + .flowi6_uid = sock_net_uid(nft_net(pkt), NULL), | |
| 166 | 168 | }; |
| 167 | 169 | struct rt6_info *rt; |
| 168 | 170 | int lookup_flags; |
| @@ -195,7 +195,7 @@ static struct sock *udp6_lib_lookup2(struct net *net, · 194 unmodified lines | ||
| 195 | 195 | result = lookup_reuseport(net, sk, skb, |
| 196 | 196 | saddr, sport, daddr, hnum); |
| 197 | 197 | /* Fall back to scoring if group has connections */ |
| 198 | − if (result && !reuseport_has_conns(sk, false)) | |
| 198 | + if (result && !reuseport_has_conns(sk)) | |
| 199 | 199 | return result; |
| 200 | 200 | |
| 201 | 201 | result = result ? : sk; |
| @@ -5865,8 +5865,9 @@ static bool nft_setelem_valid_key_end(const struct nft_set *set, · 5864 unmodified lines | ||
| 5865 | 5865 | (NFT_SET_CONCAT | NFT_SET_INTERVAL)) { |
| 5866 | 5866 | if (flags & NFT_SET_ELEM_INTERVAL_END) |
| 5867 | 5867 | return false; |
| 5868 | − if (!nla[NFTA_SET_ELEM_KEY_END] && | |
| 5869 | − !(flags & NFT_SET_ELEM_CATCHALL)) | |
| 5868 | + | |
| 5869 | + if (nla[NFTA_SET_ELEM_KEY_END] && | |
| 5870 | + flags & NFT_SET_ELEM_CATCHALL) | |
| 5870 | 5871 | return false; |
| 5871 | 5872 | } else { |
| 5872 | 5873 | if (nla[NFTA_SET_ELEM_KEY_END]) |
| @@ -1099,12 +1099,13 @@ static int qdisc_graft(struct net_device *dev, struct Qdisc *parent, · 1098 unmodified lines | ||
| 1099 | 1099 | |
| 1100 | 1100 | skip: |
| 1101 | 1101 | if (!ingress) { |
| 1102 | − notify_and_destroy(net, skb, n, classid, | |
| 1103 | − rtnl_dereference(dev->qdisc), new); | |
| 1102 | + old = rtnl_dereference(dev->qdisc); | |
| 1104 | 1103 | if (new && !new->ops->attach) |
| 1105 | 1104 | qdisc_refcount_inc(new); |
| 1106 | 1105 | rcu_assign_pointer(dev->qdisc, new ? : &noop_qdisc); |
| 1107 | 1106 | |
| 1107 | + notify_and_destroy(net, skb, n, classid, old, new); | |
| 1108 | + | |
| 1108 | 1109 | if (new && new->ops->attach) |
| 1109 | 1110 | new->ops->attach(new); |
| 1110 | 1111 | } else { |
| @@ -2224,8 +2224,12 @@ retry: · 2223 unmodified lines | ||
| 2224 | 2224 | |
| 2225 | 2225 | static void cake_reset(struct Qdisc *sch) |
| 2226 | 2226 | { |
| 2227 | + struct cake_sched_data *q = qdisc_priv(sch); | |
| 2227 | 2228 | u32 c; |
| 2228 | 2229 | |
| 2230 | + if (!q->tins) | |
| 2231 | + return; | |
| 2232 | + | |
| 2229 | 2233 | for (c = 0; c < CAKE_MAX_TINS; c++) |
| 2230 | 2234 | cake_clear_tin(sch, c); |
| 2231 | 2235 | } |
| @@ -478,24 +478,26 @@ static int fq_codel_init(struct Qdisc *sch, struct nlattr *opt, · 477 unmodified lines | ||
| 478 | 478 | if (opt) { |
| 479 | 479 | err = fq_codel_change(sch, opt, extack); |
| 480 | 480 | if (err) |
| 481 | − return err; | |
| 481 | + goto init_failure; | |
| 482 | 482 | } |
| 483 | 483 | |
| 484 | 484 | err = tcf_block_get(&q->block, &q->filter_list, sch, extack); |
| 485 | 485 | if (err) |
| 486 | − return err; | |
| 486 | + goto init_failure; | |
| 487 | 487 | |
| 488 | 488 | if (!q->flows) { |
| 489 | 489 | q->flows = kvcalloc(q->flows_cnt, |
| 490 | 490 | sizeof(struct fq_codel_flow), |
| 491 | 491 | GFP_KERNEL); |
| 492 | − if (!q->flows) | |
| 493 | − return -ENOMEM; | |
| 494 | − | |
| 492 | + if (!q->flows) { | |
| 493 | + err = -ENOMEM; | |
| 494 | + goto init_failure; | |
| 495 | + } | |
| 495 | 496 | q->backlogs = kvcalloc(q->flows_cnt, sizeof(u32), GFP_KERNEL); |
| 496 | − if (!q->backlogs) | |
| 497 | − return -ENOMEM; | |
| 498 | − | |
| 497 | + if (!q->backlogs) { | |
| 498 | + err = -ENOMEM; | |
| 499 | + goto alloc_failure; | |
| 500 | + } | |
| 499 | 501 | for (i = 0; i < q->flows_cnt; i++) { |
| 500 | 502 | struct fq_codel_flow *flow = q->flows + i; |
| 501 | 503 | |
| @@ -508,6 +510,13 @@ static int fq_codel_init(struct Qdisc *sch, struct nlattr *opt, · 6 unmodified lines | ||
| 508 | 510 | else |
| 509 | 511 | sch->flags &= ~TCQ_F_CAN_BYPASS; |
| 510 | 512 | return 0; |
| 513 | + | |
| 514 | +alloc_failure: | |
| 515 | + kvfree(q->flows); | |
| 516 | + q->flows = NULL; | |
| 517 | +init_failure: | |
| 518 | + q->flows_cnt = 0; | |
| 519 | + return err; | |
| 511 | 520 | } |
| 512 | 521 | |
| 513 | 522 | static int fq_codel_dump(struct Qdisc *sch, struct sk_buff *skb) |
| @@ -455,7 +455,8 @@ static void sfb_reset(struct Qdisc *sch) · 454 unmodified lines | ||
| 455 | 455 | { |
| 456 | 456 | struct sfb_sched_data *q = qdisc_priv(sch); |
| 457 | 457 | |
| 458 | − qdisc_reset(q->qdisc); | |
| 458 | + if (likely(q->qdisc)) | |
| 459 | + qdisc_reset(q->qdisc); | |
| 459 | 460 | q->slot = 0; |
| 460 | 461 | q->double_buffering = false; |
| 461 | 462 | sfb_zero_all_buckets(q); |
| @@ -896,7 +896,8 @@ static int smc_lgr_create(struct smc_sock *smc, struct smc_init_info *ini) · 895 unmodified lines | ||
| 896 | 896 | } |
| 897 | 897 | memcpy(lgr->pnet_id, ibdev->pnetid[ibport - 1], |
| 898 | 898 | SMC_MAX_PNETID_LEN); |
| 899 | − if (smc_wr_alloc_lgr_mem(lgr)) | |
| 899 | + rc = smc_wr_alloc_lgr_mem(lgr); | |
| 900 | + if (rc) | |
| 900 | 901 | goto free_wq; |
| 901 | 902 | smc_llc_lgr_init(lgr, smc); |
| 902 | 903 | |
| @@ -148,8 +148,8 @@ static bool tipc_disc_addr_trial_msg(struct tipc_discoverer *d, · 147 unmodified lines | ||
| 148 | 148 | { |
| 149 | 149 | struct net *net = d->net; |
| 150 | 150 | struct tipc_net *tn = tipc_net(net); |
| 151 | − bool trial = time_before(jiffies, tn->addr_trial_end); | |
| 152 | 151 | u32 self = tipc_own_addr(net); |
| 152 | + bool trial = time_before(jiffies, tn->addr_trial_end) && !self; | |
| 153 | 153 | |
| 154 | 154 | if (mtyp == DSC_TRIAL_FAIL_MSG) { |
| 155 | 155 | if (!trial) |
| @@ -568,7 +568,7 @@ bool tipc_topsrv_kern_subscr(struct net *net, u32 port, u32 type, u32 lower, · 567 unmodified lines | ||
| 568 | 568 | sub.seq.upper = upper; |
| 569 | 569 | sub.timeout = TIPC_WAIT_FOREVER; |
| 570 | 570 | sub.filter = filter; |
| 571 | − *(u32 *)&sub.usr_handle = port; | |
| 571 | + *(u64 *)&sub.usr_handle = (u64)port; | |
| 572 | 572 | |
| 573 | 573 | con = tipc_conn_alloc(tipc_topsrv(net)); |
| 574 | 574 | if (IS_ERR(con)) |
| @@ -273,7 +273,7 @@ static int tls_strp_read_copyin(struct tls_strparser *strp) · 272 unmodified lines | ||
| 273 | 273 | return desc.error; |
| 274 | 274 | } |
| 275 | 275 | |
| 276 | −static int tls_strp_read_short(struct tls_strparser *strp) | |
| 276 | +static int tls_strp_read_copy(struct tls_strparser *strp, bool qshort) | |
| 277 | 277 | { |
| 278 | 278 | struct skb_shared_info *shinfo; |
| 279 | 279 | struct page *page; |
| @@ -283,7 +283,7 @@ static int tls_strp_read_short(struct tls_strparser *strp) · 3 unmodified lines | ||
| 283 | 283 | * to read the data out. Otherwise the connection will stall. |
| 284 | 284 | * Without pressure threshold of INT_MAX will never be ready. |
| 285 | 285 | */ |
| 286 | − if (likely(!tcp_epollin_ready(strp->sk, INT_MAX))) | |
| 286 | + if (likely(qshort && !tcp_epollin_ready(strp->sk, INT_MAX))) | |
| 287 | 287 | return 0; |
| 288 | 288 | |
| 289 | 289 | shinfo = skb_shinfo(strp->anchor); |
| @@ -315,6 +315,27 @@ static int tls_strp_read_short(struct tls_strparser *strp) · 25 unmodified lines | ||
| 315 | 315 | return 0; |
| 316 | 316 | } |
| 317 | 317 | |
| 318 | +static bool tls_strp_check_no_dup(struct tls_strparser *strp) | |
| 319 | +{ | |
| 320 | + unsigned int len = strp->stm.offset + strp->stm.full_len; | |
| 321 | + struct sk_buff *skb; | |
| 322 | + u32 seq; | |
| 323 | + | |
| 324 | + skb = skb_shinfo(strp->anchor)->frag_list; | |
| 325 | + seq = TCP_SKB_CB(skb)->seq; | |
| 326 | + | |
| 327 | + while (skb->len < len) { | |
| 328 | + seq += skb->len; | |
| 329 | + len -= skb->len; | |
| 330 | + skb = skb->next; | |
| 331 | + | |
| 332 | + if (TCP_SKB_CB(skb)->seq != seq) | |
| 333 | + return false; | |
| 334 | + } | |
| 335 | + | |
| 336 | + return true; | |
| 337 | +} | |
| 338 | + | |
| 318 | 339 | static void tls_strp_load_anchor_with_queue(struct tls_strparser *strp, int len) |
| 319 | 340 | { |
| 320 | 341 | struct tcp_sock *tp = tcp_sk(strp->sk); |
| @@ -373,7 +394,7 @@ static int tls_strp_read_sock(struct tls_strparser *strp) · 52 unmodified lines | ||
| 373 | 394 | return tls_strp_read_copyin(strp); |
| 374 | 395 | |
| 375 | 396 | if (inq < strp->stm.full_len) |
| 376 | − return tls_strp_read_short(strp); | |
| 397 | + return tls_strp_read_copy(strp, true); | |
| 377 | 398 | |
| 378 | 399 | if (!strp->stm.full_len) { |
| 379 | 400 | tls_strp_load_anchor_with_queue(strp, inq); |
| @@ -387,9 +408,12 @@ static int tls_strp_read_sock(struct tls_strparser *strp) · 7 unmodified lines | ||
| 387 | 408 | strp->stm.full_len = sz; |
| 388 | 409 | |
| 389 | 410 | if (!strp->stm.full_len || inq < strp->stm.full_len) |
| 390 | − return tls_strp_read_short(strp); | |
| 411 | + return tls_strp_read_copy(strp, true); | |
| 391 | 412 | } |
| 392 | 413 | |
| 414 | + if (!tls_strp_check_no_dup(strp)) | |
| 415 | + return tls_strp_read_copy(strp, false); | |
| 416 | + | |
| 393 | 417 | strp->msg_ready = 1; |
| 394 | 418 | tls_rx_msg_ready(strp); |
| 395 | 419 | |
| @@ -70,6 +70,7 @@ TEST_PROGS += io_uring_zerocopy_tx.sh · 69 unmodified lines | ||
| 70 | 70 | TEST_GEN_FILES += bind_bhash |
| 71 | 71 | TEST_GEN_PROGS += sk_bind_sendto_listen |
| 72 | 72 | TEST_GEN_PROGS += sk_connect_zero_addr |
| 73 | +TEST_PROGS += test_ingress_egress_chaining.sh | |
| 73 | 74 | |
| 74 | 75 | TEST_FILES := settings |
| 75 | 76 | |
| @@ -0,0 +1,79 @@ | ||
| 1 | +#!/bin/bash | |
| 2 | +# SPDX-License-Identifier: GPL-2.0 | |
| 3 | + | |
| 4 | +# This test runs a simple ingress tc setup between two veth pairs, | |
| 5 | +# and chains a single egress rule to test ingress chaining to egress. | |
| 6 | +# | |
| 7 | +# Kselftest framework requirement - SKIP code is 4. | |
| 8 | +ksft_skip=4 | |
| 9 | + | |
| 10 | +if [ "$(id -u)" -ne 0 ];then | |
| 11 | + echo "SKIP: Need root privileges" | |
| 12 | + exit $ksft_skip | |
| 13 | +fi | |
| 14 | + | |
| 15 | +needed_mods="act_mirred cls_flower sch_ingress" | |
| 16 | +for mod in $needed_mods; do | |
| 17 | + modinfo $mod &>/dev/null || { echo "SKIP: Need act_mirred module"; exit $ksft_skip; } | |
| 18 | +done | |
| 19 | + | |
| 20 | +ns="ns$((RANDOM%899+100))" | |
| 21 | +veth1="veth1$((RANDOM%899+100))" | |
| 22 | +veth2="veth2$((RANDOM%899+100))" | |
| 23 | +peer1="peer1$((RANDOM%899+100))" | |
| 24 | +peer2="peer2$((RANDOM%899+100))" | |
| 25 | +ip_peer1=198.51.100.5 | |
| 26 | +ip_peer2=198.51.100.6 | |
| 27 | + | |
| 28 | +function fail() { | |
| 29 | + echo "FAIL: $@" >> /dev/stderr | |
| 30 | + exit 1 | |
| 31 | +} | |
| 32 | + | |
| 33 | +function cleanup() { | |
| 34 | + killall -q -9 udpgso_bench_rx | |
| 35 | + ip link del $veth1 &> /dev/null | |
| 36 | + ip link del $veth2 &> /dev/null | |
| 37 | + ip netns del $ns &> /dev/null | |
| 38 | +} | |
| 39 | +trap cleanup EXIT | |
| 40 | + | |
| 41 | +function config() { | |
| 42 | + echo "Setup veth pairs [$veth1, $peer1], and veth pair [$veth2, $peer2]" | |
| 43 | + ip link add $veth1 type veth peer name $peer1 | |
| 44 | + ip link add $veth2 type veth peer name $peer2 | |
| 45 | + ip addr add $ip_peer1/24 dev $peer1 | |
| 46 | + ip link set $peer1 up | |
| 47 | + ip netns add $ns | |
| 48 | + ip link set dev $peer2 netns $ns | |
| 49 | + ip netns exec $ns ip addr add $ip_peer2/24 dev $peer2 | |
| 50 | + ip netns exec $ns ip link set $peer2 up | |
| 51 | + ip link set $veth1 up | |
| 52 | + ip link set $veth2 up | |
| 53 | + | |
| 54 | + echo "Add tc filter ingress->egress forwarding $veth1 <-> $veth2" | |
| 55 | + tc qdisc add dev $veth2 ingress | |
| 56 | + tc qdisc add dev $veth1 ingress | |
| 57 | + tc filter add dev $veth2 ingress prio 1 proto all flower \ | |
| 58 | + action mirred egress redirect dev $veth1 | |
| 59 | + tc filter add dev $veth1 ingress prio 1 proto all flower \ | |
| 60 | + action mirred egress redirect dev $veth2 | |
| 61 | + | |
| 62 | + echo "Add tc filter egress->ingress forwarding $peer1 -> $veth1, bypassing the veth pipe" | |
| 63 | + tc qdisc add dev $peer1 clsact | |
| 64 | + tc filter add dev $peer1 egress prio 20 proto ip flower \ | |
| 65 | + action mirred ingress redirect dev $veth1 | |
| 66 | +} | |
| 67 | + | |
| 68 | +function test_run() { | |
| 69 | + echo "Run tcp traffic" | |
| 70 | + ./udpgso_bench_rx -t & | |
| 71 | + sleep 1 | |
| 72 | + ip netns exec $ns timeout -k 2 10 ./udpgso_bench_tx -t -l 2 -4 -D $ip_peer1 || fail "traffic failed" | |
| 73 | + echo "Test passed" | |
| 74 | +} | |
| 75 | + | |
| 76 | +config | |
| 77 | +test_run | |
| 78 | +trap - EXIT | |
| 79 | +cleanup | |